Structured Logging — istota, formaty danych i zasada działania w aplikacjach

Autor: IT Sectr Opublikowano: 2026-05-28 Czas czytania: 8 min

Structured Logging to podejście do zapisywania logów, w którym każda wiadomość jest przedstawiona w maszynowo czytelnym formacie z parami klucz-wartość, a nie jako nieustrukturyzowany tekst. W przeciwieństwie do płaskich ciągów znaków, logi strukturyzowane zawierają metadane: znacznik czasu, poziom, moduł, identyfikator zapytania — i mogą być indeksowane przez systemy analityczne. Według danych O'Reilly Effective Logging, przejście na formaty strukturyzowane skraca czas poszukiwania incydentu z godzin do minut dzięki możliwości filtrowania po polach. To standard de facto w nowoczesnym programowaniu mobilnym i serwerowym: JSON i logfmt pozwalają przetwarzać logi programami, a nie wzrokiem.

Najważniejsze

  • Structured Logging — przedstawienie logów w formacie klucz-wartość zamiast płaskiego tekstu, nadające się do automatycznego przetwarzania
  • JSON — najpopularniejszy format logów strukturyzowanych, obsługiwany przez wszystkie nowoczesne systemy zbierania i analizy
  • Logfmt — kompaktowy format od Heroku, wygodny do czytania przez człowieka i parsowania przez grep
  • ELK Stack — Elasticsearch, Logstash, Kibana — standardowa infrastruktura do przechowywania i wizualizacji logów strukturyzowanych
  • Kontekst — identyfikator zapytania, sesja użytkownika, wersja aplikacji — obowiązkowe pola każdej strukturyzowanej wiadomości

Co to jest Structured Logging

Structured Logging to metoda zapisywania logów, w której każda wiadomość zawiera nazwane pola z typowanymi wartościami. Zamiast ciągu znaków typu User 42 logged in from device ABC log strukturyzowany wygląda jak zestaw pól: user_id=42, event=login, device_id=ABC, timestamp=2026-07-04T10:30:00Z.

Główną zaletą logów strukturyzowanych w porównaniu z tekstowymi jest możliwość programowego przetwarzania. Parsowanie logów tekstowych wymaga wyrażeń regularnych i założeń dotyczących formatu ciągu. Logi strukturyzowane są parsowane bezstratnie: każde pole ma znany typ i nazwę, co pozwala na budowanie zapytań typu znajdź wszystkie błędy autoryzacji z ostatniej godziny dla użytkownika 42 bez dodatkowego przetwarzania.

Według danych Honeycomb.io (2023), zespoły używające structured logging w produkcji wykrywają incydenty średnio 4 razy szybciej w porównaniu z zespołami polegającymi na tekstowych logach i grepie.

Formaty logów strukturyzowanych

Structured Logging obsługuje kilka formatów serializacji. Wybór formatu zależy od infrastruktury: JSON jest wygodny do integracji z Elasticsearch i systemami chmurowymi, logfmt — do podglądu konsolowego przez tail i grep, Protocol Buffers — dla systemów wysokiej wydajności z ograniczeniem przepustowości.

FormatPrzykładKiedy używać
JSON{"event":"login","user_id":42}ELK Stack, zbieracze chmurowe, mikrousługi
Logfmtevent=login user_id=42 duration_ms=150Konsola, tail, heroku logs
MessagePackBinarny odpowiednik JSONSystemy o wysokim obciążeniu, IoT

JSON — format uniwersalny

JSON to najpopularniejszy format dla logów strukturyzowanych. Jest natywnie obsługiwany przez wszystkie systemy zbierania: Logstash, Fluentd, Amazon CloudWatch, Google Cloud Logging. Logi JSON są łatwo czytelne dla człowieka i parsowane przez każdy język programowania bez dodatkowych bibliotek. Główną wadą jest nadmiarowość: każda para klucz-wartość wymaga cudzysłowów i dwukropków, co zwiększa objętość przechowywanych danych o 30–50% w porównaniu z logfmt.

Logfmt — format kompaktowy

Logfmt został opracowany w Heroku do widoczności konsolowej. Jest bardziej kompaktowy niż JSON, zachowuje czytelność dla człowieka i łatwo się go przycina przez cut i awk. Przykład: ts=2026-07-04T10:30:00Z level=error module=api status=500. Logfmt nie wymaga eskapowania większości znaków i dobrze nadaje się do logowania stdout w kontenerach.

Po co Structured Logging w programowaniu mobilnym

W aplikacjach mobilnych Structured Logging rozwiązuje trzy kluczowe zadania: wyszukiwanie przyczyn awarii bez odtwarzania na urządzeniu, śledzenie sesji użytkowników i analizę wydajności według wersji aplikacji.

