openCypher ユーザー向けの Spanner Graph リファレンス

このドキュメントでは、openCypher と Spanner Graph を次の方法で比較します。

  • 用語
  • データモデル
  • スキーマ
  • クエリ
  • Mutation

このドキュメントは、openCypher v9 に精通していることを前提としています。

始める前に

Google Cloud コンソールを使用して Spanner Graph を設定しクエリを実行します。

用語

openCypher Spanner Graph
ノード ノード
関係 エッジ
ノードラベル ノードラベル
関係タイプ エッジラベル
Spanner Graph では、実行の完全な単位に statement という用語を使用し、ステートメントの修飾子に clause という用語を使用します。

たとえば、MATCH はステートメントですが、WHERE は句です。
関係の一意性

openCypher は、単一の一致においてエッジが重複する結果を返しません。
TRAIL パス

Spanner Graph で一意のエッジが必要な場合は、 TRAIL モードを使用して、1 つの一致で一意のエッジを返します。

標準への準拠

Spanner Graph は、ISO Graph Query Language(GQL)と SQL/Property Graph Queries(SQL/PGQ)標準を採用しています。

データモデル

Spanner Graph と openCypher はどちらもプロパティ グラフ データモデルを採用していますが、いくつかの違いがあります。

openCypher Spanner Graph
各関係には 1 つの関係タイプがあります。
ノードとエッジの両方に 1 つ以上のラベルがあります。

スキーマ

openCypher Spanner Graph
グラフには定義済みスキーマがありません。 グラフ スキーマは、CREATE PROPERTY GRAPH ステートメントを使用して明示的に定義する必要があります。
ラベルはスキーマで静的に定義されます。ラベルを更新するには、スキーマを更新する必要があります。
詳細については、Spanner Graph スキーマを作成、更新、削除するをご覧ください。

クエリ

Spanner Graph のクエリ機能は openCypher の機能と類似しています。このセクションでは、Spanner Graph と openCypher の違いについて説明します。

グラフを指定する

openCypher には 1 つのデフォルト グラフがあり、クエリはデフォルト グラフに対して実行されます。Spanner Graph では複数のグラフを定義できます。クエリは GRAPH 句で始まり、クエリ対象のグラフを指定する必要があります。次に例を示します。

   GRAPH FinGraph
   MATCH (p:Person)
   RETURN p.name
   ORDER BY p.name
   LIMIT 1;

詳細については、グラフクエリの構文をご覧ください。

グラフパターン マッチング

Spanner Graph は、openCypher と同様のグラフ パターン マッチング機能をサポートしています。違いについては、以降のセクションで説明します。

関係の一意性と TRAIL モード

openCypher は、単一の一致においてエッジが重複する結果を返しません。これは openCypher で「関係の一意性」と呼ばれます。Spanner Graph では、デフォルトで繰り返しエッジが返されます。一意性が必要である場合は、TRAIL モードを使用して、単一の一致に重複するエッジが存在しないようにします。TRAIL と他のパスモードの詳細なセマンティクスについては、パスモードをご覧ください。

次の例は、TRAIL モードでクエリの結果がどのように変化するかを示しています。

  • openCypher と Spanner Graph の TRAIL モードのクエリで想定される唯一のパスは t1 を 2 回繰り返すことであるため、空の結果を返します。
  • デフォルトでは、Spanner Graph クエリは有効なパスを返します。

グラフの例

openCypher Spanner Graph(TRAIL モード) Spanner Graph(デフォルト モード)
MATCH
  (src:Account)-[t1:Transfers]->
  (dst:Account)-[t2:Transfers]->
  (src)-[t1]->(dst)
WHERE src.id = 16
RETURN src.id AS src_id, dst.id AS dst_id;
      
GRAPH FinGraph
MATCH TRAIL
  (src:Account)-[t1:Transfers]->
  (dst:Account)-[t2:Transfers]->
  (src)-[t1]->(dst)
WHERE src.id = 16
RETURN src.id AS src_id, dst.id AS dst_id;
      
GRAPH FinGraph
MATCH
  (src:Account)-[t1:Transfers]->
  (dst:Account)-[t2:Transfers]->
  (src)-[t1]-> (dst)
WHERE src.id = 16
RETURN src.id AS src_id, dst.id AS dst_id;
      
空の結果。 空の結果。 結果:
src_id dst_id
16 20

グラフ要素をクエリ結果として返す

