1. Przegląd
W tym ćwiczeniu zbudujesz aplikację Neighbor Loop, która umożliwia zrównoważone udostępnianie nadwyżek i traktuje inteligencję jako podstawowy element warstwy danych.
Dzięki integracji Gemini 3.0 Flash i AlloyDB AI wyjdziesz poza podstawowe przechowywanie danych i wejdziesz w sferę inteligencji w bazie danych. Dowiesz się, jak przeprowadzać analizę elementów multimodalnych i odkrywanie semantyczne bezpośrednio w SQL, co eliminuje „podatek AI” w postaci opóźnień i nadmiaru architektury.

Co utworzysz
Wydajna aplikacja internetowa „przesuń, aby dopasować” do udostępniania nadwyżek w społeczności.
Czego się nauczysz
- Provisioning jednym kliknięciem: jak skonfigurować klaster i instancję AlloyDB zaprojektowane pod kątem zbiorów zadań AI.
- Wektory dystrybucyjne w bazie danych: generowanie wektorów text-embedding-005 bezpośrednio w instrukcjach INSERT.
- Rozumowanie multimodalne: używanie Gemini 3.0 Flash do „widzenia” elementów i automatycznego generowania dowcipnych opisów w stylu randkowym.
- Odkrywanie semantyczne: przeprowadzanie w zapytaniach SQL opartych na logice „sprawdzania nastroju” za pomocą funkcji ai.if() w celu filtrowania wyników na podstawie kontekstu, a nie tylko obliczeń.
Architektura
Neighbor Loop omija tradycyjne wąskie gardła warstwy aplikacji. Zamiast wyodrębniać dane do przetworzenia, używamy:
- AlloyDB AI: do generowania i przechowywania wektorów w czasie rzeczywistym.
- Google Cloud Storage: do przechowywania obrazów.
- Gemini 3.0 Flash:umożliwia wykonywanie w czasie poniżej sekundy wnioskowania na podstawie danych obrazów i tekstu bezpośrednio za pomocą SQL.
- Cloud Run: do hostowania lekkiego backendu Flask w jednym pliku.
Wymagania
2. Zanim zaczniesz
Utwórz projekt
- W konsoli Google Cloud na stronie wyboru projektu wybierz lub utwórz projekt Google Cloud.
- Sprawdź, czy w projekcie Cloud włączone są płatności. Dowiedz się, jak sprawdzić, czy w projekcie włączone są płatności.
- Będziesz używać Cloud Shell, czyli środowiska wiersza poleceń działającego w Google Cloud. U góry konsoli Google Cloud kliknij Aktywuj Cloud Shell.

