Présentation des requêtes Spanner Graph

<ph type="x-smartling-placeholder">

Ce document explique comment interroger des graphiques de propriétés dans Spanner Graph. Les exemples de cette section utilisent le schéma de graphique que vous créez dans la section Configurer et interroger Spanner Graph, illustré dans le diagramme suivant :

Exemple de schéma Spanner Graph.

Exécuter une requête de graphique Spanner

Vous pouvez exécuter des requêtes de graphe Spanner de différentes manières :

Structure des requêtes du graphique Spanner

Cette section décrit chaque composant de la requête en détail.

L'exemple suivant illustre la structure de base d'une requête de graphique Spanner.

Exemple de structure de requête de graphe Spanner

Spanner Graph vous permet de créer plusieurs graphiques dans une base de données. La requête commence par spécifier le graphique cible, FinGraph, en utilisant la clause GRAPH.

Mise en correspondance de modèles de graphique

La mise en correspondance de modèles de graphique permet de trouver des modèles spécifiques dans votre graphique. Les modèles les plus élémentaires sont les modèles d'éléments (modèles de nœuds et de bords), qui correspondent aux éléments de graphique (nœuds et bords, respectivement). Les modèles d'éléments peuvent être composés des modèles de chemin et des modèles plus complexes.

Modèles de nœuds

Un modèle de nœud est un modèle qui correspond aux nœuds de votre graphique. Ce modèle comprend une paire de parenthèses correspondante, qui peut éventuellement contenir une variable de modèle de graphique, une expression de libellé et des filtres de propriété.

Rechercher tous les nœuds

La requête suivante renvoie tous les nœuds du graphique. La variable n, appelée Une variable de modèle de graphique se lie aux nœuds correspondants. Dans ce cas, le modèle de nœud correspond à tous les nœuds du graphique.

GRAPH FinGraph
MATCH (n)
RETURN LABELS(n) AS label, n.id;

Résultat

La requête renvoie label et id comme suit :

étiquette id
Account 7
Account 16
Account 20
Personne 1
Personne 2
Personne 3

Rechercher tous les nœuds avec un libellé spécifique

La requête suivante correspond à tous les nœuds du graphique qui ont le libellé Person. La requête renvoie les propriétés label et id, name des nœuds correspondants.

GRAPH FinGraph
MATCH (p:Person)
RETURN LABELS(p) AS label, p.id, p.name;

Résultat

étiquette id nom
Personne 1 Alex
Personne 2 Dana
Personne 3 Lee

Rechercher tous les nœuds correspondant à une expression de libellé

Vous pouvez créer une expression de libellé avec un ou plusieurs opérateurs logiques.

La requête suivante correspond à tous les nœuds du graphique qui portent le libellé Person ou Account. L'ensemble des propriétés exposées par la variable de modèle de graphique n est le sur-ensemble des propriétés exposées par les nœuds portant le libellé Person ou Account.

GRAPH FinGraph
MATCH (n:Person|Account)
RETURN LABELS(n) AS label, n.id, n.birthday, n.create_time;
  • Dans les résultats, tous les nœuds ont la propriété id.
  • Les nœuds correspondant à l'étiquette Account ont la propriété create_time, mais pas avec la propriété birthday. Un NULL est renvoyé pour la propriété birthday pour ces nœuds.
  • Les nœuds correspondant au libellé Person possèdent la propriété birthday, mais pas la propriété create_time. Un NULL est renvoyé pour la propriété create_time pour ces nœuds.

Résultat

étiquette id jour de naissance create_time
Account 7 NULL 2020-01-10T14:22:20.222Z
Account 16 NULL 2020-01-28T01:55:09.206Z
Account 20 NULL 2020-02-18T13:44:20.655Z
Personne 1 1991-12-21T08:00:00Z NULL
Personne 2 1980-10-31T08:00:00Z NULL
Personne 3 1986-12-07T08:00:00Z NULL

Pour en savoir plus sur les règles d'expression des libellés, consultez la section Expression de libellé.

Rechercher tous les nœuds correspondant à l'expression d'étiquette et au filtre de propriété

La requête suivante correspond à tous les nœuds du graphique portant le libellé Person et pour lesquels la propriété id est égale à 1.

