Ralph, pętla autonomicznego programowania z agentem
Ralph to nazwa techniki, która sprowadza się do jednego pomysłu: uruchamiaj agenta z tym samym poleceniem w kółko, aż zadanie zostanie skończone. Postęp gromadzi się w plikach i w historii repozytorium, a nie w pamięci rozmowy, dzięki czemu agent może pracować dłużej, niż pozwala na to okno kontekstu.
Skąd to pochodzi i co się kryje pod tą nazwą
Zacznę od dwóch sprostowań, bo wcześniejsza wersja tego tekstu podawała rzeczy nieprawdziwe, a krążą one także poza nim.
Po pierwsze, nazwa nie ma nic wspólnego z odpoczywaniem podczas pracy agenta. Pochodzi od Ralpha Wigguma z Simpsonów i odnosi się do uporu połączonego z brakiem zniechęcenia: robić to samo raz po raz, aż wyjdzie. Technikę opisał Geoffrey Huntley i to jego określenie przyjęło się w branży.
Po drugie, projekt o tej nazwie nie należy do Anthropic. Adres w domenie anthropics zwraca błąd, mimo że bywa podawany w materiałach o tym narzędziu. Repozytorium, o które chodzi, to frankbria/ralph-claude-code, napisane w powłoce systemowej, na licencji MIT, z ponad dziewięcioma tysiącami gwiazdek. Anthropic wydał natomiast własną wtyczkę realizującą tę samą ideę, dostępną w repozytorium Claude Code, a w samym narzędziu pojawiły się polecenia robiące to samo w sposób wspierany.
Warto znać ten podział, bo od niego zależy, co instalujesz. Technika jest publiczna i można ją zaimplementować w kilkunastu linijkach skryptu. Istnieje kilka niezależnych projektów robiących to samo z różnymi dodatkami, a od pewnego czasu istnieje też wersja wspierana przez producenta narzędzia.
Praktyczna kolejność wyboru wygląda więc tak. Zacznij od wersji wbudowanej w narzędzie, bo jest utrzymywana razem z nim i nie wymaga instalowania niczego. Jeśli okaże się za mało elastyczna, napisz własną pętlę, bo to naprawdę kilkanaście linijek i pełna kontrola nad warunkiem zakończenia. Po projekt społecznościowy sięgnij wtedy, gdy potrzebujesz konkretnych dodatków, których nie chcesz pisać sam, na przykład rozbudowanego wykrywania momentu wyjścia albo powiadomień.
Skąd wziął się rozgłos
Warto rozumieć kontekst, w którym ta technika stała się popularna, bo wpływa on na to, czego można się po niej spodziewać.
Rozgłos przyszedł z demonstracji, w których agent działający przez noc odtwarzał funkcjonalność istniejących produktów albo generował kilka repozytoriów naraz przy koszcie liczonym w setkach dolarów. Takie pokazy dobrze ilustrują skalę, ale słabo ilustrują użyteczność, bo odtworzenie czegoś, co już istnieje i ma opisane działanie, jest znacznie łatwiejsze niż zbudowanie czegoś nowego wobec niedookreślonych wymagań.
Realna wartość leży gdzie indziej i jest mniej efektowna, podobnie jak przy innych narzędziach agentowych w rodzaju goose. To zadania nudne, powtarzalne i weryfikowalne: migracja składni w setkach plików, uzupełnienie brakujących typów, dopisanie testów do istniejącego kodu, ujednolicenie konwencji. Praca, której nikt nie chce wykonywać ręcznie i przy której człowiek popełnia więcej błędów niż maszyna, bo się nudzi.
Warto też odnotować, że sama idea nie jest niczym nowym poza kontekstem agentów. Uruchamianie procesu w pętli aż do osiągnięcia stanu docelowego to wzorzec znany z systemów, które same doprowadzają konfigurację do zadanego kształtu. Nowe jest to, że w roli wykonawcy stoi model językowy, a stanem docelowym bywa coś, czego nie da się opisać deklaratywnie.
Jak to działa w praktyce
Najprostsza postać tej techniki to pętla w powłoce systemowej, która w każdym obrocie podaje agentowi ten sam plik z poleceniem. Agent czyta stan projektu, wykonuje kolejny krok, zapisuje zmiany i kończy. Pętla uruchamia go ponownie, a on znów czyta stan, tym razem już zmieniony przez siebie.
Kluczowa jest tu obserwacja, dlaczego to w ogóle działa. Agent nie pamięta poprzedniego obrotu, ale nie musi, bo cały stan leży w repozytorium: kod, testy, notatki, lista rzeczy do zrobienia. Pamięć zostaje przeniesiona z kontekstu rozmowy do systemu plików, a to jest zasób, który się nie kończy.
Nowsze implementacje działają inaczej i sprytniej. Zamiast uruchamiać proces od nowa, przechwytują moment, w którym agent chce zakończyć pracę, blokują to zakończenie i podają mu polecenie z powrotem. Pętla dzieje się wtedy wewnątrz jednej sesji, co oszczędza czas na ponownym wczytywaniu kontekstu projektu.
Warunek zakończenia jest tu najtrudniejszą częścią i to on odróżnia implementacje. Naiwna pętla kręci się w nieskończoność, więc potrzebny jest sposób rozpoznania, że zadanie jest gotowe: przechodzące testy, pusta lista zadań, wyraźna deklaracja agenta. Projekt, o którym mowa, reklamuje się właśnie wykrywaniem momentu wyjścia i to jest jego główna wartość dodana wobec pętli napisanej samodzielnie.
Co dokładnie uruchamiasz
Pierwsze nieporozumienie dotyczy sposobu wydawania polecenia. Ralph nie przyjmuje treści zadania jako argumentu wywołania. Czyta ją z pliku .ralph/PROMPT.md w katalogu projektu, a listę rzeczy do zrobienia z .ralph/fix_plan.md, więc samo uruchomienie wygląda ubogo i tak ma być.
cd moj-projekt
ralph-enable # kreator wykrywa typ projektu i tworzy pliki Ralpha
ralph --monitor # petla razem z podgladem w tmuksieObrót pętli ma pięć kroków: wczytanie instrukcji z PROMPT.md, uruchomienie Claude Code z bieżącym kontekstem, zapisanie postępu w liście zadań i logach, sprawdzenie warunku wyjścia i powrót na początek.
Warunek wyjścia jest podwójny i to jest sedno tego projektu. Do zakończenia potrzeba dwóch rzeczy naraz: co najmniej dwóch sygnałów ukończenia rozpoznanych w treści odpowiedzi oraz jawnego EXIT_SIGNAL: true w bloku statusu wypisanym przez agenta. Sam entuzjazm w rodzaju „faza gotowa, przechodzę dalej" pętli nie zatrzyma.
Pozostałe wyjścia to odhaczenie wszystkich pozycji w fix_plan.md, zbyt wiele obrotów zajętych wyłącznie testami oraz osiągnięcie pięciogodzinnego limitu Claude. Pozycje wpisane pod nagłówkiem Optional, Future albo Nice to Have nie blokują zakończenia, co rozwiązuje zakleszczenie, w którym agent uznaje coś za nieobowiązkowe, a pętla czeka na odhaczenie.
Instalacja
Wymagania są uniksowe, bo to zestaw skryptów powłoki: Bash w wersji 4.0 lub nowszej, zainstalowany Claude Code, jq do czytania statusu, git, tmux do podglądu i polecenie timeout z GNU coreutils, które na macOS trzeba doinstalować osobno.
git clone https://github.com/frankbria/ralph-claude-code.git
cd ralph-claude-code
./install.shInstalacja dokłada do ścieżki polecenia ralph, ralph-monitor, ralph-setup, ralph-import, ralph-queue, ralph-migrate, ralph-enable i ralph-enable-ci. Robisz to raz na maszynę, potem sklonowany katalog można skasować, a do usunięcia całości służy uninstall.sh.
Jednej drogi tu nie ma: paczki o tej nazwie nie znajdziesz w rejestrze npm, więc npm install -g nie zadziała, podobnie jak wciągnięcie tego projektu jako zależności do własnego kodu. Wersja z chwili pisania to 0.11.5, czyli wciąż przed pierwszym wydaniem stabilnym.
Konfiguracja i limity
Ustawienia projektu leżą w pliku .ralphrc, który jest zestawem zmiennych powłoki, a nie dokumentem JSON.
PROJECT_NAME="moj-projekt"
CLAUDE_CODE_CMD="claude"
MAX_CALLS_PER_HOUR=100
MAX_TOKENS_PER_HOUR=0
CLAUDE_TIMEOUT_MINUTES=15
ALLOWED_TOOLS="Write,Read,Edit,Bash(git *),Bash(npm *),Bash(pytest)"
SESSION_CONTINUITY=true
SESSION_EXPIRY_HOURS=24
CB_NO_PROGRESS_THRESHOLD=3
CB_SAME_ERROR_THRESHOLD=5Limity są dwa i działają niezależnie, a oba zerują się co godzinę. Pierwszy liczy wywołania i domyślnie stoi na stu. Drugi liczy tokeny i domyślnie jest wyłączony, bo zero oznacza brak limitu. To ten drugi pilnuje rachunku, bo pojedyncze wywołanie potrafi zużyć ponad sto tysięcy tokenów, więc limit liczony w wywołaniach mówi o koszcie niewiele.
Granicę uprawnień wyznacza ALLOWED_TOOLS, czyli lista narzędzi przekazywana do Claude Code. Nie ma tu osobnych list dozwolonych i zakazanych ścieżek, więc zakres zawęża się przez tę listę oraz przez to, w jakim katalogu pętla wystartuje.
Hamulce
Bezpiecznik odcina pętlę po trzech obrotach bez postępu albo po pięciu z tym samym błędem. Po odcięciu przechodzi w stan otwarty, po trzydziestu minutach próbuje wrócić przez stan pośredni, a --circuit-status i --reset-circuit pozwalają zajrzeć do środka i wymusić powrót ręcznie.
Osobno obsłużony jest pięciogodzinny limit Claude. Po jego wykryciu pętla pyta, czy odczekać godzinę z odliczaniem, czy wyjść, a w trybie bez człowieka przy klawiaturze po trzydziestu sekundach sama wybiera czekanie.
Kopia bezpieczeństwa nie jest domyślna i to ustawienie włącz od razu. Przełącznik --backup zakłada gałąź kopii przed każdym obrotem, a --rollback przywraca z niej stan. Bez tego przełącznika nic się samo nie cofa, także po nieudanych testach.
ralph --calls 50 --timeout 30 --backup --notify
ralph --dry-run
ralph --statusSkąd bierze zadania
Polecenie ralph-import zamienia istniejący dokument wymagań na strukturę Ralpha, przyjmując pliki markdown, tekstowe, JSON, dokumenty Worda i PDF-y. To samo polecenie pobiera zgłoszenie z GitHuba przez --github-issue, a przy filtrach po etykiecie, tytule czy osobie przypisanej przełącznik --select rozstrzyga, które z pasujących wziąć.
Przy większej liczbie zgłoszeń jest kolejka. ralph-queue buduje trwałą listę zadań zapisaną w .ralph/queue.json, a ralph --process-queue przerabia ją po kolei i przeżywa restart. Pętla potrafi też zamknąć obieg po stronie GitHuba: komentować postęp co kilka obrotów, otworzyć żądanie scalenia, zamknąć zgłoszenie i założyć osobne na znaczniki TODO zostawione w kodzie.
Jest też uruchomienie w izolacji, przydatne przy szerokich uprawnieniach. Przełącznik --sandbox docker zamyka pętlę w kontenerze z limitami zasobów i polityką sieci, a --sandbox e2b wynosi ją do piaskownicy w chmurze z własnym limitem kosztu.
Podgląd i miary
Podgląd na żywo daje ralph --monitor, który sam zakłada sesję tmuksa, albo ralph-monitor w drugim terminalu przy pętli puszczonej osobno. Stan do odczytu maszynowego leży w .ralph/status.json, a logi w .ralph/logs/, przy czym główny plik obraca się po dziesięciu megabajtach i trzyma cztery archiwa.
Przełącznik --live wypisuje wyjście agenta na bieżąco i dubluje je do .ralph/live.log, co jest najprostszym sposobem sprawdzenia, czy pętla pracuje, czy krąży w miejscu. Zestawienie po fakcie robi ralph-stats, czytając zapis miar z .ralph/logs/metrics.jsonl.
Ralph kontra alternatywy
| Cecha | Ralph | Claude Code | Devin | GitHub Copilot |
|---|---|---|---|---|
| Sposób pracy | pętla bez nadzoru na Twojej maszynie | sesja prowadzona przez człowieka | agent w chmurze dostawcy | podpowiedzi i agent w edytorze |
| Warunek zakończenia | podwójny: sygnały plus EXIT_SIGNAL | koniec odpowiedzi | koniec zadania | brak, praca ciągła |
| Cofanie zmian | gałąź kopii po włączeniu --backup | ręcznie w gicie | ręcznie w gicie | ręcznie w gicie |
| Hamulec zużycia | 100 wywołań na godzinę, opcjonalny limit tokenów | limity abonamentu | przydział w planie | kredyty w planie |
| Licencja | MIT | zamknięta | zamknięta | zamknięta |
| Koszt | zero, płacisz za Claude Code | abonament Claude albo rozliczenie przez API | 0, 20 i 200 USD miesięcznie, zespół 80 USD plus 40 USD za miejsce | 0, 10, 39 i 100 USD miesięcznie, firmowo 19 i 39 USD za użytkownika |
Rozwiązywanie problemów
Pętla, która nie chce się skończyć, prawie zawsze czeka na jedną z dwóch rzeczy: nieodhaczoną pozycję w fix_plan.md albo brak jawnego sygnału wyjścia od agenta. Pierwsze naprawia przeniesienie pozycji pod nagłówek nieobowiązkowy, drugie dopisanie do promptu wprost, kiedy ten sygnał ma paść.
Pętla, która kończy się za wcześnie, zwykle trafiła na otwarty bezpiecznik. --circuit-status pokazuje stan i powód, --reset-circuit przywraca pracę, a --auto-reset-circuit robi to przy każdym starcie, co ma sens tylko przy uruchomieniach bez nadzoru.
Reszta to strojenie: --calls przy uderzaniu w limit godzinowy, --timeout przy zadaniach dłuższych niż domyślne piętnaście minut, --verbose i --live przy niejasnym przebiegu, --dry-run do przejścia obrotu bez płatnych wywołań.
FAQ
Czy mogę zostawić Ralpha bez nadzoru?
Tak, po ustawieniu czterech rzeczy: limitu tokenów na godzinę zamiast samego limitu wywołań, listy ALLOWED_TOOLS zawężonej do tego, czego zadanie faktycznie wymaga, przełącznika --backup i osobnej gałęzi. Powiadomienia z --notify dokładają sygnał, gdy pętla o coś pyta.
Ile kosztuje uruchomienie?
Sam projekt jest darmowy, płacisz za pracę Claude Code. Rachunek zależy od liczby obrotów i rozmiaru kontekstu wysyłanego w każdym z nich, a ponieważ jedno wywołanie potrafi zużyć ponad sto tysięcy tokenów, jedyną wiarygodną prognozą jest pomiar własnego zadania na kilku obrotach.
Czy to bezpieczne przy kodzie produkcyjnym?
Przy zachowaniu ostrożności. Osobna gałąź, przegląd przed scaleniem i wąska lista narzędzi to minimum, a przy szerokich uprawnieniach warto puścić pętlę w kontenerze przez --sandbox docker, żeby polecenia nie sięgnęły poza projekt.
Jak radzi sobie z dużymi projektami?
Kontekst bierze z plików, a nie z pamięci rozmowy, więc rozmiar repozytorium ogranicza go mniej niż długość pojedynczego kroku. Ciągłość sesji jest domyślnie włączona i wygasa po dobie, a --no-continue uruchamia każdy obrót od zera, co bywa lepsze przy zadaniach niezależnych od siebie.
Czy istnieje wersja wspierana przez producenta?
Tak. W repozytorium Claude Code leży wtyczka ralph-wiggum, która realizuje tę samą ideę przez hak zatrzymania: blokuje wyjście z sesji i podaje ten sam prompt z powrotem. Uruchamiasz ją poleceniem /ralph-loop z limitem obrotów i frazą kończącą, a przerywasz przez /cancel-ralph.
Kiedy pętla działa, a kiedy pali pieniądze
To najważniejsza sekcja tego tekstu, bo różnica między jednym a drugim scenariuszem wynika z kilku warunków, które da się sprawdzić z góry.
Pętla działa, gdy istnieje automatyczny sposób odróżnienia sukcesu od porażki. Zestaw testów, kompilator, sprawdzanie typów, walidator. Agent może wtedy sprawdzić własną pracę i poprawić się bez człowieka, a każdy obrót zbliża do celu. Klasyczny przypadek to migracja obejmująca setki plików: reguła jest jednoznaczna, wynik weryfikowalny, a nudy tyle, że nikt nie chce tego robić ręcznie.
Pętla pali pieniądze, gdy takiego sprawdzenia nie ma. Zadanie w rodzaju „popraw wygląd strony" nie ma warunku zakończenia, więc agent będzie kręcił się w kółko, wprowadzając zmiany, cofając je i wprowadzając ponownie. Koszt rośnie liniowo z czasem, a postęp nie.
Drugi warunek to rozmiar kroku. Zadanie musi dać się podzielić na kawałki, z których każdy da się skończyć w jednym obrocie. Jeśli pojedynczy krok nie mieści się w kontekście, agent nie skończy go nigdy, tylko za każdym razem zacznie od nowa i porzuci w połowie.
Trzeci to stan zapisany poza rozmową, najlepiej w formacie, który agent rozpozna, na przykład jako umiejętność zgodną ze standardem Agent Skills. Lista rzeczy do zrobienia w pliku, notatki z tego, co już sprawdzono, wpisy w historii repozytorium. Bez tego kolejny obrót powtórzy pracę poprzedniego, bo agent nie ma skąd wiedzieć, że coś już zrobił.
Praktyczna rada przed uruchomieniem czegokolwiek na noc: puść pętlę na pięć obrotów i przeczytaj, co powstało. Jeśli po pięciu obrotach widać postęp w jednym kierunku, można zwiększyć limit. Jeśli widać krążenie wokół tego samego miejsca, żadna liczba obrotów tego nie naprawi.
Koszty i zabezpieczenia
Rachunek przy tej technice rośnie inaczej, niż podpowiada intuicja, więc warto rozumieć mechanizm.
Każdy obrót wysyła do modelu narastający kontekst: stan projektu, treść plików, wyniki poleceń. Przy dwudziestu obrotach koszt nie jest dwudziestokrotnością pierwszego, tylko rośnie szybciej, bo za każdym razem wysyłane jest więcej. Zadanie, które w rozmowie kosztowałoby kilkadziesiąt centów, w pętli potrafi kosztować kilkadziesiąt dolarów.
Twardy limit obrotów jest więc zabezpieczeniem koniecznym, a nie opcjonalnym. Warto też ustawić limit czasu i sprawdzać zużycie po stronie dostawcy w trakcie, a nie po fakcie.
Drugie zabezpieczenie dotyczy zakresu zmian. Agent pracujący bez nadzoru na gałęzi głównej to zły pomysł niezależnie od tego, jak dobre są jego decyzje. Osobna gałąź, przegląd zmian przed scaleniem i zakaz dotykania konfiguracji wdrożeniowej to minimum, które pozwala spać spokojnie.
Trzecie to granice tego, co agent może uruchomić. Pętla wykonująca polecenia bez ograniczeń może usunąć katalog, wypchnąć zmiany albo wywołać zewnętrzną usługę. Warto zawęzić uprawnienia do tego, czego zadanie faktycznie wymaga, i traktować to tak samo jak uprawnienia w Claude Code przy zwykłej pracy.
Czwarte, najczęściej pomijane, to jakość wyniku. Kod napisany w pętli bez nadzoru bywa poprawny formalnie i zły strukturalnie: powielone funkcje, obejścia zamiast poprawek, testy dopasowane do implementacji zamiast do wymagań. Przegląd po zakończeniu jest tu obowiązkowy i zwykle zajmuje więcej czasu, niż zakłada osoba uruchamiająca pętlę pierwszy raz.
Opis oryginalnej techniki znajdziesz w artykule Geoffreya Huntleya, a kod tej implementacji w repozytorium projektu.