- Po połączeniu z Cloud Shell sprawdź, czy uwierzytelnianie zostało już przeprowadzone, a projekt jest już ustawiony na Twój identyfikator projektu, używając tego polecenia:
gcloud auth list
- Aby potwierdzić, że polecenie gcloud zna Twój projekt, uruchom w Cloud Shell to polecenie:
gcloud config list project
- Jeśli projekt nie jest ustawiony, użyj tego polecenia, aby go ustawić:
gcloud config set project <YOUR_PROJECT_ID>
- Włącz wymagane interfejsy API: kliknij link i włącz interfejsy API.
Możesz też użyć polecenia gcloud. Informacje o poleceniach gcloud i ich użyciu znajdziesz w dokumentacji.
Pułapki i rozwiązywanie problemów
Syndrom „projektu widma” | Uruchomiono polecenie |
Bariera rozliczeniowa | Projekt został włączony, ale zapomniano o koncie rozliczeniowym. AlloyDB to wydajny silnik, który nie uruchomi się, jeśli „zbiornik paliwa” (płatności) jest pusty. |
Opóźnienie propagacji interfejsu API | Kliknięto „Włącz interfejsy API”, ale w wierszu poleceń nadal wyświetla się |
Limit Quags | Jeśli korzystasz z nowego konta próbnego, możesz osiągnąć regionalny limit instancji AlloyDB. Jeśli |
„Ukryty” agent usługi | Czasami agentowi usługi AlloyDB nie jest automatycznie przyznawana rola |
3. Konfiguracja bazy danych
W tym module użyjemy AlloyDB jako bazy danych do przechowywania danych testowych. Używa klastrów do przechowywania wszystkich zasobów, takich jak bazy danych i logi. Każdy klaster ma instancję podstawową, która zapewnia punkt dostępu do danych. Tabele będą zawierać rzeczywiste dane.
Utwórzmy klaster, instancję i tabelę AlloyDB, do których zostanie załadowany testowy zbiór danych.
- Kliknij przycisk lub skopiuj poniższy link do przeglądarki, w której zalogowany jest użytkownik konsoli Google Cloud.
- Po wykonaniu tego kroku repozytorium zostanie sklonowane do lokalnego edytora Cloud Shell i będziesz mieć możliwość uruchomienia poniższego polecenia z folderu projektu (ważne jest, aby upewnić się, że jesteś w katalogu projektu):
sh run.sh
- Teraz użyj interfejsu (kliknij link w terminalu lub link „Podgląd w internecie” w terminalu).
- Aby rozpocząć, wpisz szczegóły identyfikatora projektu, klastra i nazw instancji.
- Idź po kawę, podczas gdy dzienniki będą się przewijać. Tutaj możesz przeczytać, jak to działa za kulisami.
Pułapki i rozwiązywanie problemów
Problem z „cierpliwością” | Klastry baz danych to rozbudowana infrastruktura. Jeśli odświeżysz stronę lub zakończysz sesję Cloud Shell, ponieważ „utknęła”, możesz skończyć z „duchem” instancji, która jest częściowo udostępniona i nie można jej usunąć bez ręcznej interwencji. |
Niezgodny region | Jeśli interfejsy API zostały włączone w regionie |
Zombie Clusters | Jeśli nazwa klastra była już wcześniej używana i nie została usunięta, skrypt może wyświetlić komunikat, że nazwa klastra już istnieje. Nazwy klastrów muszą być unikalne w projekcie. |
Limit czasu Cloud Shell | Jeśli przerwa na kawę trwa 30 minut, Cloud Shell może przejść w stan uśpienia i odłączyć proces |
4. Obsługa administracyjna schematu
Gdy klaster i instancja AlloyDB będą działać, przejdź do edytora SQL AlloyDB Studio, aby włączyć rozszerzenia AI i udostępnić schemat.

Może być konieczne poczekanie na zakończenie tworzenia instancji. Gdy to zrobisz, zaloguj się w AlloyDB, używając danych logowania utworzonych podczas tworzenia klastra. Do uwierzytelniania w PostgreSQL użyj tych danych:
- Nazwa użytkownika: „
postgres” - Baza danych: „
postgres” - Hasło: „
alloydb” (lub inne hasło ustawione podczas tworzenia)
Po pomyślnym uwierzytelnieniu w AlloyDB Studio polecenia SQL są wpisywane w Edytorze. Możesz dodać wiele okien Edytora, klikając znak plusa po prawej stronie ostatniego okna.

