Testowanie aplikacji cmssy
Edytor to ścieżka, której Twój build nie sprawdzi. Jeden smoke test ją pokrywa.
Serwis z martwym edytorem dalej się kompiluje, dalej się serwuje i dalej przechodzi Twoje testy jednostkowe. Nic w zwykłym buildzie nie dotyka ścieżki edycji, więc nic w zwykłym buildzie nie powie Ci, że się zepsuła.
checkCmssyEditMode to test, który to robi.
Smoke test
import { checkCmssyEditMode } from "@cmssy/next/testing";
const result = await checkCmssyEditMode({
baseUrl: "http://localhost:3000",
secret: process.env.CMSSY_DRAFT_SECRET!,
path: "/",
// Tylko jeśli Twoje URL-e niosą język. Test czyta <html lang> - kontrakt -
// zamiast szukać słowa z Twojej treści, które redaktor może zmienić
// w dowolnej chwili.
localizedPath: "/pl",
});
expect(result.failures).toEqual([]);Uruchamiaj go przeciwko wystartowanemu buildowi produkcyjnemu (next build && next start), nie przeciwko dev serverowi. To właśnie statyczne renderowanie sprawiło, że route edycyjny w ogóle był potrzebny, więc dev server testuje niewłaściwą aplikację.
Jest jeszcze jedna opcja, dla serwisów, w których prefiks URL to nie kod locale. localizedLocale nazywa język, który ma wyrenderować localizedPath; domyślnie bierze pierwszy segment ścieżki, który na serwisie z prefiksami jest językiem. Ustaw go jawnie, gdy prefiks i locale się różnią - na przykład /en-gb serwujące locale en - bo inaczej test porówna z językiem, który nie istnieje, i padnie z niewłaściwego powodu.
Co sprawdza
- Publiczna strona zwraca 200 bez edytora, z headerem i footerem wyrenderowanymi na serwerze.
- Samo
?cmssyEdit=1bez sekretu nie wchodzi w tryb edycji. Niezweryfikowane żądanie nigdy nie może otworzyć drzwi. - Zweryfikowane
cmssyEdit=1pluscmssySecretrenderuje edytor i przenosi header oraz footer na most edycyjny. - Opcjonalnie: zlokalizowany podgląd deklaruje język, o który prosi jego URL, przez
<html lang>.
Dlaczego "brak headera w SSR" oznacza sukces
To asercja, która czyta się na opak, dopóki nie zobaczysz dlaczego.
W trybie edycji header i footer montują się przez most edycyjny, który renderuje się na kliencie. Więc header wciąż obecny w HTML-u z serwera to header, który edytor może zaznaczyć, ale nie może edytować - różnica między edytowalnym blokiem a zwykłym markupem.
Gdy test pada, komunikat nazywa przyczynę, nie objaw:
edit /shop: the header and footer are still server-rendered - they will be
selectable but have no fields (is CMSSY_EDIT_HEADER set on the rewrite?)W CI
- run: pnpm build
- run: |
pnpm start &
npx wait-on http://localhost:3000 --timeout 60000
- run: pnpm smoke:editPomijaj ten job, gdy nie ma sekretów workspace'u. Zielony check, który niczego nie weryfikuje, jest gorszy niż brak checka - zamienia niewiadomą w fałszywe poczucie bezpieczeństwa.
Podpięcie jako skrypt
Aplikacja referencyjna trzyma go jako samodzielny skrypt, a nie case w test runnerze, żeby działał w CI bez frameworka:
{
"scripts": {
"smoke:edit": "node smoke-edit.mjs"
}
}// smoke-edit.mjs
import { checkCmssyEditMode } from "@cmssy/next/testing";
const result = await checkCmssyEditMode({
baseUrl: "http://localhost:3000",
secret: process.env.CMSSY_DRAFT_SECRET,
localizedPath: "/pl",
});
console.log(result.ok ? "EDITOR OK" : "EDITOR BROKEN");
for (const f of result.failures) console.log(" -", f);
process.exit(result.ok ? 0 : 1);Co jeszcze warto testować
Bloki to zwykłe komponenty React, więc testuj je zwyczajnie. Dwa nawyki specyficzne dla cmssy warto zachować:
- Wyrenderuj każdy blok z
data: undefined- dokładnie to przekazuje edytor, a blok, który rzuca wyjątkiem bez wyniku loadera, to blok psujący edytor. - Wyrenderuj z brakującym locale - treść może jeszcze nie być przetłumaczona, a ścieżka fallbacku to pierwsza, na którą trafią odwiedzający w nowym języku.
Następne kroki
- Loadery serwerowe - dlaczego
datajest undefined w edytorze. - Renderowanie - route'y, które ćwiczy smoke test.
- Edytor stron - co edytor robi, gdy już się otworzy.