Cómo solucionar problemas de Spanner Graph

En este documento, se describen los errores que puedes encontrar cuando trabajas con Spanner Graph. También se proporcionan ejemplos de errores y correcciones recomendadas.

Si necesitas más asistencia después de revisar esta guía de solución de problemas, consulta Obtén asistencia.

Errores de esquema

Los resultados del esquema se basan en el conjunto de datos que se usó en Cómo configurar y consultar Spanner Graph.

Las claves de elementos deben tener una garantía de unicidad

Mensaje de error

Neither the primary keys nor any unique index defined on the property graph element source table `Person` provides the uniqueness guarantee for graph element `Person` belonging to the graph `FinGraph`. You want to redefine the element key columns (`name`) based on the source table's primary keys, or create a unique index on the element's key columns.

Ejemplo de error

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person KEY (name)
  );

Crea un índice único en las columnas de clave de elemento y redefine las columnas de clave de elemento según las claves primarias de la tabla de origen.

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person KEY (id)
  );

Como alternativa, crea un índice único en las columnas de clave de elementos.

CREATE UNIQUE INDEX PersonNameIndex ON Person(name);
CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person KEY (name)
  );

Los nombres de las definiciones de elementos deben ser únicos

Mensaje de error

Account is defined more than once; use a unique name.

Ejemplo de error

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Account,
    Person
  )
  EDGE TABLES (
    Account
      SOURCE KEY(owner_id) REFERENCES Person
      DESTINATION KEY(account_id) REFERENCES Account
  );

Usa un nombre único para la definición de borde.

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Account,
    Person
  )
  EDGE TABLES (
    Account AS Owns
      SOURCE KEY(owner_id) REFERENCES Person
      DESTINATION KEY(account_id) REFERENCES Account
  );

La definición de las etiquetas debe ser coherente para las propiedades

Mensaje de error

The label Entity is defined with different property declarations. There is one instance of this label defined with properties of [id]. Another instance is defined with properties of [name].

Ejemplo de error

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person LABEL Entity PROPERTIES (name),
    Account LABEL Entity PROPERTIES (id)
  );

Debes usar el mismo conjunto de nombres de propiedades en la misma etiqueta.

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person LABEL Entity PROPERTIES (id, name),
    Account LABEL Entity PROPERTIES (id, name)
  );

La declaración de la propiedad debe ser coherente con el tipo de propiedad

Mensaje de error

The property declaration of name has type conflicts. There is an existing declaration of type INT64. There is a conflicting one of type STRING.

Ejemplo de error

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person PROPERTIES (name),
    Account PROPERTIES (id AS name)
  );
CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person PROPERTIES (name),
    Account PROPERTIES (CAST(id AS STRING) AS name)
  );

La definición de la propiedad no debe ser una subconsulta.

Mensaje de error

Property value expression of count cannot contain a subquery.

Ejemplo de error

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person PROPERTIES ((SELECT COUNT(*) FROM Person) AS count)
  );

N/A. Esta condición no se permite.

La definición de la propiedad debe ser coherente dentro de la misma definición de elemento.

Mensaje de error

Property location has more than one definition in the element table Person

Ejemplo de error

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person
      LABEL Person PROPERTIES (country AS location)
      LABEL Entity PROPERTIES (city AS location)
  );

Usa la misma definición de propiedad.

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person
      LABEL Person PROPERTIES (country AS location)
      LABEL Entity PROPERTIES (country AS location)
  );

Como alternativa, asigna nombres de propiedades diferentes.

CREATE OR REPLACE PROPERTY GRAPH FinGraph
  NODE TABLES (
    Person
      LABEL Person PROPERTIES (country AS location)
      LABEL Entity PROPERTIES (city AS city)
  );

Errores de consulta

Los resultados de las consultas se basan en el conjunto de datos que se usa en Configurar y consultar Spanner Graph.

Los elementos del grafo no se pueden mostrar como resultados de la consulta

Mensaje de error

Returning expressions of type GRAPH_ELEMENT is not allowed

Ejemplo de error

GRAPH FinGraph
MATCH (n:Account)
RETURN n;
GRAPH FinGraph
MATCH (n:Account)
RETURN TO_JSON(n) AS n;

La especificación de propiedades no se puede usar con la cláusula WHERE.

Mensaje de error

WHERE clause cannot be used together with property specification

Ejemplo de error

GRAPH FinGraph
MATCH (n:Account {id: 1} WHERE n.is_blocked)
RETURN n.id;

Puedes usar una de las siguientes correcciones sugeridas.