Polecenia dla AlloyDB będziesz wpisywać w oknach edytora, w razie potrzeby korzystając z opcji Uruchom, Formatuj i Wyczyść.
Włączanie rozszerzeń
Do utworzenia tej aplikacji użyjemy rozszerzeń pgvector i google_ml_integration. Rozszerzenie pgvector umożliwia przechowywanie wektorów dystrybucyjnych i wyszukiwanie ich. Rozszerzenie google_ml_integration udostępnia funkcje, których możesz używać do uzyskiwania dostępu do punktów końcowych prognozowania Vertex AI w celu uzyskiwania prognoz w SQL. Włącz te rozszerzenia, uruchamiając te DDL:
CREATE EXTENSION IF NOT EXISTS google_ml_integration CASCADE;
CREATE EXTENSION IF NOT EXISTS vector;
Tworzenie tabeli
Tabelę możesz utworzyć za pomocą instrukcji DDL poniżej w AlloyDB Studio:
-- Items Table (The "Profile" you swipe on)
CREATE TABLE items (
item_id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
owner_id UUID,
provider_name TEXT,
provider_phone TEXT,
title TEXT,
bio TEXT,
category TEXT,
image_url TEXT,
item_vector VECTOR(768),
status TEXT DEFAULT 'available',
created_at TIMESTAMP DEFAULT NOW()
);
-- Swipes Table (The Interaction)
CREATE TABLE swipes (
swipe_id SERIAL PRIMARY KEY,
swiper_id UUID,
item_id UUID REFERENCES items(item_id),
direction TEXT CHECK (direction IN ('left', 'right')),
is_match BOOLEAN DEFAULT FALSE,
created_at TIMESTAMP DEFAULT NOW()
);
Kolumna item_vector będzie przechowywać wartości wektorowe tekstu.
Przyznaj uprawnienia
Aby przyznać uprawnienia do wykonywania funkcji „embedding”, uruchom to polecenie:
GRANT EXECUTE ON FUNCTION embedding TO postgres;
Przyznawanie roli Użytkownik Vertex AI kontu usługi AlloyDB
W konsoli IAM Google Cloud przyznaj kontu usługi AlloyDB (które wygląda tak: service-<<PROJECT_NUMBER>>@gcp-sa-alloydb.iam.gserviceaccount.com) dostęp do roli „Użytkownik Vertex AI”. Zmienna PROJECT_NUMBER będzie zawierać numer Twojego projektu.
Możesz też uruchomić to polecenie w terminalu Cloud Shell:
PROJECT_ID=$(gcloud config get-value project)
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:service-$(gcloud projects describe $PROJECT_ID --format="value(projectNumber)")@gcp-sa-alloydb.iam.gserviceaccount.com" \
--role="roles/aiplatform.user"
Rejestrowanie modelu Gemini 3 Flash w AlloyDB
Uruchom poniższą instrukcję SQL w edytorze zapytań AlloyDB.
CALL google_ml.create_model(
model_id => 'gemini-3-flash-preview',
model_request_url => 'https://aiplatform.googleapis.com/v1/projects/<<YOUR_PROJECT_ID>>/locations/global/publishers/google/models/gemini-3-flash-preview:generateContent',
model_qualified_name => 'gemini-3-flash-preview',
model_provider => 'google',
model_type => 'llm',
model_auth_type => 'alloydb_service_agent_iam'
);
--replace <<YOUR_PROJECT_ID>> with your project id.
Pułapki i rozwiązywanie problemów
Pętla „amnezji hasła” | Jeśli używasz konfiguracji „Jedno kliknięcie” i nie pamiętasz hasła, otwórz stronę podstawowych informacji o instancji w konsoli i kliknij „Edytuj”, aby zresetować hasło |
Błąd „Nie znaleziono rozszerzenia” | Jeśli |
Opóźnienie propagacji uprawnień | Uruchomiono polecenie |
Niezgodność wymiarów wektora | Tabela |
Błąd w identyfikatorze projektu | Jeśli w wywołaniu |
5. Pamięć obrazów (Google Cloud Storage)
Do przechowywania zdjęć naszych nadwyżek używamy zasobnika GCS. Na potrzeby tej aplikacji w wersji demonstracyjnej chcemy, aby obrazy były publicznie dostępne, dzięki czemu będą się natychmiast renderować na kartach do przesuwania.
- Utwórz zasobnik: utwórz nowy zasobnik w projekcie GCP (np. neighborloop-images), najlepiej w tym samym regionie co baza danych i aplikacja.
- Skonfiguruj dostęp publiczny: * Otwórz kartę Uprawnienia zasobnika.
- Dodaj podmiot zabezpieczeń allUsers.
- Przypisz rolę Wyświetlający obiekty Cloud Storage (aby każdy mógł zobaczyć zdjęcia) i rolę Tworzący obiekty Cloud Storage (na potrzeby przesyłania wersji demonstracyjnej).
Alternatywa (konto usługi): jeśli nie chcesz korzystać z dostępu publicznego, upewnij się, że konto usługi Twojej aplikacji ma pełny dostęp do AlloyDB i niezbędne role Storage, aby bezpiecznie zarządzać obiektami.
Pułapki i rozwiązywanie problemów
The Region Drag | Jeśli Twoja baza danych znajduje się w |
Unikalność nazwy zasobnika | Nazwy zasobników należą do globalnej przestrzeni nazw. Jeśli spróbujesz nazwać zasobnik |
Pomylenie „twórcy” z „oglądającym” | Pomylenie „Twórcy” z „Wyświetlającym”: jeśli dodasz tylko „Wyświetlającego”, aplikacja ulegnie awarii, gdy użytkownik spróbuje dodać nowy produkt, ponieważ nie ma uprawnień do zapisu pliku. W przypadku tej konkretnej konfiguracji wersji demonstracyjnej potrzebujesz obu tych elementów. |
6. Tworzenie aplikacji
Sklonuj to repozytorium do swojego projektu i przejdźmy przez nie.
- Aby sklonować ten projekt, uruchom to polecenie w terminalu Cloud Shell (w katalogu głównym lub w dowolnym miejscu, w którym chcesz utworzyć ten projekt):
git clone https://github.com/AbiramiSukumaran/neighbor-loop
Powinno to spowodować utworzenie projektu, co możesz sprawdzić w edytorze Cloud Shell.