Logi tekstowe na urządzeniach mobilnych są prawie bezużyteczne — programista nie może grepować logów na urządzeniu użytkownika. Logi strukturyzowane są wysyłane do systemów chmurowych (Firebase, Sentry, Datadog) i tam indeksowane. Można zbudować zapytanie: pokaż wszystkie crashe na iOS 17.4, wersja aplikacji 3.2, w module checkouts — i uzyskać dokładny wybór w kilka sekund.

Według danych Sentry (2024), aplikacje używające structured breadcrumbs mają o 60% więcej kontekstu w każdym raporcie awarii w porównaniu z aplikacjami logującymi tylko tekst błędu. To bezpośrednio wpływa na szybkość naprawy błędu.

Narzędzia do zbierania i analizy

ELK Stack — Elasticsearch, Logstash, Kibana — pozostaje standardową infrastrukturą do pracy z logami strukturyzowanymi. Logstash przyjmuje logi w JSON, przekształca i wysyła do Elasticsearch w celu indeksacji, Kibana zapewnia interfejs wizualny do zapytań i dashboardów.

Dla aplikacji mobilnych popularne są rozwiązania chmurowe: Firebase Crashlytics z niestandardowymi logami, Sentry z breadcrumbs, Datadog z APM-śledzeniem. Przyjmują one logi strukturyzowane bezpośrednio z mobilnego SDK i nie wymagają wdrażania własnego backendu. Firebase oferuje darmowy pakiet do raportowania awarii, Sentry dodaje distributed tracing, a Datadog integruje się z APM do śledzenia wydajności zapytań na kliencie i serwerze jednocześnie.

Grafana Loki — alternatywa dla Elasticsearch, zoptymalizowana dla logów. Loki nie indeksuje zawartości wiadomości domyślnie, lecz używa etykiet (labels) do filtrowania. Jest to znacznie tańsze w przechowywaniu i szybsze przy zapytaniach według ustalonego zestawu pól.

swift
// Structured logging przez Swift Logger w JSON
struct StructuredLog {
    let event: String
    let attributes: [String: Any]
    let level: String

    func serialize() -> String {
        var base = "event=\(event) level=\(level)"
        for (key, value) in attributes {
            base += " \(key)=\(value)"
        }
        return base
    }
}

Najlepsze praktyki Structured Logging

Pierwsza zasada logowania strukturyzowanego: każda wiadomość musi zawierać identyfikator zapytania lub sesji. Bez kontekstu pojedynczy log jest bezużyteczny — nie można zrozumieć, do którego użytkownika lub zapytania się odnosi. Dodawaj correlation ID na starcie sesji i przekazuj go przez wszystkie warstwy aplikacji.

Druga zasada: typowanie pól. Pola numeryczne (duration_ms, status_code, retry_count) powinny być przekazywane jako liczby, a nie jako ciągi znaków. Elasticsearch i podobne systemy indeksują liczby i ciągi znaków inaczej: do liczb można stosować agregacje (średnia, mediana, percentyl), do ciągów — wyszukiwanie pełnotekstowe. Fałszywe typowanie pozbawia możliwości budowania analitycznych dashboardów.

Trzecia zasada: unikaj zagnieżdżonych obiektów. Logi JSON o głębokości zagnieżdżenia większej niż 2 poziomy są trudne do filtrowania i wizualizacji. Zamiast {"user": {"name": "Alice", "role": "admin"}} używaj płaskich kluczy: user_name=Alice user_role=admin.

kotlin
// Structured logging na Android przez Timber + logfmt
class StructuredTree : Timber.Tree() {
    override fun log(priority: Int, tag: String?,
                  message: String?, t: Throwable?) {
        val level = priorityToLevel(priority)
        val logfmt = "level=$level tag=$tag message=$message"
        sendToRemote(logfmt)
    }
}

Które pola są obowiązkowe

Minimalny zestaw pól dla każdej strukturyzowanej wiadomości: timestamp w ISO 8601, level (debug/info/warn/error/fatal), logger (nazwa modułu lub klasy), message (czytelny dla człowieka opis zdarzenia). Dodatkowo: correlation_id, user_id (jeśli znany), version (wersja aplikacji), platform (iOS/Android), environment (dev/staging/prod).

Bez correlation_id logi strukturyzowane zamieniają się w zbiór rozproszonych rekordów, których nie można połączyć w jeden scenariusz użytkownika. Generuj UUID przy każdym uruchomieniu aplikacji i dodawaj go do wszystkich logów sesji. W praktyce correlation_id powinien być przekazywany przez wszystkie warstwy: od zdarzeń UI po zapytania sieciowe i zadania w tle — w przeciwnym razie część logów pozostanie bez kontekstu i nie będzie uczestniczyć w analityce. Przy kompleksowym śledzeniu jeden UUID pozwala zebrać pełny obraz ścieżki użytkownika.

