diff --git a/extra/alerts/alert_file.sh.sample b/extra/alerts/alert_file.sh.sample index 7844c77e60..f6c2211513 100644 --- a/extra/alerts/alert_file.sh.sample +++ b/extra/alerts/alert_file.sh.sample @@ -1,109 +1,122 @@ #!/bin/sh # # Copyright 2015-2021 the Pacemaker project contributors # # The version control history for this file may have further details. # # This source code is licensed under the GNU General Public License version 2 # or later (GPLv2+) WITHOUT ANY WARRANTY. # ############################################################################## # Sample configuration (cib fragment in xml notation) # ================================ # # # # # # # # # # # # # +# Explicitly list all environment variables used, to make static analysis happy +: ${CRM_alert_version:=""} +: ${CRM_alert_recipient:=""} +: ${CRM_alert_node_sequence:=""} +: ${CRM_alert_timestamp:=""} +: ${CRM_alert_kind:=""} +: ${CRM_alert_node:=""} +: ${CRM_alert_desc:=""} +: ${CRM_alert_task:=""} +: ${CRM_alert_rsc:=""} +: ${CRM_alert_attribute_name:=""} +: ${CRM_alert_attribute_value:=""} + # No one will probably ever see this echo, unless they run the script manually. # An alternative would be to log to the system log, or similar. (We can't send # this to the configured recipient, because that variable won't be defined in # this case either.) if [ -z $CRM_alert_version ]; then echo "$0 must be run by Pacemaker version 1.1.15 or later" exit 0 fi # Alert agents must always handle the case where no recipients are defined, # even if it's a no-op (a recipient might be added to the configuration later). if [ -z "${CRM_alert_recipient}" ]; then echo "$0 requires a recipient configured with a full filename path" exit 0 fi debug_exec_order_default="false" # Pacemaker passes instance attributes to alert agents as environment variables. # It is completely up to the agent what instance attributes to support. # Here, we define an instance attribute "debug_exec_order". : ${debug_exec_order=${debug_exec_order_default}} if [ "${debug_exec_order}" = "true" ]; then tstamp=`printf "%04d. " "$CRM_alert_node_sequence"` if [ ! -z "$CRM_alert_timestamp" ]; then tstamp="${tstamp} $CRM_alert_timestamp (`date "+%H:%M:%S.%06N"`): " fi else if [ ! -z "$CRM_alert_timestamp" ]; then tstamp="$CRM_alert_timestamp: " fi fi case $CRM_alert_kind in node) echo "${tstamp}Node '${CRM_alert_node}' is now '${CRM_alert_desc}'" >> "${CRM_alert_recipient}" ;; fencing) # Other keys: # # CRM_alert_node # CRM_alert_task # CRM_alert_rc # echo "${tstamp}Fencing ${CRM_alert_desc}" >> "${CRM_alert_recipient}" ;; resource) # Other keys: # # CRM_alert_target_rc # CRM_alert_status # CRM_alert_rc # if [ ${CRM_alert_interval} = "0" ]; then CRM_alert_interval="" else CRM_alert_interval=" (${CRM_alert_interval})" fi if [ ${CRM_alert_target_rc} = "0" ]; then CRM_alert_target_rc="" else CRM_alert_target_rc=" (target: ${CRM_alert_target_rc})" fi case ${CRM_alert_desc} in Cancelled) ;; *) echo "${tstamp}Resource operation '${CRM_alert_task}${CRM_alert_interval}' for '${CRM_alert_rsc}' on '${CRM_alert_node}': ${CRM_alert_desc}${CRM_alert_target_rc}" >> "${CRM_alert_recipient}" ;; esac ;; attribute) # echo "${tstamp}Attribute '${CRM_alert_attribute_name}' on node '${CRM_alert_node}' was updated to '${CRM_alert_attribute_value}'" >> "${CRM_alert_recipient}" ;; *) echo "${tstamp}Unhandled $CRM_alert_kind alert" >> "${CRM_alert_recipient}" env | grep CRM_alert >> "${CRM_alert_recipient}" ;; esac diff --git a/extra/alerts/alert_smtp.sh.sample b/extra/alerts/alert_smtp.sh.sample index 5da83ade4a..62bfc41517 100644 --- a/extra/alerts/alert_smtp.sh.sample +++ b/extra/alerts/alert_smtp.sh.sample @@ -1,106 +1,118 @@ #!/bin/sh # -# Copyright 2016-2017 the Pacemaker project contributors +# Copyright 2016-2021 the Pacemaker project contributors # # The version control history for this file may have further details. # # This source code is licensed under the GNU General Public License version 2 # or later (GPLv2+) WITHOUT ANY WARRANTY. # ############################################################################## # # Sample configuration (cib fragment in xml notation) # ================================ # # # # # # # # # # # # +# Explicitly list all environment variables used, to make static analysis happy +: ${CRM_alert_version:=""} +: ${CRM_alert_recipient:=""} +: ${CRM_alert_timestamp:=""} +: ${CRM_alert_kind:=""} +: ${CRM_alert_node:=""} +: ${CRM_alert_desc:=""} +: ${CRM_alert_task:=""} +: ${CRM_alert_rsc:=""} +: ${CRM_alert_attribute_name:=""} +: ${CRM_alert_attribute_value:=""} + email_client_default="sendmail" email_sender_default="hacluster" email_recipient_default="root" : ${email_client=${email_client_default}} : ${email_sender=${email_sender_default}} email_recipient="${CRM_alert_recipient-${email_recipient_default}}" node_name=`uname -n` cluster_name=`crm_attribute --query -n cluster-name -q` email_body=`env | grep CRM_alert_` if [ ! -z "${email_sender##*@*}" ]; then email_sender="${email_sender}@${node_name}" fi if [ ! -z "${email_recipient##*@*}" ]; then email_recipient="${email_recipient}@${node_name}" fi if [ -z ${CRM_alert_version} ]; then email_subject="Pacemaker version 1.1.15 or later is required for alerts" else case ${CRM_alert_kind} in node) email_subject="${CRM_alert_timestamp} ${cluster_name}: Node '${CRM_alert_node}' is now '${CRM_alert_desc}'" ;; fencing) email_subject="${CRM_alert_timestamp} ${cluster_name}: Fencing ${CRM_alert_desc}" ;; resource) if [ ${CRM_alert_interval} = "0" ]; then CRM_alert_interval="" else CRM_alert_interval=" (${CRM_alert_interval})" fi if [ ${CRM_alert_target_rc} = "0" ]; then CRM_alert_target_rc="" else CRM_alert_target_rc=" (target: ${CRM_alert_target_rc})" fi case ${CRM_alert_desc} in Cancelled) ;; *) email_subject="${CRM_alert_timestamp} ${cluster_name}: Resource operation '${CRM_alert_task}${CRM_alert_interval}' for '${CRM_alert_rsc}' on '${CRM_alert_node}': ${CRM_alert_desc}${CRM_alert_target_rc}" ;; esac ;; attribute) # email_subject="${CRM_alert_timestamp} ${cluster_name}: The '${CRM_alert_attribute_name}' attribute of the '${CRM_alert_node}' node was updated in '${CRM_alert_attribute_value}'" ;; *) email_subject="${CRM_alert_timestamp} ${cluster_name}: Unhandled $CRM_alert_kind alert" ;; esac fi if [ ! -z "${email_subject}" ]; then case $email_client in # This sample script supports only sendmail for sending the email. # Support for additional senders can easily be added by adding # new cases here. sendmail) sendmail -t -r "${email_sender}" <<__EOF__ From: ${email_sender} To: ${email_recipient} Return-Path: ${email_sender} Subject: ${email_subject} ${email_body} __EOF__ ;; *) ;; esac fi diff --git a/extra/alerts/alert_snmp.sh.sample b/extra/alerts/alert_snmp.sh.sample index 8354f82308..841f30f0c7 100644 --- a/extra/alerts/alert_snmp.sh.sample +++ b/extra/alerts/alert_snmp.sh.sample @@ -1,183 +1,186 @@ #!/bin/sh # # Copyright 2013 Florian CROUZAT # Later changes copyright 2013-2021 the Pacemaker project contributors # # The version control history for this file may have further details. # # This source code is licensed under the GNU General Public License version 2 # or later (GPLv2+) WITHOUT ANY WARRANTY. # # Description: Manages a SNMP trap, provided by NTT OSSC as a # script under Pacemaker control # ############################################################################## # This sample script assumes that only users who already have # hacluster-equivalent access to the cluster nodes can edit the CIB. Otherwise, # a malicious user could run commands as hacluster by inserting shell code into # the trap_options or timestamp-format parameters. # # Sample configuration (cib fragment in xml notation) # ================================ # # # # # # # # # # # # # # ================================ # # This uses the official Pacemaker MIB. # 1.3.6.1.4.1.32723 has been assigned to the project by IANA: # http://www.iana.org/assignments/enterprise-numbers -if [ -z "$CRM_alert_version" ]; then - echo "$0 must be run by Pacemaker version 1.1.15 or later" - exit 0 -fi - -if [ -z "$CRM_alert_recipient" ]; then - echo "$0 requires a recipient configured with the SNMP server IP address" - exit 0 -fi - # Defaults for user-configurable values trap_binary_default="/usr/bin/snmptrap" trap_version_default="2c" trap_options_default="" trap_community_default="public" trap_node_states_default="all" trap_fencing_tasks_default="all" trap_resource_tasks_default="all" trap_monitor_success_default="false" trap_add_hires_timestamp_oid_default="true" trap_snmp_persistent_dir_default="/var/lib/pacemaker/snmp" trap_ignore_int32_default=2147483647 # maximum Integer32 value trap_ignore_string_default="n/a" # doesn't conflict with valid XML IDs # Ensure all user-provided variables have values. : ${trap_binary=${trap_binary_default}} : ${trap_version=${trap_version_default}} : ${trap_options=${trap_options_default}} : ${trap_community=${trap_community_default}} : ${trap_node_states=${trap_node_states_default}} : ${trap_fencing_tasks=${trap_fencing_tasks_default}} : ${trap_resource_tasks=${trap_resource_tasks_default}} : ${trap_monitor_success=${trap_monitor_success_default}} : ${trap_add_hires_timestamp_oid=${trap_add_hires_timestamp_oid_default}} : ${trap_snmp_persistent_dir=${trap_snmp_persistent_dir_default}} : ${trap_ignore_int32=${trap_ignore_int32_default}} : ${trap_ignore_string=${trap_ignore_string_default}} # Ensure all cluster-provided variables have values, regardless of alert type. : ${CRM_alert_node=${trap_ignore_string}} : ${CRM_alert_rsc=${trap_ignore_string}} : ${CRM_alert_task=${trap_ignore_string}} : ${CRM_alert_desc=${trap_ignore_string}} : ${CRM_alert_status=${trap_ignore_int32}} : ${CRM_alert_rc=${trap_ignore_int32}} : ${CRM_alert_target_rc=${trap_ignore_int32}} : ${CRM_alert_attribute_name=${trap_ignore_string}} : ${CRM_alert_attribute_value=${trap_ignore_string}} +: ${CRM_alert_version:=""} +: ${CRM_alert_recipient:=""} +: ${CRM_alert_kind:=""} + +if [ -z "$CRM_alert_version" ]; then + echo "$0 must be run by Pacemaker version 1.1.15 or later" + exit 0 +fi + +if [ -z "$CRM_alert_recipient" ]; then + echo "$0 requires a recipient configured with the SNMP server IP address" + exit 0 +fi # Echo a high-resolution equivalent of the Pacemaker-provided time values # using NetSNMP's DateAndTime specification ("%Y-%m-%d,%H:%M:%S.%01N"). get_system_date() { : ${CRM_alert_timestamp_epoch=$(date +%s)} : ${CRM_alert_timestamp_usec=0} YMDHMS=$(date --date="@${CRM_alert_timestamp_epoch}" +"%Y-%m-%d,%H:%M:%S") USEC=$(echo ${CRM_alert_timestamp_usec} | cut -b 1) echo "${YMDHMS}.${USEC}" } is_in_list() { item_list=`echo "$1" | tr ',' ' '` if [ "${item_list}" = "all" ]; then return 0 else for act in $item_list do act=`echo "$act" | tr A-Z a-z` [ "$act" != "$2" ] && continue return 0 done fi return 1 } send_pacemaker_trap() { PREFIX="PACEMAKER-MIB::pacemakerNotification" OUTPUT=$("${trap_binary}" -v "${trap_version}" ${trap_options} \ -c "${trap_community}" "${CRM_alert_recipient}" "" \ "${PREFIX}Trap" \ "${PREFIX}Node" s "${CRM_alert_node}" \ "${PREFIX}Resource" s "${CRM_alert_rsc}" \ "${PREFIX}Operation" s "${CRM_alert_task}" \ "${PREFIX}Description" s "${CRM_alert_desc}" \ "${PREFIX}Status" i "${CRM_alert_status}" \ "${PREFIX}ReturnCode" i "${CRM_alert_rc}" \ "${PREFIX}TargetReturnCode" i "${CRM_alert_target_rc}" \ "${PREFIX}AttributeName" s "${CRM_alert_attribute_name}" \ "${PREFIX}AttributeValue" s "${CRM_alert_attribute_value}" \ ${hires_timestamp} 2>&1) if [ $? -ne 0 ]; then echo "${trap_binary} returned error : rc=$? $OUTPUT" fi } if [ "${trap_add_hires_timestamp_oid}" = "true" ]; then hires_timestamp="HOST-RESOURCES-MIB::hrSystemDate s $(get_system_date)" fi if [ -z ${SNMP_PERSISTENT_DIR} ]; then export SNMP_PERSISTENT_DIR="${trap_snmp_persistent_dir}" # mkdir for snmp trap tools. if [ ! -d ${SNMP_PERSISTENT_DIR} ]; then mkdir -p ${SNMP_PERSISTENT_DIR} fi fi case "$CRM_alert_kind" in node) if is_in_list "${trap_node_states}" "${CRM_alert_desc}"; then send_pacemaker_trap fi ;; fencing) if is_in_list "${trap_fencing_tasks}" "${CRM_alert_task}"; then send_pacemaker_trap fi ;; resource) if is_in_list "${trap_resource_tasks}" "${CRM_alert_task}" && \ [ "${CRM_alert_desc}" != "Cancelled" ] ; then if [ "${trap_monitor_success}" = "false" ] && \ [ "${CRM_alert_rc}" = "${CRM_alert_target_rc}" ] && \ [ "${CRM_alert_task}" = "monitor" ]; then exit 0 fi send_pacemaker_trap fi ;; attribute) send_pacemaker_trap ;; *) ;; esac