Cypher 代码风格指南

Cypher® 风格指南旨在使查询尽可能易于阅读。

有关标签、关系类型和属性命名的规则及建议,请参阅命名规则与建议

确保查询遵循样式规则的最佳方法是使用官方 Cypher 格式化工具 cypherfmt。它作为 Neo4j VS Code 扩展的一部分提供,也可通过 Neo4j Cypher 语言支持 npm 包作为命令行工具使用。

通用建议

  • 在正文中引用 Cypher 语言构造时,请使用 等宽 字体并遵循样式规则。

  • 引用标签和关系类型时,应包含冒号,例如::Label, :REL_TYPE

  • 引用函数时,请使用小驼峰命名法并加上括号。例如:toString()

  • 如果您将 Cypher 语句存储在单独的文件中,请使用文件扩展名 .cypher

缩进和换行

  • 新子句应另起一行。

错误示例
MATCH (n) WHERE n.name CONTAINS 's' RETURN n.name
良好
MATCH (n)
WHERE n.name CONTAINS 's'
RETURN n.name
  • ON CREATEON MATCH 缩进两个空格。如果两者同时出现,请将 ON CREATE 放在 ON MATCH 之前。

错误示例
MERGE (n) ON CREATE SET n.prop = 0
MERGE (a:A)-[:T]->(b:B)
ON MATCH SET b.name = 'you'
ON CREATE SET a.name = 'me'
RETURN a.prop
良好
MERGE (n)
  ON CREATE SET n.prop = 0
MERGE (a:A)-[:T]->(b:B)
  ON CREATE SET a.name = 'me'
  ON MATCH SET b.name = 'you'
RETURN a.prop
  • 子查询应在左大括号后另起一行,并额外缩进两个空格。右大括号应独占一行。

错误示例
MATCH (a:A)
WHERE
  EXISTS { MATCH (a)-->(b:B) WHERE b.prop = 'yellow' }
RETURN a.foo
错误示例
MATCH (a:A)
WHERE EXISTS
{MATCH (a)-->(b:B)
WHERE b.prop = 'yellow'}
RETURN a.foo
良好
MATCH (a:A)
WHERE EXISTS {
  MATCH (a)-->(b:B)
  WHERE b.prop = 'yellow'
}
RETURN a.foo
  • 如果使用简化形式的子查询,请勿换行。

错误示例
MATCH (a:A)
WHERE EXISTS {
  (a)-->(b:B)
}
RETURN a.prop
良好
MATCH (a:A)
WHERE EXISTS { (a)-->(b:B) }
RETURN a.prop
  • 如果可能,行长度应限制在 80 个字符以内。换行应从最外层分组开始,每个嵌套分组依次换行,直到行长度合适或无法再插入换行符为止。每个嵌套的换行分组应增加两个空格的缩进。

错误示例
MATCH (n)
WHERE n.prop <> 'a' AND n.prop <> 'b' AND n.prop <> 'c' AND n.prop <> 'd' AND n.prop <> 'e'
RETURN n
良好
MATCH (n)
WHERE
  n.prop <> 'a' AND
  n.prop <> 'b' AND
  n.prop <> 'c' AND
  n.prop <> 'd' AND
  n.prop <> 'e'
RETURN n
  • ORDER BYLIMIT 子句应另起一行。

错误示例
MATCH (n)
RETURN 5 ORDER BY n.prop LIMIT 10
良好
MATCH (n)
RETURN 5
ORDER BY n.prop
LIMIT 10
  • 包含 CASE 表达式的分组应始终换行,且每个 WHENELSEEND 都应置于新行。此外,WHENELSE 应增加两个空格的缩进。

错误示例
MATCH (n:Person {name: 'Alice'})
RETURN CASE WHEN n.age >= 18 THEN 'Adult' ELSE 'Minor' END AS ageGroup
良好
MATCH (n:Person {name: 'Alice'})
RETURN
  CASE
    WHEN n.age >= 18 THEN 'Adult'
    ELSE 'Minor'
  END AS ageGroup
  • 当行尾的列表或映射字面量超过最大行宽时,将左括号或左大括号放在引入它的同一行。字面量的每个元素应另起一行,缩进比包含左括号或左大括号的那一行多两个空格。在原始缩进级别关闭字面量。

错误示例
RETURN
  [
    "Alice",
    "Bob",
    "Charlie",
    "David",
    "Eve",
    "Frank",
    "Grace",
    "Heidi",
    "Ivan",
    "Judy"
  ]
良好
RETURN [
  "Alice",
  "Bob",
  "Charlie",
  "David",
  "Eve",
  "Frank",
  "Grace",
  "Heidi",
  "Ivan",
  "Judy"
]
  • 可以使用单个空行来分隔子句、查询或注释。

良好
MATCH (n)-[r]->(m)
RETURN n, r, m
良好示例
MATCH (n)-[r]->(m)

RETURN n, r, m

大小写

  • 关键字请使用大写。

错误示例
match (p:Person)
where p.name starts with 'Ma'
return p.name
良好
MATCH (p:Person)
WHERE p.name STARTS WITH 'Ma'
RETURN p.name
  • null 请使用小写。

错误示例
WITH NULL AS n1, Null AS n2
RETURN n1 IS NULL AND n2 IS NOT NULL
良好
WITH null AS n1, null AS n2
RETURN n1 IS NULL AND n2 IS NOT NULL
  • BOOLEAN 字面量(truefalse)请使用小写。

错误示例
WITH TRUE AS b1, False AS b2
RETURN b1 AND b2
良好
WITH true AS b1, false AS b2
RETURN b1 AND b2
  • 以下内容请使用小驼峰命名法(以小写字母开头):

    • 函数

    • 属性

    • 变量

    • parameters