GRAPH FinGraph
MATCH (n:Account {id: 1})
WHERE n.is_blocked
RETURN n.id;
GRAPH FinGraph
MATCH (n:Account WHERE n.id = 1 AND n.is_blocked )
RETURN n.id;
GRAPH FinGraph
MATCH (n:Account {id: 1, is_blocked: TRUE})
RETURN n.id;

No se permite la referencia a variables definidas en sentencias anteriores.

Mensaje de error

Name 'account_id', defined in the previous statement, can only be referenced in the outermost WHERE clause of MATCH

Descripción

No se permite la referencia a variables definidas en sentencias anteriores dentro del patrón MATCH. En la consulta de grafo, los nombres definidos por las instrucciones anteriores solo se pueden usar en la cláusula WHERE más externa de MATCH.

Ejemplo de error
GRAPH FinGraph
LET account_id = 1
MATCH (n:Account {id: account_id})
RETURN n.id;
GRAPH FinGraph
LET account_id = 1
MATCH (n:Account)
WHERE n.id = account_id
RETURN n.id;

No se permite redefinir una variable de gráfico correlacionada.

Mensaje de error

The name account is already defined; redefining graph element variables in a subquery is not allowed. To refer to the same graph element, use a different name and add an explicit filter that checks for equality.

Descripción

En la consulta de gráfico, los nombres de los elementos del gráfico no se pueden redefinir en una subconsulta de gráfico interno. Esta situación se puede interpretar como una referencia al mismo elemento del grafo que el alcance externo o como una vinculación a elementos de grafo nuevos, que oculta el nombre del alcance externo. No se permite la redefinición.

Ejemplo de error

GRAPH FinGraph
MATCH (account:Account)
RETURN account.id AS account_id, VALUE {
  MATCH (account:Account)-[transfer:Transfers]->(:Account)
  RETURN SUM(transfer.amount) AS total_transfer
} AS total_transfer;
GRAPH FinGraph
MATCH (account:Account)
RETURN 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;

Problemas de semántica de consultas

Los resultados de las consultas se basan en el conjunto de datos que se usa en Configurar y consultar Spanner Graph.

Diferentes WHERE y FILTER generan resultados diferentes

Descripción

FILTER es una sentencia; WHERE es una cláusula, como parte de las sentencias MATCH y OPTIONAL MATCH.

En el primer ejemplo, la cláusula WHERE agrega restricciones adicionales a los patrones descritos en la sentencia OPTIONAL MATCH. No es un filtro después de que se completa la coincidencia.

En el segundo ejemplo, la sentencia FILTER es un filtro después de que finaliza la coincidencia.

Problema de ejemplo

Los siguientes ejemplos tienen resultados diferentes porque WHERE y FILTER son distintos.

Ejemplo 1

GRAPH FinGraph
MATCH (n:Account {id: 7})
OPTIONAL MATCH (m:Account)
WHERE FALSE
RETURN n.id AS n_id, m.id AS m_id;
n_id m_id
7 null

Ejemplo 2

GRAPH FinGraph
MATCH (n:Account {id: 7})
OPTIONAL MATCH (m:Account)
FILTER FALSE
RETURN n.id AS n_id, m.id AS m_id;

Resultados vacíos.

Las diferentes variables propagadas en las sentencias generan resultados diferentes.

Descripción

En el lenguaje de consulta de grafos, una variable declarada varias veces hace referencia al mismo elemento de grafo en todas las ocurrencias.

En el ejemplo 1, no hay un nodo Account cuyo id sea 7 y 16. Como resultado, se muestran resultados vacíos.

En el ejemplo 2, no se muestra el nombre n de la sentencia anterior (solo se muestra id). Por lo tanto, el segundo MATCH encuentra el nodo Account cuyo id es 16.

Problema de ejemplo

Los siguientes ejemplos tienen resultados diferentes porque se propagan diferentes variables entre las sentencias.

Ejemplo 1

GRAPH FinGraph
MATCH (n:Account {id: 7})
RETURN n

NEXT

MATCH (n:Account {id: 16})
RETURN n.id AS n_id;

Resultados vacíos.

Ejemplo 2

GRAPH FinGraph
MATCH (n:Account {id: 7})
RETURN n.id AS id

NEXT

MATCH (n:Account {id: 16})
RETURN n.id AS n_id;
n_id
16

Se ignora ORDER BY si hay una sentencia posterior que no es LIMIT.

Descripción

En el lenguaje de consulta de gráficos, se ignora la sentencia ORDER BY, a menos que se cumpla una de las siguientes condiciones:

  • ORDER BY es la última sentencia.
  • ORDER BY está seguido inmediatamente por LIMIT.

En el ejemplo 1, LIMIT no sigue inmediatamente a ORDER BY; el LIMIT final está separado. Esto significa que el motor ignora ORDER BY.