openCypher Spanner Graph
MATCH (account:Account)
WHERE account.id = 16;
RETURN account;
GRAPH FinGraph
MATCH (account:Account)
WHERE account.id = 16;
RETURN TO_JSON(account) AS account;

Spanner Graph では、クエリ結果にグラフ要素は返されません。TO_JSON 関数を使用して、グラフ要素を JSON として返します。

可変長のパターン マッチングとパターン定量化

openCypher の変数長パターン マッチングは、Spanner Graph では「パスの定量化」と呼ばれます。パスの定量化では、次の例に示すように、異なる構文が使用されます。詳細については、定量化されたパスパターンをご覧ください。

openCypher Spanner Graph
MATCH (src:Account)-[:Transfers*1..2]->(dst:Account)
WHERE src.id = 16
RETURN dst.id
ORDER BY dst.id;
     
GRAPH FinGraph
MATCH (src:Account)-[:Transfers]->{1,2}(dst:Account)
WHERE src.id = 16
RETURN dst.id
ORDER BY dst.id;
      

可変長パターン: 要素のリスト

Spanner Graph を使用すると、パスの定量化で使用される変数に直接アクセスできます。次の例では、Spanner Graph の e は openCypher の edges(p) と同じです。

openCypher Spanner Graph
MATCH p=(src:Account)-[:Transfers*1..3]->(dst:Account)
WHERE src.id = 16
RETURN edges(p);
      
GRAPH FinGraph
MATCH (src:Account) -[e:Transfers]->{1,3} (dst:Account)
WHERE src.id = 16
RETURN TO_JSON(e) AS e;
     

最短パス

openCypher には、ノード間の最短パスを見つけるための 2 つの組み込み関数(shortestPathallShortestPath)があります。

  • shortestPath は、ノード間の単一の最短パスを見つけます。
  • allShortestPath は、ノード間のすべての最短パスを見つけます。同じ長さのパスが複数存在する場合があります。

Spanner Graph では、ノード間の単一の最短パスを見つけるために、別の構文(shortestPath.ANY SHORTEST)を使用します。allShortestPath 関数は Spanner Graph ではサポートされていません。

openCypher Spanner Graph
MATCH
  (src:Account {id: 7}),
  (dst:Account {id: 20}),
  p = shortestPath((src)-[*1..10]->(dst))
RETURN length(p) AS path_length;
      
GRAPH FinGraph
MATCH ANY SHORTEST
  (src:Account {id: 7})-[e:Transfers]->{1, 3}
  (dst:Account {id: 20})
RETURN ARRAY_LENGTH(e) AS path_length;
      

ステートメントと句

次の表に、openCypher 句と、Spanner Graph でサポートされているかどうかを示します。

openCypher Spanner Graph
MATCH サポートされています。詳細については、グラフ パターン マッチングをご覧ください。
OPTIONAL MATCH サポートされています。詳細については、グラフ パターン マッチングをご覧ください。
RETURN / WITH サポートされています。詳細については、 RETURN ステートメント WITH ステートメントをご覧ください。
Spanner Graph では、複雑な式に明示的なエイリアシングが必要です。

サポート対象
GRAPH FinGraph
MATCH (p:Person)
RETURN EXTRACT(YEAR FROM p.birthday) AS birthYear;

サポート対象外
GRAPH FinGraph
MATCH (p:Person)
RETURN EXTRACT(YEAR FROM p.birthday); -- No aliasing
WHERE サポートされています。詳細については、 グラフパターンの定義をご覧ください。
ORDER BY サポートされています。詳細については、ORDER BY ステートメント をご覧ください。
SKIP / LIMIT サポートされています。詳細については、 SKIP ステートメント LIMIT ステートメントをご覧ください。

Spanner Graph では、オフセットと上限に定数式が必要です。

サポート対象
GRAPH FinGraph
MATCH (n:Account)
RETURN n.id
SKIP @offsetParameter
LIMIT 3;

サポート対象外
GRAPH FinGraph
MATCH (n:Account)
RETURN n.id
LIMIT VALUE {
  MATCH (m:Person)
  RETURN COUNT(*) AS count
} AS count; -- Not a constant expression
UNION サポートされています。詳細については、複合グラフクエリをご覧ください。
UNION ALL サポートされています。詳細については、複合グラフクエリをご覧ください。
UNWIND FOR ステートメントでサポートされています。
GRAPH FinGraph
LET arr = [1, 2, 3]
FOR num IN arr
RETURN num;
MANDATORY MATCH 非対応。
CALL[YIELD...] 非対応。
CREATE, DELETE, SET, REMOVE, MERGE 詳細については、ミューテーション セクションと Spanner Graph でデータを挿入、更新、削除するをご覧ください。

