Here's the next version. The start cmd might look a little scary (to me at least), but now it starts the cmd without leaving the actual "su" command around.

Here's a senseless example configuration:

<primitive id="sleep" class="ocf" type="anything" provider="dk">
<instance_attributes id="ia-sleep">
<attributes>
<nvpair id="ia-sleep-1" name="binfile" value="/bin/sleep"/>
<nvpair id="ia-sleep-2" name="cmdline_options" value="50000"/>
<nvpair id="ia-sleep-3" name="pidfile" value="/tmp/sleep.pid"/>
<nvpair id="ia-sleep-4" name="logfile" value="/tmp/sleep.log"/>
<nvpair id="ia-sleep-5" name="errlogfile" value="/tmp/sleep.err.log"/>
</attributes>
</instance_attributes>
<operations>
<op id="op-sleep-1" name="monitor" interval="60s" timeout="15s"/>
</operations>
</primitive>

Regards
Dominik
#!/bin/sh
#
#       OCF Resource Agent compliant resource script.
#
# Copyright (c) 2008 IN-telegence GmbH & Co. KG, Dominik Klein
#                    All Rights Reserved.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of version 2 of the GNU General Public License as
# published by the Free Software Foundation.
#
# This program is distributed in the hope that it would be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
#
# Further, this software is distributed without any warranty that it is
# free of the rightful claim of any third person regarding infringement
# or the like.  Any license provided herein, whether implied or
# otherwise, applies only to this software file.  Patent licenses, if
# any, provided herein do not apply to combinations of this program with
# other software, or any other product whatsoever.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write the Free Software Foundation,
# Inc., 59 Temple Place - Suite 330, Boston MA 02111-1307, USA.

# OCF instance parameters
#       OCF_RESKEY_binfile
#       OCF_RESKEY_cmdline_options
#       OCF_RESKEY_pidfile
#       OCF_RESKEY_logfile
#       OCF_RESKEY_errlogfile
#       OCF_RESKEY_user
#       OCF_RESKEY_stop_escalation_sec
#       OCF_RESKEY_monitor_hook

# Initialization:
. ${OCF_ROOT}/resource.d/heartbeat/.ocf-shellfuncs

getpid() { # make sure that the file contains a number
        grep '^[0-9][0-9]*$' $1
}

anything_status() {
        if test -f "$pidfile" && pid=`getpid $pidfile` && kill -0 $pid
        then
                return $OCF_RUNNING
        else
                return $OCF_NOT_RUNNING
        fi
}

anything_start() {
        if ! anything_status
        then
                if [ -n "$logfile" -a -n "$errlogfile" ]
                then
                        # We have logfile and errlogfile, so redirect STDOUT 
und STDERR to different files
                        cmd="su - $user -c \"nohup $binfile $cmdline_options >> 
$logfile 2>> $errlogfile & \"'echo \$!' "
                else if [ -n "$logfile" ]
                        then
                                # We only have logfile so redirect STDOUT and 
STDERR to the same file
                                cmd="su - $user -c \"nohup $binfile 
$cmdline_options >> $logfile 2>&1 & \"'echo \$!' "
                        else
                                # We have neither logfile nor errlogfile, so 
we're not going to redirect anything
                                cmd="su - $user -c \"nohup $binfile 
$cmdline_options & \"'echo \$!'"
                        fi
                fi
                ocf_log debug "Starting $process: $cmd"
                # Execute the command as created above
                eval $cmd > $pidfile
                #echo $! > $pidfile
                if anything_status
                then
                        ocf_log debug "$process: $cmd started successfully"
                        return $OCF_SUCCESS
                else 
                        ocf_log err "$process: $cmd could not be started"
                        return $OCF_ERR_GENERIC
                fi
        else
                # If already running, consider start successful
                ocf_log debug "$process: $cmd is already running"
                return $OCF_SUCCESS
        fi
}

anything_stop() {
        if anything_status
        then
                pid=`getpid $pidfile`
                kill $pid
                i=0
                while [ $i -lt $stop_escalation_sec ]
                do
                        # there may be programs without command line options
                        sleep 1
                        if ! anything_status
                        then
                                rm -f $pidfile > /dev/null 2>&1
                                return $OCF_SUCCESS
                        fi
                        let "i++"
                done
                # one last attempt with sigkill
                ocf_log warn "Stop $process: $process could not be stopped by 
SIGTERM, now sending SIGKILL."
                kill -9 $pid
                if ! anything_status
                then
                        ocf_log debug "Stop $process: SIGKILL did the job."
                        return $OCF_SUCCESS
                else
                        ocf_log err "Stop $process: failed to stop even with 
SIGKILL."
                        return $OCF_ERR_GENERIC
                fi
        else
                # was not running, so stop can be considered successful
                rm -f $pidfile > /dev/null 2>&1
                return $OCF_SUCCESS
        fi
        return $OCF_ERR_GENERIC
}

anything_monitor() {
        anything_status
        ret=$?
        if [ $ret -eq $OCF_SUCCESS ]
        then
                # implement your deeper monitor operation here
                if [ -n "$OCF_RESKEY_monitor_hook" ]; then
                        eval "$OCF_RESKEY_monitor_hook"
                        return
                else
                        true
                fi
        else
                return $ret
        fi
}

