Con Firebase Data Connect, diseñas un esquema de GraphQL que representa el modelo de datos requerido para tu aplicación. Data Connect convierte este esquema en la instancia de Cloud SQL para PostgreSQL que respalda tu app. Luego, creas consultas y mutaciones para interactuar con el backend y agrupar estas operaciones en conectores para usar tus datos desde el código del cliente.
Data Connect ofrece herramientas de IA para ayudarte a diseñar e implementar tus esquemas. En esta guía, se presentan conceptos importantes del diseño de esquemas para complementar y respaldar tus flujos de trabajo estándar y asistidos por IA cuando comiences a desarrollar una app y más allá.
En la guía de inicio, se presentó un esquema de app de revisión de películas para PostgreSQL.
En esta guía, se desarrolla aún más ese esquema y se proporciona un listado de SQL equivalente al esquema final de la app de reseñas de películas.
El esquema de una app de opiniones sobre películas
Imagina que quieres crear un servicio que permita a los usuarios enviar y ver reseñas de películas.
Necesitas un esquema inicial para que la app admita consultas básicas. Extenderás este esquema más adelante para crear consultas relacionales complejas.
En Data Connect, definirás tipos de GraphQL para definir la forma de los datos que tus clientes pueden consultar y manipular. Cuando escribes tu esquema, tus tipos se traducen a tablas de Cloud SQL para PostgreSQL, la mayoría de las veces en una relación directa entre los tipos de GraphQL y las tablas de la base de datos, aunque son posibles otras asignaciones. En esta guía, se muestran algunos ejemplos, desde los más básicos hasta los más avanzados.
Cómo definir un tipo Movie
básico
Puedes comenzar con un tipo de Movie
.
El esquema de Movie
contiene directivas principales, como las siguientes:
@table(name)
y@col(name)
para personalizar los nombres de las tablas y las columnas de SQL Data Connect genera nombres en formato snake_case si no se especifican.@col(dataType)
para personalizar los tipos de columnas de SQL@default
para configurar los valores predeterminados de las columnas de SQL durante la inserción.
Para obtener más detalles, consulta los documentos de referencia de @table
, @col
y @default
.
# Movies
type Movie @table(name: "movie", key: "id") {
id: UUID! @col(name: "movie_id") @default(expr: "uuidV4()")
title: String!
releaseYear: Int
genre: String @col(dataType: "varchar(20)")
rating: Int
description: String
}
Almacena automáticamente datos importantes del usuario en un tipo User
Tu app hará un seguimiento de los usuarios, por lo que necesitas un tipo User
.
La directiva @default
es especialmente útil en este caso. El campo id
aquí puede tomar automáticamente el ID del usuario de la autenticación: observa el uso de @default(expr: "auth.uid")
en el siguiente ejemplo.
# Users
# Suppose a user can leave reviews for movies
type User @table {
id: String! @default(expr: "auth.uid")
username: String! @col(dataType: "varchar(50)")
}
Escalares de claves y valores del servidor
Antes de analizar más la app de reseñas de películas, es importante presentar los escalares clave y los valores del servidor de Data Connect.
Los escalares clave son identificadores de objetos concisos que Data Connect ensambla automáticamente a partir de los campos clave de tus esquemas. Los escalares clave se relacionan con la eficiencia, ya que te permiten encontrar en una sola llamada información sobre la identidad y la estructura de tus datos. Son especialmente útiles cuando deseas realizar acciones secuenciales en registros nuevos y necesitas un identificador único para pasar a las próximas operaciones, y también cuando deseas acceder a claves relacionales para realizar operaciones adicionales más complejas.
Con los valores del servidor, puedes permitir que el servidor complete de forma dinámica los campos de tus tablas con valores almacenados o que se pueden calcular fácilmente según expresiones CEL particulares del servidor en el argumento expr
. Por ejemplo, puedes definir un campo con una marca de tiempo aplicada cuando se accede al campo con la hora almacenada en una solicitud de operación, updatedAt: Timestamp!
@default(expr: "request.time")
.
Cómo controlar relaciones de varios a varios en tipos Actor
y MovieActor
Con los usuarios controlados, puedes volver a modelar los datos de películas.
Luego, querrás que los actores protagonicen tus películas.
La tabla Actor
es bastante sencilla.
# Actors
# Suppose an actor can participate in multiple movies and movies can have multiple actors
# Movie - Actors (or vice versa) is a many to many relationship
type Actor @table {
id: UUID! @default(expr: "uuidV4()")
name: String! @col(dataType: "varchar(30)")
}
Si quieres que los actores participen en varias películas y que las películas tengan varios actores, necesitarás una "tabla de unión".
La tabla MovieActor
controla la relación de varios a varios, y su clave primaria es una combinación de [movie, actor]
(los campos de clave externa de movie
y actor
).
# Join table for many-to-many relationship for movies and actors
# The 'key' param signifies the primary keys of this table
# In this case, the keys are [movieId, actorId], the foreign key fields of the reference fields [movie, actor]
type MovieActor @table(key: ["movie", "actor"]) {
movie: Movie!
# movieId: UUID! <- implicitly added foreign key field
actor: Actor!
# actorId: UUID! <- implicitly added foreign key field
role: String! # "main" or "supporting"
# optional other fields
}
Cuando defines una relación de SQL en la tabla con una restricción de clave externa, Data Connect genera automáticamente el campo correspondiente en el otro lado. No es necesario que definas el campo de asignación inversa (p.ej., de Actor
a MovieActor
).
Cómo controlar relaciones de uno a uno en un tipo MovieMetadata
Ahora, haz un seguimiento de los directores de películas y configura una relación uno a uno con Movie
.
Puedes usar la directiva @ref
para personalizar las restricciones de clave externa:
@ref(fields)
especifica qué campos de clave externa se deben usar.@ref(references)
especifica los campos a los que se hace referencia en la tabla de destino (de forma predeterminada, la clave primaria, pero los campos@unique
también funcionan). Esta es una opción más avanzada; Data Connect a menudo puede inferir esto por ti.
Para obtener más detalles, consulta los documentos de referencia de @ref
.
# Movie Metadata
# Movie - MovieMetadata is a one-to-one relationship
type MovieMetadata @table {
# @unique ensures that each Movie only has one MovieMetadata.
movie: Movie! @unique
# Since it references to another table type, it adds a foreign key constraint.
# movie: Movie! @unique @ref(fields: "movieId", references: "id")
# movieId: UUID! <- implicitly added foreign key field
director: String
}
Usa los campos generados a partir de tu esquema para crear operaciones
Tus operaciones de Data Connect extenderán un conjunto de campos Data Connect generados automáticamente según los tipos y las relaciones de tipos en tu esquema. Estos campos se generan con herramientas locales cada vez que editas tu esquema.
Supongamos que tu esquema contiene un tipo Movie
y un tipo Actor
asociado.
Data Connect genera los campos movie
, movies
y actors_on_movies
, entre otros.
Consulta con el campo
movie
El campo |
Usa este campo para consultar una sola película por su clave. query GetMovie($myKey: Movie_Key!) { movie(key: $myKey) { title } } |
Consulta con el campo
movies
El campo |
Usa este campo para consultar varias películas, por ejemplo, todas las películas de un año determinado. query GetMovies($myYear: Int!) { movies(where: { year: { eq: $myYear } }) { title } } |
Consulta con el campo
actors_on_movies
El campo |
Usa este campo para consultar todos los actores asociados con una película determinada. query GetActorsOnMovie($myKey: Movie_Key!) { actors_on_movies(where: { movie: { key: { eq: $myKey } } }) { actor { name } } } |
Teniendo esto en cuenta, puedes leer cómo implementar operaciones con estos campos en la guía para implementar consultas y la guía para implementar mutaciones.
Conceptos de esquema más avanzados
Para ir más allá de los tipos y las relaciones básicos, pero útiles, consulta los ejemplos en la documentación de referencia.
Tipos de datos admitidos
Data Connect admite los siguientes tipos de datos escalares, con asignaciones a tipos de PostgreSQL a través de @col(dataType:)
.
Data Connect type | Tipo integrado de GraphQL o tipo personalizado Data Connect |
Tipo de PostgreSQL predeterminado | Tipos de PostgreSQL admitidos (alias entre paréntesis) |
---|---|---|---|
String | GraphQL | texto | text bit(n), varbit(n) char(n), varchar(n) |
Int | GraphQL | int | Int2 (smallint, smallserial), int4 (integer, int, serial) |
Número de punto flotante | GraphQL | float8 | float4 (real) float8 (doble precisión) numeric (decimal) |
Booleano | GraphQL | booleano | booleano |
UUID | Personalizado | uuid | uuid |
Int64 | Personalizado | bigint | int8 (bigint, bigserial) numeric (decimal) |
Fecha | Personalizado | date | fecha |
Marca de tiempo | Personalizado | timestamptz | timestamptz Nota: No se almacena información sobre la zona horaria local. |
Vector | Personalizado | vector | vector Consulta Cómo realizar una búsqueda de similitud de vectores con Vertex AI. |
- El
List
de GraphQL se asigna a un array unidimensional.- Por ejemplo,
[Int]
se asigna aint5[]
y[Any]
se asigna ajsonb[]
. - Data Connect no admite arrays anidados.
- Por ejemplo,
Esquema de SQL equivalente
-- Movies Table
CREATE TABLE Movies (
movie_id UUID DEFAULT uuid_generate_v4() PRIMARY KEY,
title VARCHAR(255) NOT NULL,
release_year INT,
genre VARCHAR(30),
rating INT,
description TEXT,
tags TEXT[]
);
-- Movie Metadata Table
CREATE TABLE MovieMetadata (
movie_id UUID REFERENCES Movies(movie_id) UNIQUE,
director VARCHAR(255) NOT NULL,
PRIMARY KEY (movie_id)
);
-- Actors Table
CREATE TABLE Actors (
actor_id UUID DEFAULT uuid_generate_v4() PRIMARY KEY,
name VARCHAR(30) NOT NULL
);
-- MovieActor Join Table for Many-to-Many Relationship
CREATE TABLE MovieActor (
movie_id UUID REFERENCES Movies(movie_id),
actor_id UUID REFERENCES Actors(actor_id),
role VARCHAR(50) NOT NULL, # "main" or "supporting"
PRIMARY KEY (movie_id, actor_id),
FOREIGN KEY (movie_id) REFERENCES Movies(movie_id),
FOREIGN KEY (actor_id) REFERENCES Actors(actor_id)
);
-- Users Table
CREATE TABLE Users (
user_id UUID DEFAULT uuid_generate_v4() PRIMARY KEY,
user_auth VARCHAR(255) NOT NULL
username VARCHAR(30) NOT NULL
);
-- Reviews Table
CREATE TABLE Reviews (
review_id UUID DEFAULT uuid_generate_v4() PRIMARY KEY,
user_id UUID REFERENCES Users(user_id),
movie_id UUID REFERENCES Movies(movie_id),
rating INT,
review_text TEXT,
review_date TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
UNIQUE (movie_id, user_id)
FOREIGN KEY (user_id) REFERENCES Users(user_id),
FOREIGN KEY (movie_id) REFERENCES Movies(movie_id)
);
-- Self Join Example for Movie Sequel Relationship
ALTER TABLE Movies
ADD COLUMN sequel_to UUID REFERENCES Movies(movie_id);
Próximos pasos
También te puede interesar:
- Genera esquemas para tus apps con herramientas de asistencia de IA
- Revisa la documentación de referencia de sintaxis.