W przypadku Firebase Data Connect projektujesz schemat GraphQL, który reprezentuje model danych wymagany przez Twoją aplikację. Data Connect przekształca ten schemat w instancję Cloud SQL for PostgreSQL, która obsługuje Twoją aplikację. Następnie tworzysz zapytania i mutacje, aby komunikować się z backendem, i łączysz te operacje w konektory, aby używać danych z kodu klienta.
Data Connect udostępnia narzędzia AI, które pomagają projektować i wdrażać schematy. W tym przewodniku przedstawiamy ważne koncepcje projektowania schematów, które pomogą Ci w standardowych i wspomaganych przez AI przepływach pracy podczas tworzenia aplikacji i po jego zakończeniu.
W przewodniku dla początkujących przedstawiliśmy schemat aplikacji do oceniania filmów w PostgreSQL.
W tym przewodniku rozwijamy ten schemat i podajemy listę SQL odpowiadającą ostatecznemu schematowi aplikacji do recenzowania filmów.
Schemat aplikacji do recenzowania filmów
Załóżmy, że chcesz utworzyć usługę, która umożliwia użytkownikom przesyłanie i wyświetlanie recenzji filmów.
Aby obsługiwać podstawowe zapytania, musisz mieć początkowy schemat takiej aplikacji. Ten schemat możesz później rozszerzyć, aby tworzyć złożone zapytania relacyjne.
W Data Connect zdefiniujesz typy GraphQL, aby określić kształt danych, o które klienci mogą wysyłać zapytania i którymi mogą manipulować. Podczas pisania schematu typy są tłumaczone na tabele Cloud SQL for PostgreSQL, najczęściej w bezpośredniej relacji między typami GraphQL a tabelami bazy danych, chociaż możliwe są też inne mapowania. W tym przewodniku znajdziesz przykłady od podstawowych po bardziej zaawansowane.
Zdefiniuj podstawowy typ Movie
Możesz zacząć od typu Movie
.
Schemat pliku Movie
zawiera podstawowe dyrektywy, takie jak:
@table(name)
i@col(name)
, aby dostosować nazwy tabel i kolumn SQL. Jeśli nie podasz nazwy, Data Connect wygeneruje nazwy w formacie snake_case.@col(dataType)
, aby dostosować typy kolumn SQL.@default
, aby skonfigurować domyślne wartości kolumn SQL podczas wstawiania.
Więcej informacji znajdziesz w dokumentacji referencyjnej dotyczącej @table
, @col
i @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
}
Automatyczne przechowywanie ważnych danych użytkowników w User
Aplikacja będzie śledzić użytkowników, więc potrzebujesz typu User
.
W tym przypadku szczególnie przydatna jest dyrektywa @default
. Pole id
może automatycznie pobierać identyfikator użytkownika z uwierzytelniania. Zwróć uwagę na użycie @default(expr: "auth.uid")
w tym przykładzie.
# Users
# Suppose a user can leave reviews for movies
type User @table {
id: String! @default(expr: "auth.uid")
username: String! @col(dataType: "varchar(50)")
}
Kluczowe wartości skalarne i wartości serwera
Zanim przyjrzymy się bliżej aplikacji do oceniania filmów, warto zapoznać się z Data Connect kluczowymi skalarami i wartościami serwera.
Kluczowe skalary to zwięzłe identyfikatory obiektów, które Data Connect automatycznie tworzy na podstawie kluczowych pól w Twoich schematach. Kluczowe skalary dotyczą wydajności, ponieważ umożliwiają uzyskanie w ramach jednego wywołania informacji o tożsamości i strukturze danych. Są one szczególnie przydatne, gdy chcesz wykonywać sekwencyjne działania na nowych rekordach i potrzebujesz unikalnego identyfikatora do przekazywania do kolejnych operacji, a także gdy chcesz uzyskać dostęp do kluczy relacyjnych, aby wykonywać dodatkowe, bardziej złożone operacje.
Korzystając z wartości serwera, możesz skutecznie zezwolić serwerowi na dynamiczne wypełnianie pól w tabelach za pomocą przechowywanych lub łatwo obliczalnych wartości zgodnie z określonymi wyrażeniami CEL po stronie serwera w argumencie expr
. Możesz na przykład zdefiniować pole z sygnaturą czasową, która jest stosowana, gdy uzyskuje się do niego dostęp przy użyciu czasu przechowywanego w żądaniu operacji, updatedAt: Timestamp!
@default(expr: "request.time")
.
Obsługa relacji „wiele do wielu” w przypadku typów Actor
i MovieActor
Po obsłużeniu użytkowników możesz wrócić do modelowania danych o filmach.
Następnie chcesz, aby w Twoich filmach występowali aktorzy.
Tabela Actor
jest dość prosta.
# 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)")
}
Jeśli chcesz, aby aktorzy występowali w wielu filmach, a filmy miały wielu aktorów, musisz utworzyć „tabelę złączeń”.
Tabela MovieActor
obsługuje relację wiele do wielu, a jej klucz podstawowy to kombinacja [movie, actor]
(pola klucza obcego z tabel movie
i 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
}
Gdy zdefiniujesz relację SQL w tabeli z ograniczeniem klucza obcego, Data Connect automatycznie wygeneruje odpowiednie pole po drugiej stronie. Nie musisz definiować pola mapowania odwrotnego (np. z Actor
z powrotem do MovieActor
).
Obsługa relacji jeden do jednego w typie MovieMetadata
Teraz możesz śledzić reżyserów filmowych i skonfigurować relację jeden do jednego z Movie
.
Aby dostosować ograniczenia klucza obcego, możesz użyć dyrektywy @ref
:
@ref(fields)
określa, których pól klucza obcego użyć.@ref(references)
określa pola, do których odwołuje się tabela docelowa (domyślnie jest to klucz podstawowy, ale działają też pola@unique
). Jest to bardziej zaawansowana opcja. Data Connect często może to zrobić za Ciebie.
Więcej informacji znajdziesz w dokumentacji referencyjnej dotyczącej @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
}
Używaj pól wygenerowanych na podstawie schematu do tworzenia operacji
Operacje Data Connect rozszerzą zestaw pól automatycznie wygenerowanych Data Connect na podstawie typów i relacji między typami w schemacie. Pola te są generowane przez narzędzia lokalne za każdym razem, gdy edytujesz schemat.
Załóżmy, że schemat zawiera typ Movie
i powiązany z nim typ Actor
.
Data Connect generuje pola movie
, movies
, actors_on_movies
i inne.
Zapytanie z polem
movie
Pole |
Użyj tego pola, aby wysłać zapytanie o jeden film na podstawie jego klucza. query GetMovie($myKey: Movie_Key!) { movie(key: $myKey) { title } } |
Zapytanie z polem
movies
Pole |
Użyj tego pola, aby wysłać zapytanie dotyczące wielu filmów, np. wszystkich filmów z danego roku. query GetMovies($myYear: Int!) { movies(where: { year: { eq: $myYear } }) { title } } |
Zapytanie z polem
actors_on_movies
Pole |
Użyj tego pola, aby wysłać zapytanie o wszystkich aktorów powiązanych z danym filmem. query GetActorsOnMovie($myKey: Movie_Key!) { actors_on_movies(where: { movie: { key: { eq: $myKey } } }) { actor { name } } } |
W przewodniku po implementacji zapytań i przewodniku po implementacji mutacji znajdziesz informacje o tym, jak implementować operacje za pomocą tych pól.
Bardziej zaawansowane koncepcje schematu
Aby wyjść poza podstawowe, ale przydatne typy i relacje, zapoznaj się z przykładami w dokumentacji.
Obsługiwane typy danych
Data Connect obsługuje te skalarne typy danych, które są przypisane do typów PostgreSQL za pomocą @col(dataType:)
.
Data Connect type | Wbudowany typ GraphQL lub Data Connect typ niestandardowy |
Domyślny typ PostgreSQL | Obsługiwane typy PostgreSQL (alias w nawiasach) |
---|---|---|---|
Ciąg znaków | GraphQL | tekst | text bit(n), varbit(n) char(n), varchar(n) |
Liczba całkowita | GraphQL | int | Int2 (smallint, smallserial), int4 (integer, int, serial) |
Liczba zmiennoprzecinkowa | GraphQL | float8 | float4 (real) float8 (double precision) numeric (decimal) |
Wartość logiczna | GraphQL | Wartość logiczna | Wartość logiczna |
UUID | Niestandardowy | uuid | uuid |
Int64 | Niestandardowy | bigint | int8 (bigint, bigserial) numeric (decimal) |
Data | Niestandardowy | date | data |
Sygnatura czasowa | Niestandardowy | timestamptz | timestamptz Uwaga: informacje o lokalnej strefie czasowej nie są przechowywane. |
Wektor | Niestandardowy | vector | wektor Zobacz Przeprowadzanie wyszukiwania podobieństwa wektorowego za pomocą Vertex AI. |
- GraphQL
List
jest mapowany na tablicę jednowymiarową.- Na przykład
[Int]
jest mapowany naint5[]
, a[Any]
najsonb[]
. - Data Connect nie obsługuje zagnieżdżonych tablic.
- Na przykład
Odpowiednik w schemacie SQL
-- 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);
Dalsze kroki
Może Cię zainteresować:
- Generowanie schematów aplikacji za pomocą narzędzi wspomaganych przez AI
- Zapoznaj się z dokumentacją składni.