# ZapiszPrzepis: jak używam AI w projektach

Aplikacja zbudowana i wdrożona od zera z AI — projekt zaliczeniowy 10xDevs 3.0 zdany w pierwszym terminie z wyróżnieniem Best Project. Jak wygląda ten proces.

**Canonical:** https://spoko.space/pl/blog/zapiszprzepis-aplikacja-ai-first/  
**Language:** pl  
**Published:** 2026-08-23  
**Updated:** 2026-09-21  
**Tags:** AI, Next.js, React, TypeScript, Supabase, PWA, Cloudflare  
**Category:** AI

---
**AI jest częścią mojej codziennej pracy od dawna — ale deklaracja niewiele znaczy, więc pokażę projekt.** [ZapiszPrzepis](https://zapiszprzepis.pl) zbudowałem od zera i wdrożyłem na produkcję: aplikacja działa, kod jest publiczny, a jako praca zaliczeniowa kursu **10xDevs 3.0** przeszła w pierwszym terminie i dostała wyróżnienie **Best Project**.

To wciąż wersja testowa: korzysta z niej na co dzień kilka bliskich mi osób, a rejestracja nie jest otwarta.

Ten wpis jest o tym, jak wygląda ten proces w praktyce — bo to jest rzecz, którą wnoszę do każdego projektu klienckiego, a nie tylko do własnych zabawek.

## Co robi aplikacja {#co-robi-aplikacja}

Przepisy krążą dziś jako posty, Reelsy i filmy. Odruch jest jeden: zapisać zakładką albo funkcją „Zapisz" w danej platformie. Problem w tym, że **wszystkie te sposoby przechowują odnośnik, a nie treść**.

Po kilku miesiącach spora część zapisanych linków przestaje działać. Autor kasuje Reela, grupa kulinarna znika, blog gaśnie, post idzie w prywatne. Zapisana kolekcja zamienia się w listę błędów 404 — i dowiadujesz się o tym dopiero wtedy, gdy chcesz z niej skorzystać.

ZapiszPrzepis działa odwrotnie — **archive-first**. Z każdego linku robi trwałą kopię: tytuł, składniki, kroki i zdjęcie lądują w bazie użytkownika. Adres źródła zapisuje się razem z nimi, więc do oryginału wracasz jednym kliknięciem — dopóki istnieje. Kiedy zniknie, nie tracisz nic poza tym przyciskiem.

Ta kopia nie jest zrzutem strony. **Tekst układa model OpenAI** — zostawia składniki i kroki, a wycina nawigację, reklamy i długi wstęp, przez który trzeba się przewijać do właściwego przepisu. Angielskie źródła tłumaczy przy okazji na polski.

Projektowałem dla osoby nietechnicznej — takiej, która nie wpisuje ręcznie składników, nie wypełnia formularzy i nie zarządza folderami ani tagami. To ograniczenie okazało się najbardziej użytecznym filtrem w całym projekcie: natychmiast wykluczyło większość „oczywistych" funkcji.

## Jak to działa {#jak-to-działa}

Cała ścieżka wejścia to jeden gest. Aplikacja rejestruje się jako **Web Share Target**, czyli pojawia się na systemowej liście „Udostępnij" obok Messengera i WhatsAppa. Użytkownik wysyła do niej link i nie robi nic więcej.

![Ekran główny ZapiszPrzepis na telefonie](https://spoko.space/_spoko/zapiszprzepis-mobile.CQoWwiQ5.webp)

Dalej wszystko dzieje się w tle:

**Co dzieje się po udostępnieniu linku**

1. **Rozpoznanie źródła** — Inaczej traktowany jest wpis na blogu, inaczej film, inaczej post w social mediach.
2. **Pobranie treści** — Przez Firecrawl, a dla blogów na Bloggerze przez ich feed JSON — deterministyczny wynik zamiast zgadywania ze scrapowanego HTML-a.
3. **Ekstrakcja** — Model OpenAI (gpt-4o-mini) wyciąga tytuł, składniki, kroki i kategorię, a źródła anglojęzyczne tłumaczy na polski.
4. **Archiwizacja zdjęcia** — Obrazek ląduje we własnym storage, żeby nie zniknął razem ze źródłem.
5. **Zapis** — Gotowy przepis trafia do bazy z izolacją per użytkownik.

Ekstrakcja potrafi trwać kilkanaście sekund i bywa zawodna, więc nie działa w cyklu żądania. Wrzuca zdarzenie do **Inngest**, który zajmuje się kolejkowaniem i ponawianiem. Użytkownik dostaje odpowiedź natychmiast, a przepis dopisuje się chwilę później.

Później doszła jeszcze wyszukiwarka przepisów w internecie z wejściem głosowym — bo samo archiwizowanie rozwiązywało tylko połowę problemu. Druga połowa to znalezienie czegoś, czego jeszcze nie masz.

## Stack i dlaczego akurat taki {#stack-i-dlaczego-akurat-taki}

| Warstwa | Wybór i powód |
| --- | --- |
| Framework | **Next.js 15** (App Router) — Server Actions, czyli formularze bez budowania osobnego API |
| Baza i auth | **Supabase** — Postgres z RLS i logowanie magic linkiem, bez haseł |
| Zadania w tle | **Inngest** — ponawianie i kolejkowanie bez utrzymywania własnej infrastruktury |
| Ekstrakcja | **Firecrawl + OpenAI** (gpt-4o-mini) — pobranie treści i wyciągnięcie z niej struktury |
| Hosting | **Cloudflare Workers** (OpenNext) — reszta projektu już tam była |
| Warstwa klienta | **PWA + Web Share Target** — jedyny sposób na wejście jednym gestem |

Jedna decyzja zdeterminowała pozostałe: **hosting na Cloudflare Workers oznacza brak Node.js API w runtime**. Każda integracja musiała działać przez zwykły `fetch`. To wykluczyło kilka bibliotek, zanim napisałem pierwszą linijkę — i dobrze, bo odkrycie tego w trakcie wdrożenia kosztowałoby jeden z niewielu dostępnych dni.

Wybór między Next.js a lżejszymi generatorami rozbieram dokładniej w [porównaniu frameworków do aplikacji webowych](https://spoko.space/pl/blog/frameworki-aplikacje-webowe-2026/) — tutaj przeważyła potrzeba dynamicznego stanu po stronie serwera.

## Jak wygląda u mnie praca z AI {#jak-wygląda-u-mnie-praca-z-ai}

Sposób, w jaki pracuję z AI, przenosi się na projekty klienckie jeden do jednego.

### Kontekst projektu jako pamięć długoterminowa {#kontekst-projektu-jako-pamięć-długoterminowa}

W repozytorium leży katalog z opisem wymagań, roadmapą, planami poszczególnych zmian i rejestrem wyciągniętych wniosków. To nie jest dokumentacja pisana dla ludzi po fakcie — to **materiał wejściowy dla modelu przed każdą zmianą**.

Różnica jest odczuwalna. Model bez kontekstu generuje kod, który wygląda rozsądnie, ale ignoruje decyzje podjęte trzy dni wcześniej. Model z wymaganiami i planem pod ręką proponuje rozwiązania spójne z tym, co już istnieje — i sam zwraca uwagę, gdy prosisz go o coś, co przeczy wcześniejszemu ustaleniu.

Dla Ciebie jako klienta ma to prozaiczny skutek: te dokumenty zostają. Nie kupujesz czarnej skrzynki, tylko projekt, w którym widać, co i dlaczego zostało zdecydowane.

### Plan przed kodem, zawsze {#plan-przed-kodem-zawsze}

Każda większa zmiana zaczyna się od dokumentu z rozpisanymi fazami, kryteriami akceptacji i listą ryzyk — a nie od polecenia „dodaj wyszukiwarkę". Dopiero zatwierdzony plan idzie do implementacji.

Brzmi jak biurokracja. W praktyce to właśnie ten krok skraca całość, bo eliminuje najdroższą kategorię błędów: zbudowanie czegoś działającego, co rozwiązuje niewłaściwy problem. Wyszukiwarka z lipca to dobry przykład — miała budżet tygodnia, a powstała w trzy dni, bo plan był gotowy, zanim poszła pierwsza linijka.

### Testy tam, gdzie logika jest podstępna {#testy-tam-gdzie-logika-jest-podstępna}

Projekt ma **ponad 70 testów jednostkowych** i zestaw testów E2E w Playwrighcie. Nie są rozłożone równomiernie i to jest celowe — stoją tam, gdzie najłatwiej o cichą pomyłkę: rozpoznawanie typu źródła, redakcja składników, ocena czy pobrana treść w ogóle nadaje się na przepis, parsowanie identyfikatorów filmów.

O tym, jak wpinam AI w testy E2E, pisałem szerzej w [przewodniku po testach E2E z Playwrightem](https://spoko.space/pl/blog/testy-e2e-ai-playwright-przewodnik/).

### Review jako bramka, nie formalność {#review-jako-bramka-nie-formalność}

Kod, przy którym pomagał model, rzadko myli się w sposób oczywisty. Myli się tam, gdzie coś **działa, ale opiera się na błędnym założeniu**: wyrażenie regularne, które wygląda na szczelne. Dopasowanie, które działa dla dzisiejszych danych wejściowych. Uprawnienie nadane „na wszelki wypadek".

To są dokładnie te rzeczy, które przechodzą przez kompilator i przez testy. Dlatego review nie jest u mnie ostatnim punktem listy, tylko miejscem, w którym spędzam nieproporcjonalnie dużo czasu — i im więcej kodu pisze model, tym bardziej to się opłaca. Jak to wygląda, gdy review jest w całości automatyczne, a kod pisze wyłącznie model, opisałem w tekście [co się dzieje, gdy kod pisze wyłącznie AI](https://spoko.space/pl/blog/gdy-kod-pisze-wylacznie-ai/).

## Co z tego ma Twój projekt {#co-z-tego-ma-twój-projekt}

Konkretnie, bez ogólników:

- **Wymagania spisane przed kodem.** Wiesz, co powstaje i po czym poznamy, że jest gotowe.
- **Szybsze dojście do działającej wersji.** AI skraca pisanie, więc więcej czasu zostaje na to, co realnie decyduje o wyniku.
- **Testy w miejscach, które psują się po cichu.** Nie po to, żeby mieć ładny wskaźnik pokrycia, tylko żeby regresja nie dojechała do produkcji.
- **Kod i dokumentacja u Ciebie.** Repozytorium, decyzje i historia zmian są Twoje — możesz z tym pójść dalej, ze mną albo bez.
- **Jedna osoba odpowiedzialna za całość.** Od architektury, przez wdrożenie, po wsparcie po starcie.

## Podsumowanie {#podsumowanie}

- **AI nie zastępuje myślenia, tylko skraca pisanie.** Cała różnica robi się na etapie, na którym ustalamy, co w ogóle budujemy.
- **Kontekst projektu w repozytorium jest infrastrukturą**, nie dokumentacją — i zostaje u klienta.
- **Review i testy zyskują na znaczeniu, im więcej kodu pisze model**, bo błędy przesuwają się z „nie kompiluje się" w stronę „działa, ale na błędnym założeniu".
- **Ograniczenia platformy warto poznać przed pierwszą linijką**, a nie w trakcie wdrożenia.

ZapiszPrzepis powstał w ramach [10xDevs 3.0](https://10xdevs.pl/), został zaliczony w pierwszym terminie z wyróżnieniem Best Project — [certyfikat do weryfikacji](https://credsverse.com/credentials/d9f99ad8-ed75-4c81-a8ae-2a014d385725) — a kod jest publiczny na [GitHubie](https://github.com/spokospace/zapiszprzepis).

## Najczęściej zadawane pytania {#faq}

### Czy używanie AI oznacza gorszy kod? {#faq-czy-używanie-ai-oznacza-gorszy-kod}

Zależy wyłącznie od procesu. Model bez kontekstu generuje kod, który wygląda sensownie i nie trzyma się wcześniejszych decyzji. Z opisem wymagań i planem pod ręką proponuje rozwiązania spójne z resztą systemu. Dlatego u mnie plan powstaje przed kodem, a każda zmiana przechodzi przez review.

### Czy dzięki AI projekt jest tańszy albo szybszy? {#faq-czy-dzięki-ai-projekt-jest-tańszy-albo-szybszy}

Szybszy bywa — AI skraca pisanie, nie skraca myślenia. Największa oszczędność nie bierze się z tempa generowania kodu, tylko z tego, że rozmowa o wymaganiach i plan wychodzą przed implementacją. Najdroższy błąd to zbudowanie czegoś działającego, co rozwiązuje niewłaściwy problem.

### Kto odpowiada za jakość kodu, który współtworzy AI? {#faq-kto-odpowiada-za-jakość-kodu-który-współtworzy-ai}

Ja. Model jest narzędziem, tak jak framework czy edytor — odpowiedzialność za to, co trafia na produkcję, zostaje po mojej stronie. W praktyce oznacza to testy w miejscach, gdzie łatwo o cichą pomyłkę, i review jako bramkę, a nie formalność.

### Czy dostanę kod i dokumentację projektu? {#faq-czy-dostanę-kod-i-dokumentację-projektu}

Tak. Repozytorium, opis wymagań i decyzje architektoniczne są Twoje. ZapiszPrzepis jest publiczny, więc możesz zobaczyć dokładnie, jak taki projekt wygląda w środku — razem z dokumentacją, testami i historią zmian.

### Czy mogę założyć konto w ZapiszPrzepis? {#faq-czy-mogę-założyć-konto-w-zapiszprzepis}

Na razie nie. To wersja testowa, z której korzysta na co dzień kilka bliskich mi osób, a rejestracja nie jest otwarta. Kod jest publiczny, więc możesz zobaczyć, jak aplikacja działa w środku — razem z dokumentacją i testami.

### Czym różni się podejście archive-first od zwykłych zakładek? {#faq-czym-różni-się-podejście-archive-first-od-zwykłych-zakładek}

Zakładka zapisuje <strong>odnośnik</strong> — działa tylko dopóki źródło istnieje. Archive-first zapisuje <strong>kopię treści</strong>: tytuł, składniki, kroki i zdjęcie lądują w Twojej bazie. Adres oryginału zostaje zapisany razem z nimi, więc wracasz do źródła jednym kliknięciem, a gdy post zniknie — przepis i tak zostaje.


## Źródła {#sources}

- [Next.js — dokumentacja App Router](https://nextjs.org/docs/app)
- [Supabase — Row Level Security](https://supabase.com/docs/guides/database/postgres/row-level-security) — Izolacja danych per użytkownik na poziomie bazy, nie aplikacji
- [Web Share Target API — MDN](https://developer.mozilla.org/en-US/docs/Web/Manifest/share_target)
- [OpenNext — adapter Cloudflare dla Next.js](https://opennext.js.org/cloudflare)
- [Inngest — dokumentacja](https://www.inngest.com/docs) — Kolejkowanie i ponawianie zadań asynchronicznych