process="$OCF_RESOURCE_INSTANCE"
binfile="$OCF_RESKEY_binfile"
cmdline_options="$OCF_RESKEY_cmdline_options"
pidfile="$OCF_RESKEY_pidfile"
[ -z "$pidfile" -a -n "$binfile" ] && pidfile=/var/run/anything_${process}.pid
logfile="$OCF_RESKEY_logfile"
errlogfile="$OCF_RESKEY_errlogfile"
user="$OCF_RESKEY_user"
[ -z "$user" ] && user=root
stop_escalation_sec="$OCF_RESKEY_stop_escalation_sec"
[ -z "$stop_escalation_sec" ] && stop_escalation_sec=10000

#ocf_log debug "binfile $binfile"
#ocf_log debug "cmdline_options $cmdline_options"
#ocf_log debug "logfile $logfile"
#ocf_log debug "errlogfile $errlogfile"
#ocf_log debug "process $process"
#ocf_log debug "pidfile $pidfile"
#ocf_log debug "stop_escalation_sec $stop_escalation_sec"

anything_validate() {
        if [ ! -x "$binfile" ]
        then
                exit $OCF_ERR_INSTALLED
        fi
        if ! id $user &>/dev/null
        then
                exit $OCF_ERR_INSTALLED
        fi
        for filename in "$logfile" "$errlogfile"
        do
                if [ -n "$filename" ]
                then
                        if [ ! -d "$(dirname $filename)" ]
                        then
                                ocf_log err "$(dirname $filename) for $filename 
does not exist! Please create it."
                                exit $OCF_ERR_INSTALLED
                        fi
                fi
        done
        return $OCF_SUCCESS
}

anything_meta() {
cat <<END
<?xml version="1.0"?>
<!DOCTYPE resource-agent SYSTEM "ra-api-1.dtd">
<resource-agent name="anything_ra">
<version>1.0</version>
<longdesc lang="en">
This is a custom OCF RA to start IN-telegence programs
</longdesc>
<shortdesc lang="en">DK's custom OCF resource agent</shortdesc>

<parameters>
<parameter name="binfile" required="1" unique="1">
<longdesc lang="en">
The full name of the binary to be executed
</longdesc>
<shortdesc lang="en">Full path name of the binary to be executed</shortdesc>
<content type="string" default="" />
</parameter>
<parameter name="cmdline_options">
<longdesc lang="en">
Command line options to pass to the binary
</longdesc>
<shortdesc lang="en">Command line options</shortdesc>
<content type="string" />
</parameter>
<parameter name="pidfile">
<longdesc lang="en">
File to read/write the PID from/to.
</longdesc>
<shortdesc lang="en">File to write STDOUT to</shortdesc>
<content type="string" />
</parameter>
<parameter name="logfile">
<longdesc lang="en">
File to write STDOUT to
</longdesc>
<shortdesc lang="en">File to write STDOUT to</shortdesc>
<content type="string" />
</parameter>
<parameter name="errlogfile">
<longdesc lang="en">
File to write STDERR to
</longdesc>
<shortdesc lang="en">File to write STDERR to</shortdesc>
<content type="string" />
</parameter>
<parameter name="user">
<longdesc lang="en">
User to run the command as
</longdesc>
<shortdesc lang="en">User to run the command as</shortdesc>
<content type="string" default="root"/>
</parameter>
<parameter name="stop_escalation_sec">
<longdesc lang="en">
In the stop operation: Seconds to wait for kill -TERM to succeed
before sending kill -KILL. Defaults to 10000, which usually translates to 
the configured stop operation timeout (unless that is really looong).
</longdesc>
<shortdesc lang="en">seconds to wait before SIGKILL in stop</shortdesc>
<content type="string" default="10000"/>
</parameter>
<parameter name="monitor_hook">
<longdesc lang="en">
Command to run in monitor operation
</longdesc>
<shortdesc lang="en">Command to run in monitor operation</shortdesc>
<content type="string"/>
</parameter>
</parameters>
<actions>
<action name="start"   timeout="90" />
<action name="stop"    timeout="100" />
<action name="monitor" depth="0"  timeout="20" interval="10" />
<action name="meta-data"  timeout="5" />
<action name="validate-all"  timeout="5" />
</actions>
</resource-agent>
END
exit 0
}

case "$1" in
        meta-data|metadata|meta_data)
                anything_meta
        ;;
        start)
                anything_start
        ;;
        stop)
                anything_stop
        ;;
        monitor)
                anything_monitor
        ;;
        validate-all)
                anything_validate
        ;;
        promote|demote|notify)
                exit $OCF_SUCCESS
        ;;
        *)
                ocf_log err "$0 was called with unsupported arguments: $*"
                exit $OCF_ERR_GENERIC
        ;;
esac
_______________________________________________
Linux-HA mailing list
[email protected]
http://lists.linux-ha.org/mailman/listinfo/linux-ha
See also: http://linux-ha.org/ReportingProblems

Reply via email to