GRAPH FinGraph
MATCH (p:Person {id: 1})
RETURN LABELS(p) AS label, p.id, p.name, p.birthday;

Résultat

étiquette id nom jour de naissance
Personne 1 Alex 1991-12-21T08:00:00Z

Vous pouvez utiliser la clause WHERE pour créer des conditions de filtrage plus complexes sur des libellés et des propriétés.

La requête suivante correspond à tous les nœuds du graphique ayant le Person et la propriété birthday est antérieure à 1990-01-10.

GRAPH FinGraph
MATCH (p:Person WHERE p.birthday < '1990-01-10')
RETURN LABELS(p) AS label, p.name, p.birthday;

Résultat

étiquette nom jour de naissance
Personne Dana 1980-10-31T08:00:00Z
Personne Lee 1986-12-07T08:00:00Z

Modèles de bord

Un modèle de arête correspond aux arêtes ou aux relations entre les nœuds. Les motifs d'arêtes sont placés entre crochets [] avec les symboles -, -> ou <- pour indiquer les directions.

Comme pour les modèles de nœuds, les variables de modèle de graphique sont utilisées pour lier les éléments de bord correspondants.

Rechercher toutes les arêtes correspondant aux libellés correspondants

La requête suivante renvoie tous les arcs du graphique portant le libellé Owns. La variable de modèle de graphique e est liée aux arêtes correspondantes.

GRAPH FinGraph
MATCH -[e:Owns]->
RETURN e.id AS owner_id, e.account_id;

Résultat

owner_id Identifiant du compte
1 7
3 16
2 20

Rechercher toutes les arêtes correspondant à l'expression d'étiquette et au filtre de propriété

À l'instar d'un modèle de nœud, un modèle de périphérie peut utiliser les expressions de type "étiquette", la spécification des propriétés et les clauses WHERE, comme indiqué dans les la requête suivante. La requête trouve toutes les arêtes étiquetées Owns et comporte la la propriété create_time au cours d'une période spécifiée.

GRAPH FinGraph
MATCH -[e:Owns WHERE e.create_time > '2020-01-14'
                 AND e.create_time < '2020-05-14']->
RETURN e.id AS owner_id, e.create_time, e.account_id;

Résultat

owner_id create_time Identifiant du compte
2 2020-01-28T01:55:09.206Z 20
3 2020-02-18T13:44:20.655Z 16

Trouver toutes les arêtes à l'aide de n'importe quel modèle d'arête de direction

Bien que tous les arcs du graphique Spanner soient orientés, vous pouvez utiliser le modèle d'arc any direction -[]- dans une requête pour faire correspondre les arcs dans les deux sens.

La requête suivante recherche tous les transferts impliquant un compte bloqué.

GRAPH FinGraph
MATCH (account:Account)-[transfer:Transfers]-(:Account)
WHERE account.is_blocked
RETURN transfer.order_number, transfer.amount;

Résultat

order_number amount
304330008004315 300
304120005529714 100
103650009791820 300
302290001255747 200

Formats de chemin

Un modèle de chemin d'accès est créé à partir d'un alternance de modèles de nœud et de périphérie.

Rechercher tous les chemins d'un nœud avec des filtres de libellé et de propriété spécifiés, à l'aide d'un modèle de chemin

La requête suivante recherche tous les transferts vers un compte initiés à partir d'un compte appartenant à Person avec id égale à 2.

Chaque résultat correspondant représente un chemin d'Person {id: 2} via un Account connecté à l'aide de l'arête Owns, vers un autre Account à l'aide de l'arête Transfers.

GRAPH FinGraph
MATCH
  (p:Person {id: 2})-[:Owns]->(account:Account)-[t:Transfers]->
  (to_account:Account)
RETURN
  p.id AS sender_id, account.id AS from_id, to_account.id AS to_id;

Résultat

sender_id from_id to_id
2 20 7
2 20 16

Modèles de tracé quantifiés

Un modèle quantifié permet de répéter un modèle dans une plage spécifiée.

Correspondre à un schéma de bord quantifié

La requête suivante recherche tous les comptes de destination un à trois transferts depuis une source Accountid est égal à 7, sauf lui-même.

Modèle de bordure postfixé avec le quantificateur {1, 3}.

