Skip to content

Commit 565a98a

Browse files
authored
Merge branch 'dev' into tags-for-READ-query-section
2 parents 0dc841c + fca175b commit 565a98a

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

43 files changed

+4004
-3252
lines changed

antora.yml

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
name: cypher-manual
22
title: Cypher Manual
3-
version: '5'
3+
version: '2025'
44
start_page: ROOT:introduction/index.adoc
55
nav:
66
- modules/ROOT/content-nav.adoc
77
asciidoc:
88
attributes:
9-
neo4j-version: '5'
10-
neo4j-version-minor: '5.26'
11-
neo4j-version-exact: '5.26.0'
9+
neo4j-version: '2025'
10+
neo4j-version-minor: '2025.01'
11+
neo4j-version-exact: '2025.01'

modules/ROOT/content-nav.adoc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -116,7 +116,7 @@
116116
** xref:syntax/parsing.adoc[]
117117
** xref:syntax/naming.adoc[]
118118
** xref:syntax/variables.adoc[]
119-
** xref:syntax/reserved.adoc[]
119+
** xref:syntax/keywords.adoc[]
120120
** xref:syntax/parameters.adoc[]
121121
** xref:syntax/operators.adoc[]
122122
** xref:syntax/comments.adoc[]

modules/ROOT/images/graph_match_clause.svg

Lines changed: 1 addition & 1 deletion
Loading

modules/ROOT/pages/appendix/gql-conformance/additional-cypher.adoc

Lines changed: 92 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
:description: Information about Cypher features not included in GQL.
2+
:test-skip: true
23
= Additional Cypher features
34

45
While the link:https://www.iso.org/standard/76120.html[GQL Standard] incorporates a lot of capabilities in Cypher, Cypher contains additional features that are not part of GQL and no GQL alternatives currently exist for them.
@@ -78,6 +79,93 @@ Either the pattern already exists, or it needs to be created.
7879
| Syntactic construct for creating a `LIST` based on matchings of a pattern.
7980
|===
8081