- Jak uzyskać klucz interfejsu Gemini API
- Otwórz Google AI Studio: wejdź na stronę aistudio.google.com.
- Zaloguj się na to samo konto Google, którego używasz w projekcie Google Cloud.
- Utwórz klucz interfejsu API:
- Na pasku bocznym po lewej stronie kliknij „Uzyskaj klucz API”.
- Kliknij przycisk „Utwórz klucz interfejsu API w nowym projekcie”.
- Skopiuj klucz: po wygenerowaniu klucza kliknij ikonę kopiowania.
- Teraz ustaw zmienne środowiskowe w pliku .env.
GEMINI_API_KEY=<<YOUR_GEMINI_API_KEY>>
DATABASE_URL=postgresql+pg8000://postgres:<<YOUR_PASSWORD>>@<<HOST_IP>>:<<PORT>>/postgres
GCS_BUCKET_NAME=<<YOUR_GCS_BUCKET>>
Zastąp wartości symboli zastępczych <<YOUR_GEMINI_API_KEY>>, <<YOUR_PASSWORD>, <<HOST_IP>>, <<PORT>> and <<YOUR_GCS_BUCKET>>.
Pułapki i rozwiązywanie problemów
Wiele kont | Jeśli korzystasz z kilku kont Google (osobistego i służbowego), AI Studio może domyślnie używać niewłaściwego konta. Sprawdź awatara w prawym górnym rogu, aby upewnić się, że pasuje do konta projektu GCP. |
Osiągnięcie limitu w ramach „poziomu bezpłatnego” | Jeśli korzystasz z poziomu bezpłatnego, obowiązują limity szybkości (RPM – liczba żądań na minutę). Jeśli w trybie sąsiedzkim przesuniesz palcem zbyt szybko, może pojawić się błąd |
Exposed Key Security | Jeśli przypadkowo |
Pustka „Przekroczenie limitu czasu połączenia” | W pliku .env używasz prywatnego adresu IP, ale próbujesz połączyć się z zewnątrz sieci VPC (np. z komputera lokalnego). Prywatne adresy IP są dostępne tylko w ramach tej samej sieci Google Cloud. Przełącz na publiczny adres IP. |
Założenie dotyczące portu 5432 | Chociaż 5432 to standardowy port PostgreSQL, AlloyDB czasami wymaga określonych konfiguracji portów, jeśli używasz serwera proxy uwierzytelniania. Na potrzeby tego modułu upewnij się, że na końcu ciągu hosta używasz :5432. |
Strażnik dostępu „Autoryzowane sieci” | Nawet jeśli masz publiczny adres IP, AlloyDB będzie odrzucać połączenia, chyba że dodasz do białej listy adres IP maszyny, na której jest uruchomiony kod.Rozwiązanie: w ustawieniach instancji AlloyDB dodaj 0.0.0.0/0 (tylko do tymczasowego testowania) lub konkretny adres IP do autoryzowanych sieci. |
Nie udało się uzgodnić połączenia za pomocą protokołu SSL/TLS | AlloyDB preferuje bezpieczne połączenia. Jeśli zmienna DATABASE_URL nie określa prawidłowo sterownika (np. używa pg8000), uzgadnianie może się nie powieść bez powiadomienia, co spowoduje wyświetlenie ogólnego błędu „Nie można nawiązać połączenia z bazą danych”. |
Zamiana „puli podstawowej” na „pulę odczytu” | Jeśli przypadkowo skopiujesz adres IP puli odczytu zamiast głównej instancji, aplikacja będzie działać podczas wyszukiwania produktów, ale ulegnie awarii z błędem „Tylko do odczytu”, gdy spróbujesz dodać nowy produkt. Zawsze używaj adresu IP instancji głównej do zapisów. |
7. Sprawdźmy kod
„Profil randkowy” Twoich rzeczy

