„Format Unix Timestamp vs ISO 8601: Którego powinieneś używać?

Programista porównujący format Unix timestamp i ISO 8601 do użytku w API i bazach danych

Jeśli kiedykolwiek integrować musiałeś dwa systemy przechowujące daty w różnych formatach, doskonale znasz ten ból. Jedno API zwraca 1714521600, drugie 2024-05-01T00:00:00Z, a ty o północy piszesz logikę konwersji. Wybór właściwego formatu – Unix timestamp czy ISO 8601 – już na starcie projektu potrafi zaoszczędzić godziny debugowania i zapobiec subtelnym błędom na produkcji. Oba formaty są powszechnie stosowane, oba mają realne zalety i żaden nie jest uniwersalnie „lepszy". Liczy się to, żebyś dokładnie wiedział, kiedy który pasuje do twojej sytuacji i dlaczego zły wybór generuje realne koszty.

Najważniejsze wnioski:

  • Unix timestamp to integer zliczający sekundy (lub milisekundy) od 1 stycznia 1970 UTC – idealny do obliczeń, przechowywania danych i komunikacji między API.
  • ISO 8601 to ustandaryzowany, czytelny dla człowieka format stringowy – idealny do logów, interfejsów użytkownika i wymiany danych między systemami.
  • Oba formaty się uzupełniają, a nie konkurują ze sobą. Wiele systemów produkcyjnych przechowuje czas wewnętrznie jako Unix timestamp, a na zewnątrz udostępnia go jako ISO 8601.
  • Użycie niewłaściwego formatu w złym kontekście prowadzi do błędów stref czasowych, problemów z parsowaniem i niepotrzebnej złożoności kodu.

Czym jest format Unix timestamp?

Unix timestamp (znany też jako Unix time lub epoch time) to pojedynczy integer reprezentujący liczbę sekund, które upłynęły od epoki Unix: 1 stycznia 1970, godz. 00:00:00 UTC. Format Unix time jest z definicji niezależny od strefy czasowej, ponieważ zawsze odnosi się do UTC. Nie ma tu żadnej niejednoznaczności związanej z czasem letnim ani regionalnymi przesunięciami.

Na przykład Unix timestamp 1714521600 reprezentuje dokładnie jeden konkretny moment w czasie, niezależnie od tego, gdzie na świecie go odczytujesz. Współczesne systemy często rozszerzają tę precyzję do milisekund (1714521600000) lub mikrosekund. Więcej o tych wariantach znajdziesz w naszym przewodniku na temat sekund, milisekund i mikrosekund w Unix timestamp.

Technicznie rzecz biorąc, Unix timestamp to po prostu liczba. Ta prostota jest jednocześnie jego największą zaletą i źródłem największego problemu z czytelnością.

Więcej o historii i podstawach tego pojęcia znajdziesz w naszym artykule o epoch time i jego fundamentach.

Czym jest format daty ISO 8601?

ISO 8601 to międzynarodowy standard opublikowany przez Międzynarodową Organizację Normalizacyjną, który definiuje sposób reprezentowania dat i godzin jako stringów. Typowy datetime w formacie ISO 8601 wygląda tak: 2024-05-01T00:00:00Z.

Rozkładając to na części:

  • 2024-05-01 – data w formacie YYYY-MM-DD
  • T – separator między datą a godziną
  • 00:00:00 – godzina w formacie HH:MM:SS
  • Z – oznacza UTC (można też używać przesunięć, np. +05:30)

ISO 8601 stanowi podstawę standardu RFC 3339, powszechnie stosowanego w protokołach internetowych. Jest czytelny dla człowieka, sortowalny jako string i jednoznaczny we wszystkich lokalizacjach. W odróżnieniu od zapisu „05/01/2024" – który w USA oznacza 1 maja, a w Europie 5 stycznia – ISO 8601 jest spójny globalnie.

Kluczowe różnice na pierwszy rzut oka

Właściwość Format Unix timestamp Format daty ISO 8601
Typ danych Integer (lub float) String
Czytelny dla człowieka Nie Tak
Obsługa stref czasowych Zawsze UTC (niejawne) Jawne przesunięcie lub Z
Przyjazny dla obliczeń Tak (odejmowanie, porównywanie) Nie (wymaga parsowania)
Rozmiar w pamięci Mały (4–8 bajtów) Większy (20+ znaków)
Sortowalny bez przetwarzania Tak (sortowanie numeryczne) Tak (leksykograficznie)
Niezależny od lokalizacji Tak Tak

