J'ai un script en cours d'exécution que je génère dans un fichier journal:
script.sh >> /var/log/logfile
Je voudrais ajouter un horodatage avant chaque ligne ajoutée au journal. Comme:
Sat Sep 10 21:33:06 UTC 2011 The server has booted up. Hmmph.
Y a-t-il un jujitsu que je peux utiliser?
Vous pouvez diriger la sortie du script via une boucle qui préfixe la date et l'heure actuelles:
./script.sh | while IFS= read -r line; do printf '%s %s\n' "$(date)" "$line"; done >>/var/log/logfile
Si vous l'utilisez beaucoup, il est facile de créer une fonction bash pour gérer la boucle:
adddate() {
while IFS= read -r line; do
printf '%s %s\n' "$(date)" "$line";
done
}
./thisscript.sh | adddate >>/var/log/logfile
./thatscript.sh | adddate >>/var/log/logfile
./theotherscript.sh | adddate >>/var/log/logfile
Voir ts
du paquet Ubuntu moreutils
:
command | ts
Ou si $command
effectue une mise en mémoire tampon automatique (nécessite expect-dev
paquet):
unbuffer command | ts
La commande ( date fournira ces informations
date -u
Sat Sep 10 22:39:24 UTC 2011
afin que vous puissiez
echo $(date -u) "Some message or other"
c'est ce que tu voulais?
Vous pouvez simplement echo les sorties de commande dans le fichier journal. c'est à dire,
echo "`date -u` `./script.sh`" >> /var/log/logfile
Ça marche vraiment :)
Exemple:
[sparx@E1]$ ./script.sh
Hello Worldy
[sparx@E1]$ echo "`date -u` `./script.sh`" >> logfile.txt
[sparx@E1]$ cat logfile.txt
Mon Sep 12 20:18:28 UTC 2011 Hello Worldy
[sparx@E1]$
Faire un config.sh
fichier
#!/usr/bin/env bash
LOGFILE="/path/to/log.log"
TIMESTAMP=`date "+%Y-%m-%d %H:%M:%S"`
Lorsque vous devez envoyer au fichier journal, utilisez
#!/usr/bin/env bash
source /path/to/config.sh
echo "$TIMESTAMP Say what you are doing" >> $LOGFILE
do_what_you_want >> $LOGFILE
Le fichier journal ressemblera à
2013-02-03 18:22:30 Say what you are doing
Il sera donc facile de trier par date
La réponse acceptée https://serverfault.com/a/310104 peut être un peu lente, si beaucoup de lignes doivent être traitées, avec la surcharge de démarrage du processus date
permettant environ 50 lignes par seconde dans Ubuntu, et seulement environ 10-20 dans Cygwin.
Lorsque bash
peut être supposé, une alternative plus rapide serait le printf
intégré avec son spécificateur de format %(...)T
. Comparer
>> while true; do date; done | uniq -c
47 Wed Nov 9 23:17:18 STD 2016
56 Wed Nov 9 23:17:19 STD 2016
55 Wed Nov 9 23:17:20 STD 2016
51 Wed Nov 9 23:17:21 STD 2016
50 Wed Nov 9 23:17:22 STD 2016
>> while true; do printf '%(%F %T)T\n'; done | uniq -c
20300 2016-11-09 23:17:56
31767 2016-11-09 23:17:57
32109 2016-11-09 23:17:58
31036 2016-11-09 23:17:59
30714 2016-11-09 23:18:00
Tu veux dire comme:
(date && script.sh) >> /var/log/logfile
Essaye ça
timestamp()
{
date +"%Y-%m-%d %T"
}
Appelez cette fonction d'horodatage dans chaque commande d'écho:
echo "$(timestamp): write your log here" >> /var/log/<logfile>.log
script.sh | gawk '{ print strftime("[%Y-%m-%d %H:%M:%S]"), $0 }' >> /var/log/logfile
awk
s'exécute rapidement et est capable de fonctionner en tant que filtre de tuyau Unix et imprime la date de lui-même.
gawk '{ print strftime("[%Y-%m-%d %H:%M:%S]"), $0 }'
Essayons de le comparer:
yes |head -5000000 |gawk '{ print strftime("[%Y-%m-%d %H:%M:%S]"), $0 }' |uniq -c
461592 [2017-02-28 19:46:44] y
488555 [2017-02-28 19:46:45] y
491205 [2017-02-28 19:46:46] y
498568 [2017-02-28 19:46:47] y
502605 [2017-02-28 19:46:48] y
494048 [2017-02-28 19:46:49] y
493299 [2017-02-28 19:46:50] y
498005 [2017-02-28 19:46:51] y
502916 [2017-02-28 19:46:52] y
495550 [2017-02-28 19:46:53] y
73657 [2017-02-28 19:46:54] y
Sed semble courir beaucoup plus vite,
sed -e "s/^/$(date -R) /"
yes |head -5000000 |sed -e "s/^/$(date -R) /" |uniq -c
5000000 Tue, 28 Feb 2017 19:57:00 -0500 y
Cependant, en y regardant de plus près, le jeu ne semble pas changer le temps,
vmstat 1 | sed -e "s/^/$(date -R) /"
Parce que date
(qui est plus lent d'ailleurs) n'est appelé qu'une seule fois.
Une autre option consiste à configurer une fonction à appeler chaque fois que vous souhaitez générer des données dans votre code:
PrintLog(){
information=$1
logFile=$2
echo "$(date +'%Y-%m-%d %H:%M:%S" $information} >> $logFile
}
Ensuite, chaque fois dans votre code, vous souhaitez l'envoyer à l'appel du fichier journal
PrintLog "Stuff you want to add..." ${LogFileVariable}
Peasy facile....
Voici le contenu de mon fichier journal
xiongyu@ubuntu:~/search_start_sh$ tail restart_scrape.log
2017-08-25 21:10:09 scrape_yy_news_main.py got down, now I will restart it
2017-08-25 21:10:09 check_yy_news_warn.py got down, now I will restart it
2017-08-25 21:14:53 scrape_yy_news_main.py got down, now I will restart it
une partie de mon contenu Shell est comme ci-dessous
log_file="restart_scrape.log"
TIMESTAMP=`date "+%Y-%m-%d %H:%M:%S"`
echo "$TIMESTAMP $search_py_file got down, now I will restart it" | tee -a $log_file
Ce script imprime la sortie dans le terminal et enregistre également dans le fichier journal.
#!/bin/bash
MY_LOG=/var/log/output.log
echolog(){
if [ $# -eq 0 ]
then cat - | while read -r message
do
echo "$(date +"[%F %T %Z] -") $message" | tee -a $MY_LOG
done
else
echo -n "$(date +'[%F %T %Z]') - " | tee -a $MY_LOG
echo $* | tee -a $MY_LOG
fi
}
echolog "My script is starting"
whoami | echolog
Exemple de sortie:
[2017-10-29 19:46:36 UTC] - My script is starting
[2017-10-29 19:46:36 UTC] - root
Pipe un "sed":
script.sh | sed "s|^|$('date') :: |" >> /var/log/logfile