GRAPH FinGraph
MATCH (src:Account {id: 7})-[e:Transfers]->{1, 3}(dst:Account)
WHERE src != dst
RETURN src.id AS src_account_id, ARRAY_LENGTH(e) AS path_length, dst.id AS dst_account_id;

Résultat

src_account_id path_length dst_account_id
7 1 16
7 1 16
7 1 16
7 3 16
7 3 16
7 2 20
7 2 20

L'exemple précédent utilise la fonction ARRAY_LENGTH pour accéder à la e group variable. Pour en savoir plus, consultez la section Variable de groupe d'accès.

Certaines lignes des exemples de résultats sont répétées, car il peut y avoir plusieurs chemins entre la même paire de comptes src et dst correspondant au format.

Correspondre à un format de chemin d'accès quantifié

La requête suivante recherche les chemins entre Account nœuds avec un à deux nœuds Transfers passe par des comptes intermédiaires bloqués.

Le modèle de chemin d'accès entre parenthèses est quantifié et la clause WHERE est utilisée dans la parenthèse pour spécifier les conditions du modèle répété.

GRAPH FinGraph
MATCH
  (src:Account)
  ((:Account)-[:Transfers]->(interm:Account) WHERE interm.is_blocked){1,2}
    -[:Transfers]->(dst:Account)
RETURN src.id AS src_account_id, dst.id AS dst_account_id;

Résultat

src_account_id dst_account_id
7 20
7 20
20 20

Variables de groupe

Une variable de modèle de graphique déclarée dans un modèle quantifié est considérée comme une variable de groupe lorsqu'il est accessible en dehors du modèle quantifié, et se lie à un tableau de les éléments de graphique correspondants.

Vous pouvez accéder à une variable de groupe en tant que tableau dans lequel les éléments du graphique sont conservés dans l'ordre d'apparition le long des chemins correspondants. Vous pouvez agréger une variable de groupe à l'aide de l'agrégation horizontale.

Variable de groupe d'accès

Dans l'exemple suivant, l'accès à la variable e est le suivant:

  • Variable de modèle de graphique liée à un seul arc dans la clause e.amount > 100 WHERE (dans le modèle quantifié).
  • Variable de groupe liée à un tableau d'éléments de bord dans ARRAY_LENGTH(e) dans l'instruction RETURN (en dehors du modèle quantifié).
  • Variable de groupe liée à un tableau d'éléments de bord, qui est agrégée par SUM(e.amount) en dehors du modèle quantifié. Dans cet exemple, agrégation horizontale.
GRAPH FinGraph
MATCH
  (src:Account {id: 7})-[e:Transfers WHERE e.amount > 100]->{0,2}
  (dst:Account)
WHERE src.id != dst.id
LET total_amount = SUM(e.amount)
RETURN
  src.id AS src_account_id, ARRAY_LENGTH(e) AS path_length,
  total_amount, dst.id AS dst_account_id;

Résultat

src_account_id path_length total_amount dst_account_id
7 1 300 16
7 2 600 20

"Tout" et "Touts les chemins les plus courts"

Pour limiter les chemins correspondants dans chaque groupe de chemins partageant la même source de destination, vous pouvez utiliser le préfixe de recherche du chemin ANY ou ANY SHORTEST. Vous ne pouvez appliquer ces préfixes qu'avant un modèle de chemin d'accès complet et non entre parenthèses.

Établir une correspondance à l'aide de N'IMPORTE LAQUELLE

La requête suivante recherche tous les comptes uniques accessibles correspondant à un ou deux À Transfers d'un nœud Account donné.

Le préfixe de recherche de chemin ANY garantit qu'un seul chemin entre une paire unique de nœuds Account src et dst est renvoyé. Dans l'exemple suivant, bien que vous puissiez atteindre le nœud Account avec {id: 16} dans deux chemins à partir du nœud source Account, les résultats n'incluent qu'un seul chemin d'accès.

GRAPH FinGraph
MATCH ANY (src:Account {id: 7})-[e:Transfers]->{1,2}(dst:Account)
LET ids_in_path = ARRAY(SELECT e.to_id FROM UNNEST(e) AS e)
RETURN src.id AS src_account_id, dst.id AS dst_account_id, ids_in_path;

Résultat

src_account_id dst_account_id ids_in_path
7 16 16
7 20 16,20

Modèles de graphiques