Kiedy używać formatu Unix timestamp?

Format Unix time sprawdza się doskonale w konkretnych, dobrze określonych sytuacjach. Używaj go, gdy:

1. Wykonujesz obliczenia na datach

Obliczanie czasu trwania jest trywialne przy użyciu Unix timestamp. Żeby sprawdzić, ile sekund minęło, wystarczy odjąć jeden integer od drugiego. W przypadku stringów ISO 8601 musisz najpierw sparsować oba do obiektów datetime, a dopiero potem obliczyć różnicę. Przy operacjach o wysokiej częstotliwości – jak logowanie milionów zdarzeń – ten narzut parsowania szybko się kumuluje.

2. Przechowujesz daty w bazach danych

Kolumny z integerami są szybsze do indeksowania i porównywania niż kolumny ze stringami. Jeśli wykonujesz zapytania w stylu „daj mi wszystkie zdarzenia z ostatnich 7 dni", porównywanie dwóch integerów jest wydajniejsze niż parsowanie i porównywanie stringów. Nasz szczegółowy przewodnik dotyczący Unix timestamp w bazach danych omawia strategie indeksowania i wzorce zapytań.

3. Komunikacja między wewnętrznymi serwisami

Gdy dwa serwisy backendowe, które kontrolujesz, muszą przekazywać sobie znaczniki czasu, format Unix redukuje złożoność parsowania. Obie strony uzgadniają kontrakt oparty na integerze i nie ma ryzyka błędnej interpretacji stringu ze strefą czasową.

4. Logika wygasania i TTL

Tokeny JWT, wpisy cache i czas wygasania sesji są niemal powszechnie wyrażane jako Unix timestamp. Claim exp w JSON Web Token (JWT) jest właśnie Unix timestamp z tego powodu: porównanie exp > Date.now() / 1000 to jedno szybkie porównanie integerów.

5. Unikanie błędów stref czasowych

Ponieważ Unix timestamp jest zawsze UTC, eliminuje całą klasę błędów związanych z czasem letnim. Jeśli twoja aplikacja obsługuje użytkowników z wielu stref czasowych, przechowywanie Unix timestamp i konwersja do czasu lokalnego wyłącznie w warstwie prezentacji to sprawdzony wzorzec architektoniczny.

Pamiętaj o problemie roku 2038, jeśli używasz 32-bitowych integerów ze znakiem do przechowywania Unix timestamp – w nowoczesnych systemach zawsze stosuj 64-bitowe integery.

Kiedy używać formatu daty ISO 8601?

Format daty ISO 8601 sprawdza się w kontekstach, gdzie ludzie lub zewnętrzne systemy muszą czytać, zapisywać lub walidować daty bez uruchamiania kodu.

1. Odpowiedzi API konsumowane przez strony trzecie

Jeśli budujesz publiczne API, zwracanie "created_at": "2024-05-01T12:30:00Z" jest o wiele bardziej przyjazne dla deweloperów niż "created_at": 1714562200. Zewnętrzni deweloperzy mogą od razu zrozumieć wartość bez konieczności jej konwertowania. Wiele przewodników stylu API – w tym te od Stripe i GitHub – domyślnie stosuje ISO 8601 właśnie z tego powodu.

2. Pliki logów i ścieżki audytu

Logi są czytane przez ludzi podczas incydentów. Linia logu [2024-05-01T14:22:05Z] ERROR: payment failed jest natychmiast zrozumiała i gotowa do działania. Log z [1714569725] ERROR: payment failed zmusza czytelnika do konwersji znacznika czasu, zanim w ogóle zacznie debugować.

3. Internacjonalizacja i lokalizacja

ISO 8601 zawiera jawne informacje o przesunięciu strefy czasowej. Gdy twój system musi zachować oryginalny czas lokalny użytkownika – na przykład zdarzenie w kalendarzu utworzone o godz. 9:00 w Tokio – ISO 8601 z odpowiednim przesunięciem (2024-05-01T09:00:00+09:00) zachowuje ten zamiar. Sam Unix timestamp nie powie ci, w jakiej strefie czasowej znajdował się użytkownik w momencie tworzenia zdarzenia.

4. Pliki konfiguracyjne i formaty wymiany danych

Pliki JSON, YAML i CSV, które ludzie edytują ręcznie, powinny używać ISO 8601. Jeśli deweloper musi ręcznie ustawić datę wygasania w pliku konfiguracyjnym, wpisanie 2025-01-01T00:00:00Z jest znacznie mniej podatne na błędy niż ręczne obliczanie i wpisywanie Unix timestamp.

