LinuxQuestions.org

LinuxQuestions.org (/questions/)
-   Programming (https://www.linuxquestions.org/questions/programming-9/)
-   -   log bash script output to file with timestamp (https://www.linuxquestions.org/questions/programming-9/log-bash-script-output-to-file-with-timestamp-936746/)

daisychick 03-27-2012 02:33 PM

log bash script output to file with timestamp
 
I'm trying to get this little script here to output to a logfile with a timestamp. I've got everything mostly working but the timestamp. Is there a better way to do this? it's my first attempt at writing a script.

Code:

#!/bin/bash
#
LOGFILE=/home/test/test.log
echo "`date +%H:%M:%S : Starting work" >> $LOGFILE
#
service test stop >> $LOGFILE
#
mv /var/run/test/test.pid /var/run/test/test.pid.bak
#
echo "`date +%H:%M:%S : process file moved" >> $LOGFILE
#
service test start >> $LOGFILE
#
echo "`date +%H:%M:%S : Finished" >> $LOGFILE


MensaWater 03-27-2012 02:47 PM

I'd say that's what most people do to log from scripts.

However you are doing only >>$LOGFILE which means you're only sending standard output (STDOUT - a/k/a file descriptor 1) to the log. If there were errors it would go there. Most people redirect standard error (STDERR - a/k/a file descriptor 2) to the log as well. The shorthand to do this would be:

>>$LOGFILE 2>&1

The 2 >&1 says to redirect file descriptor 2 to file descriptor 1. Note that order is important. Typing:
2>&1 >>$LOGFILE wouldn't work because STDERR would go to whatever STDOUT was defined as BEFORE you did the redirect of STDOUT.

Another option is not to put the redirects in the script at all but rather to do them at invocation. For example if your script were called billybob.sh you could type:

billybob.sh >>pathto/logfile 2>&1
This is commonly done if you're putting the script into cron:

* * * * * /pathto/billybob.sh >>pathto/logfile 2>&1

It's really a matter of personal preference. Even in cron you can call a script that has its own internal logging
defined.

daisychick 03-27-2012 03:06 PM

ahhhh. I had read that but it didn't make sense. Now it does. I'm still having a problem with the timestamp though. It prints exactly what I typed instead of the actual time and date.

i.e.
Code:

date +%H:%M:%S : Starting work
instead of
Code:

03262012 20:37.00 : starting work
------------------latest script-----------------
Code:

#!/bin/bash
#
LOGFILE=/home/test/test.log
echo "`date +%H:%M:%S : Starting work" >> $LOGFILE 2>&1
#
service test stop >> $LOGFILE 2>&1
#
mv /var/run/test/test.pid /var/run/test/test.pid.bak
#
echo "`date +%H:%M:%S : process file moved" >> $LOGFILE 2>&1
#
service test start >> $LOGFILE 2>&1
#
echo "`date +%H:%M:%S : Finished" >> $LOGFILE 2>&1


colucix 03-27-2012 03:42 PM

You missed the closing backticks in the command substitutions:
Code:

echo "`date +%H:%M:%S` : Starting work" >> $LOGFILE 2>&1
Furthermore, if you want the calendar date, not only the time, you should have something like this:
Code:

date "+%m%d%Y %H:%M:%S"
or simply
Code:

date "+%m%d%Y %T"
An additional note: since you're using bash, why not try the new syntax for command substitution (unless you care for compatibility with the older Bourne Shell)? Example:
Code:

echo "$(date "+%m%d%Y %T") : Starting work" >> $LOGFILE 2>&1
I think it is more readable and less prone to errors than backticks. Hope this helps.

daisychick 03-27-2012 04:56 PM

Wow! that's awesome! I'll give it a try! thank you so so much! (yes I'm very excited I learned something cool and new)

David the H. 03-28-2012 06:50 AM

$(..) is defined in the posix standard, which means it's supported by all modern bourne-based shells. So unless you have to script for really old shells, there's no reason at all to use backticks any more, and several reasons not to.

$(..) is highly recommended over `..`

Frankly, the backticks have been deprecated for so long that I have to wonder just where and why they are still being learned by so many new scripters. Just who is it that keeps teaching them?

colucix 03-28-2012 07:13 AM

Quote:

Originally Posted by David the H. (Post 4638625)
Frankly, the backticks have been deprecated for so long that I have to wonder just where and why they are still being learned by so many new scripters. Just who is it that keeps teaching them?

Unfortunately, even the Advanced Bash Scripting Guide starts the chapter on command substitution with backticks. The new syntax is relegated to the bottom of the chapter! :(

MensaWater 03-28-2012 07:24 AM

Yep - I've been doing shell scripting for many years but it is only in the last couple that I started using $() instead of back ticks - mainly because of 2 different presentations I saw at user group meetings about shell scripting in which both presenters mentioned it among other things they were suggesting.

The nesting is a major benefit to using $().

daisychick 03-29-2012 04:42 PM

Quote:

Originally Posted by David the H. (Post 4638625)
Frankly, the backticks have been deprecated for so long that I have to wonder just where and why they are still being learned by so many new scripters. Just who is it that keeps teaching them?

Google... You search, your read, you learn. Then you realize you broke something and come here. I don't know about most, but I try to research something before coming to the community and asking for help so I have a basic grasp of the concept. (Also because I'm the first to ask someone "did you read the FAQs??! Did you try google?")

chrism01 03-29-2012 08:45 PM

In my case I've been doing *nix for many years, going back to before when linux became commonly/commercially available.
Back then we only had backticks & they still exist in many many scripts, especially non-bash on non-linux systems.
:)

Which one I use now tends to vary a bit, but I still tend towards them on non-linux ;)

MensaWater 03-30-2012 08:45 AM

Except that even on non-Linux systems ksh or posix shell accepts the $(..) syntax for most UNIX flavors.

When I first started working on UNIX, Linux wasn't even a gleam in Linus' eye. :D

The funny thing about UNIX is that it has been "going away any day now" for over 40 years but is still going strong.

That reminds me of the Dilbert cartoon referenced in Wikipedia:
Quote:

The lamentation "You had ones? Lucky you, all we had were zeros!", commonly used in IT industry[original research?], also originated in a Dilbert comic strip. This dates from a strip from September 1992,[14] in which Dilbert responds by saying "You had zeros? We had to use the letter 'O'".
I'm going to have to dig out the Dilbert book that strip appears in since it seems Wikipedia doubts the research on it.

illiak 05-08-2013 01:50 AM

Quote:

Originally Posted by daisychick (Post 4637995)
I'm trying to get this little script here to output to a logfile with a timestamp. I've got everything mostly working but the timestamp. Is there a better way to do this? it's my first attempt at writing a script.

Code:

#!/bin/bash
#
LOGFILE=/home/test/test.log
echo "`date +%H:%M:%S : Starting work" >> $LOGFILE
#
service test stop >> $LOGFILE
#
mv /var/run/test/test.pid /var/run/test/test.pid.bak
#
echo "`date +%H:%M:%S : process file moved" >> $LOGFILE
#
service test start >> $LOGFILE
#
echo "`date +%H:%M:%S : Finished" >> $LOGFILE


I have created an article with a procedure I have created to support similar function:
http://linuxadvices.blogspot.ru/2013...-to-reuse.html

Here is the code:
Code:

write_log()
{
  while read text
  do
      LOGTIME=`date "+%Y-%m-%d %H:%M:%S"`
      # If log file is not defined, just echo the output
      if [ "$LOG_FILE" == "" ]; then
    echo $LOGTIME": $text";
      else
        LOG=$LOG_FILE.`date +%Y%m%d`
    touch $LOG
        if [ ! -f $LOG ]; then echo "ERROR!! Cannot create log file $LOG. Exiting."; exit 1; fi
    echo $LOGTIME": $text" | tee -a $LOG;
      fi
  done
}



All times are GMT -5. The time now is 05:02 AM.