[ Team LiB ] Previous Section Next Section

Recipe 9.32 Writing Log Entries via Shell Scripts

9.32.1 Problem

You want to add information to the system log using a shell script.

9.32.2 Solution

Use logger and this handy API, which emulates that of Perl and C:

syslog-api.sh:
#!/bin/sh
ident="$USER"
facility="user"
openlog( ) {
        if [ $# -ne 3 ]
        then
                echo "usage: openlog ident option[,option,...] facility" 1>&2
                return 1
        fi
        ident="$1"
        local option="$2"
        facility="$3"
        case ",$option," in
                *,pid,*)            ident="$ident[$$]";;
        esac
}

syslog( ) {
        if [ $# -lt 2 ]
        then
                echo "usage: syslog [facility.]priority format ..." 1>&2
                return 1
        fi
        local priority="$1"
        local format="$2"
        shift 2
        case "$priority" in
                *.*)    ;;
                *)      priority="$facility.$priority";;
        esac
        printf "$format" "$@" | logger -t "$ident" -p "$priority"
}

closelog( ) {
        ident="$USER"
        facility="user"
}

To use the functions in a shell script:

#!/bin/sh
source syslog-api.sh
openlog `basename "$0"` pid local3
syslog warning "%d connections from %s" $count $host
syslog authpriv.err "intruder alert!"
closelog

The syslog API

The standard API for the system logger provides the following three functions for Perl scripts and C programs, and we provide an implementation for Bash shell scripts as well. [Recipe 9.32]

openlog

Specify the identifier prepended to each message, conventionally the basename of the program or script. An option is provided to add the process ID as well; other options are less commonly used. Finally, a default facility is established for subsequent messages: local0 through local6 are good choices.

syslog

Send messages. It is used like printf, with an added message priority. Specify a facility to override the default established by openlog: this should be done sparingly, e.g., to send security messages to authpriv. Each message should be a single line—omit newlines at the end of the messages too. Don't use data from untrusted sources in the format string, to avoid security holes that result when the data is maliciously crafted to contain unexpected "%" characters (this advice applies to any function using printf-style formatting): use "%s" as the format string instead, with the insecure data as a separate argument.

closelog

Close the socket used to communicate with the system logger. This function can be employed to clean up file descriptors before forking, but in most cases is optional.

9.32.3 Discussion

Our recipe shows how to use shell functions to implement the syslog API (see The syslog API) within shell scripts. The openlog function can be readily extended to recognize other, comma-separated options. The syslog function uses the same syntax as logger for the optional facility. The closelog function just restores the defaults for the identifier and facility, which are stored in global variables. These functions can be stored in a separate file and sourced by other shell scripts, as a convenient alternative to the direct use of logger.

9.32.4 See Also

logger(1), syslog(3).

    [ Team LiB ] Previous Section Next Section