Baza danych cieni Prismy i niezgodność w nazewnictwie: Podręcznik obsługi
Dlaczego prisma migrate dev prosi o sformatowanie bazy danych, jak skonfigurować bezpieczną bazę cienia oraz jak mapować zasady wielkości liter w Prismie na format snake_case w Postgresie.
Dwa powtarzające się problemy pojawiają się, gdy zespoły używają Prismy z PostgreSQL: narzędzie do migracji ciągle proponuje usunięcie bazy danych rozwojowej, a tworzone przez nie tabele nie przypominają nazw używanych przez administratora Postgresa. Oba te zjawiska są udokumentowane i nie wskazują na to, że Prisma nie nadaje się do użycia w środowisku produkcyjnym. Ten przewodnik wyjaśnia, co dzieje się w każdym z tych przypadków, oraz przedstawia krótki zestaw zasad pomagających zachować integralność danych i konwencji schematu.
Dlaczego prisma migrate dev proponuje sformatowanie bazy danych
Typowy przypadek wygląda tak: ktoś uruchamia polecenie npx prisma migrate dev, komenda zatrzymuje się z błędem informującym, że tabela lub typ wybieralny „już istnieje”, a najszybszym sposobem na usunięcie tego komunikatu wydaje się być użycie polecenia prisma migrate reset. To polecenie usuwa wszystkie tabele i od nowa przeprowadza całą historię migracji.
Dla czego służy baza danych cieniowa
Podczas rozwoju Prisma Migrate wykorzystuje drugą, tymczasową bazę danych zwaną bazą danych cieniową. Jej jedynym zadaniem jest wykrywanie odchyleń. Przy każdym uruchomieniu polecenia migrate dev Prisma tworzy czystą bazę danych cieniową, aplikuje do niej wszystkie pliki migracyjne, analizuje powstałą strukturę schematu i porównuje ją z rzeczywistą bazą danych rozwojową.
Gdy te dwie bazy się nie pokrywają, oznacza to, że coś zmieniło bazę danych rozwojową poza historią migracji. Częste przyczyny to:
- polecenie
prisma db push, które zmieniło tabele bez tworzenia pliku migracyjnego - ręczna edycja dokonana za pomocą klienta SQL
- plik migracyjny stworzony przez kolegę z zespołu, ale nigdy nie zsynchronizowany
Prisma nie wie, jaką wersję danych chcesz zachować, dlatego proponuje jedyną bezpieczną opcję automatyczną, jaką ma do dyspozycji dla bazy danych rozwojowej: usuwa ją i odbudowuje na podstawie migracji.
Sposób awarii, który nie jest dobrze udokumentowany
Zaskakuje zespoły inny problem, który powoduje podobne objawy. W zarządzanych usługach Postgres, takich jak Neon czy Supabase, użytkownik bazy danych w ciągu połączenia często nie ma uprawnień do tworzenia i usuwania baz danych według potrzeb. W takiej sytuacji Prisma nie może utworzyć swojej tymczasowej bazy cienia i zawodzi z powodu błędu uprawnień.
Rozwijający często interpretują ten błąd jako „migracje są uszkodzone” i, zgodnie z poradami z wątków społecznościowych, uruchamiają migrate reset, aby go usunąć. Jest to niebezpieczne, ponieważ właśnie ten polecenie gwarantowanie niszczy dane, jeśli ciąg połączenia wskazuje na rzeczywisty adres. W publicznych dyskusjach na GitHubie znajdują się dokładnie takie historie: błąd w bazie danych, nieplanowane wywołanie resetu jako „rozwiązanie” oraz utrata tabel w trakcie realizacji projektu.
Zasady zapewniające bezpieczeństwo migracji
- Daj Prisma dedykowaną bazę danych cienia. Ustaw
shadowDatabaseUrlna oddzielną bazę danych, w której użytkownik może swobodnie tworzyć i usuwać tabele. Nigdy nie skieruj go na bazę produkcyjną ani wspólną bazę testową. W zależności od wersji Prisma, ta ustawienie znajduje się w konfiguracji źródła danych pliku schematu lub w pliku konfiguracyjnym Prisma, więc sprawdź aktualną dokumentację, gdzie wymagana jest ta wartość dla Twojej wersji. - Zawsze traktuj
migrate resetjako działanie destruktywne. Jeśli zostanie zalecone jako pierwszy krok naprawczy, zatrzymaj się i sprawdź raczej dane dostępowe, uprawnienia oraz ewentualne odchylenia. - Zrozum, że środowisko produkcyjne jest inne.
prisma migrate deploystosuje jedynie oczekujące na realizację migracje. Nigdy nie tworzy bazy danych cienia ani nie prosi o jej sformatowanie. Funkcja sformatowania jest elementem procesu rozwojowego zgodnie z projektem.
Modele w formacie PascalCase versus tabele w formacie snake_case
Drugim punktem sprzeciwu jest nazewnictwo. Język schematów Prismy zaleca nazwy modeli w formacie PascalCase oraz nazwy pól w formacie camelCase, co jest zgodne z standardami JavaScript i TypeScript. W świecie Postgresa zazwyczaj oczekuje się czegoś przeciwnego: identyfikatorów w formacie snake_case, często z nazwami tabel w liczbie mnogiej.
Dzięki ustawieniom domyślnym model o nazwie User z polem firstName staje się tabelą o nazwie User z kolumną o nazwie firstName. Postgres to akceptuje, ale identyfikatory o mieszanej wielkości liter muszą być umieszczone w podwójnych cudzysłowach w surowym SQL, a taki format wydaje się obcy administratorom bazy danych, narzędziom raportowania oraz wszelkim usługom, które odczytują bazę danych bez pośrednictwa Prismy.
Mapowanie nazw za pomocą @map i @@map
Prisma rozwiązuje ten problem za pomocą dwóch atrybutów: @map zmienia nazwę kolumny dla pojedynczego pola, a @@map zmienia nazwę tabeli odpowiadającej modelowi. Twój kod w TypeScript zachowuje nazwę user.firstName, podczas gdy baza danych przechowuje users.first_name. To mapowanie działa dobrze, ale nie jest stosowane automatycznie. Masz dwie opcje:
- ręcznie adnotować każde pole i model, co jest żmudne, ale całkowicie jawne i łatwe do sprawdzenia
- skorzystać z narzędzia zewnętrznego
prisma-case-formatCLI, które masowo zmienia wielkość liter w plikach schematu i można je ponownie uruchomić, aby nowe pola nie wracały do domyślnych wartości
Niezależnie od wyboru, podjąj decyzję przed pierwszą migracją. Przenoszenie nazw tabel i kolumn później oznacza konieczność tworzenia migracji, które wpływają na istniejące dane, a każde surowe zapytanie SQL w kodzie musi zostać dostosowane.
Jak Drizzle radzi sobie z tym samym problemem
Drizzle, najważniejsza alternatywa oparta na TypeScript, oferuje ustawienie casing, które przekształca nazwy w formacie camelCase w kodzie na nazwy w formacie snake_case w bazie danych we wszystkich schematach. To rzadki przypadek, gdy zwykła kolejność działa odwrotnie. Prisma jest zazwyczaj opisywane jako narzędzie bardziej abstrakcyjne, natomiast Drizzle jako bliższe SQL; jednakże podejście Drizzle oparte na kodzie ułatwia zarządzanie wielkoskładniowymi nazwami, podczas gdy oddzielny język schematów w Prismie sprawił, że opcja globalna pozostaje od dawna prośbą o nową funkcjonalność.
Główne wnioski
- Prośba o ponowne uruchomienie z
migrate devwskazuje na odchylenia lub problemy z uprawnieniami do bazy cienia, a nie na uszkodzone migracje. - Konfiguruj wyraźną, oddzielną bazę cienia dla każdego hostowanego dostawcy Postgres.
migrate reset jako ogólnej metody naprawczej; wdrożenia produkcyjne opierają się na migrate deploy, który nie może niczego sformatować.@map i @@map (ręcznie lub za pomocą prisma-case-format), a nie później.Jeśli rozważasz Prismę w porównaniu z Drizzle, nasze porównanie raw SQL, Prisma i Drizzle omawia szerszy zakres korzyści i wad.
Literatura pokrewna
- Przewodnik po MovieVault: API lista oglądania z Express 5, Prisma 7 i JWT — Specyfikacja ćwiczenia full-stack z ograniczeniem czasowym oraz jego backend oparty na Express, Prisma i JWT, wraz z notatkami dotyczącymi sprawdzania praw własności, mechanizmów kaskadowych i obsługi błędów.
- Konfiguracja Prisma 7 z PostgreSQL w projekcie TypeScript Node.js — Naprawa powszechnych błędów podczas konfiguracji Prisma 7 w środowisku TypeScript, od problemów z adresami URL typu string lub undefined po problemy z rootDir, oraz podłączenie PostgreSQL za pomocą adaptera sterownika pg.