Przykłady logowania strukturyzowanego w Swift i Kotlin

Na iOS logowanie strukturyzowane można zrealizować przez opakowanie os_log, które serializuje pola do formatu logfmt. Na Android — przez Timber z niestandardowym Tree, który przekształca wiadomości w JSON lub logfmt przed wysłaniem na serwer.

swift
import OSLog

struct StructuredLogger {
    let subsystem: String
    let category: String

    func log(level: OSLogType,
              event: String,
              context: [String: Any]) {
        let oslogger = Logger(
            subsystem: subsystem,
            category: category
        )
        let fields = context.map {
            "\($0.key)=\($0.value)"
        }.joined(separator: " ")
        oslogger.log(level: level,
                     "\(event) \(fields)")
    }
}

Structured vs Unstructured: porównanie podejść

Wybór między logami strukturyzowanymi a tekstowymi zależy od etapu projektu. Na wczesnych etapach rozwoju logi tekstowe są prostsze i szybsze — programista pisze message bezpośrednio bez dodatkowych opakowań. Ale gdy tylko projekt wykracza poza jedną drużynę lub jeden serwer, logi strukturyzowane stają się obowiązkowe.

KryteriumLogi tekstoweLogi strukturyzowane
CzytelnośćWysoka w konsoliŚrednia (wymaga pretty-print)
Wyszukiwaniegrep po podciąguZapytania po polach i wartościach
AgregacjaNieobsługiwanaŚrednia, mediana, percentyle
IntegracjaWymaga parsowaniaNatywna w ELK/Loki/Datadog
Objętość przechowywaniaMniejsza (bez metadanych)Większa (pola + wartości)

Często zadawane pytania

Jaki format jest najlepszy do logowania mobilnego?

Do wysyłania na serwer używaj JSON — jest natywnie obsługiwany przez Firebase Crashlytics, Sentry i Datadog. Do lokalnego podglądu w logach Xcode lub Android Studio używaj logfmt — jest bardziej kompaktowy i czytelny bez formatowania.

Czy trzeba logować w formacie strukturyzowanym na kliencie?

Tak, logi strukturyzowane na kliencie pozwalają dodać kontekst do każdego raportu awarii: wersję OS, stan sieci, ostatnie działania użytkownika. Bez strukturyzowanych breadcrumbs raport awarii zawiera tylko stos wywołań bez scenariusza użytkownika.

Czym logfmt różni się od JSON?

Logfmt jest bardziej kompaktowy (o 30–50% mniejsza objętość) i łatwiej czyta się go w terminalu. JSON obsługuje zagnieżdżone obiekty i tablice, ale wymaga eskapowania cudzysłowów. Wybór zależy od infrastruktury: dla ELK — JSON, do podglądu konsolowego — logfmt.

Jak dodać correlation ID do wszystkich logów?

Utwórz jedną instancję UUID przy uruchomieniu aplikacji, zapisz ją w singletonie lub kontenerze DI i przekazuj do wszystkich loggerów przez konstruktor. Alternatywą jest użycie threading-local lub Continuation Local Storage w Kotlin coroutines.

Czy można mieszać logi strukturyzowane i tekstowe?

Można, ale nie jest zalecane — mieszanie powoduje utratę możliwości automatycznej indeksacji. Jeśli część logów jest tekstowa, trzeba je parsować wyrażeniami regularnymi, co obniża wydajność i niezawodność wyszukiwania. Lepiej migrować wszystkie logi na format strukturyzowany.

Podsumowanie

  • Structured Logging — format logów z parami klucz-wartość, nadający się do automatycznej indeksacji i zapytań, w przeciwieństwie do tekstowych ciągów
  • JSON i logfmt — główne formaty: JSON uniwersalny dla systemów zbierania, logfmt kompaktowy do podglądu konsolowego i logów dockerowych
  • Correlation ID — obowiązkowe pole każdej strukturyzowanej wiadomości, bez niego logów nie można połączyć w sesję użytkownika
  • ELK Stack i Grafana Loki — standardowe rozwiązania infrastrukturalne do przechowywania, indeksacji i wizualizacji logów strukturyzowanych
  • Wydajność — zespoły ze structured logging wykrywają incydenty 4 razy szybciej dzięki zapytaniom po polach zamiast grepa po tekście
  • Typowanie — liczby powinny być przekazywane jako liczby, a nie ciągi, aby umożliwić agregacje (średnia, mediana, percentyle) w systemach analitycznych

Opracujemy aplikację mobilną pod klucz

IT Sectr tworzy aplikacje na iOS i Androida dla startupów i firm od 2017 roku. Doradzimy Ci i zaproponujemy najlepsze rozwiązanie.

Omów projekt

Przeczytaj również