Przykłady kodu w JavaScript i Python

JavaScript: konwersja między formatami

// Pobierz aktualny Unix timestamp (sekundy)
const unixNow = Math.floor(Date.now() / 1000);
console.log(unixNow); // np. 1714521600

// Konwertuj Unix timestamp na string ISO 8601
const isoString = new Date(unixNow * 1000).toISOString();
console.log(isoString); // "2024-05-01T00:00:00.000Z"

// Konwertuj string ISO 8601 z powrotem na Unix timestamp
const parsed = new Date("2024-05-01T00:00:00Z");
const backToUnix = Math.floor(parsed.getTime() / 1000);
console.log(backToUnix); // 1714521600

// Oblicz czas trwania między dwoma Unix timestamp (bez parsowania)
const start = 1714521600;
const end = 1714608000;
const durationSeconds = end - start;
console.log(`Duration: ${durationSeconds / 3600} hours`); // 24 hours

Python: praca z obydwoma formatami

import time
from datetime import datetime, timezone

# Pobierz aktualny Unix timestamp
unix_now = int(time.time())
print(unix_now)  # np. 1714521600

# Konwertuj Unix timestamp na string ISO 8601
dt = datetime.fromtimestamp(unix_now, tz=timezone.utc)
iso_string = dt.isoformat()
print(iso_string)  # "2024-05-01T00:00:00+00:00"

# Konwertuj string ISO 8601 z powrotem na Unix timestamp
parsed_dt = datetime.fromisoformat("2024-05-01T00:00:00+00:00")
back_to_unix = int(parsed_dt.timestamp())
print(back_to_unix)  # 1714521600

# Oblicz czas trwania – trivialnie proste z Unix timestamp
start = 1714521600
end = 1714608000
duration_hours = (end - start) / 3600
print(f"Duration: {duration_hours} hours")  # 24.0 hours

Ważne: W Python zawsze przekazuj tz=timezone.utc przy wywołaniu datetime.fromtimestamp(). Bez tego Python używa lokalnej strefy czasowej systemu, co może dawać błędne wyniki na serwerach w różnych regionach.

Konkretny przykład: system rezerwacji

Wyobraź sobie, że budujesz API do rezerwacji hotelowych. Użytkownik w Nowym Jorku rezerwuje pokój z zameldowaniem 15 czerwca 2024 o godz. 15:00 czasu lokalnego. Oto jak oba formaty zachowują się w praktyce.

Przechowywanie jako Unix timestamp: Konwertujesz czas lokalny użytkownika na UTC i zapisujesz 1718470800. Jest to kompaktowe i szybkie w zapytaniach. Jednak gdy personel hotelowy w Nowym Jorku spojrzy na surowy rekord w bazie danych, zobaczy liczbę. Potrzebuje narzędzia, żeby ją zdekodować. Co gorzej, jeśli zapomnisz skonwertować czas lokalny na UTC przed zapisaniem, wprowadzasz cichy błąd 4-godzinny (Nowy Jork to UTC-4 latem).

Przechowywanie jako ISO 8601: Zapisujesz 2024-06-15T15:00:00-04:00. Przesunięcie jest zachowane. Personel może odczytać rekord bezpośrednio. Oryginalny zamiar strefy czasowej nie zostaje utracony. Jednak porównania stringów w SQL są nieco wolniejsze, a obliczenie „ile godzin do zameldowania" wymaga najpierw sparsowania stringa.

Rozwiązanie produkcyjne stosowane przez większość zespołów: Przechowuj Unix timestamp w bazie danych dla wydajności i poprawności, a w odpowiedzi API zwracaj string ISO 8601 dla użyteczności. To wzorzec stosowany przez największe platformy. Zyskujesz to, co najlepsze w obu światach.

Pełny opis wzorców konwersji znajdziesz w naszym kompletnym przewodniku konwersji Unix timestamp na datę.

Jednoznaczne rekomendacje według przypadku użycia