データ型

Spanner Graph は、すべての GoogleSQL データ型をサポートしています。詳細については、GoogleSQL のデータ型をご覧ください。

以降のセクションでは、openCypher データ型と Spanner Graph データ型を比較します。

構造型

openCypher Spanner Graph
ノード ノード
Edge Edge
パス [Path]

プロパティ型

openCypher Spanner Graph
INT INT64
FLOAT FLOAT64
STRING STRING
BOOLEAN BOOL
LIST
シンプルな型の同種のリスト。
たとえば、INT のリスト、STRING のリストなど。
1 つのリスト内で INTSTRING を混在させることはできません。
ARRAY

複合タイプ

openCypher Spanner Graph
LIST ARRAY または JSON
MAP STRUCT または JSON

Spanner Graph は、異なる型の異種リスト、動的キーリストのマップ、異種要素値型をサポートしていません。このようなユースケースには JSON を使用します。

型の強制変換

openCypher Spanner Graph
INT -> FLOAT サポート対象

型変換ルールの詳細については、GoogleSQL の変換ルールをご覧ください。

関数と式

Spanner Graph は、グラフ関数と式に加えて、GoogleSQL の組み込み関数と式もすべてサポートしています。

このセクションでは、openCypher の関数と式、および Spanner Graph でこれらに対応する関数について説明します。

構造型の関数と式

openCypher
関数または式
Spanner Graph
関数または式

ノードとエッジ
exists(n.prop) PROPERTY_EXISTS(n, prop)
id(整数を返します) サポートされていません。
properties TO_JSON
keys
(プロパティの型名、ただしプロパティの値は除く)
PROPERTY_NAMES
labels LABELS
Edge endNode サポートされていません。
startNode サポートされていません。
type LABELS
パス length サポートされていません。
nodes サポートされていません。
relationships サポートされていません。
ノードとエッジ .
property reference
.
[]
dynamic property reference
MATCH (n)
RETURN n[n.name]

サポートされていません。
式としてのパターン size(pattern) サポートされていません。次のようにサブクエリを使用します。
VALUE {
  MATCH pattern
  RETURN COUNT(*) AS count;
}

プロパティ型の関数と式

openCypher
関数または式
Spanner Graph
関数または式
Scalar coalesce COALESCE
head ARRAY_FIRST
last ARRAY_LAST
size(list) ARRAY_LENGTH
size(string) LENGTH
timestamp UNIX_MILLIS(CURRENT_TIMESTAMP())
toBoolean/toFloat/toInteger CAST(expr AS type)
集計 avg AVG
collect ARRAY_AGG
count COUNT
max MAX
min MIN
percentileCont PERCENTILE_CONT
percentileDisc PERCENTILE_DISC
stDev STDDEV
stDevP サポートされていません。
sum SUM
リスト range GENERATE_ARRAY
reverse ARRAY_REVERSE
tail Spanner Graph は tail をサポートしていません。
代わりに ARRAY_SLICEARRAY_LENGTH を使用してください。
数学関数 abs ABS
ceil CEIL
floor FLOOR
rand RAND
round ROUND
sign SIGN
e EXP(1)
exp EXP
log LOG
log10 LOG10
sqrt SQRT
acos ACOS
asin ASIN
atan ATAN
atan2 ATAN2
cos COS
cot COT
degrees r * 90 / ASIN(1)
pi ACOS(-1)
radians d * ASIN(1) / 90
sin SIN
tan TAN
文字列 left LEFT
ltrim LTRIM
replace REPLACE
reverse REVERSE
right RIGHT
rtrim RTRIM
split SPLIT
substring SUBSTR
tolower LOWER
tostring CAST(expr AS STRING)
toupper UPPER
trim TRIM
DISTINCT DISTINCT DISTINCT
数学関数 + +
- -
* *
/ /
% MOD
^ POW
比較 = =
<> <>
< <
> >
<= <=
>= >=
IS [NOT] NULL IS [NOT] NULL
比較の連鎖
a < b < c

Spanner Graph は比較のチェーンをサポートしていません。これは、AND で結合された比較と同じです。
次に例を示します。

      a < b AND b < C
      

ブール値 AND AND
OR OR
XOR
Spanner Graph は XOR をサポートしていません。<> を使用してクエリを記述します。

