Che ora è? Che giorno sarà tra tre settimane? Quanti giorni mancano a Natale? E come si mette la data nel nome di un file di backup? Tutte queste domande hanno la stessa risposta: date, il comando che mostra la data e l'ora del sistema e le sa formattare e calcolare.
Cos'è
date fa parte delle coreutils GNU, ed è presente su ogni distribuzione Linux. Legge l'orologio del sistema e lo mostra nel formato che vuoi; in più sa interpretare date scritte a parole (come "tomorrow" o "next friday"), convertirle e fare somme e sottrazioni. Con i privilegi di amministratore può anche impostare l'ora, anche se per questo esistono strumenti migliori (vedi più avanti). Gli esempi usano la versione GNU di date, quella di Linux: su macOS e sui sistemi BSD alcune opzioni sono diverse.
Cosa fa
Senza argomenti stampa data e ora attuali, nella lingua e nel fuso orario del sistema. Con un argomento che comincia per + stampa la data nel formato indicato, in cui ogni sequenza %lettera viene sostituita da una parte della data. Con -d invece di "adesso" usa la data che indichi.
Come si usa
$ date [opzioni] [+formato]Gli esempi sono stati scritti il 26 ottobre 2026, alle 7:25, in un sistema italiano (fuso di Roma). Con un'altra lingua, i nomi dei giorni e dei mesi cambiano.
Esempio 1: data e ora attuali
$ date
lun 26 ott 2026, 07:25:41, CET
$ date -u
lun 26 ott 2026, 06:25:41, UTC
$ LC_ALL=C date
Mon Oct 26 07:25:41 CET 2026Senza opzioni date stampa giorno della settimana, data, ora e fuso orario (CET è l'ora solare dell'Europa centrale; in estate si vedrebbe CEST). Con -u si ottiene l'ora universale (UTC), quella usata dai server e dai registri per evitare ambiguità. Con LC_ALL=C si forza il formato neutro in inglese, utile quando l'output deve essere uguale su ogni computer.
Esempio 2: scegliere il formato
$ date +%F
2026-10-26
$ date +%T
07:25:41
$ date "+%d/%m/%Y"
26/10/2026
$ date "+%H:%M"
07:25
$ date "+Oggi è %A %d %B %Y, ore %H:%M"
Oggi è lunedì 26 ottobre 2026, ore 07:25Il formato inizia con + e, se contiene spazi o simboli, si scrive tra virgolette. Le sequenze più usate sono nella tabella qui sotto. %F è la data in formato internazionale anno-mese-giorno (che ha il vantaggio di essere ordinata correttamente anche in ordine alfabetico) e %T l'ora completa.
| Sequenza | Significato | Esempio |
|---|---|---|
%Y %m %d | Anno, mese, giorno | 2026 10 26 |
%H %M %S | Ore, minuti, secondi | 07 25 41 |
%F / %T | Data completa / ora completa | 2026-10-26 / 07:25:41 |
%A / %a | Giorno della settimana, esteso / breve | lunedì / lun |
%B / %b | Mese, esteso / breve | ottobre / ott |
%u | Giorno della settimana (1 = lunedì) | 1 |
%j | Giorno dell'anno | 299 |
%V | Numero della settimana (ISO) | 44 |
%s | Secondi dal 1° gennaio 1970 (UTC) | 1792995941 |
%Z / %z | Fuso orario, nome / scarto | CET / +0100 |
%% | Il simbolo di percentuale | % |
Esempio 3: un nome di file con la data
$ tar czf "backup-$(date +%F).tar.gz" progetto/
$ ls backup-*
backup-2026-10-26.tar.gz
$ cp db.sql "db-$(date +%Y%m%d-%H%M%S).sql"
$ ls db-*
db-20261026-072541.sql
$ date +%F_%H-%MÈ l'uso più comune: $(date +%F) viene sostituito dalla data, e il file prende un nome come backup-2026-10-26.tar.gz. Le date nel formato anno-mese-giorno o annomesegiorno-oraminutisecondi hanno il vantaggio di comparire in ordine cronologico con un semplice ls. Meglio evitare i due punti nei nomi dei file (%T), perché alcuni programmi e sistemi non li accettano. Vedi l'articolo su tar per la parte di archivio.
Esempio 4: date a parole con -d
$ date -d tomorrow +%F
2026-10-27
$ date -d yesterday +%F
2026-10-25
$ date -d "+3 days" +%F
2026-10-29
$ date -d "next friday" +%F
2026-10-30
$ date -d "last friday" +%F
2026-10-23
$ date -d "2 weeks ago" +%F
2026-10-12
$ date -d "2026-12-25 - 1 week" +%F
2026-12-18
$ date -d 2026-12-25 +%A
venerdìL'opzione -d (date) dice a date di partire da una data descritta a parole invece che dall'ora attuale. Capisce espressioni come tomorrow, yesterday, +3 days, next friday, 2 weeks ago, next month, last year, e si possono combinare con una data di partenza (2026-12-25 - 1 week). Le parole devono essere in inglese: domani non è riconosciuto. Con -d e un formato si ricava anche solo il giorno della settimana di una data qualsiasi.
Esempio 5: quanti giorni mancano?
$ ORA=$(date +%s)
$ NATALE=$(date -d 2026-12-25 +%s)
$ echo $(( (NATALE - ORA) / 86400 ))
59
$ echo "Mancano $(( (NATALE - ORA) / 86400 )) giorni a Natale"
Mancano 59 giorni a NatalePer fare calcoli tra date si convertono in secondi con %s, si sottraggono e si divide per la durata dell'unità: 60 secondi per i minuti, 3600 per le ore, 86400 per i giorni. L'aritmetica $(( ... )) della shell lavora solo con numeri interi, quindi il risultato è arrotondato per difetto: dal 26 ottobre alle 7:25 al 25 dicembre a mezzanotte passano 59 giorni e 16 ore, che il calcolo riporta come 59.
Esempio 6: convertire da e verso i secondi (epoch)
$ date +%s
1792995941
$ date -d @1792886400
dom 25 ott 2026, 02:00:00, CEST
$ date -u -d @1792886400
dom 25 ott 2026, 00:00:00, UTC
$ date -d "2026-10-25 00:00 UTC" +%s
1792886400Il numero di secondi dal 1° gennaio 1970, detto epoch o timestamp Unix, è il formato usato da molti programmi, database e registri per memorizzare un istante. date +%s lo stampa; con -d @numero si fa il contrario, per capire a quale data corrisponde. L'ultimo comando mostra la conversione di una data in UTC. Nota che lo stesso istante, alle 00:00 UTC del 25 ottobre, è per l'Italia le 02:00 in ora legale (CEST): quella notte l'ora legale finisce.
Esempio 7: altri fusi orari
$ TZ=America/New_York date
lun 26 ott 2026, 02:25:41, EDT
$ TZ=Asia/Tokyo date +%H:%M
15:25
$ TZ=UTC date -d 'TZ="Europe/Rome" 2026-11-05 15:00'
gio 5 nov 2026, 14:00:00, UTC
$ ls /usr/share/zoneinfo/Europe | head -n 4
Amsterdam
Andorra
Astrakhan
AthensCon la variabile TZ davanti al comando (vedi l'articolo su export) si mostra l'ora in un altro fuso orario, senza cambiare nulla nel sistema. I nomi dei fusi sono nella cartella /usr/share/zoneinfo, nella forma Continente/Città. Il terzo esempio converte un orario di Roma in UTC, indicando il fuso dentro la data con TZ="...": comodo per organizzare un incontro con persone in altri paesi.
Esempio 8: formati standard e data di un file
$ date -Iseconds
2026-10-26T07:25:41+01:00
$ date -R
Mon, 26 Oct 2026 07:25:41 +0100
$ date -r backup-2026-10-26.tar.gz
lun 26 ott 2026, 07:20:11, CET
$ date -r /etc/passwd +%F
2026-09-03-I (ISO 8601, con seconds per includere i secondi) e -R (RFC 5322, il formato delle email e delle intestazioni HTTP) stampano la data nei formati standard, non ambigui e interpretabili da altri programmi. -r file mostra la data di ultima modifica di un file. Per vedere tutte le date di un file (modifica, accesso, cambio) si usa stat.
Esempio 9: il registro di ieri
$ IERI=$(LC_ALL=C date -d yesterday +%d/%b/%Y)
$ echo "$IERI"
25/Oct/2026
$ grep "$IERI" /var/log/nginx/access.log | wc -l
8421
$ date -d yesterday +%d/%b/%Y
25/ott/2026I registri di nginx e Apache scrivono la data con il mese in inglese (25/Oct/2026). In un sistema italiano date +%b darebbe ott, e grep non troverebbe niente. La soluzione è LC_ALL=C davanti a date, che forza i nomi in inglese. Un classico trucco per estrarre dai registri solo le righe di una giornata (vedi gli articoli su grep e wc).
Esempio 10: cambiare l'ora del sistema, e il modo giusto
$ timedatectl
Local time: lun 2026-10-26 07:25:41 CET
Universal time: lun 2026-10-26 06:25:41 UTC
Time zone: Europe/Rome (CET, +0100)
System clock synchronized: yes
NTP service: active
$ sudo timedatectl set-timezone Europe/Rome
$ sudo timedatectl set-ntp true
$ sudo date -s "2026-10-26 07:30:00"Sui sistemi con systemd, lo strumento giusto è timedatectl: mostra data, fuso orario e se l'orologio è sincronizzato, e permette di impostare il fuso (set-timezone) e la sincronizzazione automatica con server di riferimento via rete (set-ntp true, protocollo NTP). Su un server non si imposta l'ora a mano: si lascia a NTP. L'ultimo comando, date -s, imposta l'orologio a mano e richiede sudo: serve solo in casi particolari, come un computer isolato dalla rete o una macchina virtuale di prova.
Esempio 11: uso negli script
#!/bin/bash
LOG="$HOME/backup.log"
INIZIO=$(date +%s)
echo "$(date '+%F %T') inizio backup" >> "$LOG"
tar czf "$HOME/backup-$(date +%F).tar.gz" "$HOME/documenti"
FINE=$(date +%s)
DURATA=$((FINE - INIZIO))
printf '%s fine backup (%02d:%02d:%02d)\n' "$(date '+%F %T')" \
$((DURATA / 3600)) $((DURATA % 3600 / 60)) $((DURATA % 60)) >> "$LOG"
find "$HOME" -maxdepth 1 -name 'backup-*.tar.gz' -mtime +30 -deleteUn piccolo script di backup che usa date in tre modi: per mettere un orario nel registro ('%F %T'), per nominare l'archivio con la data del giorno e per misurare la durata, sottraendo due letture di %s. L'ultima riga elimina con find i backup più vecchi di 30 giorni (-mtime +30), con -delete: provala prima con -print al posto di -delete. Se lo script gira con cron, si può programmare con crontab.
Opzioni utili
+formato: stampa nel formato indicato (%Y,%m,%d,%H,%M,%S,%F,%T,%s…).-d "descrizione": usa la data descritta (in inglese) invece di "adesso";-d @secondiparte da un timestamp.-u: ora universale (UTC);TZ=Fuso date: un altro fuso orario.-I[specificatore]: formato ISO 8601 (-Idate,-Iseconds);-R: formato RFC 5322.-r file: data di ultima modifica di un file.-f file: legge una data per riga da un file e le converte tutte.-s "data": imposta l'orologio (richiedesudo).LC_ALL=C date: nomi in inglese e formato neutro.timedatectl: data, fuso orario e sincronizzazione NTP;cal: calendario del mese (pacchettoncalobsdmainutilssu alcune distribuzioni).
Attenzione a
- Le date con la barra sono ambigue:
date -d "10/11/2026"viene letto in formato americano, cioè 11 ottobre e non 10 novembre. Per evitare errori usa sempre il formato2026-11-10(anno-mese-giorno). - Le parole vanno in inglese:
domani,ierielunedì prossimonon funzionano. Si usatomorrow,yesterday,next monday. - I mesi non sono tutti uguali:
date -d "2026-01-31 +1 month"dà2026-03-03, perché il 31 febbraio non esiste e il calcolo trabocca nel mese dopo. Lo stesso vale perlast montha fine mese. Per calcoli sui mesi, parti dal giorno 1 o dal 15. - Il formato dentro virgolette: se contiene spazi,
date "+%F %T"va scritto tra virgolette, altrimenti la shell lo spezza in due parole edatedà errore. Il+iniziale è obbligatorio. - Il carattere % in
crontab: dentro una riga dicrontabil%è un a capo, e$(date +%F)va scritto$(date +\%F). Nel file dello script non serve (vedi l'articolo sucrontab). - La lingua cambia l'output: i nomi dei mesi e dei giorni dipendono da
LANGe daLC_ALL. Se il risultato serve a un altro programma (come un registro, un nome di file da confrontare o un confronto congrep), blocca la lingua conLC_ALL=C. - L'ora legale: due volte all'anno una "giornata" dura 23 o 25 ore, e i calcoli con i secondi (
/86400) possono sbagliare di un giorno, soprattutto se uno dei due orari è a mezzanotte. Per calcoli di giorni è più sicuro usare le12:00come orario, o l'ora UTC. - Non cambiare l'ora a mano sui server: un salto dell'orologio può confondere
cron, i registri, i certificati e le sessioni, e dopo poco NTP la corregge. Usatimedatectl set-ntp truee, se serve,chronyosystemd-timesyncd. - Orologio hardware e fuso orario: nei sistemi con doppio avvio (Linux e Windows) l'orologio può risultare sfasato di un'ora o due, perché i due sistemi interpretano diversamente l'orologio della scheda madre. Si risolve con
timedatectl set-local-rtcoppure impostando Windows su UTC. - Un solo secondo di differenza: se chiami
datepiù volte per ricostruire una stringa ($(date +%F)e poi$(date +%T)), tra le due chiamate l'ora può cambiare, e a mezzanotte anche il giorno. Se serve la coerenza, salva il valore in una variabile e riusalo (ORA=$(date +%F_%T)). - GNU contro BSD:
-dcon le espressioni a parole esiste solo nella versione GNU. Su macOS e BSD si usa-v(date -v+1d) e le conversioni sono diverse. Gli script portabili vanno testati sul sistema di destinazione. - Il timestamp Unix è in UTC:
%sè lo stesso in tutto il mondo, mentre le altre sequenze dipendono dal fuso orario. Per confrontare istanti diversi, il timestamp è il modo più affidabile.
Riepilogo
| Comando | Cosa fa |
|---|---|
date | Data e ora attuali |
date +%F | Data nel formato 2026-10-26 |
date "+%F %T" | Data e ora, per i registri |
date +%Y%m%d-%H%M%S | Marca temporale per nomi di file |
date -d tomorrow +%F | La data di domani |
date -d "next friday" +%F | La data del prossimo venerdì |
date -d "2026-12-25 - 1 week" +%F | Calcola una data a partire da un'altra |
date +%s | Secondi dal 1° gennaio 1970 (UTC) |
date -d @1792886400 | Converte un timestamp in data |
date -u | Ora universale (UTC) |
TZ=Asia/Tokyo date | Ora in un altro fuso orario |
date -Iseconds | Formato ISO 8601 |
date -r file | Data di ultima modifica di un file |
LC_ALL=C date -d yesterday +%d/%b/%Y | Data di ieri nel formato dei registri web |
timedatectl | Stato di data, fuso orario e sincronizzazione |