Un modèle de graphique se compose d'un ou de plusieurs modèles de chemin, séparés par une virgule ,. Les modèles de graphique peuvent contenir une clause WHERE, qui vous permet d'accéder à toutes les des variables de motifs graphiques dans les modèles de chemin pour créer des conditions de filtrage. Chaque modèle de chemin génère une collection de chemins.

Correspondre à l'aide d'un modèle de graphique

La requête suivante identifie les comptes intermédiaires et leurs propriétaires concernés de transactions d'un montant supérieur à 200, via lesquelles les fonds sont transférés depuis un compte source vers un compte bloqué.

Les formats de chemin suivants constituent le modèle de graphique :

  • Le premier modèle trouve les chemins d'accès vers un compte bloqué en utilisant un compte intermédiaire.
  • Le second modèle trouve les chemins d'accès d'un compte à son propriétaire.

La variable interm sert de lien commun entre les deux modèles de chemin, ce qui nécessite que interm fasse référence au même nœud d'élément dans les deux modèles de chemin. Cela crée une opération d'équivalence en fonction de la variable interm.

GRAPH FinGraph
MATCH
  (src:Account)-[t1:Transfers]->(interm:Account)-[t2:Transfers]->(dst:Account),
  (interm)<-[:Owns]-(p:Person)
WHERE dst.is_blocked = TRUE AND t1.amount > 200 AND t2.amount > 200
RETURN
  src.id AS src_account_id, dst.id AS dst_account_id,
  interm.id AS interm_account_id, p.id AS owner_id;

Résultat

src_account_id dst_account_id interm_account_id owner_id
20 16 7 1

Instructions de requête linéaire

Vous pouvez associer plusieurs instructions de graphique pour former une instruction de requête linéaire. Les instructions sont exécutées dans l'ordre dans lequel elles apparaissent dans la requête.

  • Chaque instruction prend en entrée la sortie de l'instruction précédente. La l'entrée est vide pour la première instruction.
  • Le résultat de la dernière instruction est le résultat final.

Identifier le nombre maximal de transferts vers un compte bloqué

La requête suivante permet de trouver le compte et son propriétaire ayant généré le plus grand vers un compte bloqué.

GRAPH FinGraph
MATCH (src_account:Account)-[transfer:Transfers]->(dst_account:Account)
WHERE dst_account.is_blocked
ORDER BY transfer.amount DESC
LIMIT 1
MATCH (src_account:Account)<-[owns:Owns]-(owner:Person)
RETURN src_account.id AS account_id, owner.name AS owner_name;

Le tableau suivant montre comment les résultats intermédiaires sont transmis. les déclarations. Par souci de concision, seules certaines propriétés des résultats intermédiaires sont affichées.

Propos Résultat intermédiaire (abrégé)
MATCH
  (src_account:Account)
    -[transfer:Transfers]->
  (dst_account:Account)
WHERE dst_account.is_blocked
src_account transfert dst_account
{id: 7} {amount: 300.0} {id: 16, is_blocked: true}
{id: 7} {amount: 100.0} {id: 16, is_blocked: true}
{id: 20} {amount: 200.0} {id: 16, is_blocked: true}

ORDER BY transfer.amount DESC
src_account transfert dst_account
{id: 7} {amount: 300.0} {id: 16, is_blocked: true}
{id: 20} {amount: 200.0} {id: 16, is_blocked: true}
{id: 7} {amount: 100.0} {id: 16, is_blocked: true}

LIMIT 1
src_account transfert dst_account
{id: 7} {amount: 300.0} {id: 16, is_blocked: true}

MATCH
  (src_account:Account)
    <-[owns:Owns]-
  (owner:Person)
src_account transfert dst_account possède Propriétaire
{id: 7} {amount: 300.0} {id: 16, is_blocked: true} {person_id: 1, account_id: 7} {id: 1, name: Alex}

RETURN
  src_account.id AS account_id,
  owner.name AS owner_name
account_id owner_name
7 Alex

Résultat

Identifiant du compte owner_name
7 Alex

Relevé de renvoi

L'instruction de retour définit ce qui doit être renvoyé à partir des modèles correspondants. Il peut accéder aux variables de modèle de graphique, contenir des expressions et d'autres clauses telles que ORDER_BY et GROUP_BY. Consultez l'instruction RETURN.

