Identyfikatory korelacyjne end-to-end pokazują, jak stworzyć jeden ID we frontendzie, przekazać go przez API i umieścić w logach, żeby support mógł szybko śledzić problemy.

Support rzadko dostaje czyste zgłoszenie błędu. Użytkownik mówi: "Kliknąłem Zapłać i to się nie powiodło", ale to jedno kliknięcie może przejść przez przeglądarkę, gateway API, serwis płatności, bazę danych i zadanie w tle. Każdy element loguje swoją część historii w różnych momentach, na różnych maszynach. Bez wspólnej etykiety trudno ustalić, które linie logów należą do tej samej akcji.
Identyfikator korelacyjny to właśnie ta wspólna etykieta. To jeden ID przypisany do jednej akcji użytkownika (albo jednego logicznego workflowu) i przenoszony przez każde żądanie, retry i przeskok między serwisami. Przy prawdziwym pokryciu end-to-end możesz zacząć od zgłoszenia użytkownika i wyciągnąć pełny przebieg we wszystkich systemach.
Ludzie często mylą kilka podobnych ID. Oto klarowne rozróżnienie:
Dobry przykład zastosowania jest prosty: użytkownik zgłasza problem, prosisz go o identyfikator korelacyjny pokazany w UI (lub znaleziony w ekranie wsparcia), i każdy w zespole może znaleźć pełną historię w kilka minut. Widzisz żądanie frontendu, odpowiedź API, kroki backendu i wynik bazy danych — wszystko powiązane jednym ID.
Zanim zaczniesz generować ID, uzgodnij kilka zasad. Jeśli każdy zespół wybierze inny nagłówek lub pole w logu, support nadal będzie zgadywał.
Zacznij od jednej kanonicznej nazwy i używaj jej wszędzie. Częstym wyborem jest nagłówek HTTP, np. X-Correlation-Id, oraz strukturalne pole logu jak correlation_id. Wybierz jedno pisownię i jedną wielkość liter, udokumentuj to i upewnij się, że reverse proxy lub gateway nie zmieni ani nie usunie tego nagłówka.
Wybierz format, który łatwo wygenerować i bezpiecznie udostępnić w ticketach i czatach. UUIDy sprawdzają się dobrze, bo są unikalne i „nudne”. Trzymaj ID na tyle krótkie, by dało się je skopiować, ale nie tak krótkie, by ryzykować kolizje. Konsekwencja jest ważniejsza niż pomysłowość.
Zdecyduj także, gdzie ID musi się pojawiać, żeby ludzie mogli go używać. W praktyce oznacza to jego obecność w żądaniach, logach i komunikatach o błędach oraz możliwość wyszukiwania w narzędziu, z którego korzysta zespół.
Określ też, jak długo ma żyć jedno ID. Dobry domyślny czas to jedna akcja użytkownika, np. "kliknięto Zapłać" lub "zapisano profil". W dłuższych workflowach, które przechodzą przez serwisy i kolejki, trzymaj ten sam ID aż do zakończenia workflowu, a potem rozpocznij nowy dla następnej akcji. Unikaj "jednego ID dla całej sesji", bo wyszukiwania szybko staną się hałaśliwe.
Twarda zasada: nigdy nie umieszczaj w ID danych osobowych. Żadne e-maile, numery telefonów, identyfikatory użytkowników czy numery zamówień. Jeśli potrzebujesz kontekstu, loguj go w oddzielnych polach z odpowiednimi zasadami prywatności.
Najłatwiejsze miejsce na rozpoczęcie identyfikatora korelacyjnego to moment, gdy użytkownik zaczyna akcję, którą chcesz śledzić: kliknięcie "Zapisz", wysłanie formularza lub uruchomienie przepływu, który powoduje wiele żądań. Jeśli poczekasz, aż backend wygeneruje ID, często utracisz pierwszą część historii (błędy UI, retry, anulowane żądania).
Użyj losowego, unikalnego formatu. UUID v4 to częsty wybór, bo łatwo go wygenerować i ma niskie ryzyko kolizji. Trzymaj go jako wartość nieczytelną (opaque) — bez nazw użytkowników, e-maili czy znaczników czasu — żeby nie wyciekały dane osobowe w nagłówkach i logach.
Traktuj "workflow" jako jedną akcję użytkownika, która może wywołać wiele żądań: walidacja, upload, utworzenie rekordu, odświeżenie list. Utwórz jedno ID na początku workflowu i zachowaj je do momentu zakończenia (sukces, porażka lub anulowanie przez użytkownika). Prosty wzorzec to przechowywanie go w stanie komponentu lub lekkim kontekście żądania.
Jeśli użytkownik uruchomi tę samą akcję dwa razy, wygeneruj nowy identyfikator korelacyjny dla drugiej próby. Dzięki temu support odróżni "ten sam klik z retrypem" od "dwóch niezależnych zgłoszeń".
Dodaj ID do każdego wywołania API uruchomionego przez workflow, zwykle przez nagłówek taki jak X-Correlation-ID. Jeśli używasz wspólnego klienta API (wrapper fetch, instancja Axios itp.), przekaż ID raz, a klient niech wstrzykuje go do wszystkich wywołań.
// 1) when the user action starts
const correlationId = crypto.randomUUID(); // UUID v4 in modern browsers
// 2) pass it to every request in this workflow
await api.post('/orders', payload, {
headers: { 'X-Correlation-ID': correlationId }
});
await api.get('/orders/summary', {
headers: { 'X-Correlation-ID': correlationId }
});
Jeśli UI wykonuje zapytania w tle niezwiązane z akcją (polling, analytics, auto-refresh), nie używaj dla nich ID workflowu. Trzymaj identyfikatory korelacyjne skupione, żeby jedno ID opowiadało jedną historię.
Gdy już wygenerujesz identyfikator korelacyjny w przeglądarce, zadanie jest proste: musi on opuścić frontend w każdym żądaniu i dotrzeć niezmieniony na każde API boundary. To jest miejsce, w którym najczęściej coś się psuje, gdy zespoły dodają nowe endpointy, nowe klienty lub nowe middleware.
Najbezpieczniejszym domyślnym rozwiązaniem jest nagłówek HTTP w każdym wywołaniu (np. X-Correlation-Id). Nagłówki łatwo dodać w jednym miejscu (wrapper fetch, interceptor Axios, warstwa sieciowa w mobilnej aplikacji) i nie wymagają zmiany payloadów.
Jeśli masz żądania cross-origin, upewnij się, że API pozwala na ten nagłówek. W przeciwnym razie przeglądarka może go cicho zablokować i będziesz myślał, że go wysyłasz, a tak naprawdę nie.
Jeśli musisz umieścić ID w query stringu lub ciele żądania (niektóre narzędzia zewnętrzne lub uploady plików tego wymagają), trzymaj to spójne i udokumentowane. Wybierz jedno pole i używaj go wszędzie. Nie mieszaj correlationId, requestId i cid zależnie od endpointu.
Retry to kolejna pułapka. Retry powinien zachować ten sam identyfikator korelacyjny, jeżeli to wciąż ta sama akcja użytkownika. Przykład: użytkownik klika "Zapisz", sieć siada, klient retryuje POST. Support powinien zobaczyć jedną powiązaną ścieżkę, a nie trzy niezależne. Nowy klik (albo nowe zadanie background) powinno dostać nowy ID.
Dla WebSocketów dołączaj ID w kopercie wiadomości, a nie tylko w początkowym handshake. Jedne połączenie może przenosić wiele akcji użytkowników.
Jeśli chcesz szybkiego testu niezawodności, trzymaj to proste:
correlationId.Edge API (gateway, load balancer lub pierwszy serwis otrzymujący ruch) to miejsce, gdzie identyfikatory korelacyjne albo stają się wiarygodne, albo zamieniają się w zgadywanie. Traktuj ten punkt wejścia jako źródło prawdy.
Akceptuj przychodzący ID, jeśli klient go wysłał, ale nie zakładaj, że zawsze będzie obecny. Jeśli go brakuje, wygeneruj nowy od razu i używaj go przez resztę obsługi żądania. Dzięki temu system działa nawet wtedy, gdy niektóre klienty są starsze lub źle skonfigurowane.
Wykonuj lekką walidację, żeby złe wartości nie zanieczyszczały logów. Bądź przy tym permissywny: sprawdź długość i dozwolone znaki, ale unikaj ścisłych formatów, które odrzucą rzeczywisty ruch. Na przykład pozwól na 16–64 znaków oraz litery, cyfry, myślnik i podkreślenie. Jeśli wartość nie przejdzie walidacji, zastąp ją nowym ID i kontynuuj.
Uczyń ID widocznym dla klienta. Zawsze zwracaj go w nagłówkach odpowiedzi i dołączaj go do ciał błędów. W ten sposób użytkownik może go skopiować z UI, a agent wsparcia może poprosić o niego i znaleźć dokładny ślad w logach.
Praktyczna polityka edge wygląda tak:
X-Correlation-ID (lub wybrany nagłówek) z żądania.X-Correlation-ID do każdej odpowiedzi, włącznie z błędami.Przykład payloadu błędu (co support powinien widzieć w ticketach i zrzutach ekranu):
{
"error": {
"code": "PAYMENT_FAILED",
"message": "We could not confirm the payment.",
"correlation_id": "c3a8f2d1-9b24-4c61-8c4a-2a7c1b9c2f61"
}
}
Gdy żądanie trafi do backendu, traktuj identyfikator korelacyjny jako część kontekstu żądania, a nie coś, co trzymasz w zmiennej globalnej. Globalne stają się problemem, gdy obsługujesz dwa żądania na raz albo gdy asynchroniczna praca trwa po wysłaniu odpowiedzi.
Zasada skalująca się: każda funkcja, która może logować lub wywołać inny serwis, powinna otrzymać kontekst zawierający ID. W serwisach Go zwykle oznacza to przekazywanie context.Context przez handlery, logikę biznesową i kod klienta.
Gdy Serwis A wywołuje Serwis B, skopiuj ten sam ID do wychodzącego żądania. Nie generuj nowego w trakcie przepływu, chyba że zachowasz oryginał jako oddzielne pole (np. parent_correlation_id). Jeśli zmienisz ID, support straci pojedynczą nić łączącą historię.
Propagacja często jest pomijana w kilku przewidywalnych miejscach: zadania background wyzwalane podczas żądania, retry wewnątrz bibliotek klientów, webhooki wyzwalane później i wywołania fan-out. Każda wiadomość asynchroniczna (kolejka/zadanie) powinna nieść ID, a każdy mechanizm retry powinien go zachować.
Logi powinny być strukturalne z ustalonym polem jak correlation_id. Wybierz jedną pisownię i trzymaj ją wszędzie. Unikaj mieszania requestId, req_id i traceId, chyba że masz jasne mapowanie.
Jeśli to możliwe, dołącz ID także do widoczności bazy danych. Praktyczne podejście to dodanie go do komentarzy zapytań lub metadanych sesji, żeby slow query logi mogły go pokazywać. Gdy ktoś zgłasza "Przycisk zapis zawiesił się przez 10 sekund", support może wyszukać correlation_id=abc123 i zobaczyć log API, wywołanie serwisu downstream i jedno wolne zapytanie SQL, które spowodowało opóźnienie.
Identyfikator korelacyjny pomaga tylko wtedy, gdy ludzie mogą go znaleźć i śledzić. Uczyń go polem pierwszej klasy w logu (nie ukrywaj wewnątrz tekstu wiadomości) i zachowaj spójność reszty wpisu logu między serwisami.
Sparuj identyfikator korelacyjny z małym zbiorem pól, które odpowiadają na: kiedy, gdzie, co i kto (bez ujawniania danych osobowych). Dla większości zespołów to znaczy:
timestamp (ze strefą czasową)service i env (api, worker, prod, staging)route (lub nazwa operacji) i methodstatus i duration_msaccount_id lub zahashowane ID, nie e-mail)Dzięki temu support może wyszukać po ID, potwierdzić, że patrzy na właściwe żądanie i zobaczyć, który serwis je obsłużył.
Celuj w kilka silnych breadcrumbów na żądanie, nie w pełen transkrypt.
rows=12).Aby unikać głośnych logów, trzymaj szczegóły debugowe domyślnie wyłączone i promuj tylko wpisy, które pomagają odpowiedzieć "gdzie się zepsuło?". Jeśli linia nie pomaga zlokalizować problemu lub zmierzyć wpływu, prawdopodobnie nie należy jej trzymać na poziomie info.
Redakcja ma taką samą wagę jak struktura. Nigdy nie umieszczaj PII w identyfikatorze korelacyjnym ani w logach: żadnych e-maili, imion, numerów telefonów, pełnych adresów czy surowych tokenów. Jeśli musisz zidentyfikować użytkownika, loguj wewnętrzne ID lub hashowaną wartość jednostronną.
Użytkownik pisze do supportu: "Checkout nie powiódł się, gdy kliknąłem Zapłać." Najlepsze pytanie follow-up to proste: "Czy możesz wkleić identyfikator korelacyjny pokazany na ekranie błędu?" Odpowiada cid=9f3c2b1f6a7a4c2f.
Support ma teraz uchwyt łączący UI, API i pracę w bazie. Celem jest, aby każda linia logu dla tej akcji miała ten sam ID.
Support wyszukuje w logach 9f3c2b1f6a7a4c2f i widzi przebieg:
frontend INFO cid=9f3c2b1f6a7a4c2f event="checkout_submit" cart=3 items
api INFO cid=9f3c2b1f6a7a4c2f method=POST path=/api/checkout user=1842
api ERROR cid=9f3c2b1f6a7a4c2f msg="payment failed" provider=stripe status=502
Stąd inżynier śledzi ten sam ID do następnego hopu. Kluczem jest to, że backendowe wywołania (i wszelkie zadania w kolejkach) też przekazują ID.
payments INFO cid=9f3c2b1f6a7a4c2f action="charge" amount=49.00 currency=USD
payments ERROR cid=9f3c2b1f6a7a4c2f err="timeout" upstream=stripe timeout_ms=3000
db INFO cid=9f3c2b1f6a7a4c2f query="insert into failed_payments" rows=1
Teraz problem jest konkretny: serwis płatności przekroczył czas po 3 sekundach i zapisano rekord błędu. Inżynier może sprawdzić ostatnie deploye, potwierdzić, czy ustawienia timeoutu się zmieniły, i zobaczyć, czy retry są wywoływane.
Aby domknąć pętlę, wykonaj cztery kroki sprawdzające:
Najszybszy sposób, by uczynić identyfikatory korelacyjne bezużytecznymi, to przerwać łańcuch. Większość awarii wynika z małych decyzji, które wydają się nieszkodliwe podczas budowy, ale przeszkadzają, gdy support potrzebuje odpowiedzi.
Klasyczny błąd to generowanie nowego ID na każdym hopie. Jeśli przeglądarka wysyła ID, gateway API powinien go zachować, a nie zastępować. Jeśli naprawdę potrzebujesz wewnętrznego ID (np. dla wiadomości w kolejce), zachowaj oryginał jako pole parent, żeby historia nadal się łączyła.
Inna luka to częściowe logowanie. Zespoły dodają ID do pierwszego API, ale zapominają o workerach, zadaniach cyklicznych czy warstwie dostępu do bazy. Efekt to martwy koniec: widzisz żądanie wchodzące do systemu, ale nie wiesz, gdzie poszło dalej.
Nawet gdy ID jest wszędzie, może być trudno je wyszukać, jeśli każdy serwis używa innej nazwy pola lub formatu. Wybierz jedną nazwę i trzymaj się jej we frontendzie, API i logach (np. correlation_id). Wybierz też jeden format (często UUID) i traktuj go jako rozróżniający wielkość liter, aby kopiuj-wklej działało bez niespodzianek.
Nie trać ID, gdy coś pójdzie źle. Jeśli API zwraca 500 lub błąd walidacji, dołącz identyfikator korelacyjny w odpowiedzi (i najlepiej także w nagłówku). Dzięki temu użytkownik może wkleić go do czatu z supportem, a zespół od razu znajdzie pełną ścieżkę.
Szybki test: czy osoba z supportu może zacząć od jednego ID i śledzić każdą linię logu związaną z żądaniem, włącznie z błędami?
Użyj tego jako sanity checka, zanim powiesz supportowi „po prostu przeszukaj logi”. To działa tylko, gdy każdy hop stosuje te same zasady.
correlation_id w logach związanych z żądaniami jako pole strukturalne.Wybierz najmniejszą zmianę, która sprawi, że łańcuch nie będzie przerwany.
correlation_id i dodaj osobne span_id, jeśli potrzebujesz więcej szczegółów.Szybki test, który wykrywa braki: otwórz devtools, wywołaj akcję, skopiuj identyfikator korelacyjny z pierwszego żądania, a następnie potwierdź, że widzisz tę samą wartość we wszystkich powiązanych nagłówkach API i w każdym odpowiadającym wpisie w logach.
Identyfikatory korelacyjne pomagają tylko wtedy, gdy wszyscy używają ich w ten sam sposób, za każdym razem. Traktuj zachowanie związane z correlation ID jako wymagany element definicji ukończenia zadania (definition of done), a nie jako miły dodatek do logowania.
Dodaj mały krok śledzalności do definicji gotowości dla każdego nowego endpointu lub akcji UI. Opisz, jak ID jest tworzone (lub ponownie używane), gdzie przechowuje się podczas przepływu, który nagłówek go niesie i co robi każdy serwis, gdy nagłówek jest nieobecny.
Lekka lista kontrolna wystarczy:
correlation_id) we wszystkich aplikacjach i serwisach.Support potrzebuje też prostego skryptu, aby debugowanie było szybkie i powtarzalne. Zdecyduj, gdzie ID pokazuje się użytkownikom (np. przycisk "Kopiuj debug ID" w dialogach błędów) i zapisz, o co support ma pytać i gdzie szukać.
Zanim polegasz na tym w produkcji, przeprowadź etapowany przepływ, który odpowiada rzeczywistemu użyciu: kliknij przycisk, wywołaj błąd walidacji, potem dokończ akcję. Potwierdź, że możesz śledzić ten sam ID od żądania w przeglądarce, przez logi API, do jakiegokolwiek workera i aż do logów wywołań bazy danych, jeśli je rejestrujesz.
Jeśli budujesz aplikacje na Koder.ai, warto wpisać konwencje nagłówka i logowania identyfikatorów korelacyjnych do Planning Mode, żeby generowane frontendy React i serwisy Go były zgodne domyślnie.
Identyfikator korelacyjny to jeden wspólny identyfikator, który taguje wszystko związane z jedną akcją użytkownika lub workflowem — przeglądarkę, API, serwisy i workery. Dzięki niemu support może rozpocząć od jednego ID i wyciągnąć pełną oś czasu, zamiast zgadywać, które linie logów do siebie należą.
Używaj identyfikatora korelacyjnego, gdy chcesz szybko debugować jedno zdarzenie end-to-end, np. „kliknąłem Zapłać i to się nie powiodło”. Session ID jest zbyt szeroki (obejmuje wiele działań), a request ID jest zbyt wąski (dotyczy jednego żądania HTTP i zmienia się przy retry).
Domyślnie twórz go na początku akcji użytkownika we frontendzie — w momencie rozpoczęcia workflowu (wysłanie formularza, kliknięcie przycisku). Dzięki temu zachowasz najwcześniejszą część historii, włącznie z błędami w UI, retry i anulowanymi żądaniami.
Użyj wartości podobnej do UUID — nieczytelnej, łatwej do skopiowania i bezpiecznej do udostępnienia w zgłoszeniach. Nie umieszczaj w ID danych osobowych, nazw użytkowników, e-maili, numerów zamówień ani znaczników czasu; te informacje loguj oddzielnie z odpowiednimi kontrolami prywatności.
Wybierz jedną kanoniczną nazwę nagłówka i używaj jej wszędzie, np. X-Correlation-ID, i zapisuj go w logach pod spójnym polem strukturalnym, np. correlation_id. Spójność jest ważniejsza niż dokładna nazwa, bo support potrzebuje jednego przewidywalnego punktu do wyszukiwania.
Retry powinien używać tego samego identyfikatora korelacyjnego, jeśli to wciąż ta sama akcja użytkownika — dzięki temu logi pozostają połączone. Nowy identyfikator generujemy tylko wtedy, gdy użytkownik rozpoczyna osobną próbę, np. ponownie klikając przycisk później.
Wejście API powinno przyjąć przychodzący nagłówek, gdy jest obecny, a gdy go brakuje lub jest ewidentnie niepoprawny — wygenerować nowy. Powinno też odzwierciedlać identyfikator w odpowiedzi (w nagłówkach i w ciele błędu), aby użytkownicy i support mogli go skopiować z komunikatu w UI.
Przekazuj go jako część kontekstu żądania i kopiuj ten sam ID do wszystkich wywołań downstream, włączając HTTP/gRPC i zadania w kolejkach. Unikaj tworzenia nowego ID w trakcie przepływu; jeśli potrzebujesz dodatkowej szczegółowości, dodaj odrębny wewnętrzny identyfikator, nie łamiąc oryginalnego łańcucha.
Loguj go jako pole strukturalne pierwszej klasy (nie chowaj w treści wiadomości), aby można go było przeszukiwać i filtrować. Sparuj go z kilkoma praktycznymi polami, jak nazwa serwisu, trasa, status, czas trwania i bezpieczny identyfikator użytkownika, i upewnij się, że błędy również go logują, żeby ślad nie urywał się w najważniejszym momencie.
Dobrą szybką metodą jest wywołać jedną akcję, skopiować identyfikator korelacyjny z pierwszego żądania lub ekranu błędu, a następnie potwierdzić, że ta sama wartość pojawia się we wszystkich pokrewnych nagłówkach żądań i liniach logów usług obsługujących workflow. Jeśli ID znika w workerach, retry lub odpowiedziach błędów — to pierwszy problem do naprawy.