Na podstawie realnych ograniczeń – oto bezpośrednie rekomendacje dla każdego scenariusza:

  • Przechowywanie w bazie danych: Używaj Unix timestamp (integer). Szybsze indeksowanie, brak parsowania stref czasowych, mniejszy rozmiar.
  • Komunikacja wewnętrzna między mikroserwisami: Używaj Unix timestamp. Obie strony kontrolują kontrakt, a żaden człowiek nie czyta surowego payloadu.
  • Odpowiedzi publicznego REST API: Używaj ISO 8601. Zewnętrzni deweloperzy potrzebują czytelnych, samodokumentujących się wartości.
  • Pliki logów i ścieżki audytu: Używaj ISO 8601. Ludzie czytają logi pod presją czasu podczas incydentów.
  • JWT i wygasanie sesji: Używaj Unix timestamp. Specyfikacja tego wymaga, a porównania to pojedyncza operacja.
  • Pliki konfiguracyjne i zaplanowane zadania: Używaj ISO 8601. Ludzie piszą i edytują te pliki bezpośrednio.
  • Funkcje kalendarza i harmonogramowania: Używaj ISO 8601 z jawnym przesunięciem strefy czasowej. Zachowuje oryginalny zamiar strefy czasowej użytkownika.
  • Arytmetyka dat w logice aplikacji: Najpierw konwertuj na Unix timestamp, wykonaj obliczenia, a następnie w razie potrzeby konwertuj z powrotem.

Szerszy zestaw najlepszych praktyk dotyczących pracy ze znacznikami czasu w kodzie backendowym znajdziesz w naszym samouczku Unix timestamp dla deweloperów, który szczegółowo omawia wzorce przechowywania, formatowania i obsługi stref czasowych.

Podsumowanie

Debata między formatem Unix timestamp a formatem daty ISO 8601 nie dotyczy tego, który z nich jest lepszy. Chodzi o dopasowanie właściwego narzędzia do właściwego zadania. Unix timestamp należy do kolumn w bazie danych, wewnętrznych kontraktów serwisowych i logiki wygasania. ISO 8601 należy do odpowiedzi API, logów i każdego pliku, który może otworzyć człowiek. Większość solidnych systemów produkcyjnych używa obu: przechowuje jako Unix time, udostępnia jako ISO 8601. Jeśli ten jeden wzorzec dobrze zapamiętasz, unikniesz najczęstszych błędów obsługi dat, zanim w ogóle trafią na produkcję.

Darmowy konwerter Unix timestamp – natychmiastowa konwersja między Unix time a ISO 8601

Przestań zgadywać, jakiego formatu daty użyć

Wypróbuj nasz darmowy konwerter Unix timestamp na unixtimestamp.app i konwertuj między Unix time a ISO 8601 natychmiast – bez pisania kodu. Wklej znacznik czasu i w kilka sekund otrzymaj czytelną datę.

Wypróbuj nasze darmowe narzędzie →

Tak, i wiele baz danych obsługuje natywne typy datetime przechowujące ISO 8601 wewnętrznie. Jednak integery Unix timestamp są generalnie szybsze przy zapytaniach zakresowych i porównaniach indeksów. W przypadku tabel o dużym wolumenie z częstym filtrowaniem po datach, integery dają mierzalną przewagę wydajnościową nad kolumnami stringowymi lub datetime.

Unix timestamp jest z definicji zawsze UTC. Nie przechowuje informacji o strefie czasowej. Aby wyświetlić Unix timestamp w lokalnej strefie czasowej użytkownika, konwertujesz go w warstwie prezentacji. To jest w rzeczywistości zaleta: przechowywana wartość jest całkowicie jednoznaczna, a konwersja strefy czasowej jest obsługiwana jawnie tam, gdzie powinna być.

Unix timestamp oparty na sekundach (np. 1714521600) to tradycyjny format używany w większości systemów Unix i standardach takich jak JWT. Milisekundy (np. 1714521600000) są powszechne w JavaScript i środowiskach przeglądarek. Zawsze sprawdzaj, jakiej precyzji oczekuje API – wysłanie sekund zamiast milisekund skutkuje datami przesuniętymi o 1000 razy w przeszłość.

RFC 3339 to profil ISO 8601 zaprojektowany specjalnie do użytku internetowego. Jest nieco bardziej restrykcyjny: wymaga przesunięcia strefy czasowej (jak Z lub +00:00) i nie dopuszcza niektórych opcjonalnych funkcji ISO 8601. W praktyce większość deweloperów traktuje je zamiennie w przypadku standardowych stringów datetime, takich jak 2024-05-01T00:00:00Z.

GitHub używa stringów ISO 8601 w odpowiedziach swojego REST API. Stripe używa Unix timestamp (integerów) w swoim API. Oba wybory są celowe i zgodne z ich przypadkami użycia. Ilustruje to, że nie ma jednej ogólnobranżowej reguły – właściwy wybór zależy od odbiorców twojego API i operacji, które konsumenci muszą wykonywać na wartościach.