次に例を示します。
      boolean_1 <> boolean_2
      

NOT NOT
文字列 STARTS WITH STARTS_WITH
ENDS WITH ENDS_WITH
CONTAINS REGEXP_CONTAINS
+ CONCAT
リスト + ARRAY_CONCAT
IN ARRAY_INCLUDES
[] []

その他の式

openCypher Spanner Graph
CASE 式 サポート対象
EXISTS サブクエリ サポート対象
マップ投影 サポートされていません。
STRUCT 型は同様の機能を提供します。
リスト内包表記 サポートされていません。
GENERATE_ARRAYARRAY_TRANSFORM は、ほとんどのユースケースに対応しています。

クエリ パラメータ

次のクエリは、openCypher と Spanner Graph でのパラメータの使用方法の違いを示しています。

openCypher Spanner Graph
パラメータ
MATCH (n:Person)
WHERE n.id = $id
RETURN n.name;
GRAPH FinGraph
MATCH (n:Person)
WHERE n.id = @id
RETURN n.name;

Mutation

Spanner Graph は GoogleSQL DML を使用して、ノードとエッジの入力テーブルを変更します。詳細については、Spanner Graph データを挿入、更新、削除するをご覧ください。

ノードとエッジを作成する

openCypher Spanner Graph
ノードとエッジを作成する
CREATE (:Person {id: 100, name: 'John'});
CREATE (:Account {id: 1000, is_blocked: FALSE});

MATCH (p:Person {id: 100}), (a:Account {id: 1000}) CREATE (p)-[:Owns {create_time: timestamp()}]->(a);
INSERT INTO
Person (id, name)
VALUES (100, "John");

INSERT INTO Account (id, is_blocked) VALUES (1000, FALSE);
INSERT INTO PersonOwnAccount (id, account_id, create_time) VALUES (100, 1000, CURRENT_TIMESTAMP());
クエリ結果を使用してノードとエッジを作成する
MATCH (a:Account {id: 1}), (oa:Account)
WHERE oa <> a
CREATE (a)-[:Transfers {amount: 100, create_time: timestamp()}]->(oa);
INSERT INTO AccountTransferAccount(id, to_id, create_time, amount)
SELECT a.id, oa.id, CURRENT_TIMESTAMP(), 100
FROM GRAPH_TABLE(
  FinGraph
  MATCH
    (a:Account {id:1000}),
    (oa:Account)
  WHERE oa <> a
);

Spanner Graph では、ラベルは CREATE PROPERTY GRAPH DDL ステートメントに従って静的に割り当てられます。

ノードとエッジを更新する

openCypher Spanner Graph
プロパティを更新する
MATCH (p:Person {id: 100})
SET p.country = 'United States';
UPDATE Person AS p
SET p.country = 'United States'
WHERE p.id = 100;

Spanner Graph ラベルを更新するには、Spanner Graph スキーマを作成、更新、削除するをご覧ください。

ノードとエッジを結合する

openCypher Spanner Graph
新しい要素を挿入する、またはプロパティを更新する
MERGE (p:Person {id: 100, country: 'United States'});
INSERT OR UPDATE INTO Person
(id, country)
VALUES (100, 'United States');

ノードとエッジを削除する

エッジの削除は、入力テーブルの削除と同じです。

openCypher Spanner Graph
ノードとエッジを削除する
MATCH (p:Person {id:100}), (a:Account {id:1000})
DELETE (p)-[:Owns]->(a);
DELETE PersonOwnAccount
WHERE id = 100 AND account_id = 1000;

ノードを削除するには、ダングリング エッジの可能性を処理する必要があります。DELETE CASCADE が指定されている場合、DELETE は openCypher の DETACH DELETE などのノードに関連付けられたエッジを削除します。詳細については、Spanner のスキーマの概要をご覧ください。

openCypher Spanner Graph
ノードと関連するエッジを削除する
DETACH DELETE (:Account {id: 1000});
DELETE Account
WHERE id = 1000;

ミューテーションの結果を返す

openCypher Spanner Graph
挿入または更新後に結果を返す
MATCH (p:Person {id: 100})
SET p.country = 'United States'
RETURN p.id, p.name;
UPDATE Person AS p
SET p.country = 'United States'
WHERE p.id = 100
THEN RETURN id, name;
削除後に結果を返す
DELETE (p:Person {id: 100})
RETURN p.country;
DELETE FROM Person
WHERE id = 100
THEN RETURN country;

次のステップ