Jetzt mit KI-gestütztem Page Building über den MCP-Server

Eine cmssy-App testen

Der Editor ist der Pfad, den dein Build nicht prüfen kann. Ein Smoke-Test deckt ihn ab.

Eine Website mit totem Editor kompiliert weiterhin, liefert weiterhin aus und besteht weiterhin deine Unit-Tests. Nichts in einem normalen Build berührt den Edit-Pfad - also sagt dir auch nichts, wenn er kaputtgeht.

checkCmssyEditMode ist die Prüfung, die es tut.

Der Smoke-Test

import { checkCmssyEditMode } from "@cmssy/next/testing";

const result = await checkCmssyEditMode({
  baseUrl: "http://localhost:3000",
  secret: process.env.CMSSY_DRAFT_SECRET!,
  path: "/",
  // Nur wenn deine URLs die Sprache tragen. Die Prüfung liest <html lang> -
  // einen Vertrag - statt nach einem Wort aus deinen Texten zu suchen, das
  // eine Redaktion jederzeit ändern kann.
  localizedPath: "/de",
});

expect(result.failures).toEqual([]);

Führe ihn gegen einen gestarteten Production-Build aus (next build && next start), nicht gegen den Dev-Server. Genau das statische Rendering hat die Edit-Route überhaupt nötig gemacht - der Dev-Server testet also die falsche App.

Es gibt eine weitere Option für Sites, deren URL-Präfix nicht der Locale-Code ist. localizedLocale benennt die Sprache, die localizedPath rendern muss; standardmäßig ist es das erste Pfadsegment, das auf einer präfixierten Site die Sprache ist. Setze es explizit, wenn Präfix und Locale auseinandergehen - etwa /en-gb für Locale en - sonst vergleicht die Prüfung mit einer Sprache, die es nicht gibt, und schlägt aus dem falschen Grund fehl.

Was er zusichert

  1. Die öffentliche Seite liefert 200 ohne Editor, mit serverseitig gerendertem Header und Footer.
  2. Ein bloßes ?cmssyEdit=1 ohne Secret geht nicht in den Edit-Modus. Eine unverifizierte Anfrage darf die Tür nie öffnen.
  3. Ein verifiziertes cmssyEdit=1 plus cmssySecret rendert den Editor und verschiebt Header und Footer auf die Edit-Bridge.
  4. Optional: Die lokalisierte Vorschau deklariert die Sprache, die ihre URL verlangt, per <html lang>.

Warum "kein Header im SSR" Erfolg bedeutet

Diese Zusicherung liest sich verkehrt herum, bis man den Grund sieht.

Im Edit-Modus mounten Header und Footer über die Edit-Bridge, die auf dem Client rendert. Ein Header, der noch im servergerenderten HTML steckt, ist also ein Header, den der Editor auswählen, aber nicht bearbeiten kann - der Unterschied zwischen einem editierbaren Block und bloßem Markup.

Schlägt der Test fehl, benennt die Meldung die Ursache statt des Symptoms:

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?)

In CI

- run: pnpm build
- run: |
    pnpm start &
    npx wait-on http://localhost:3000 --timeout 60000
- run: pnpm smoke:edit

Überspringe den Job, wenn die Workspace-Secrets fehlen. Ein grüner Haken, der nichts prüft, ist schlechter als gar keine Prüfung - er macht aus einer Unbekannten eine falsche Sicherheit.

Als Skript verdrahten

Die Referenz-App hält ihn als eigenständiges Skript statt als Test-Runner-Fall, damit er ohne Framework in CI laufen kann:

{
  "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: "/de",
});

console.log(result.ok ? "EDITOR OK" : "EDITOR BROKEN");
for (const f of result.failures) console.log("  -", f);
process.exit(result.ok ? 0 : 1);

Was sonst noch zu testen ist

Blöcke sind gewöhnliche React-Komponenten, teste sie also gewöhnlich. Zwei cmssy-spezifische Gewohnheiten lohnen sich:

  • Rendere jeden Block mit data: undefined - genau das übergibt der Editor, und ein Block, der ohne Loader-Ergebnis wirft, ist ein Block, der den Editor bricht.
  • Rendere mit fehlendem Locale - Inhalte sind vielleicht noch nicht übersetzt, und der Fallback-Pfad ist der erste, auf den Besucher in einer neuen Sprache treffen.

Nächste Schritte