Gdy użytkownik przesyła zdjęcie produktu, nie musi pisać długiego opisu. Używam Gemini 3 Flash, aby „zobaczyć” produkt i napisać opis.
W backendzie użytkownik podaje tylko tytuł i zdjęcie. Gemini zajmie się resztą:
prompt = """
You are a witty community manager for NeighborLoop.
Analyze this surplus item and return JSON:
{
"bio": "First-person witty dating-style profile bio for the product, not longer than 2 lines",
"category": "One-word category",
"tags": ["tag1", "tag2"]
}
"""
response = genai_client.models.generate_content(
model="gemini-3-flash-preview",
contents=[types.Part.from_bytes(data=image_bytes, mime_type="image/jpeg"), prompt],
config=types.GenerateContentConfig(response_mime_type="application/json")
)

Wektory dystrybucyjne w bazie danych w czasie rzeczywistym

Jedną z najciekawszych funkcji AlloyDB jest możliwość generowania wektorów dystrybucyjnych bez opuszczania kontekstu SQL. Zamiast wywoływać model osadzania w Pythonie i wysyłać wektor z powrotem do bazy danych, wykonuję to wszystko w jednej instrukcji INSERT za pomocą funkcji embedding():
INSERT INTO items (owner_id, provider_name, provider_phone, title, bio, category, image_url, status, item_vector)
VALUES (
:owner, :name, :phone, :title, :bio, :cat, :url, 'available',
embedding('text-embedding-005', :title || ' ' || :bio)::vector
)
Dzięki temu każdy element jest „wyszukiwalny” według znaczenia od momentu opublikowania. Pamiętaj, że ta część dotyczy funkcji „wystawiania produktu” w aplikacji Neighbor Loop.

Zaawansowane wyszukiwanie wektorowe i inteligentne filtrowanie z Gemini 3.0
Standardowe wyszukiwanie słów kluczowych jest ograniczone. Jeśli wyszukasz „coś do naprawy krzesła”, tradycyjna baza danych może nie zwrócić żadnych wyników, jeśli słowo „krzesło” nie występuje w tytule. Neighbor Loop rozwiązuje ten problem dzięki zaawansowanemu wyszukiwaniu wektorowemu w AlloyDB AI.
Dzięki rozszerzeniu pgvector i zoptymalizowanemu przechowywaniu w AlloyDB możemy przeprowadzać niezwykle szybkie wyszukiwania podobieństw. Prawdziwa „magia” zaczyna się jednak, gdy połączymy bliskość wektorową z logiką opartą na LLM.
AlloyDB AI umożliwia wywoływanie modeli takich jak Gemini bezpośrednio w zapytaniach SQL. Oznacza to, że możemy przeprowadzić odkrywanie semantyczne, które obejmuje opartą na logice „kontrolę poprawności” za pomocą funkcji ai.if():
SELECT item_id, title, bio, category, image_url,
1 - (item_vector <=> embedding('text-embedding-005', :query)::vector) as score
FROM items
WHERE status = 'available'
AND item_vector IS NOT NULL
AND ai.if(
prompt => 'Does this text: "' || bio ||'" match the user request: "' || :query || '", at least 60%? "',
model_id => 'gemini-3-flash-preview'
)
ORDER BY score DESC
LIMIT 5
To zapytanie reprezentuje znaczącą zmianę w architekturze: przenosimy logikę do danych. Zamiast pobierać tysiące wyników do kodu aplikacji w celu ich filtrowania, Gemini 3 Flash przeprowadza „sprawdzenie atmosfery” w silniku bazy danych. Zmniejsza to czas oczekiwania, obniża koszty ruchu wychodzącego i zapewnia, że wyniki są nie tylko podobne pod względem matematycznym, ale też odpowiednie w kontekście.