Notez que Spanner Graph ne permet pas de renvoyer des éléments de graphique en tant que résultats de requête. Pour renvoyer l'élément graphique complet, utilisez la fonction TO_JSON.

Renvoyer les éléments du graphique au format JSON

GRAPH FinGraph
MATCH (n:Account {id: 7})
-- Returning a graph element in the final results is NOT allowed. Instead, use
-- the TO_JSON function or explicitly return the graph element's properties.
RETURN TO_JSON(n) AS n;

Résultat

n
{&quot;identifier&quot;:&quot;mUZpbkdyYXBoLkFjY291bnQAeJEO&quot;,&quot;kind&quot;:&quot;node&quot;,&quot;labels&quot;:[&quot;Account&quot;],&quot;properties&quot;:{&quot;create_time&quot;:&quot;2020-01-10T14:22:20.222Z&quot;,&quot;id&quot;:7,&quot;is_blocked&quot;:false,&quot;nick_name&quot;:&quot;Vacation Fonds"}}

Composition de requêtes plus larges à l'aide du mot clé NEXT

Vous pouvez lier plusieurs instructions de requête linéaire de graphique à l'aide du mot clé NEXT. L'entrée de la première instruction de requête linéaire est vide. Le résultat de chaque commande l'instruction de requête linéaire devient l'entrée de l'instruction de requête linéaire suivante.

L'exemple suivant permet de trouver le propriétaire du compte ayant le plus de transferts entrants en enchaînant plusieurs instructions linéaires de graphique. Notez que vous pouvez utiliser la même variable, account dans cet exemple, pour faire référence au même élément de graphique dans plusieurs instructions linéaires.

GRAPH FinGraph
MATCH (:Account)-[:Transfers]->(account:Account)
RETURN account, COUNT(*) AS num_incoming_transfers
GROUP BY account
ORDER BY num_incoming_transfers DESC
LIMIT 1

NEXT

MATCH (account:Account)<-[:Owns]-(owner:Person)
RETURN account.id AS account_id, owner.name AS owner_name, num_incoming_transfers;

Résultat

Identifiant du compte owner_name num_incoming_transfers
16 Lee 3

Fonctions et expressions

Vous pouvez utiliser l'ensemble des fonctions, opérateurs et conditions dans GoogleSQL, y compris des fonctions d'agrégation et d'autres fonctions scalaires dans une requête de graphique Spanner.

Spanner Graph est également compatible avec les fonctions et opérateurs intégrés pour les éléments de graphe.

Fonctions et opérateurs intégrés

Les fonctions et les opérateurs suivants sont couramment utilisés dans GQL :

  • PROPERTY_EXISTS(n, birthday) : indique si n expose la propriété birthday.
  • LABELS(n) : renvoie les libellés de n tels que définis dans le schéma du graphique.
  • PROPERTY_NAMES(n) : renvoie les noms de propriété de n.
  • TO_JSON(n): renvoie n au format JSON. Pour en savoir plus, consultez les Fonction TO_JSON.

La requête suivante illustre le prédicat PROPERTY_EXISTS, la fonction LABELS et TO_JSON, ainsi que d'autres fonctions intégrées comme ARRAY_AGG et CONCAT

GRAPH FinGraph
MATCH (person:Person)-[:Owns]->(account:Account)
RETURN person, ARRAY_AGG(account.nick_name) AS accounts
GROUP BY person

NEXT

RETURN
  LABELS(person) AS labels,
  TO_JSON(person) AS person,
  accounts,
  CONCAT(person.city, ", ", person.country) AS location,
  PROPERTY_EXISTS(person, is_blocked) AS is_blocked_property_exists,
  PROPERTY_EXISTS(person, name) AS name_property_exists
LIMIT 1;

Résultat

is_blocked_property_exists name_property_exists labels comptes emplacement Personne
faux vrai Personne ["Vacation Fund"] Adélaïde, Australie {&quot;identifier&quot;:&quot;mUZpbkdyYXBoLlBlcnNvbgB4kQI=&quot;,&quot;kind&quot;:&quot;node&quot;,&quot;labels&quot;:[&quot;Person&quot;],&quot;properties&quot;:{&quot;birthday&quot;:&quot;1991-12-21T08:00:00Z&quot;,&quot;city&quot;:&quot;Adelaide&quot;,&quot;country&quot;:&quot;Australia&quot;,&quot;id&quot;:1,&quot;name&quot;:&quot;Alex&quot;}}

Sous-requêtes

Une sous-requête est une requête imbriquée dans une autre requête. La liste suivante présente les règles de sous-requête de Spanner Graph :

  • Une sous-requête est placée entre accolades {}.
  • Une sous-requête peut commencer par la clause GRAPH initiale pour spécifier le graphique. Il n'est pas nécessaire que le graphique spécifié soit identique à celui utilisé dans la requête externe.
  • Lorsque la clause GRAPH est omise dans la sous-requête, voici ce qui se passe :
    • Le graphique en champ d'application est inféré à partir du contexte de requête externe le plus proche.
    • La sous-requête doit commencer par une instruction de mise en correspondance de modèle de graphique avec MATCH..
  • Une variable de modèle de graphique déclarée en dehors du champ d'application de la sous-requête ne peut pas être déclaré à nouveau dans la sous-requête, mais il est possible de s'y référer dans expressions ou fonctions à l'intérieur de la sous-requête.

Utiliser une sous-requête pour trouver le nombre total de transferts effectués depuis chaque compte

La requête suivante illustre l'utilisation de la sous-requête VALUE. La sous-requête est entre accolades {} et précédée du mot clé VALUE. La requête renvoie le total le nombre de transferts effectués à partir d'un compte.

GRAPH FinGraph
MATCH (p:Person)-[:Owns]->(account:Account)
RETURN p.name, account.id AS account_id, VALUE {
  MATCH (a:Account)-[transfer:Transfers]->(:Account)
  WHERE a = account
  RETURN SUM(transfer.amount) AS total_transfer
} AS total_transfer;

Résultat

nom Identifiant du compte total_transfer
Alex 7 400
Dana 20 700
Lee 16 300

Pour obtenir la liste des expressions de sous-requêtes acceptées, consultez Sous-requêtes du graphique Spanner.

Paramètres de requête

Vous pouvez interroger le graphique Spanner avec des paramètres. Pour en savoir plus, consultez les syntaxe et apprendrez à Interroger des données avec des paramètres dans les bibliothèques clientes Spanner.

La requête suivante illustre l'utilisation des paramètres de requête.

GRAPH FinGraph
MATCH (person:Person {id: @id})
RETURN person.name;

Interroger les graphiques et les tableaux ensemble

Vous pouvez utiliser des requêtes Graph conjointement avec SQL pour accéder aux informations de vos graphiques et tableaux dans une seule instruction.

GRAPH_TABLE

L'opérateur GRAPH_TABLE prend une requête de graphe linéaire et renvoie son résultat dans un formulaire tabulaire qui peut être intégré de manière transparente dans une requête SQL. Ce vous permet d'enrichir les résultats des requêtes basées sur un graphique avec du contenu autre que celui-ci l'inverse.

Par exemple, vous pouvez créer une table CreditReports et insérer quelques crédits , comme illustré dans l'exemple suivant:

CREATE TABLE CreditReports (
  person_id     INT64 NOT NULL,
  create_time   TIMESTAMP NOT NULL,
  score         INT64 NOT NULL,
) PRIMARY KEY (person_id, create_time);
INSERT INTO CreditReports (person_id, create_time, score)
VALUES
  (1,"2020-01-10 06:22:20.222", 700),
  (2,"2020-02-10 06:22:20.222", 800),
  (3,"2020-03-10 06:22:20.222", 750);

Ensuite, identifiez les personnes d'intérêt grâce à la correspondance de modèles de graphique dans GRAPH_TABLE. et joindre les résultats de la requête graphique à la table CreditReports pour accéder au crédit le score.

SELECT
  gt.person.id,
  credit.score AS latest_credit_score
FROM GRAPH_TABLE(
  FinGraph
  MATCH (person:Person)-[:Owns]->(:Account)-[:Transfers]->(account:Account)
  WHERE account.is_blocked
  RETURN DISTINCT person
) AS gt
JOIN CreditReports AS credit
  ON gt.person.id = credit.person_id
ORDER BY credit.create_time;

Résultat:

person_id latest_credit_score
1 700
2 800

Étape suivante

Découvrez les bonnes pratiques pour optimiser les requêtes.