En el ejemplo 2, se aplica ORDER BY porque LIMIT sigue inmediatamente a ORDER BY.

Problema de ejemplo

Los siguientes ejemplos tienen resultados diferentes porque se ignora la sentencia ORDER BY cuando se usa sin LIMIT en el ejemplo 1.

Ejemplo 1

GRAPH FinGraph
MATCH (n:Account)
ORDER BY n.id DESC
RETURN n.id
LIMIT 3;
n_id
7

Ejemplo 2

GRAPH FinGraph
MATCH (n:Account)
ORDER BY n.id DESC
LIMIT 3
RETURN n.id;
n_id
20

Los diferentes patrones de bordes generan resultados diferentes

Descripción

En el conjunto de datos que se usa en el ejemplo de error, el patrón de borde de dirección ANY coincide con cada borde Transfers del gráfico dos veces.

En el ejemplo 1, un borde Transfers de Account(id=x) a Account(id=y) se puede hacer coincidir dos veces, de la siguiente manera:

  • n= Account(id=x), m= Account(id=y)
  • n= Account(id=y), m= Account(id=x)

Solo hay una coincidencia en el ejemplo 2, en el que n=Account(id=x) y m=Account(id=y).

Como resultado, la consulta del ejemplo 1 muestra 10 y la del ejemplo 2 muestra 5.

Problema de ejemplo

Los siguientes ejemplos tienen resultados diferentes porque se usan diferentes patrones de bordes.

Ejemplo 1

GRAPH FinGraph
MATCH (n:Account)-[:Transfers]-(m:Account)
RETURN COUNT(*) AS num_transfer_edges;
num_transfer_edges
10

Ejemplo 2

GRAPH FinGraph
MATCH (n:Account)-[:Transfers]->(m:Account)
RETURN COUNT(*) AS num_transfer_edges;
num_transfer_edges
5

Errores de mutación

Los resultados de la mutación se basan en el conjunto de datos que se usó en Configurar y consultar Spanner Graph.

Falta el nodo fuente que incumple la restricción de clave externa

Mensaje de error

Parent row for row [...] in table AccountTransferAccount is missing. Row cannot be written.

Descripción

La tabla de aristas AccountTransferAccount es la tabla INTERLEAVED INTO PARENT Account node. Para crear el borde Transfer, su nodo superior Account ya debe existir.

Ejemplo de error

INSERT INTO AccountTransferAccount (id, to_id, create_time, amount)
VALUES (100, 1, PENDING_COMMIT_TIMESTAMP(), 200);

Primero, crea el nodo Account principal y, luego, crea el borde Transfer.

Falta el nodo de destino que incumple la restricción de clave externa

Mensaje de error

Foreign key constraint FK_TransferTo is violated on table AccountTransferAccount. Cannot find referenced values in Account(id)

Descripción

La tabla AccountTransferAccount hace referencia a Accounttable a través de un ForeignKey llamado FK_TransferTo. Para crear el borde Transfer, el nodo Account de nodo de cola al que se hace referencia ya debe existir.

Ejemplo de error

INSERT INTO AccountTransferAccount (id, to_id, create_time, amount)
VALUES (1, 100, PENDING_COMMIT_TIMESTAMP(), 200);

Primero, crea el nodo de cuenta final y, luego, crea el borde Transfer.

El borde saliente huérfano incumple la relación superior-secundario

Mensaje de error

Integrity constraint violation during DELETE/REPLACE. Found child row [...] in table AccountTransferAccount

Descripción

La tabla de aristas AccountTransferAccount es la tabla de nodos Account INTERLEAVED INTO PARENT y el nodo Account que se borrará aún tiene aristas salientes adjuntas.

Ejemplo de error

DELETE FROM Account WHERE id = 1;

Primero, borra todos los bordes Transfer salientes y, luego, borra el nodo Account. Como alternativa, define ON DELETE CASCADE para INTERLEAVE y haz que Spanner borre automáticamente esos bordes.

El borde entrante huérfano incumple la relación superior-secundario

Mensaje de error

Foreign key constraint violation when deleting or updating referenced row(s): referencing row(s) found in table AccountTransferAccount

Descripción

La tabla de aristas AccountTransferAccount hace referencia a la tabla de nodos Account a través de un ForeignKey, y el nodo Account que se borrará aún tiene aristas entrantes adjuntas.

Ejemplo de error

DELETE FROM Account WHERE id = 1;

Primero, borra todos los bordes Transfer entrantes y, luego, borra el nodo Account. Como alternativa, define ON DELETE CASCADE para ForeignKey y haz que Spanner borre automáticamente esos bordes.