Przepisy na Node.js/Express
ENPrzepisy Node.js dla agentów AI to prompty i bramki weryfikacyjne, dzięki którym Claude Code, Codex i Cursor tworzą produkcyjne usługi Express 5 w TypeScripcie: czysty shutdown, walidację wejścia, rotację refresh tokenów, limity żądań, transakcje Prisma odporne na współbieżność, zadania BullMQ i logi z redakcją sekretów. Kod akceptujesz na podstawie wyników bramek, a nie lektury linijka po linijce.
Twoje API w Expressie przechodzi wszystkie testy napisane przez agenta, a potem pierwszy deploy zrywa trwające żądania, dwóch klientów kupuje ostatnią sztukę towaru w tej samej chwili, a refresh token pojawia się jawnym tekstem w wyszukiwarce logów. Kod wyglądał idiomatycznie. Każdy z tych błędów to produkcyjny szczegół, którego testy happy path nigdy nie dotknęły.
Ta strona jest dla programistów, którzy budują backendy Node.js z agentem i chcą przestać przeglądać każdy middleware wzrokiem. Produkcyjne szczegóły trafiają do promptów, a dowód dostarcza maszyna.
Co wyniesiesz z tych przepisów Node.js
Dział zatytułowany „Co wyniesiesz z tych przepisów Node.js”- Blok reguł
AGENTS.mddla TypeScriptu na Node.js, którego przestrzegają wszystkie trzy narzędzia, oraz bramkęnpm run check, którą agent uruchamia, zanim powie „gotowe” - Siedem promptów do skopiowania: szkielet Express 5 z czystym shutdownem, walidacja i mapowanie błędów, rotacja refresh tokenów, rate limiting, transakcja zamówienia w Prisma, worker BullMQ oraz ustrukturyzowane logi z redakcją
- Tabelę weryfikacji, która mówi, która bramka łapie który błąd, więc czytasz wynik bramek zamiast diffa
- Kroki naprawcze dla sześciu najczęstszych awarii Node.js napisanego przez agenta
Przygotuj konwencje Node.js i bramkę, którą agent musi przejść
Dział zatytułowany „Przygotuj konwencje Node.js i bramkę, którą agent musi przejść”Większość pracy wykonują dwa artefakty: plik reguł, który agent czyta przy każdym zadaniu, i jedno polecenie, które kończy się błędem, gdy kod nie jest gotowy. Przygotuj oba, zanim poprosisz o jakikolwiek kod.
-
Przypnij wspieraną wersję środowiska. Według harmonogramu wydań Node.js Node.js 24 jest w fazie Active LTS do 2026-10-20, kiedy przechodzi w Maintenance LTS, Node.js 22 w fazie Maintenance LTS, a Node.js 20 osiągnął koniec wsparcia 2026-04-30. Node.js 26 ma zostać wersją LTS 2026-10-28. Przypnij 24 w
.nvmrci wpackage.json:{"type": "module","engines": { "node": ">=24" }}Jawna wersja powstrzymuje agenta przed obejściami, których aktualny Node.js już nie potrzebuje, na przykład
dotenvtam, gdzie działanode --env-file=.env. -
Dodaj bramkę do
package.json. To definicja „gotowe” dla każdego promptu na tej stronie.{"scripts": {"typecheck": "tsc --noEmit","lint": "eslint .","test": "vitest run","check": "npm run typecheck && npm run lint && npm run test && npm audit --omit=dev --audit-level=high"}}Aktualne wersje w npm na 2026-09-26:
express5.2.1,zod4.6.5,vitest5.0.2,supertest7.3.0,pino10.3.1,bullmq6.3.9,@prisma/client7.10.0,testcontainers12.1.0. Dwa pakiety wymagają uwagi, a sekcja o awariach wyjaśnia dlaczego: instalujtypescript@~6.0.3zamiastlatest, jeśli używasz regułtypescript-eslintopartych na typach, oraz instalujprismai@prisma/clientw tej samej wersji. -
Zapisz reguły Node.js w
AGENTS.mdw katalogu głównym repozytorium. Codex czytaAGENTS.mdnatywnie; zakładki poniżej pokazują, jak Claude Code go wczytuje i jak Cursor dostaje jego kopię.## Node.js conventions- Node.js 24, ESM, TypeScript strict. Express 5, never Express 4 idioms.- Express 5 forwards rejected promises from handlers to the error middleware.Do not add express-async-errors or a catchAsync wrapper.- Named wildcards only: app.all('/*splat', ...), never app.get('*', ...).- Config comes from one Zod-validated module, src/config.ts. No process.envreads anywhere else.- One PrismaClient for the process, created in src/db.ts. Never per request.- Every error response uses { error: { code, message } }; no stack tracesoutside development.- Tests: Vitest and supertest. Database tests use Testcontainers, not mocks.- Never edit an existing test assertion, add .skip, or add .only to make atest pass. If a test looks wrong, stop and say why.- Done means `npm run check` passes. Paste its last 20 lines in your final message.
Najważniejsze są dwie ostatnie reguły. Pierwsza nie pozwala agentowi osłabiać testów, żeby dojść do zielonego wyniku; w artykule chroń wyrocznię znajdziesz wyjaśnienie, dlaczego to najczęstszy sposób, w jaki praca agenta udaje sukces. Druga zamienia „chyba działa” w dowód, który przeczytasz w dziesięć sekund.
Podłącz reguły i bramkę w każdym narzędziu
Dział zatytułowany „Podłącz reguły i bramkę w każdym narzędziu”Reguły i prompty są identyczne we wszystkich narzędziach. Różni się to, jak każde narzędzie wczytuje reguły, formatuje zmiany i recenzuje wynik.
Claude Code w pierwszej kolejności czyta CLAUDE.md, więc utwórz plik, który importuje wspólne reguły. Składnia @path wstawia plik do kontekstu przy starcie:
@AGENTS.mdBez pliku CLAUDE.md Claude Code w wersji v2.1.277 i nowszej (oba kanały wydań, stan na 2026-10-12) czyta AGENTS.md bezpośrednio (v2.1.281 na Bedrocku, Google Cloud, Foundry i bramkach LLM; przełącznik w /config → Project instructions); import ma znaczenie, gdy trzymasz też reguły specyficzne dla Claude.
Formatuj każdy plik TypeScript edytowany przez agenta hookiem PostToolUse w .claude/settings.json (wymaga Prettiera w devDependencies: npm install -D prettier):
{ "hooks": { "PostToolUse": [ { "matcher": "Edit|Write", "hooks": [ { "type": "command", "command": "jq -r '.tool_input.file_path' | grep -E '\\.(ts|js)$' | xargs -r npx --no-install prettier --write" } ] } ] }}Daj agentowi wyszukiwanie referencji i diagnostykę przez plugin typescript-lsp z oficjalnego marketplace’u Anthropic. Plugin tylko rejestruje serwer, więc najpierw zainstaluj serwer języka. Przypnij typescript@6: TypeScript 7.0.2 zawiera tylko tsc, bez tsserver, którego serwer języka potrzebuje (sprawdzono 2026-09-26). W terminalu:
npm install -g typescript-language-server typescript@6claude plugin install typescript-lsp@claude-plugins-officialZanim otworzysz pull request, uruchom w sesji /code-review, żeby dostać drugą opinię o diffie.
Codex czyta AGENTS.md bezpośrednio, więc dodatkowy plik nie jest potrzebny. Uruchom zadanie z zapisem w obszarze roboczym i pytaniem o zgodę na wszystko szersze (terminal):
codex -s workspace-write -a on-request "Implement POST /api/v1/orders as described in docs/tasks/orders.md. Done means npm run check passes."Zrecenzuj gałąź względem main, zanim ją wypchniesz:
codex review --base mainUtwórz regułę projektu w ustawieniach Rules Cursora z tą samą listą, ograniczoną do plików *.ts, żeby agent wczytywał ją przy każdym kontakcie z TypeScriptem. Przy wieloplikowych promptach z tej strony używaj Plan Mode, żeby zatwierdzić listę plików przed napisaniem kodu. Niezależne przepisy uruchamiaj w Worktrees, a pull request oddaj do recenzji Bugbotowi.
Zacznij od domyślnego modelu narzędzia i zwiększ poziom effort, zanim zmienisz model; aktualne domyślne modele znajdziesz w przeglądzie modeli.
Zbuduj produkcyjne API na Express 5 z agentem krok po kroku
Dział zatytułowany „Zbuduj produkcyjne API na Express 5 z agentem krok po kroku”Każdy krok to jeden prompt i sprawdzenie, które go dowodzi. Wykonuj je po kolei: późniejsze prompty zakładają, że szkielet i moduł bazy danych już istnieją.
Jak wygenerować usługę Express 5, która czysto się zamyka?
Dział zatytułowany „Jak wygenerować usługę Express 5, która czysto się zamyka?”Najczęstsze pominięcie w pierwszym podejściu to shutdown. Agent wywołuje app.listen() i nic więcej, więc każdy deploy przerywa trwające żądania i zostawia otwarte połączenia z bazą.
Dobra odpowiedź ma taki rdzeń:
const server = app.listen(config.PORT);
function shutdown(signal: NodeJS.Signals) { logger.info({ signal }, 'shutting down'); setTimeout(() => process.exit(1), 10_000).unref(); server.close(async (err) => { await prisma.$disconnect(); await redis.quit(); process.exit(err ? 1 : 0); });}
process.once('SIGTERM', shutdown);process.once('SIGINT', shutdown);Nie musisz tego sprawdzać wzrokiem: test nie przejdzie, jeśli żądanie zostanie zerwane albo proces zawiśnie. Rozdzielenie app.ts i server.ts pozwala też supertestowi sterować aplikacją bez otwierania portu.
Jak uzyskać walidację i odpowiedzi błędów, na których klient może polegać?
Dział zatytułowany „Jak uzyskać walidację i odpowiedzi błędów, na których klient może polegać?”Agenci wytrenowani na Expressie 4 owijają każdy handler w catchAsync albo instalują express-async-errors. Express 5 sam przekazuje odrzucone obietnice z handlerów do middleware’u błędów, więc te wrappery to martwy kod, a reguła w AGENTS.md trzyma je z dala od repozytorium.
Agenci zwykle pomijają właśnie mapowanie błędów Prismy. Bez niego zduplikowany e-mail kończy się kodem 500, a klient ponawia żądanie, które nigdy się nie powiedzie. Test błędu 500 w trybie produkcyjnym dowodzi, że żaden wewnętrzny szczegół nie trafia do klienta.
Jak skłonić agenta do napisania rotacji refresh tokenów, której można ufać?
Dział zatytułowany „Jak skłonić agenta do napisania rotacji refresh tokenów, której można ufać?”Kod uwierzytelniania to miejsce, w którym czytanie diffa daje największe poczucie bezpieczeństwa i najmniej realnej pewności. Opisz scenariusze ataku jako testy i to one niech niosą dowód.
Kluczowy jest test ponownego użycia tokenu. Bez niego implementacja, która nigdy nie unieważnia starego tokenu, przechodzi wszystkie pozostałe przypadki. Jako drugie, niezależne sprawdzenie tego kodu dodaj bramkę bezpieczeństwa, która uruchamia agenta recenzującego przy każdym pull requeście; opcje dla każdego narzędzia opisuje strona o bramkach bezpieczeństwa dla agentów.
Jak ograniczyć liczbę żądań do API w Expressie za load balancerem?
Dział zatytułowany „Jak ograniczyć liczbę żądań do API w Expressie za load balancerem?”Wygenerowany limiter zwykle działa lokalnie i zawodzi na produkcji na jeden z dwóch sposobów: liczniki żyją w pamięci procesu, więc każda replika przepuszcza pełny limit, albo każde żądanie wygląda, jakby przyszło z adresu IP load balancera.
Test z dwiema instancjami dowodzi, że magazyn jest wspólny; test w jednym procesie przechodzi z domyślnym magazynem w pamięci i nie mówi nic o produkcji.
Jak uzyskać transakcje Prisma, które wytrzymają równoległe zamówienia?
Dział zatytułowany „Jak uzyskać transakcje Prisma, które wytrzymają równoległe zamówienia?”Pierwsza próba agenta przy „sprawdź stan, potem zmniejsz” odczytuje stan magazynu, porównuje go w JavaScripcie i zapisuje z powrotem. Dwa równoległe zamówienia odczytują stock = 1 i oba kończą się sukcesem. Zamockowane repozytorium nie pokaże tego błędu; pokaże go tylko prawdziwa baza pod równoległymi żądaniami.
Dwa szczegóły Prisma, których agent może nie znać. Prisma 7 wymaga driver adaptera: klienta tworzy się jako new PrismaClient({ adapter: new PrismaPg({ connectionString }) }) z generatorem prisma-client i plikiem prisma.config.ts, więc ustawienia puli należą do adaptera, a nie do connection stringa. Poza tym 2026-09-26 tag latest w npm dla CLI prisma wskazuje 8.0.0-rc.17, czyli release candidate nowego CLI Prisma dla Prisma Developer Platform, podczas gdy latest dla @prisma/client to 7.10.0. Prisma 8 dostarcza własne skille dla agentów (npx prisma skills sync instaluje je w .claude/skills/, .cursor/skills/ i .agents/skills/), co czyni ją atrakcyjną dla nowych projektów. Wybierz ją świadomie, a nie dlatego, że tak zdecydowało npm install prisma.
Żeby agent czytał prawdziwy schemat zamiast zgadywać nazwy kolumn, podłącz serwer MCP bazy danych do bazy deweloperskiej przez rolę tylko do odczytu. Przewodnik po MCP dla baz danych porównuje serwery i ich przełączniki trybu tylko do odczytu. Nie używaj @modelcontextprotocol/server-postgres: npm oznacza go jako przestarzały.
Jak przenieść wolną pracę do kolejki BullMQ, nie gubiąc zadań?
Dział zatytułowany „Jak przenieść wolną pracę do kolejki BullMQ, nie gubiąc zadań?”Pierwsza wersja agenta wykonuje pracę wewnątrz żądania albo ponawia nieidempotentne zadanie i wysyła e-mail dwa razy.
Test idempotencji sprawia, że ponowienia są bezpieczne. Bez niego ponowienie po timeoucie, który nastąpił już po udanym zapisie, tworzy zduplikowane pliki, e-maile lub obciążenia karty.
Jak uzyskać ustrukturyzowane logi, które nigdy nie ujawniają sekretów?
Dział zatytułowany „Jak uzyskać ustrukturyzowane logi, które nigdy nie ujawniają sekretów?”Pierwsza wersja agenta loguje req.body, więc hasła i tokeny trafiają do wyszukiwarki logów.
Test redakcji to jedyny sposób, żeby wiedzieć, że redakcja działa; ścieżka, która nie pasuje do rzeczywistego kształtu obiektu, zawodzi po cichu. Dashboardy, alerty i tracing na bazie tych logów opisują wzorce monitoringu i logowania.
Jak zweryfikować Node.js napisany przez agenta bez czytania każdej linijki?
Dział zatytułowany „Jak zweryfikować Node.js napisany przez agenta bez czytania każdej linijki?”Czytaj wynik bramek i listy przypadków testowych, a nie diff. Każda bramka poniżej łapie klasę błędów, która w code review wygląda poprawnie.
| Bramka | Polecenie | Co łapie |
|---|---|---|
| Typy | tsc --noEmit | Niezgodne kształty danych między warstwami, nieobsłużone undefined, literówki w polach |
| Linter | eslint . z regułami typescript-eslint opartymi na typach | Porzucone obietnice (no-floating-promises), niewłaściwie użyte obietnice w callbackach (no-misused-promises), niebezpieczne any |
| Testy jednostkowe i HTTP | vitest run z supertestem | Kody statusu, treść błędów, walidacja, redakcja, shutdown |
| Testy integracyjne | Testcontainers z Postgresem i Redisem | Błędny SQL, brakujące ograniczenia unikalności, wyścigi takie jak nadsprzedaż, wspólne liczniki rate limitu |
| Zależności | npm audit --omit=dev --audit-level=high | Znane podatności w zależnościach produkcyjnych |
| Obciążenie | npx autocannon -c 100 -d 30 https://staging.example.com/api/v1/orders na stagingu | Wyczerpanie puli, blokowanie pętli zdarzeń, rosnące zużycie pamięci |
| Agent recenzujący | /code-review (Claude Code), codex review --base main (Codex), Bugbot (Cursor) | Błędy logiczne i brakujące przypadki, których bramki nie wyrażą |
Na szczególną uwagę zasługuje no-floating-promises: obietnica, na którą agent zapomniał dać await, staje się nieobsłużonym odrzuceniem, a Node.js domyślnie kończy proces przy nieobsłużonych odrzuceniach od wersji 15. Mocniejszy dowód, że same testy są dobre, opisuje strona o testach mutacyjnych i sile wyroczni.
Pięć pierwszych bramek uruchamiaj w CI przy każdym pull requeście; plik workflow znajdziesz we wzorcach pipeline’ów CI/CD. Inżynier odpowiedzialny za usługę zatwierdza trzy rzeczy: listy przypadków testowych, zieloną bramkę i wynik testu obciążeniowego. Ludzka lektura trafia do fragmentów oznaczonych przez agenta recenzującego oraz do kodu, który dotyka uwierzytelniania, pieniędzy lub transakcji. Podział tej pracy w zespole opisuje recenzja PR z agentem.
Gdy Node.js napisany przez agenta psuje się na produkcji
Dział zatytułowany „Gdy Node.js napisany przez agenta psuje się na produkcji”Każda z poniższych awarii przechodzi zestaw testów happy path. Każda ma objaw, który wykryjesz, i sposób naprawy, który zastosujesz.
- Nadsprzedaż albo podwójne przetwarzanie pod obciążeniem. Objaw: ujemny stan magazynu, zduplikowane zamówienia lub e-maile po skoku ruchu. Przyczyna: logika „odczytaj, a potem zapisz” poza jedną atomową instrukcją albo nieidempotentne zadanie, które zostało ponowione. Naprawa: dodaj współbieżny test Testcontainers z przepisu o Prisma, a potem użyj promptu: „Find every place that reads a value, decides in JavaScript, and writes it back. Replace each with a conditional update or a row lock, and add a concurrent test for each.”
- Wyczerpanie połączeń. Objaw: żądania wiszą, a potem kończą się timeoutem, choć CPU bazy jest niskie. Przyczyna:
new PrismaClient()na żądanie albo na moduł, często dodane, gdy agent tworzy nowy plik. Naprawa:grep -rn "new PrismaClient" src/musi zwracać jedną linię. Sam grep kończy się kodem 0 w obu przypadkach, więc testem musi być liczba linii: dodaj doscriptswpis"check:prisma": "test $(grep -rn 'new PrismaClient' src/ | wc -l) -eq 1"i dopisz&& npm run check:prismadocheck, żeby bramka odrzucała drugiego klienta. - Idiomy Expressa 4 w aplikacji na Expressie 5. Objaw: serwer nie startuje z błędem
path-to-regexp„Missing parameter name” albo wrappercatchAsyncukrywa błąd. Przyczyna: dane treningowe zdominowane przez Express 4. Naprawa: użyj promptu: „Migrate this codebase to Express 5 idioms: name every wildcard route (/*splat), delete catchAsync and express-async-errors, and change no behaviour. Done means npm run check passes.” - Wszyscy naraz dostają limit. Objaw: skok odpowiedzi 429 u wszystkich użytkowników albo błąd walidacji express-rate-limit dotyczący
X-Forwarded-For. Przyczyna: braktrust proxylub wartość niezgodna z liczbą proxy, więc wszyscy klienci dzielą adres IP load balancera. Naprawa: ustawtrust proxyna rzeczywistą liczbę przeskoków i sprawdź w teście, żereq.ipto adres klienta, gdy ustawiony jestX-Forwarded-For. - Instalacja psuje się na tagach wersji. Objaw:
npm installkończy się błędemERESOLVE, botypescript-eslint8.70.1 deklarujetypescript<6.1.0, atypescript@latestto 7.0.2, albo wynikprisma generateprzestaje pasować do klienta, bo CLI pochodzi z release candidate Prisma 8. Naprawa: przypnij oba pakiety do dokładnych wersji wpackage.json, zacommituj lockfile i zapisz wAGENTS.md, że agent nie zmienia przypiętych wersji bez pytania. - Agent osłabia test, żeby dojść do zielonego wyniku. Objaw: poluzowana asercja, usunięty przypadek albo dodane
.skipw tym samym diffie co poprawka. Naprawa: przywróć plik testu, powtórz regułę zAGENTS.mdi skonfiguruj CI tak, żeby odrzucał pull request zmieniający istniejący*.test.tsbez etykietytest-change.
Dokąd dalej z usługami Node.js
Dział zatytułowany „Dokąd dalej z usługami Node.js”- Jeśli repozytorium nie jest jeszcze gotowe na agenta, zacznij od tego: kod gotowy na agenta.
- Zaprojektuj kontrakt API przed handlerami: wzorce tworzenia API.
- Utwardź warstwę danych: dobre praktyki ORM i wzorce migracji baz danych.
- Wdróż usługę: wzorce Dockera i wzorce pipeline’ów CI/CD.
- Zdecyduj, co agent może uruchamiać bez nadzoru: uprawnienia i sandboxing.
- Porównaj z innym stosem backendowym: przepisy na Pythona albo wróć do przeglądu przepisów backendowych.
Czy ten artykuł Ci pomógł?
Jedno kliknięcie, bez logowania.
Co z tym zrobisz?
Jak się czytało?
Co przeszkadzało? Możesz zaznaczyć kilka
Twoja rola?
Dzięki. Czytam każdą odpowiedź. Michał Jaskólski
Pomógł Ci ten artykuł?
Każde to jedno kliknięcie. Zamknij, kiedy chcesz.
bez logowania