82+
[[dynamic-queries]]
83+
== Dynamic queries
84+
85+
Node labels, relationship types, properties, and CSV columns can be referenced dynamically using Cypher.
86+
This allows for more flexible queries and mitigates the risk of Cypher injection.
87+
(For more information about Cypher injection, see link:https://neo4j.com/developer/kb/protecting-against-cypher-injection/[Neo4j Knowledge Base -> Protecting against Cypher injection]).
88+
89+
[options="header", cols="2a,5a"]
90+
|===
91+
| Cypher feature
92+
| Description
93+
94+
a|
95+
[source, cypher, role="noheader"]
96+
----
97+
MATCH (n:$($label)),
98+
()-[r:$($type)]->()
99+
----
100+
101+
| xref:clauses/match.adoc#dynamic-match[`MATCH` nodes and relationships using dynamic node labels and relationship types]
102+
103+
a|
104+
[source, cypher, role="noheader"]
105+
----
106+
CREATE (n:$($label)),
107+
()-[r:$($type)]->()
108+
----
109+
110+
| xref:clauses/create.adoc#dynamic-create[`CREATE` nodes and relationships using dynamic node labels and relationship types]
111+
112+
a|
113+
[source, cypher, role="noheader"]
114+
----
115+
MERGE (n:$($label)),
116+
()-[r:$($type)]->()
117+
----
118+
119+
| xref:clauses/merge.adoc#dynamic-merge[`MERGE` nodes and relationships using dynamic node labels and relationship types]
120+
121+
a|
122+
[source, cypher, role="noheader"]
123+
----
124+
LOAD CSV WITH HEADERS FROM 'file:///artists-with-headers.csv' AS line
125+
CREATE (n:$(line.label) {name: line.Name})
126+
----
127+
128+
| xref:clauses/load-csv.adoc#dynamic-columns[Import CSV files using dynamic columns]
129+
130+
131+
a|
132+
[source, cypher, role="noheader"]
133+
----
134+
MATCH (n)
135+
SET n[$key] = value
136+
----
137+
138+
| xref:clauses/set.adoc#dynamic-set-property[Dynamically `SET` or update a property]
139+
140+
a|
141+
[source, cypher, role="noheader"]
142+
----
143+
MATCH (n:Label)
144+
SET n:$(n.property)
145+
----
146+
147+
| xref:clauses/set.adoc#dynamic-set-node-label[Dynamically `SET` a node label]
148+
149+
a|
150+
[source, cypher, role="noheader"]
151+
----
152+
MATCH (n {name: 'Peter'})
153+
REMOVE n:$($label)
154+
----
155+
156+
| xref:clauses/remove.adoc#dynamic-remove-property[Dynamically `REMOVE` a property]
157+
158+
a|
159+
[source, cypher, role="noheader"]
160+
----
161+
MATCH (n {name: 'Peter'})
162+
REMOVE n:$($label)
163+
----
164+
165+
| xref:clauses/remove.adoc#dynamic-remove-node-label[Dynamically `REMOVE` a node label]
166+
167+
|===
168+
81169

82170
[[functions]]
83171
== Functions
@@ -118,7 +206,10 @@ Either the pattern already exists, or it needs to be created.
118206
| Description
119207

120208
| xref:functions/graph.adoc#functions-graph-by-elementid[`graph.byElementId()`]
121-
| Returns the graph reference with the given element id. It is only supported in the `USE` clause, on composite databases.
209+
| Returns the graph reference with the given element id.
210+
It is only supported in the xref:clauses/use.adoc[`USE`] clause.
211+
As of Neo4j 5.26, it is supported on both link:{neo4j-docs-base-uri}/operations-manual/{page-version}/database-administration/[standard and composite databases].
212+
On earlier versions, it is only supported on composite databases.
122213

123214
| xref:functions/graph.adoc#functions-graph-byname[`graph.byName()`]
124215
| Returns the graph reference of the given name. It is only supported in the `USE` clause, on composite databases.

modules/ROOT/pages/appendix/gql-conformance/unsupported-mandatory.adoc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,5 +41,5 @@ Cypher Shell also offers specific link:{neo4j-docs-base-uri}/operations-manual/{
4141
| 21.3
4242
| <token>, <separator>, and <identifier>
4343
| GQL specifies a list of link:https://standards.iso.org/iso-iec/39075/ed-1/en/ISO_IEC_39075(en).bnf.txt[reserved words] that cannot be used for unquoted variable names, labels, and property names.
44-
Cypher also specifies a list of xref:syntax/reserved.adoc[reserved keywords], but it differs from GQL's.
44+
Cypher also specifies a list of xref:syntax/keywords.adoc[reserved keywords], but it differs from GQL's.
4545
|===

modules/ROOT/pages/clauses/call.adoc

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -189,6 +189,8 @@ CALL db.labels() YIELD *
189189
If the procedure has deprecated return columns, those columns are also returned.
190190
191191
Note that `YIELD *` is only valid in standalone procedure calls.
192+
Variables must be explicitly named in a `YIELD` clause if other clauses than a single procedure `CALL` are present.
193+
This restriction simplifies query logic and protects against output variables from the procedure accidentally clashing with other query variables.
192194
For example, the following is not valid:
193195
194196
.Not allowed
@@ -204,7 +206,7 @@ RETURN count(*) AS results
204206
====
205207
206208
`YIELD` can be used to filter for specific results.
207-
This requires knowing the names of the arguments within a procedure's signature, which can either be found in the link:{neo4j-docs-base-uri}/operations-manual/{page-version}/reference/procedures/[Operations Manual -> Procedures] or returned by a `SHOW PROCEDURES` query.
209+
This requires knowing the names of the arguments within a procedure's signature, which can either be found in the link:{neo4j-docs-base-uri}/operations-manual/{page-version}/reference/procedures/[Operations Manual -> Procedures] or in the `signature` column returned by a `SHOW PROCEDURES` command (see example below).
208210
209211
.Find the argument names of `db.propertyKeys`
210212
[source, cypher]

modules/ROOT/pages/clauses/create.adoc

Lines changed: 54 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -205,10 +205,63 @@ Nodes created: 2 +
205205
Properties set: 4
206206
|===
207207

208+
[role=label--new-5.26]
209+
[[dynamic-create]]
210+
== CREATE using dynamic node labels and relationship types
211+
212+
Node labels and relationship types can be referenced dynamically in expressions, parameters, and variables when creating nodes and relationships.
213+
This allows for more flexible queries and mitigates the risk of Cypher injection.
214+
(For more information about Cypher injection, see link:https://neo4j.com/developer/kb/protecting-against-cypher-injection/[Neo4j Knowledge Base -> Protecting against Cypher injection]).
215+
216+
.Syntax for creating nodes and relationships dynamically
217+
[source, syntax]
218+
----
219+
CREATE (n:$(<expr>))
220+
CREATE ()-[r:$(<expr>)]->()
221+
----
222+
223+
The expression must evaluate to a `STRING NOT NULL | LIST<STRING NOT NULL> NOT NULL` value.
224+
Using a `LIST<STRING>` with more than one item when creating a relationship using dynamic relationship types will fail.
225+
This is because a relationship can only have exactly one type.
226+
227+
.Parameters
228+
[source, parameters]
229+
----
230+
{
231+
"nodeLabels": ["Person", "Director"],
232+
"relType": "DIRECTED",
233+
"movies": ["Ladybird", "Little Women", "Barbie"]
234+
}
235+
----
236+
237+
.Create nodes and relationships using dynamic node labels and relationship types
238+
// tag::clauses_create_dynamic_create[]
239+
[source, cypher]
240+
----
241+
CREATE (greta:$($nodeLabels) {name: 'Greta Gerwig'})
242+
WITH greta
243+
UNWIND $movies AS movieTitle
244+
CREATE (greta)-[rel:$($relType)]->(m:Movie {title: movieTitle})
245+
RETURN greta.name AS name, labels(greta) AS labels, type(rel) AS relType, collect(m.title) AS movies
246+
----
247+
// end::clauses_create_dynamic_create[]
248+
249+
.Result
250+
[role="queryresult",options="footer",cols="4*<m"]
251+
|===
252+
| name | labels | relType | movies
253+
254+
| "Greta Gerwig"
255+
| ["Person", "Director"]
256+
| "DIRECTED"
257+
| ["Ladybird", "Little Women", "Barbie"]
258+
4+d|Rows: 1 +
259+
|===
260+
208261
[role=label--new-5.18]
209262
[[insert-as-synonym-of-create]]
210263
== `INSERT` as a synonym of `CREATE`
211-
264+
212265
`INSERT` can be used as a synonym to `CREATE` for creating nodes and relationships, and was introduced as part of Cypher's xref:appendix/gql-conformance/index.adoc[].
213266
However, `INSERT` requires that multiple labels are separated by an ampersand `&` and not by colon `:`.
214267

modules/ROOT/pages/clauses/load-csv.adoc

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -299,6 +299,53 @@ Added 4 nodes, Set 8 properties, Added 4 labels
299299
|===
300300
====
301301

302+
[role=label--new-5.26]
303+
[[dynamic-columns]]
304+
=== Import CSV files using dynamic columns
305+
306+
CSV columns can be referenced dynamically to map labels to nodes in the graph.
307+
This enables flexible data handling, allowing labels to be be populated from CSV column values without manually specifying each entry.
308+
It also mitigates the risk of Cypher injection.
309+
(For more information about Cypher injection, see link:https://neo4j.com/developer/kb/protecting-against-cypher-injection/[Neo4j Knowledge Base -> Protecting against Cypher injection]).
310+
311+
.bands-with-headers.csv
312+
[source, csv, filename="bands-with-headers.csv"]
313+
----
314+
Id,Label,Name
315+
1,Band,The Beatles
316+
2,Band,The Rolling Stones
317+
3,Band,Pink Floyd
318+
4,Band,Led Zeppelin
319+
----
320+
321+
.Query
322+
// tag::clauses_load_csv_dynamic_columns[]
323+
[source, cypher]
324+
----
325+
LOAD CSV WITH HEADERS FROM 'file:///bands-with-headers.csv' AS line
326+
MERGE (n:$(line.Label) {name: line.Name})
327+
RETURN n AS bandNodes
328+
----
329+
// end::clauses_load_csv_dynamic_columns[]
330+
331+
.Result
332+
[role="queryresult",options="header,footer",cols="1*<m"]
333+
|===
334+
| bandNodes
335+
336+
| (:Band {name: 'The Beatles'})
337+
| (:Band {name: 'The Rolling Stones'})
338+
| (:Band {name: 'Pink Floyd'})
339+
| (:Band {name: 'Led Zeppelin'})
340+
341+
1+d|Rows: 4 +
342+
Added 4 nodes, Set 4 properties, Added 4 labels
343+
|===
344+
345+
[NOTE]
346+
`MERGE` queries using dynamic values may not be as performant as those using static values.
347+
This is because the xref:planning-and-tuning/execution-plans.adoc[Cypher planner] uses statically available information when planning queries to determine whether to use an xref:indexes/search-performance-indexes/overview.adoc[index] or not, and this is not possible when using dynamic values.
348+
For more information, see xref:clauses/merge.adoc#dynamic-merge-caveats[`MERGE` using dynamic node labels and relationship types -> Performance caveats].
302349

303350
=== Import compressed CSV files
304351

0 commit comments

Comments
 (0)