Convalida della data nella shell


14

Voglio convalidare il seguente formato data nello script della shell

2015-Jul-13

Sto usando date -d "2015-Jul-13" +"%Y-%b-%d"ma sta dando errore come

date: invalid date '2015-Jul-13'

@Pandya: OP è chiaro sulla sua domanda. OP vuole convalidare (verificare che la data inserita sia valida o meno) il formato data indicato ma sta dicendo che la data inserita non è valida.
Thushi,

GNU datenon riconosce YYYY-MMM-DD. Potresti usare YYYY-MM-DDo DD MMM YYYYinvece?
roaima,

Sono abbastanza sicuro at, e - penso - lo touchfa anche. Ho scritto una funzione di shell di convalida della data basata su touchuna volta ... no, non touch- gestisce solo i numeri, ma atesegue un analisi abbastanza approfondita ...
mikeserv

@Thushi chiariamo il nostro commento ridondante
Pandya,

6
Ho letto male il titolo: la convalida della data è un inferno
Adam Davis,

Risposte:


12

GNU datenon supporta YYYY-MMM-DD. Tuttavia, capisce DD-MMM-YYYY. Quindi, se devi davvero gestire le date di questo formato, puoi farlo con qualcosa del genere, che scambia semplicemente gli argomenti con un formato che dateprevede:

ymd='2015-Jul-13'

dmy=$(echo "$ymd" | awk -F- '{ OFS=FS; print $3,$2,$1 }')
if date --date "$dmy" >/dev/null 2>&1
then
    echo OK
fi

Ecco una soluzione all shell. Scomponendolo, le IFS=-istruzioni dicono alla shell di dividere una riga di comando imminente per trattino -anziché spazio bianco. Il set $ymdanalizza la $ymdvariabile come per una linea di comando, ma ora divide da un trattino, assegnando valori ai parametri $1, $2 e segg . L' echo "$3-$2-$1"output banalmente i tre valori acquisiti in ordine inverso.

ymd='2015-Jul-13'

dmy=$(IFS=-; set $ymd; echo "$3-$2-$1")
if date --date "$dmy" >/dev/null 2>&1
then
    echo OK
fi

@mikeserv: Coolness! Ha funzionato con: ymd=$(IFS=-;set $ymd; echo "$3-$2-$1") potresti forse rivelare la magia dietro il setcomando?
giovedì

11

Dalla manpage: -

DATE STRING
       The --date=STRING is a mostly free format human readable date string such as "Sun, 29 Feb 2004 16:21:42 -0800"
       or  "2004-02-29  16:21:42" or even "next Thursday".  A date string may contain items indicating calendar date,
       time of day, time zone, day of week, relative time, relative date, and numbers.  An empty string indicates the
       beginning  of  the  day.   The  date string format is more complex than is easily documented here but is fully
       described in the info documentation.

Ma sembra non riconoscere il YYYY-MMM-DDformato. Quindi, puoi usare dal basso o simili come:

$ date -d "2015-07-13" +"%Y-%b-%d"
2015-Jul-13
$ date -d "Jul 13 2015" +"%Y-%b-%d"
2015-Jul-13
$ date -d "13 Jul 2015" +"%Y-%b-%d"
2015-Jul-13

O devi convertirlo / riformattarlo prima di inviarlo a date!

Vedi anche Come si specifica un formato per l'input fino ad oggi?


Consiglio di visitare: formati di input data .

Ecco le regole.

Per i mesi numerici , è consentito il formato ISO 8601 "anno-mese-giorno", dove l'anno è un numero positivo, il mese è un numero compreso tra 01 e 12 e il giorno è un numero compreso tra 01 e 31. Deve essere presente uno zero iniziale se un numero è inferiore a dieci. Se l'anno è 68 o inferiore, viene aggiunto 2000; in caso contrario, se l'anno è inferiore a 100, viene aggiunto 1900. Il costrutto "mese / giorno / anno", popolare negli Stati Uniti, è accettato. Anche "mese / giorno", omettendo l'anno.

I mesi letterali possono essere indicati per esteso: "gennaio", "febbraio", "marzo", "aprile", "maggio", "giugno", "luglio", "agosto", "settembre", "ottobre", " Novembre "o" Dicembre ". I mesi letterali possono essere abbreviati nelle prime tre lettere, eventualmente seguiti da un punto abbreviato. È anche consentito scrivere "settembre" anziché "settembre".

Quando i mesi sono scritti letteralmente , la data del calendario può essere indicata come una delle seguenti:

 giorno mese anno
 giorno mese
 mese giorno anno
 giorno-mese-anno

enfatizzato da me

Qui puoi vedere che non esiste un formato come anno-mese-giorno ! (per mesi sono scritti letteralmente)


7

Con zshte puoi usare il strftimebuiltin (disponibile via zsh/datetime) con -r(reverse):

timestring in formato strftime -r

che utilizza il formato per analizzare il timestring e generare il numero di secondi dall'epoca:

zmodload zsh/datetime
strftime -r %Y-%b-%d 2015-Jul-13
1436734800

Questo errore se la data non è valida:

strftime -r %Y-%b-%d 2015-Jul-33
zsh: strftime: 5: formato non corrispondente

Puoi anche convertire i secondi dall'epoca in qualsiasi altro formato di data standard / personalizzato, ad es

strftime '%A, %B %d, %Y' 1447970400
Venerdì 20 novembre 2015
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.