#
Migrating from Gremlin to Curiosity
If you are familiar with Gremlin (the graph traversal language used by Apache TinkerPop and others), this guide will help you translate your knowledge to Curiosity's C# Query fluent interface.
Both Gremlin and Curiosity's Query are imperative, fluent-style query builders, so the transition is often quite natural.
#
Basic Lookups
#
1. Get all nodes of a label
Gremlin
g.V().hasLabel('Person')
Curiosity
Query().StartAt("Person").Emit()
#
2. Get a node by ID
Gremlin
g.V().hasLabel('Person').hasId('123')
Curiosity
Query().StartAt("Person", "123").Emit()
#
3. Get a node by Key/Property
Gremlin
g.V().hasLabel('Person').has('email', 'alice@example.com')
Curiosity
Query().StartAt("Person", "email", "alice@example.com").Emit()
// OR
Query().StartAt("Person").WhereString("email", "alice@example.com").Emit()
#
Filtering
#
4. Filter by string property
Gremlin
g.V().hasLabel('Person').has('status', 'Active')
Curiosity
Query().StartAt("Person").WhereString("status", "Active").Emit()
#
5. Filter by numeric property
Gremlin
g.V().hasLabel('Product').has('price', gt(100))
Curiosity
Query().StartAt("Product").Where(n => n.GetFloat("price") > 100).Emit()
#
6. Filter by boolean
Gremlin
g.V().hasLabel('Task').has('completed', true)
Curiosity
Query().StartAt("Task").Where(n => n.GetBool("completed")).Emit()
#
7. Filter NOT equal
Gremlin
g.V().hasLabel('Person').has('status', neq('Deleted'))
Curiosity
Query().StartAt("Person").WhereNotString("status", "Deleted").Emit()
#
8. Filter IN list
Gremlin
g.V().hasLabel('Person').has('role', within('Admin', 'Manager'))
Curiosity
Query().StartAt("Person").WhereString("role", new[]{"Admin", "Manager"}).Emit()
#
9. Filter by Timestamp
Gremlin
g.V().hasLabel('Log').has('timestamp', gte(new Date())) // Syntax varies by implementation
Curiosity
Query().StartAt("Log").WhereTimestamp(from: new Time(2023, 1, 1), to: Time.MaxValue, insideBoundary: true).Emit()
#
Relationships
#
10. Simple Traversal
Gremlin
g.V().hasLabel('Person').out('KNOWS').hasLabel('Person')
Curiosity
Query().StartAt("Person").Out("Person", "KNOWS").Emit()
#
11. Traversal ignoring edge type
Gremlin
g.V().hasLabel('Person').out().hasLabel('Department')
Curiosity
Query().StartAt("Person").Out("Department").Emit()
#
12. Traversal ignoring target label
Gremlin
g.V().hasLabel('Person').out('HAS_FILE')
Curiosity
Query().StartAt("Person").Out(edgeType: "HAS_FILE").Emit()
#
13. Multi-hop Traversal
Gremlin
g.V().hasLabel('Person').repeat(out('KNOWS').hasLabel('Person')).times(2)
Curiosity
Query().StartAt("Person").OutMany(levels: 2, nodeTypes: new[] { "Person" }, edgeTypes: new[] { "KNOWS" }).Emit()
#
14. Check if related to specific node
Gremlin
g.V().hasLabel('Person').filter(out('WORKS_FOR').hasId('C1'))
Curiosity
Query().StartAt("Person").IsRelatedToVia(Node.GetUID("Company", "C1"), "WORKS_FOR").Emit()
#
15. Check if NOT related
Gremlin
g.V().hasLabel('Person').filter(not(out('HAS_Badge')))
Curiosity
Query().StartAt("Person").IsNotRelatedToVia(edgeType: "HAS_Badge").Emit()
#
Advanced Logic
#
16. Union
Gremlin
g.V().hasLabel('Manager').union(g.V().hasLabel('Director'))
Curiosity
var q1 = Query().StartAt("Manager");
var q2 = Query().StartAt("Director");
q1.Union(q2).Emit();
#
17. Intersection
Gremlin
g.V().hasLabel('Person').has('age', gt(30)).has('status', 'Active')
// (Implicit chain)
Curiosity
// Fluent chaining acts as intersection
Query().StartAt("Person").Where(n => n.GetInt("age") > 30).WhereString("status", "Active").Emit()
// Or explicit set intersection
var q1 = Query().StartAt("Person").Where(n => n.GetInt("age") > 30);
var q2 = Query().StartAt("Person").WhereString("status", "Active");
q1.Intersect(q2).Emit();
#
18. Sorting and Limiting
Gremlin
g.V().hasLabel('Product').order().by('created', decr).limit(10)
Curiosity
Query().StartAt("Product").SortByTimestamp(oldestFirst: false).Take(10).Emit()
#
19. Counting
Gremlin
g.V().hasLabel('Person').count()
Curiosity
int count = Query().StartAt("Person").Count();
#
20. Distinct
Gremlin
g.V().out('FRIEND').dedup()
Curiosity
Query().StartAt("Person").Out("Person", "FRIEND").Distinct().Emit()
#
21. Path Finding (Shortest Path)
Gremlin
g.V('A').repeat(both().simplePath()).until(hasId('B')).path().limit(1)
Curiosity
Query().PathBetween(Node.GetUID("Person", "A"), Node.GetUID("Person", "B"))
#
22. Text Search
Gremlin
// Vendor specific (e.g., JanusGraph or Neptune text predicates)
g.V().hasLabel('Document').has('content', textContains('project'))
Curiosity
Query().StartSearch("Document", "content", Search.Parse("project")).Emit()