to_char() și EXTRACT() în PostgreSQL

Date, timp și generare serii PostgreSQL 8.0+ (standard în PostgreSQL 15–17)

Formatează date, ore și numere în șiruri personalizate (to_char) sau extrage componente numerice din timestamp-uri (EXTRACT).

Sintaxă SQL
to_char(timestamp, 'YYYY-MM-DD HH24:MI:SS');nEXTRACT(YEAR FROM timestamp);nEXTRACT(EPOCH FROM interval);

Ce face to_char() și EXTRACT()

Funcția to_char() convertește o dată/oră (timestamp, timestamptz, interval) sau o valoare numerică într-un șir de caractere formatat conform unei măști (precum 'DD.MM.YYYY HH24:MI').

În sens invers sau complementar, EXTRACT(camp FROM sursa) (sau echivalentul date_part('camp', sursa)) extrage o singură componentă numerică (anul, luna, ziua săptămânii, trimestrul sau numărul de secunde Unix EPOCH) sub formă de numeric.

Clauze, operatori și argumente

Clauză / Operator Descriere
to_char(ts, 'sablon') Formatează timestamp-ul ca text: YYYY (an), MM (lună 01–12), DD (zi 01–31), HH24 (oră 00–23), MI (minut), SS (secundă).
to_char(numar, '999G990D00') Formatează un număr cu separatori de mii și zecimale.
EXTRACT(YEAR | MONTH | DAY FROM ts) Returnează anul, luna (1–12) sau ziua lunii (1–31) ca număr.
EXTRACT(ISODOW FROM ts) Returnează ziua săptămânii conform standardului ISO 8601: 1 (Luni) până la 7 (Duminică).
EXTRACT(EPOCH FROM ts / interval) Returnează numărul total de secunde (cu zecimale) de la 1 ianuarie 1970 UTC sau durata în secunde a unui interval.

Exemple

Exemplul 1: Formatarea datelor în stil românesc și extragerea zilei săptămânii (ISODOW)

Afișăm data comenzii în formatul ZZ.LL.AAAA OO:MM și identificăm ziua săptămânii (1 = Luni, 7 = Duminică).

SELECT id,
       to_char(plasata_la, 'DD.MM.YYYY HH24:MI') AS data_formatata,
       EXTRACT(ISODOW FROM plasata_la) AS zi_sapt_iso,
       EXTRACT(QUARTER FROM plasata_la) AS trimestru
FROM comenzi
LIMIT 3;

Rezultat interogare

  id  |  data_formatata  | zi_sapt_iso | trimestru 
------+------------------+-------------+-----------
 5042 | 14.03.2025 16:22 |           5 |         1
 5048 | 16.03.2025 11:05 |           7 |         1
 5051 | 18.03.2025 19:40 |           2 |         1
(3 rows)

Exemplul 2: Calcularea duratei în secunde și minute cu EXTRACT(EPOCH FROM …)

Măsurăm timpul exact de procesare al unei comenzi scăzând două coloane timestamptz și extrăgând EPOCH (numărul total de secunde).

SELECT id,
       ROUND(EXTRACT(EPOCH FROM (livrata_la - plasata_la)) / 3600.0, 1) AS ore_pana_la_livrare
FROM comenzi
WHERE status = 'livrata'
ORDER BY id DESC
LIMIT 3;

Rezultat interogare

  id  | ore_pana_la_livrare 
------+---------------------
 5042 |                21.5
 5039 |                44.2
 5031 |                18.0
(3 rows)

Greșeli frecvente

  • Confuzia între MM (lună, 01–12) și MI (minute, 00–59) în șablonul to_char(): scrierea 'YYYY-MM-DD HH24:MM:SS' va afișa numărul lunii în locul minutelor!
  • Folosirea EXTRACT(DOW FROM ts) când te aștepți ca Luni să fie 1 și Duminică 7: DOW returnează 0 pentru Duminică; folosește ISODOW pentru standardul european (1 = Luni … 7 = Duminică).

Comenzi și funcții înrudite

  • NOW(), INTERVAL și date_trunc(): Lucrează cu momente de timp cu fus orar (timestamptz), aritmetică de durate (INTERVAL) și rotunjire calendaristică (date_trunc).
  • generate_series(): Generează pe loc serii de numere întregi sau calendare de date/ore pentru rapoarte fără zile lipsă și date de test.
  • GROUP BY, HAVING și clauza FILTER: Grupează rândurile pentru agregări și aplică condiții individuale pe fiecare funcție agregată prin FILTER (WHERE …).