Pętla „Przesuń, aby dopasować”
Interfejs to klasyczna talia kart.
Przesuń w lewo: odrzuć.
Przesuń w prawo: to pasuje!

Gdy przesuniesz palcem w prawo, backend zarejestruje interakcję w naszej tabeli przesunięć i oznaczy element jako dopasowany. Interfejs natychmiast wyświetli okno modalne z informacjami kontaktowymi dostawcy, aby umożliwić Ci umówienie odbioru.
8. Wdróżmy go w Cloud Run
- Wdróż go w Cloud Run, uruchamiając to polecenie w terminalu Cloud Shell, w którym projekt jest sklonowany. Upewnij się, że jesteś w folderze głównym projektu.
Uruchom to polecenie w terminalu Cloud Shell:
gcloud beta run deploy neighbor-loop \
--source . \
--region=us-central1 \
--network=<<YOUR_NETWORK_NAME>> \
--subnet=<<YOUR_SUBNET_NAME>> \
--allow-unauthenticated \
--vpc-egress=all-traffic \
--set-env-vars GEMINI_API_KEY=<<YOUR_GEMINI_API_KEY>>,DATABASE_URL=postgresql+pg8000://postgres:<<YOUR_PASSWORD>>@<<PRIVATE_IP_HOST>>:<<PORT>>/postgres,GCS_BUCKET_NAME=<<YOUR_GCS_BUCKET>>
Zastąp wartości symboli zastępczych <<YOUR_GEMINI_API_KEY>>, <<YOUR_PASSWORD>, <<PRIVATE_IP_HOST>>, <<PORT>> and <<YOUR_GCS_BUCKET>>
Po zakończeniu polecenia wyświetli się URL usługi. Skopiuj go.
- Przyznaj kontu usługi Cloud Run rolę Klient AlloyDB.Umożliwi to aplikacji bezserwerowej bezpieczne tunelowanie do bazy danych.
Uruchom to polecenie w terminalu Cloud Shell:
# 1. Get your Project ID and Project Number
PROJECT_ID=$(gcloud config get-value project)
PROJECT_NUMBER=$(gcloud projects describe $PROJECT_ID --format="value(projectNumber)")
# 2. Grant the AlloyDB Client role
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member="serviceAccount:$PROJECT_NUMBER-compute@developer.gserviceaccount.com" \
--role="roles/alloydb.client"
Teraz użyj adresu URL usługi (punktu końcowego Cloud Run skopiowanego wcześniej) i przetestuj aplikację. Prześlij zdjęcie starego elektronarzędzia i pozwól Gemini wykonać resztę.
Pułapki i rozwiązywanie problemów
Pętla „Nie udało się wprowadzić zmian” | Jeśli wdrożenie się zakończy, ale adres URL zwróci |
Rola „Shadow” w IAM | Nawet jeśli Ty masz uprawnienia do wdrożenia, konto usługi Cloud Run (zwykle |
9. Ogólne rozwiązywanie problemów

10. Prezentacja
Powinien być dostępny punkt końcowy do testów.
Jednak na potrzeby demonstracji możesz przez kilka dni wypróbować to rozwiązanie:
11. Czyszczenie danych
Po ukończeniu tego modułu nie zapomnij usunąć klastra i instancji AlloyDB.
Powinien on wyczyścić klaster wraz z instancjami.
12. Gratulacje
Udało Ci się utworzyć aplikację Neighbor Loop dla zrównoważonych społeczności za pomocą Google Cloud. Dzięki przeniesieniu logiki osadzania i AI Gemini 3 Flash do AlloyDB aplikacja działa niezwykle szybko (w zależności od ustawień wdrożenia), a kod jest wyjątkowo przejrzysty. Nie przechowujemy tylko danych, ale też intencje.
Połączenie szybkości Gemini 3 Flash i zoptymalizowanego przetwarzania wektorowego AlloyDB to prawdziwa przyszłość platform opartych na społeczności.