Git Product home page Git Product logo

ogre's Introduction

Ogre

Ogre is a Clojure Gremlin Language Variant of the Gremlin graph traversal language from Apache Tinkerpop. Like Gremlin, it can be used to query any graphs that are TinkerPop-enabled.

Project Goals

  • Provide an API that enhances the expressivity of Gremlin when working in Clojure.
  • Expose the features of TinkerPop as it makes sense in Clojure.
  • Don't introduce any significant amount of performance overhead.

Community

Questions related to Ogre can be asked on the clojure-titanium mailing list.

To subscribe for announcements of releases, important changes and so on, please follow @ClojureWerkz on Twitter.

Project Maturity

Despite being first released in 2014, Orge is a relatively young project that regained active development in 2016. Most of Ogre's features are driven by changes to Apache TinkerPop (specifically the Traversal API) which has largely stabilized itself in over the course of the 3.2.x line of code. As a result, Ogre tends to be fairly stable with its implementation of that API. Ogre also implements the TinkerPop Process Test Suite, which helps validate that Ogre is compliant with Gremlin.

Ogre currently targets TinkerPop 3.4.x.

Artifacts

Orge artifacts are released to Clojars. Maven users should add the following repository definition to your pom.xml:

<repository>
  <id>clojars.org</id>
  <url>http://clojars.org/repo</url>
</repository>

The Most Recent Release

With Leiningen:

[clojurewerkz/ogre "3.4.11.0"]

With Maven:

<dependency>
  <groupId>clojurewerkz</groupId>
  <artifactId>ogre</artifactId>
  <version>3.4.11.0</version>
</dependency>

Documentation & Examples

You'll need to choose a TinkerPop-enabled graph database and add that to your project's dependencies. Here we use the in-memory graph database implementation provided by org.apache.tinkerpop/tinkergraph-gremlin, e.g.:

With Leiningen:

[org.apache.tinkerpop/tinkergraph-gremlin "3.4.11"]

With Maven:

<dependency>
  <groupId>org.apache.tinkerpop</groupId>
  <artifactId>tinkergraph-gremlin</artifactId>
  <version>3.4.11</version>
</dependency>

REPL examples:

