bitflicker64 commented on code in PR #499:
URL: https://github.com/apache/hugegraph-doc/pull/499#discussion_r4097186496


##########
content/en/docs/language/cypher-compatibility.md:
##########
@@ -0,0 +1,59 @@
+---
+title: "Cypher Compatibility"
+linkTitle: "Cypher Compatibility"
+weight: 3
+---
+
+### Scope of this page
+
+HugeGraph executes Cypher by translating statements to Gremlin through the
+[`cypher-for-gremlin`](https://github.com/opencypher/cypher-for-gremlin)
+transpiler (`org.opencypher.gremlin:translation:1.0.4`, released 2019-11-05).
+Cypher coverage in HugeGraph therefore equals what that translator implements
+of openCypher 9 — see [HugeGraph Cypher](/docs/language/hugegraph-cypher/) for
+usage and [Known 
limitations](/docs/language/hugegraph-cypher/#known-limitations)
+for the short list.
+
+The transpiler's own conformance self-report for 1.0.4 is **879 pass / 79 fail
+(~91.7%)** of the openCypher TCK scenario set it targets. The matrix below
+classifies features by the best available evidence; rows are not a substitute
+for testing your own workload.
+
+### Feature matrix
+
+| openCypher feature | Status | Evidence tier | Notes / Gremlin workaround |
+|---|---|---|---|
+| `MATCH` + `WHERE` + `RETURN` (node patterns) | ✅ Works | Documented examples 
| [Language guide](/docs/language/hugegraph-cypher/) |
+| Relationship patterns `(a)-[:KNOWS]->(b)` | ✅ Works | Documented examples | 
— |
+| `ORDER BY` / `LIMIT` / `SKIP` | ✅ Works | Documented examples | — |
+| `CREATE` vertex / edge, `SET` / `REMOVE`, `DELETE` / `DETACH DELETE` | ✅ 
Works | Documented examples | — |
+| Aggregations (`count`, `sum`, `min`, `max`, `avg`) | ✅ Works | Documented 
examples | — |
+| `MERGE` (basic) | ⚠️ Partial | Transpiler report | `MERGE ... ON CREATE SET` 
/ `ON MATCH SET` not translated → check-then-create pattern via Gremlin |
+| Variable-length paths `(a)-[:KNOWS*1..3]->(b)` | ⚠️ Untested | — | Prefer 
`traverser` REST APIs (k-out, paths) or Gremlin `repeat()` |
+| `OPTIONAL MATCH`, `WITH`, `UNWIND` | ⚠️ Untested | — | Test before relying 
on them; fall back to Gremlin |
+| String / math functions | ⚠️ Partial | Transpiler report | Subset of 
openCypher 9 functions; unsupported ones fail at translation time |
+| `date()` / `datetime()` functions | ❌ Not supported | Issue reports | 
Compute timestamps client-side and pass as literal values |
+| Regex `=~` and `NOT (... IN ...)` forms | ❌ Not supported | Issue reports | 
Filter client-side or via Gremlin predicates (`TextP.regex`) |

Review Comment:
   Important: The matrix marks several constructs as not supported or not 
translated, but transpiler 1.0.4 translates them with the translator definition 
HugeGraph uses. This row lists `=~` and `NOT (... IN ...)` as "Not supported", 
line 31 says `MERGE ... ON CREATE SET` / `ON MATCH SET` is "not translated", 
and `hugegraph-cypher.md` line 125 repeats all three in Known limitations. The 
CN pages carry the same text (compatibility lines 27 and 32, guide line 125).
   
   Evidence: I ran `CypherAst.parse(...).translate(...)` from 
`translation-1.0.4.jar` with 
`gremlin+cfog_server_extensions+inline_parameters`, the default in 
`CypherOpProcessor.DEFAULT_TRANSLATOR_DEFINITION`. Results:
   - `MERGE (n:person {name: 'x'}) ON CREATE SET n.age = 1 ON MATCH SET n.age = 
2` translates to a `choose(...)` traversal.
   - `WHERE n.name =~ 'ma.*'` translates to `has('name', cypherRegex('ma.*'))`. 
`cypherRegex` comes from `CustomPredicate`, which the shipped 
`conf/gremlin-server.yaml` imports (lines 69-75).
   - `WHERE NOT n.name IN ['a','b']` and `WHERE NOT (n.name IN ['a','b'])` both 
translate to `has('name', without('a', 'b'))`.
   
   `date()`, `datetime()` and map projection do fail at translation, so those 
rows are right.
   
   Requested change: move MERGE with ON CREATE/ON MATCH, `=~` and `NOT ... IN` 
out of the "Not supported" rows and out of the Known limitations bullet in both 
languages. Mark them "translates, not verified on HugeGraph" unless you run 
them against a server. Change the evidence tier from "Issue reports" to the 
transpiler check, or link the issues it refers to.



##########
content/en/docs/language/migrate-from-neo4j.md:
##########
@@ -0,0 +1,60 @@
+---
+title: "Migrating from Neo4j"
+linkTitle: "Migrating from Neo4j"
+weight: 4
+---
+
+### Who this page is for
+
+Neo4j users evaluating HugeGraph. HugeGraph's Cypher coverage is defined by
+the [`cypher-for-gremlin`](https://github.com/opencypher/cypher-for-gremlin)
+translator and is not 1:1 with Neo4j — see the
+[Cypher compatibility matrix](/docs/language/cypher-compatibility/) for the
+feature-level differences and
+[HugeGraph Cypher](/docs/language/hugegraph-cypher/) for usage.
+
+### What carries over directly
+
+| Neo4j concept | HugeGraph equivalent |
+|---|---|
+| Property graph model (nodes / relationships / properties) | Same — vertex 
labels / edge labels / properties |
+| Core Cypher: `MATCH`/`WHERE`/`RETURN`/`CREATE`/`SET`/`DELETE` | Works as-is 
(REST `/cypher` endpoint or Java client `CypherManager`) |
+| Simple aggregations (`count`/`sum`/`min`/`max`/`avg`) | Works as-is |
+| Traversal-heavy queries | Gremlin traversals or the [traverser REST 
APIs](/docs/clients/restful-api/traverser/) (k-out, shortest path, 
personalrank, ...) |
+
+### Habits you need to change
+
+| In Neo4j | In HugeGraph |
+|---|---|
+| `CREATE INDEX` / `CREATE CONSTRAINT` | Create indexes/constraints through 
the [schema REST APIs](/docs/clients/restful-api/schema/); Cypher carries no 
DDL |
+| Implicit schema (add properties freely) | **Strong schema**: define 
VertexLabel / EdgeLabel / PropertyKey before writing data |
+| Parameterized queries `$param` | Not supported — escape/validate values 
client-side and interpolate literals |
+| `CALL dbms.*` / `CALL algo.*` procedures | Equivalent capabilities live in 
the [traverser](/docs/clients/restful-api/traverser/), 
[task](/docs/clients/restful-api/task/), and other REST APIs |
+| Driver: Neo4j Bolt driver | 
[hugegraph-client](/docs/clients/hugegraph-client/) (`CypherManager`) or any 
HTTP client |
+| Transaction boundaries inside a Cypher statement | One statement per 
request; bulk writes use the [Loader](/docs/guides/toolchain/) or bulkport |

Review Comment:
   Minor: `/docs/guides/toolchain/` does not exist. `content/en/docs/guides/` 
has no `toolchain` page or section, so this link returns 404. The CN link 
`/cn/docs/guides/toolchain/` on line 33 of the CN page is broken in the same 
way. "bulkport" does not appear anywhere else in the docs, and I could not find 
a HugeGraph tool with that name.
   
   Requested change: point the Loader link to 
`/docs/quickstart/toolchain/hugegraph-loader/` (and 
`/cn/docs/quickstart/toolchain/hugegraph-loader/`), and remove "bulkport" or 
replace it with the tool you meant, with a link.



##########
content/en/docs/language/cypher-compatibility.md:
##########
@@ -0,0 +1,59 @@
+---
+title: "Cypher Compatibility"
+linkTitle: "Cypher Compatibility"
+weight: 3
+---
+
+### Scope of this page
+
+HugeGraph executes Cypher by translating statements to Gremlin through the
+[`cypher-for-gremlin`](https://github.com/opencypher/cypher-for-gremlin)
+transpiler (`org.opencypher.gremlin:translation:1.0.4`, released 2019-11-05).
+Cypher coverage in HugeGraph therefore equals what that translator implements
+of openCypher 9 — see [HugeGraph Cypher](/docs/language/hugegraph-cypher/) for
+usage and [Known 
limitations](/docs/language/hugegraph-cypher/#known-limitations)
+for the short list.
+
+The transpiler's own conformance self-report for 1.0.4 is **879 pass / 79 fail
+(~91.7%)** of the openCypher TCK scenario set it targets. The matrix below
+classifies features by the best available evidence; rows are not a substitute
+for testing your own workload.
+
+### Feature matrix
+
+| openCypher feature | Status | Evidence tier | Notes / Gremlin workaround |
+|---|---|---|---|
+| `MATCH` + `WHERE` + `RETURN` (node patterns) | ✅ Works | Documented examples 
| [Language guide](/docs/language/hugegraph-cypher/) |
+| Relationship patterns `(a)-[:KNOWS]->(b)` | ✅ Works | Documented examples | 
— |
+| `ORDER BY` / `LIMIT` / `SKIP` | ✅ Works | Documented examples | — |
+| `CREATE` vertex / edge, `SET` / `REMOVE`, `DELETE` / `DETACH DELETE` | ✅ 
Works | Documented examples | — |
+| Aggregations (`count`, `sum`, `min`, `max`, `avg`) | ✅ Works | Documented 
examples | — |
+| `MERGE` (basic) | ⚠️ Partial | Transpiler report | `MERGE ... ON CREATE SET` 
/ `ON MATCH SET` not translated → check-then-create pattern via Gremlin |
+| Variable-length paths `(a)-[:KNOWS*1..3]->(b)` | ⚠️ Untested | — | Prefer 
`traverser` REST APIs (k-out, paths) or Gremlin `repeat()` |
+| `OPTIONAL MATCH`, `WITH`, `UNWIND` | ⚠️ Untested | — | Test before relying 
on them; fall back to Gremlin |
+| String / math functions | ⚠️ Partial | Transpiler report | Subset of 
openCypher 9 functions; unsupported ones fail at translation time |
+| `date()` / `datetime()` functions | ❌ Not supported | Issue reports | 
Compute timestamps client-side and pass as literal values |
+| Regex `=~` and `NOT (... IN ...)` forms | ❌ Not supported | Issue reports | 
Filter client-side or via Gremlin predicates (`TextP.regex`) |
+| Map projection `n { .name, .age }` | ❌ Not supported | Issue reports | 
Return the node or explicit properties |
+| Query parameters (`$param`) | ❌ Not supported | API surface (`CypherAPI` 
accepts statement string only) | Escape/sanitize values client-side before 
interpolating |
+| `CALL` procedures (graph algorithms) | ❌ Not supported | API surface | Use 
[traverser REST APIs](/docs/clients/restful-api/traverser/) or Gremlin |
+| Multi-statement scripts | ❌ Not supported | API surface | One statement per 
request |
+| Schema DDL in Cypher (`CREATE INDEX`, constraints) | ❌ Not supported | 
Architecture | Create schema via the [schema REST 
APIs](/docs/clients/restful-api/schema/) |
+| `EXPLAIN` / `PROFILE` | ❌ Not supported | API surface | Use Gremlin 
`profile()` on the traversal API |

Review Comment:
   Important: `EXPLAIN` works through the Cypher API. 
`CypherOpProcessor.evalCypher` checks `ast.getOptions().contains(EXPLAIN)` and 
calls `explainQuery`, which returns a SUCCESS response with `{"translation": 
<gremlin>, "options": ...}`. `CypherClient.doQueryList` puts that map into 
`result.data`. With transpiler 1.0.4, `EXPLAIN MATCH (n:person) RETURN n` 
parses with options `[EXPLAIN]`, so it takes that path. Only `PROFILE` fails: 
it is a syntax error ("Invalid input 'P'"). The CN row (line 38) says the same 
thing.
   
   This matters for the migration guide. `EXPLAIN` shows the Gremlin that 
HugeGraph will run, which is the fastest way to write the Gremlin fallback the 
pages recommend.
   
   Requested change: split the row. Mark `EXPLAIN` as supported, returning the 
translated Gremlin in `result.data[0].translation`. Keep `PROFILE` as not 
supported with the Gremlin `profile()` workaround. Update the CN row to match.



##########
content/en/docs/language/hugegraph-cypher.md:
##########
@@ -0,0 +1,135 @@
+---
+title: "HugeGraph Cypher"
+linkTitle: "Cypher Query Language"
+weight: 2
+---
+
+### Overview
+
+HugeGraph supports [Cypher](https://opencypher.org/), the declarative graph 
query language originally created by Neo4j and standardized as 
[openCypher](https://github.com/opencypher/openCypher). While Gremlin is an 
imperative traversal language, Cypher lets you describe the graph pattern you 
want (`MATCH`, `WHERE`, `RETURN`) and lets the engine decide how to execute it.
+
+HugeGraph executes Cypher by translating the statement to Gremlin through the 
[cypher-for-gremlin](https://github.com/opencypher/cypher-for-gremlin) 
transpiler, then running the resulting traversal on the TinkerPop stack. This 
means Cypher support in HugeGraph covers the openCypher 9 surface that the 
transpiler implements — see [Known limitations](#known-limitations) below.
+
+### When to use Cypher vs Gremlin
+
+| Use Cypher when | Use Gremlin when |
+|---|---|
+| You are migrating from Neo4j or already know Cypher | You need the full 
HugeGraph feature surface |
+| You want declarative pattern matching (`MATCH (a)-[:KNOWS]->(b)`) | You need 
fine-grained traversal control, custom steps, or lambdas |
+| Your queries are read-mostly patterns and projections | You need graph 
algorithms, OLAP, or features Cypher does not expose |
+
+For anything Cypher cannot express, the equivalent Gremlin query always works 
— examples below show both.
+
+### Calling the Cypher API
+
+Cypher statements are submitted to the HugeGraph Server through the REST 
endpoint:
+
+```http
+GET  /graphspaces/{graphspace}/graphs/{graph}/cypher?cypher={statement}
+POST /graphspaces/{graphspace}/graphs/{graph}/cypher
+```
+
+The endpoint always requires an `Authorization` header (`Basic` or `Bearer`), 
even when server authentication is disabled — the credentials are forwarded to 
the Gremlin Server. See the [Cypher REST API 
reference](/docs/clients/restful-api/cypher/) for the full request/response 
format.
+
+Example:
+
+```bash
+curl -H "Authorization: Bearer $TOKEN" \
+  
"http://localhost:8080/graphspaces/DEFAULT/graphs/hugegraph/cypher?cypher=MATCH%20(n:person)%20RETURN%20n.name%20LIMIT%2010"
+```
+
+From the Java client, use `CypherManager` (see 
[hugegraph-client](/docs/clients/hugegraph-client/)):
+
+```java
+ResultSet resultSet = hugeClient.cypher().execute("MATCH (n:person) RETURN 
n.name LIMIT 10");
+```
+
+### Basic examples
+
+The examples below assume a graph with `person` vertices (`name`, `age`, 
`city` properties) and `knows` edges.
+
+#### Read — MATCH / WHERE / RETURN
+
+```cypher
+// All persons named "marko"
+MATCH (n:person) WHERE n.name = 'marko' RETURN n
+
+// Projection with ordering and limit
+MATCH (n:person)
+WHERE n.age > 30
+RETURN n.name AS name, n.age AS age
+ORDER BY age DESC
+LIMIT 10
+
+// Relationship pattern
+MATCH (a:person)-[:knows]->(b:person)
+WHERE a.name = 'marko'
+RETURN b.name AS friend
+```
+
+#### Create — CREATE
+
+```cypher
+// Create a vertex
+CREATE (n:person {name: 'josh', age: 32, city: 'beijing'})
+
+// Create two vertices and an edge between them
+CREATE (a:person {name: 'peter'})-[:knows]->(b:person {name: 'lop'})
+```
+
+#### Update — SET / REMOVE
+
+```cypher
+MATCH (n:person) WHERE n.name = 'josh'
+SET n.age = 33
+REMOVE n.city
+```
+
+#### Delete — DELETE / DETACH DELETE
+
+```cypher
+// Delete an edge
+MATCH (a:person)-[r:knows]->(b:person)
+WHERE a.name = 'peter' AND b.name = 'lop'
+DELETE r
+
+// Delete a vertex and all its edges
+MATCH (n:person) WHERE n.name = 'josh'
+DETACH DELETE n
+```
+
+#### Aggregation
+
+```cypher
+MATCH (n:person) RETURN count(n) AS total
+MATCH (n:person) RETURN n.city AS city, count(*) AS cnt ORDER BY cnt DESC
+```
+
+### Gremlin equivalents
+
+Every Cypher statement is translated to Gremlin internally. When a Cypher 
feature is unsupported, write the traversal directly:
+
+| Cypher | Gremlin equivalent |
+|---|---|
+| `MATCH (n:person) WHERE n.name='marko' RETURN n` | 
`g.V().hasLabel('person').has('name','marko')` |
+| `MATCH (a)-[:knows]->(b) RETURN b` | `g.V().out('knows')` |
+| `CREATE (n:person {name:'x'})` | `g.addV('person').property('name','x')` |
+| `MATCH (n) DETACH DELETE n` | `g.V().drop()` |
+| `MATCH (n:person) RETURN count(n)` | `g.V().hasLabel('person').count()` |
+
+### Known limitations
+
+Cypher support in HugeGraph is bounded by the transpiler layer, which is based 
on openCypher 9 era tooling. Known gaps:
+
+- **No parameterized queries** — the API accepts a raw statement string only; 
`$param` placeholders are not supported. Sanitize/escape values on the client 
side before interpolating them into the statement.

Review Comment:
   Minor: The API does not accept parameters, as this line says, but a 
statement that uses `$param` does not fail. `CypherClient.createRequest` sends 
only the statement (no bindings), and `CypherOpProcessor` passes an empty map 
to `CypherAst.parse`. With `inline_parameters`, transpiler 1.0.4 replaces the 
missing parameter with the null marker: `MATCH (n:person) WHERE n.name = $name 
RETURN n` translates to `where(__.choose(__.constant('  cypher.null'), ...))`. 
The request returns status 200 and no rows. Line 125 and the Failure behaviour 
section on the compatibility page tell readers that unsupported constructs fail 
at translation time, so a Neo4j user will expect an error here and get an empty 
result instead.
   
   Requested change: add one sentence to this bullet, in EN and CN, saying that 
a `$param` statement still runs, the parameter evaluates to null, and the query 
returns no rows or writes null values. Give the same warning in the `$param` 
row of the compatibility matrix.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to