错误示例
CREATE (N:Label {Prop: 0})
WITH N, RAND() AS Rand, $pArAm AS MAP
RETURN Rand, MAP.property_key, count(N)
良好
CREATE (n:Label {prop: 0})
WITH n, rand() AS rand, $param AS map
RETURN rand, map.propertyKey, count(n)

间距

  • 对于字面量映射:

    • 左大括号和第一个键之间不要有空格

    • 键和冒号之间不要有空格

    • 冒号和值之间应有一个空格

    • 值和逗号之间不要有空格

    • 逗号和下一个键之间应有一个空格

    • 最后一个值和右大括号之间不要有空格

错误示例
WITH { key1 :'value' ,key2  :  42 } AS map
RETURN map
良好
WITH {key1: 'value', key2: 42} AS map
RETURN map
  • 在模式中,标签/类型谓词和属性谓词之间应有一个空格。

错误示例
MATCH (p:Person{property: -1})-[:KNOWS   {since: 2016}]->()
RETURN p.name
良好
MATCH (p:Person {property: -1})-[:KNOWS {since: 2016}]->()
RETURN p.name
  • 模式内不要有空格。

错误示例
MATCH (:Person) --> (:Vehicle)
RETURN count(*)
良好
MATCH (:Person)-->(:Vehicle)
RETURN count(*)
  • 运算符两侧应使用包裹空格。

错误示例
MATCH p=(s)-->(e)
WHERE s.name<>e.name
RETURN length(p)
良好
MATCH p = (s)-->(e)
WHERE s.name <> e.name
RETURN length(p)
  • 标签谓词内不要有空格。

错误示例
MATCH (person    : Person  :  Owner  )
RETURN person.name
良好
MATCH (person:Person:Owner)
RETURN person.name
  • 列表和枚举中,每个逗号后应使用空格。

错误示例
MATCH (),()
WITH ['a','b',3.14] AS list
RETURN list,2,3,4
良好
MATCH (), ()
WITH ['a', 'b', 3.14] AS list
RETURN list, 2, 3, 4
  • 函数调用的括号内不要有内边距空格。

错误示例
RETURN split( 'original', 'i' )
良好
RETURN split('original', 'i')
  • 简单的子查询表达式内应使用内边距空格。

错误示例
MATCH (a:A)
WHERE EXISTS {(a)-->(b:B)}
RETURN a.prop
良好
MATCH (a:A)
WHERE EXISTS { (a)-->(b:B) }
RETURN a.prop

模式

  • 当模式需要换行时,请在箭头之后换行,而不是之前。

错误示例
MATCH (:Person)-->(vehicle:Car)-->(:Company)
      <--(:Country)
RETURN count(vehicle)
良好
MATCH (:Person)-->(vehicle:Car)-->(:Company)<--
      (:Country)
RETURN count(vehicle)
  • 如果变量不会被用到,请使用匿名节点和关系。

错误示例
MATCH (kate:Person {name: 'Kate'})-[r:LIKES]-(c:Car)
RETURN c.type
良好
MATCH (:Person {name: 'Kate'})-[:LIKES]-(c:Car)
RETURN c.type
  • 将模式串联起来以避免重复变量。

错误示例
MATCH (:Person)-->(vehicle:Car), (vehicle:Car)-->(:Company)
RETURN count(vehicle)
良好
MATCH (:Person)-->(vehicle:Car)-->(:Company)
RETURN count(vehicle)
  • 将具名节点置于匿名节点之前。

错误示例
MATCH ()-->(vehicle:Car)-->(manufacturer:Company)
WHERE manufacturer.foundedYear < 2000
RETURN vehicle.mileage
良好
MATCH (manufacturer:Company)<--(vehicle:Car)<--()
WHERE manufacturer.foundedYear < 2000
RETURN vehicle.mileage
  • 保持锚点节点位于 MATCH 子句的开头。

错误示例
MATCH (:Person)-->(vehicle:Car)-->(manufacturer:Company)
WHERE manufacturer.foundedYear < 2000
RETURN vehicle.mileage
良好
MATCH (manufacturer:Company)<--(vehicle:Car)<--(:Person)
WHERE manufacturer.foundedYear < 2000
RETURN vehicle.mileage
  • 优先使用向外(从左到右)的关系模式,而不是向内的关系模式。

错误示例
MATCH (:Country)-->(:Company)<--(vehicle:Car)<--(:Person)
RETURN vehicle.mileage
良好
MATCH (:Person)-->(vehicle:Car)-->(:Company)<--(:Country)
RETURN vehicle.mileage

元字符

  • 字面量 STRING 值请使用单引号 '

错误示例
RETURN "Cypher"
良好
RETURN 'Cypher'
  • 如果字面量 STRING 值本身包含单引号,则不适用此规则。如果 STRING 同时包含两者,请使用转义字符最少的形式。如果转义次数相同,则优先选择单引号。

错误示例
RETURN 'Cypher\'s a nice language', "Mats' quote: \"statement\""
良好
RETURN "Cypher's a nice language", 'Mats\' quote: "statement"'
  • 尽量避免使用需要用反引号包裹输入的字符和关键字。

错误示例
MATCH (`odd-ch@racter$`:`Spaced Label` {`&property`: 42})
RETURN labels(`odd-ch@racter$`)
良好
MATCH (node:NonSpacedLabel {property: 42})
RETURN labels(node)
  • 语句末尾不要使用分号。

错误示例
RETURN 1;
良好
RETURN 1