user=> (load "clojurewerkz/ogre/core")
nil
user=> (in-ns 'clojurewerkz.ogre.core)
#object[clojure.lang.Namespace 0x2bcfe59c "clojurewerkz.ogre.core"]
clojurewerkz.ogre.core=> (def graph (open-graph {(Graph/GRAPH) (.getName org.apache.tinkerpop.gremlin.tinkergraph.structure.TinkerGraph)}))
#'clojurewerkz.ogre.core/graph
clojurewerkz.ogre.core=> (def g (traversal graph))
#'clojurewerkz.ogre.core/g
clojurewerkz.ogre.core=> (org.apache.tinkerpop.gremlin.tinkergraph.structure.TinkerFactory/generateModern graph)
nil
clojurewerkz.ogre.core=> (traverse g V (match
                    #_=>   (__ (as :a) (out :created) (as :b))
                    #_=>   (__ (as :b) (has :name "lop"))
                    #_=>   (__ (as :b) (in :created) (as :c))
                    #_=>   (__ (as :c) (has :age 29)))
                    #_=>   (select :a :c) (by :name)
                    #_=>   (into-seq!))
({"a" "marko", "c" "marko"} {"a" "josh", "c" "marko"} {"a" "peter", "c" "marko"})

As an alternative to embedded graph databases like TinkerGraph, you might also choose to utilize a remote graph (e.g. one hosted in Gremlin Server or a Remote Gremlin Provider). In such case, you would first need org.apache.tinkerpop/gremlin-driver to connect to the remote graph:

With Leiningen:

[org.apache.tinkerpop/gremlin-driver "3.4.11"]

With Maven:

<dependency>
  <groupId>org.apache.tinkerpop</groupId>
  <artifactId>gremlin-driver</artifactId>
  <version>3.4.11</version>
</dependency>

From the driver, you create a DriverRemoteConnection and pass that to the traversal function (rather than the Graph instance as demonstrated in the last example):

clojurewerkz.ogre.core=> (def conn (org.apache.tinkerpop.gremlin.driver.remote.DriverRemoteConnection/using "localhost" 8182 "g"))
#'clojurewerkz.ogre.core/conn
clojurewerkz.ogre.core=> (def g (traversal conn))
#'clojurewerkz.ogre.core/g
clojurewerkz.ogre.core=> (traverse g V (has :name "josh") (values :age) (into-seq!))
(32)

In short, to connect to a remote graph simply use Java interop to construct a DriverRemoteConnection instance in the ways specified by the TinkerPop Reference Documentation and then give that object to the traversal function to create g.

Ogre has more complete documentation here.

Supported Clojure Versions

Orge requires Clojure 1.8+. The most recent stable release is always recommended.

Continuous Integration

Build Status

Development

Orge uses Leiningen 2. Once installed and run tests using:

lein test

License

Copyright (C) 2014-2017 Zack Maril, and the ClojureWerkz team. Copyright (C) 2017-2021 Stephen Mallette, Zack Maril, and the ClojureWerkz team.

Licensed under the Eclipse Public License (the same as Clojure).

Acknowledgements

Joe Lee illustrated the "Gremlin Ogre" image based on the original Clojurewerkz Ogre logo and Apache TinkerPop's Gremlin character developed Ketrina Yim.

ogre's People

Contributors

bronsa avatar fitzoh avatar harleqin avatar jafingerhut avatar jgmize avatar michaelklishin avatar phreed avatar ray1729 avatar rduplain avatar robsteranium avatar spmallette avatar zmaril avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

ogre's Issues

Complete Filter Steps

Remaining steps to be added to filter.clj include:

  • cyclicPath
  • inject
  • overloads for except/retain
  • where

Consider Removal of Element Traversal Functions

It seems like there's some redundancy in the Ogre shorthand for traversal and functions defined in edge.clj and vertex.clj. My guess is that this was leftover from the merge of Ogre with Archimedes. Given that "everything is a Traversal" in TP3, Ogre should probably win here and the Archimedes functions dropped.

For example, in vertex.clj there is outgoing-edges-of which is basically just q/-E>. Seems like we should drop the more verbose outgoing-edges-ofin favor of a single way of writing a Traversal.

Transactional Implementation

TP3 transaction handling is somewhat different from TP2. While the thread local model is the same, TP3 offers more control over transactional behavior with respect to starting/stopping transactions and how to handle open transactions on close of the graph. For example, this control enables a user to decided whether they want to do "manual" transactions or "automatic" transactions (where TP2 was all "automatic") or to provide their own behavior completely.

Furthermore, the notion of transactional retry is baked directly into the TP3 transaction object, making this Ogre code obsolete:

(defn with-transaction-retry*

There is greater detail here: http://www.tinkerpop.com/docs/3.0.0-SNAPSHOT/#transactions

"No such var: q/query, compiling:(*cider-repl ogre*:49:6) "

I tried going through the tutorial and get this:

user> (require '[ogre.tinkergraph :as g]) 
nil
user> (require '[ogre.core :as q]) 
nil
user> (g/use-new-tinker-graph!)
#object[com.tinkerpop.blueprints.impls.tg.TinkerGraph 0xcb785ff "tinkergraph[vertices:6 edges:6]"]
user> (q/query (g/find-by-id 1)
         q/-->
         q/into-vec!)
CompilerException java.lang.RuntimeException: No such var: q/query, compiling:(*cider-repl ogre*:49:6) 
user>

Any idea what's wrong there?

Should annotations be keywords?

Personally I like using strings to annotate things. It looks right to me, seeing as how keywords are used to label edges. It really doesn't matter a great deal, but if anybody has a good reason either way, I'd be happy to hear ideas.

Improve use of T

In Gremlin and java T gets statically imported so that you don't have to see it so much. This:

g.addV(T.id, 1)

becomes

g.addV(id,1)

Perhaps there could be something smart for Ogre to avoid:

(addV T/id 1)

Documentation

How should the library be documented? Something ala gremlindocs? ogredocs? Maybe just forking gremlindocs could work.

Support for Hiddens

TP3 introduces the notion of hidden properties. Would be nice to have a nice Ogre representation of hiddens. For example, gremlin-groovy introduces the syntax of:

assertEquals(Graph.Key.hide("g"), -"g");

Have has accept only a predicate instead of predicate and value

This would solve two issues:

  1. right now it's impossible to use a unary predicate in has (for instance to check for some invariant)

  2. it would remove the ambiguity of argument order. The current situation is less than ideal as the property is inserted as the second argument which breaks with clj expectations (note how > changes to < between has and every?):

(let [g (u/classic-tinkergraph)
       vs (q/query (v/get-all-vertices g)
                      (q/has :age > (int 30))
                      q/into-vec!)]
   (every? (partial < 30) (u/get-ages vs))))

On the other hand, if we automatically change the order around it might mess with the heads of people coming from Gremlin in other languages. Therefor I think it best to have the user be explicit about where to stick the property by closing over the constants themselves.

Project still maintained?

We're starting to use ogre (v2.5.0 + archimedes to fill in missing pieces, which seems to work) and there's some concern whether the project is maintained. It looks like the last green CI build was about 10 months ago and commits after that have been failing.

We're happy to jump in to help put out some fires, just want to get an idea of where things are at.

Add a bang to count

It executes the pipeline and returns a number. Also, it looks to be undocumented on OgreDocs. Is it tested even?

Consider Label Step Returning Keyword

Ogre deals with vertex/edge labels as keywords (e.g. see label-of), but the label step returns a String natively from Gremlin. Seems inconsistent.

Random

Write a test for random.

Provide Consistent Approach to Side Effects

Ogre seemed to take a position of popping off side effects from a traversal by terminating the traversal with functions like get-group-by! or get-group-count!. That's kinda neat - we just need to get consistent with an approach.

select-only for one label is a special case in Gremlin

This is pretty obscure, but it came up during implementing match. Assume we have match implemented as per my proposition in #37:

(q/query (v/get-all-vertices g)
                      (q/match :a
                        :a (-> q/out (q/as :b))
                        :b (-> (q/out [:created]) (q/has :name "lop"))
                        :b (-> (q/match :x
                                 :x (-> (q/out [:created]) (q/as :y))
                                 :y (q/has :name "ripple"))
                             (q/select-only [:y])
                             (q/as :c)))
                      (q/select-only [:a :c] #(v/get % :name))
                      q/all-into-maps!)

this explodes with:

Caused by java.lang.IllegalArgumentException
   No implementation of method: :get of protocol:
   #'clojurewerkz.ogre.element/GetItemProperties found for class:
   java.util.LinkedHashMap

              core_deftype.clj:  544  clojure.core/-cache-protocol-fn
                   element.clj:    7  clojurewerkz.ogre.element/eval5374/fn/G
                match_test.clj:   25  clojurewerkz.ogre.map.match-test/eval23733/fn
                      util.clj:   65  clojurewerkz.ogre.util/f-to-function/reify
               SelectStep.java:   58  com.tinkerpop.gremlin.process.graph.step.map.SelectStep/lambda$null$349
                           nil:   -1  com.tinkerpop.gremlin.process.graph.step.map.SelectStep$$Lambda$84/1797600206/accept
                ArrayList.java: 1249  java.util.ArrayList/forEach
               SelectStep.java:   56  com.tinkerpop.gremlin.process.graph.step.map.SelectStep/lambda$new$350
                           nil:   -1  com.tinkerpop.gremlin.process.graph.step.map.SelectStep$$Lambda$50/980063814/apply
                  MapStep.java:   27  com.tinkerpop.gremlin.process.graph.step.map.MapStep/processNextStart
             AbstractStep.java:   89  com.tinkerpop.gremlin.process.util.AbstractStep/next
             AbstractStep.java:   15  com.tinkerpop.gremlin.process.util.AbstractStep/next
                Traversal.java:  181  com.tinkerpop.gremlin.process.Traversal/fill
                Traversal.java:  157  com.tinkerpop.gremlin.process.Traversal/toList
                 traversal.clj:   27  clojurewerkz.ogre.traversal/into-vec!
                 traversal.clj:   78  clojurewerkz.ogre.traversal/all-into-maps!
                match_test.clj:   16  clojurewerkz.ogre.map.match-test/eval23733

Turns out Gremlin special-cases select with only one label. If we slightly tweak the original Groovy example, we get the same error:

g.V().match('a',
            g.of().as('a').out('knows').as('b'),
            g.of().as('b').out('created').has('name','lop'),
            g.of().as('b').match('x',
                g.of().as('x').out('created').as('y'),
                g.of().as('y').has('name','ripple')).select(['y','x']).as('c')).        // <- added another label here
            select(['a','c']){it.value('name')}
No signature of method: java.util.LinkedHashMap.value() is applicable for argument types: (java.lang.String) values: [name]

The fix in of itself is trivial, the question is should we just handle separately the case where we get passed a vector of one, or do we add an overload so that a singleton label is passed as-is (without being wrapped in a vec)?
I'm in favour of the second approach as it at least gives you a visual hint that there might be differences in what you are getting back. Although at this point do we even need select and select-only, or can all functionality be folded into select?

GraphFactory Support

The recommended method for Graph construction in TP3 is by using GraphFactory Ogre should have a nice way of supporting that as it generalizes graph creation across all implementations.

Add Until Step

Add Until step to branch.clj which enables while-do semantics...this had no TP2 equivalent.

Consider Support for the TP3 Test Suite

The testing pattern for Ogre for TP2 seems to have been to re-implement the tests from gremlin-groovy. While this may ultimately be the pattern to follow for Ogre in TP3, JVM languages have the ability to take advantage of the gremlin-test suite which provides access to hundreds of tests to clearly validate the "gremlin flavor" against its specification. In this way, there is a consistent way to test Gremlin from a traversal perspective. From Ogre's perspective, the benefit to using this suite is that it gets a complete battery of tests without having the test code to maintain. Implementations simply provide a Traversal object to the gremlin-test suite in order to have its results validated.

It is worth keeping in mind that these tests will only cover the Gremlin "Process" features (i.e. traversals). Ogre will need to maintain tests for other aspects of the language (e.g. transactions, graph strategies, etc.)

In addition to gremlin-java and gremlin-groovy, gremlin-scala (a project external to TinkerPop) currently uses the test suite to its advantage.

It would be nice if there was a way for Ogre to use this test suite. It does mean that Ogre would need to somehow leverage JUnit in its testing (as gremlin-test is based on that framework). There's some other Java-interop issues as well related to Java annotations and other odds and ends that will need to be sorted to get this going.

In the end, perhaps this may not be possible for some technical reason....if so, Ogre will need to maintain its own set of tests.

Reduce number of reflection warnings

Performing task 'test' with profile(s): 'dev'
Reflection warning, clojurewerkz/ogre/graph.clj:13:3 - reference to field supportsComputer can't be resolved.
Reflection warning, clojurewerkz/ogre/graph.clj:18:3 - reference to field supportsPersistence can't be resolved.
Reflection warning, clojurewerkz/ogre/graph.clj:23:3 - reference to field supportsThreadedTransactions can't be resolved.
Reflection warning, clojurewerkz/ogre/graph.clj:28:3 - reference to field supportsTransactions can't be resolved.
Reflection warning, clojurewerkz/ogre/graph.clj:36:3 - reference to field newTransaction on com.tinkerpop.gremlin.structure.Graph can't be resolved.
Reflection warning, clojurewerkz/ogre/util.clj:8:24 - call to method as on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/element.clj:17:45 - call to method properties on com.tinkerpop.gremlin.structure.Element$Iterators can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/element.clj:18:22 - reference to field hasNext can't be resolved.
Reflection warning, clojurewerkz/ogre/element.clj:18:49 - reference to field value can't be resolved.
Reflection warning, clojurewerkz/ogre/traversal.clj:83:10 - reference to field count on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/vertex.clj:26:9 - reference to field id can't be resolved.
Reflection warning, clojurewerkz/ogre/vertex.clj:26:3 - call to method v can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/vertex.clj:35:3 - reference to field remove can't be resolved.
Reflection warning, clojurewerkz/ogre/vertex.clj:52:10 - call to method v can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/vertex.clj:53:29 - call to method v can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/vertex.clj:53:29 - call to method v can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/vertex.clj:58:9 - reference to field V can't be resolved.
Reflection warning, clojurewerkz/ogre/vertex.clj:58:14 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/vertex.clj:63:3 - reference to field V can't be resolved.
Reflection warning, clojurewerkz/ogre/vertex.clj:114:5 - call to method addVertex on com.tinkerpop.gremlin.structure.Graph can't be resolved (argument types: unknown).
Reflection warning, clojurewerkz/ogre/vertex.clj:121:5 - call to method addVertex on com.tinkerpop.gremlin.structure.Graph can't be resolved (argument types: unknown).
Reflection warning, clojurewerkz/ogre/edge.clj:27:3 - call to method e can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/edge.clj:58:5 - call to method e can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/edge.clj:59:24 - call to method e can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/edge.clj:59:24 - call to method e can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/edge.clj:64:3 - reference to field E can't be resolved.
Reflection warning, clojurewerkz/ogre/edge.clj:95:73 - reference to field id can't be resolved.
Reflection warning, clojurewerkz/ogre/edge_test.clj:116:12 - reference to field id can't be resolved.
Reflection warning, clojurewerkz/ogre/edge_test.clj:116:23 - reference to field id can't be resolved.
Reflection warning, clojurewerkz/ogre/filter.clj:10:5 - reference to field cyclicPath on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/filter.clj:16:5 - reference to field dedup on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/filter.clj:18:5 - call to method dedup on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:22:35 - call to method except on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:26:20 - call to method filter on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:41:5 - call to method hasNot on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:48:3 - call to method interval on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:52:20 - call to method limit on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:56:20 - call to method localLimit on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:60:27 - call to method localRange on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:64:30 - call to method random on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:68:27 - call to method range on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:74:32 - call to method retain on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/filter.clj:78:18 - reference to field simple_path on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/map.clj:9:30 - call to method back on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/map.clj:16:19 - reference to field fold on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/map.clj:20:19 - reference to field id on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/map.clj:31:19 - reference to field label on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/map.clj:36:5 - call to method map on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/map.clj:45:21 - call to method order on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/map.clj:54:5 - call to method path on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/map.clj:59:5 - call to method properties on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/map.clj:70:5 - call to method select on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/map.clj:77:5 - call to method select on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/map.clj:84:19 - reference to field unfold on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/map.clj:92:5 - call to method values on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/side_effect.clj:11:4 - call to method aggregate on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/side_effect.clj:15:19 - reference to field cap on com.tinkerpop.gremlin.process.Traversal can't be resolved.
Reflection warning, clojurewerkz/ogre/side_effect.clj:16:21 - call to method cap on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/side_effect.clj:28:3 - call to method sideEffect on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/side_effect.clj:37:24 - call to method groupBy on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/side_effect.clj:38:24 - reference to field cap can't be resolved.
Reflection warning, clojurewerkz/ogre/side_effect.clj:39:24 - reference to field toList can't be resolved.
Reflection warning, clojurewerkz/ogre/side_effect.clj:51:9 - call to method groupCount on com.tinkerpop.gremlin.process.Traversal can't be resolved (no such method).
Reflection warning, clojurewerkz/ogre/side_effect.clj:52:9 - reference to field cap can't be resolved.
Reflection warning, clojurewerkz/ogre/side_effect.clj:53:9 - reference to field toList can't be resolved.
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - call to method both can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - call to method bothE can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - reference to field bothV can't be resolved.
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - call to method in can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - call to method inE can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - reference to field inV can't be resolved.
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - call to method out can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - call to method outE can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/core.clj:11:1 - reference to field outV can't be resolved.
Reflection warning, clojurewerkz/ogre/filter/has_test.clj:12:23 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/filter/has_test.clj:20:23 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/filter/has_test.clj:27:23 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/filter/has_test.clj:44:23 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/god_test.clj:42:23 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/god_test.clj:55:23 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/god_test.clj:61:23 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/graph_test.clj:22:13 - reference to field close can't be resolved.
Reflection warning, clojurewerkz/ogre/io.clj:29:37 - call to method vertexIdKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:30:35 - call to method edgeIdKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:31:40 - call to method vertexLabelKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:32:38 - call to method edgeLabelKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:33:34 - call to method batchSize can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:34:7 - reference to field create can't be resolved.
Reflection warning, clojurewerkz/ogre/io.clj:35:58 - call to method readGraph can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:41:33 - call to method normalize can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:42:40 - call to method vertexKeyTypes can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:43:38 - call to method edgeKeyTypes can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:44:40 - call to method vertexLabelKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:45:38 - call to method edgeLabelKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:46:43 - call to method xmlSchemaLocation can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:47:7 - reference to field create can't be resolved.
Reflection warning, clojurewerkz/ogre/io.clj:48:60 - call to method writeGraph can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:54:37 - call to method vertexIdKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:55:35 - call to method edgeIdKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:56:37 - call to method customModule can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:57:43 - call to method loadCustomModule can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:58:35 - call to method embedTypes can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:59:34 - call to method batchSize can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:60:7 - reference to field create can't be resolved.
Reflection warning, clojurewerkz/ogre/io.clj:61:59 - call to method readGraph can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:67:33 - call to method normalize can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:68:37 - call to method customModule can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:69:43 - call to method loadCustomModule can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:70:35 - call to method embedTypes can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:71:7 - reference to field create can't be resolved.
Reflection warning, clojurewerkz/ogre/io.clj:72:61 - call to method writeGraph can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:78:37 - call to method vertexIdKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:79:35 - call to method edgeIdKey can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:80:30 - call to method custom can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:81:41 - call to method workingDirectory can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:82:34 - call to method batchSize can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:83:7 - reference to field create can't be resolved.
Reflection warning, clojurewerkz/ogre/io.clj:84:55 - call to method readGraph can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:90:30 - call to method custom can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io.clj:91:7 - reference to field create can't be resolved.
Reflection warning, clojurewerkz/ogre/io.clj:92:57 - call to method writeGraph can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/io_test.clj:10:33 - reference to field V can't be resolved.
Reflection warning, clojurewerkz/ogre/io_test.clj:10:24 - reference to field toList can't be resolved.
Reflection warning, clojurewerkz/ogre/io_test.clj:13:33 - reference to field E can't be resolved.
Reflection warning, clojurewerkz/ogre/io_test.clj:13:24 - reference to field toList can't be resolved.
Reflection warning, clojurewerkz/ogre/map/map_test.clj:18:41 - reference to field get can't be resolved.
Reflection warning, clojurewerkz/ogre/map/map_test.clj:28:41 - reference to field get can't be resolved.
Reflection warning, clojurewerkz/ogre/map/path_test.clj:10:16 - reference to field objects can't be resolved.
Reflection warning, clojurewerkz/ogre/side_effect/side_effect_test.clj:16:19 - reference to field get can't be resolved.
Reflection warning, clojurewerkz/ogre/traversal_test.clj:162:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:166:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:170:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:185:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:189:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:193:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:208:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:212:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:216:18 - call to method has can't be resolved (target class is unknown).
Reflection warning, clojurewerkz/ogre/traversal_test.clj:236:18 - call to method has can't be resolved (target class is unknown).

Support Choose Step

Add Choose step to branch.clj enables if-then-else semantics and replaces the ifThenElse step from TP2:

Complete Map Steps

Support steps remaining Map steps in map.clj (note that some map-related steps have been documented as issues separately...this list represents what remains):

  • flatMap
  • fold (with BiFunction overload)
  • identity
  • orderBy
  • otherV
  • shuffle
  • to

Optional type checking

gremlin-scala has the nice feature of typechecking traversals and thereby catching semantical errors. Can we do something similar with core.typed?

Complete Side Effect Steps

Add the following to side_effect.clj:

  • addIn/Out*E
  • aggregate
  • count
  • store
  • tree

Note that these are the remaining steps for side effects given other issues: #40

Support Match Step

Match step is a new and powerful feature of TP3 that enables a more declarative style of graph pattern matching. Add to map.clj.

Gremlin Kryo IO

TP3 introduces a JVM-only graph serialization approach that is configurably non-lossy that uses the Kryo serialization format. This needs to be added to Ogre in the same way that there are reader/writer options for GraphML and GraphSON.

has-not is not a true complement of has

has-not only checks existence while has can also check for equality or arbitrary predicate. To conform with clj convention of not-x being a true complement, the remaining functionality should be added.

Variations of addV() and V()

Ogre has both addV from GraphTraversal and add-V from GraphTraversalSource- It would be nice if the functions didn't have to be named that way and could be more consistent.

Equally irritating is V and midV where the latter is use for a mid-traversal V(). Would be nice if midV could just be V somehow or another.

Improve use of P

The use of P in could be better. You get ugly stuff like this right now:

(q/where :a (P/eq "b"))

That's just an example, but it shows how you have to use the String "b" rather than :b which would be more consistent with the rest of Ogre. There are similar weird bits with other aspects of P like:

(P/without [1])

where Ogre forces use of [] to denote the collection.

Documentation error?

This issue is reported with the assumption of the https://raw.githubusercontent.com/tinkerpop/blueprints/master/doc/images/graph-example-1.jpg graph in mind.

The documentation describes in the chapter "Traversals" that to query for the things Josh created we should do:

(q/query (g/find-by-id 4)
         (q/--> :created)
         q/into-vec!)

This throws an error:

java.lang.IllegalArgumentException: Don't know how to create ISeq from: clojure.lang.Keyword
RT.java:505 clojure.lang.RT.seqFrom
RT.java:486 clojure.lang.RT.seq
core.clj:133 clojure.core/seq
core.clj:2595 clojure.core/filter[fn]
LazySeq.java:40 clojure.lang.LazySeq.sval
LazySeq.java:49 clojure.lang.LazySeq.seq
RT.java:484 clojure.lang.RT.seq
core.clj:133 clojure.core/seq
core.clj:2551 clojure.core/map[fn]
LazySeq.java:40 clojure.lang.LazySeq.sval
LazySeq.java:49 clojure.lang.LazySeq.seq
RT.java:484 clojure.lang.RT.seq
core.clj:133 clojure.core/seq
core.clj:3165 clojure.core/into-array
util.clj:35 clojurewerkz.ogre.util/str-array
util.clj:39 clojurewerkz.ogre.util/keywords-to-strings
core.clj:119 clojurewerkz.ogre.core/out[fn]
util.clj:58 clojurewerkz.ogre.util/compile-query[fn]
ArrayChunk.java:58 clojure.lang.ArrayChunk.reduce
protocols.clj:98 clojure.core.protocols/fn
protocols.clj:19 clojure.core.protocols/fn[fn]
protocols.clj:31 clojure.core.protocols/seq-reduce
protocols.clj:48 clojure.core.protocols/fn
protocols.clj:13 clojure.core.protocols/fn[fn]
core.clj:6289 clojure.core/reduce
util.clj:58 clojurewerkz.ogre.util/compile-query
pipe.clj:26 clojurewerkz.ogre.pipe/into-vec!
(...)

After investigation into the test suite of the library I came across the following lines:

The first argument for clojurewerkz.ogre.core/out is expected to be a vector, instead of a keyword. The following code worked:

(q/query (g/find-by-id 4)
         (q/--> [:created])
         q/into-vec!)

Somewhere there is something wrong: either with the docs describing expect behaviour (but the behaviour is not in line with the code), or the docs describing behaviour not congruent with the code as proven by the results and test suite.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.