Mercurial > hgrepos > FreeBSD > ports > sysutils > local-bsdtools
changeset 124:47c7223bea76
Move bsmtp2dma to sbin.
This is because Bacula's bsmtp lives in sbin also.
| author | Franz Glasner <fzglas.hg@dom66.de> |
|---|---|
| date | Wed, 16 Oct 2019 00:49:48 +0200 |
| parents | 397bf58e85d2 |
| children | 8f91de3c121b |
| files | Makefile bin/bsmtp2dma pkg-plist sbin/bsmtp2dma |
| diffstat | 4 files changed, 348 insertions(+), 347 deletions(-) [+] |
line wrap: on
line diff
--- a/Makefile Wed Oct 16 00:23:53 2019 +0200 +++ b/Makefile Wed Oct 16 00:49:48 2019 +0200 @@ -30,7 +30,8 @@ do-extract: ${MKDIR} ${WRKSRC}/bin -.for _rp in bin/check-ports bin/fjail bin/fpkg bin/bsmtp2dma + ${MKDIR} ${WRKSRC}/sbin +.for _rp in bin/check-ports bin/fjail bin/fpkg sbin/bsmtp2dma ${CP} -v ${SRC}/${_rp} ${WRKSRC}/${_rp} ${SED} -i "" -E -e "s|\\\$$Date\\\$$|\$$Date: ${HGDATE} \$$|" ${WRKSRC}/${_rp} ${SED} -i "" -E -e "s|\\\$$Revision\\\$$|\$$Revision: ${HGREVISION} \$$|" ${WRKSRC}/${_rp} @@ -53,7 +54,7 @@ .endfor do-install: -.for _rp in bin/check-ports bin/fjail bin/fpkg bin/bsmtp2dma +.for _rp in bin/check-ports bin/fjail bin/fpkg sbin/bsmtp2dma ${INSTALL_SCRIPT} ${WRKSRC}/${_rp} ${STAGEDIR}${PREFIX}/${_rp} .endfor ${MKDIR} ${STAGEDIR}${ETCDIR}
--- a/bin/bsmtp2dma Wed Oct 16 00:23:53 2019 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,344 +0,0 @@ -#!/bin/sh -# -*- indent-tabs-mode: nil; -*- -: 'A simple replacement for Bacula `bsmtp` when the underlying mailer does -not listen on TCP ports (e.g. `dma`, `ssmtp` et al.). - -:Author: Franz Glasner -:Copyright: (c) 2019 Franz Glasner. - All rights reserved. -:License: BSD 3-Clause "New" or "Revised" License. - See LICENSE for details. - If you cannot find LICENSE see - <https://opensource.org/licenses/BSD-3-Clause> -:ID: @(#)@@PKGORIGIN@@ $HGid$ - -' - -VERSION="@@VERSION@@" - -USAGE=' -USAGE: bsmtp2dma [OPTIONS] RECIPIENT ... - -Options: - - -V Show the program version and usage and exit. - - -8 Does nothing. Just a compatibility option for `bsmtp`. - - -c ADDRESS Set then "CC:" header. - - -d n Does nothing. Just a compatibility option for `bsmtp`. - - -f ADDRESS Set the "From:" header. - - -h MAILHOST:PORT Does nothing. Just a compatibility option for `bsmtp`. - - -l NUMBER Does nothing. Just a compatibility option for `bsmtp`. - - -r ADDRESS Set the "Reply-To:" header - - -s SUBJECT Set the "Subject:" header - - -Usage: - - The body of the email message is read from standard input. Message is - ended by sending the `EOF` character (`Ctrl-D` on many systems) on the - start of a new line, much like many `mail` commands. - - -Files: - - The shell style configuration file in - - @@ETCDIR@@/bsmtp2dma.conf is - - sourced in at script start. - -' - -# -# Configuration directory -# -: ${CONFIGDIR:=@@ETCDIR@@} - -test -r "${CONFIGDIR}/bsmtp2dma.conf" && . "${CONFIGDIR}/bsmtp2dma.conf" - - -# -# Default configuration values -# -# `sendmail` is also valid for `dma` because of the mapping within -# `/etc/mail/mailer.conf` -# -: ${MAILER:=/usr/sbin/sendmail} - - -parse_addr() { - : 'Parse an possibly complex email address. - - Addresses can be of the form - - - Name Parts <user@domain.tld> - - user@domain.tld - - `Name Parts` may not contain ``<`` or ``>`` characters. - - Args: - _addr: the complex email address - - Returns: - 0 on success, 1 on errors - - Output (Globals): - email_name: the name part (or empty) - email_addr: the technical address part (or empty) - - ' - local _addr - - _addr="$1" - test -n "${_addr}" || return 1 - - if printf "%s" "${_addr}" | grep -q -E -e '^[^<>]+<[^<>]+@[^<>]+>$'; then - email_name=$(printf '%s' "${_addr}" | sed -E -e 's/[[:space:]]*<.+$//') - email_addr=$(printf '%s' "${_addr}" | sed -E -e 's/^[^<>]+<//' | sed -E -e 's/>$//') - return 0 - fi - if printf "%s" "${_addr}" | grep -q -E -e '^[^<>]+@[^<>]+$'; then - email_name="" - email_addr="${_addr}" - return 0 - fi - return 1 -} - - -send_mail() { - : 'Send the mail via the underlying configured mailer (dma, sendmail et al.). - - Args: - _recipient: The recipient name. - - Will be written into the "To:" header also. - - Input (Globals): - MAILER - MAILCONTENT - MAILFIFO_STDIN - MAILFIFO_STDOUT - CC - FROM - REPLYTO - SUBJECT - - Returns: - 0 on success, other values on errors or the error exit code from the - underlying mailer - - This procedure starts the configured mailer as coproc and sends - email headers and contents to the started mailer. - - ' - local _recipient _rc _oifs _text _pid_mailer _recipient_addr - local _from_from _from_addr _sender_addr _dummy - - _recipient="$1" - _rc=0 - - if parse_addr "${_recipient}"; then - _recipient_addr="${email_addr}" - else - echo "ERROR: unknown recipient address format in \`${_recipient}'" >&2 - return 1 - fi - _sender_addr="$(whoami)@$(hostname -f)" - if [ -z "${FROM}" ]; then - _from_addr="${_sender_addr}" - _from_from="${_from_addr}" - else - if parse_addr "${FROM}"; then - _from_from="${FROM}" - _from_addr="${email_addr}" - else - echo "ERROR: unknown sender name in \`${FROM}'" >&2 - return 1 - fi - fi - - mkfifo -m 0600 "${MAILFIFO_STDIN}" - _rc=$? - if [ ${_rc} -ne 0 ]; then - return ${_rc} - fi - mkfifo -m 0600 "${MAILFIFO_STDOUT}" - _rc=$? - if [ ${_rc} -ne 0 ]; then - rm -f "${MAILFIFO_STDIN}" - return ${_rc} - fi - - # - # Start the mailer **before** opening the pipe; otherwise a - # deadlock occurs - # - "$MAILER" -f "${_sender_addr}" "${_recipient_addr}" <${MAILFIFO_STDIN} >${MAILFIFO_STDOUT} & - _pid_mailer=$! - - exec 3>"${MAILFIFO_STDIN}" - exec 4<"${MAILFIFO_STDOUT}" - - printf "To: %s\n" "${_recipient}" >&3 - printf "From: %s\n" "${_from_from}" >&3 - if [ "${_sender_addr}" != "${_from_addr}" ]; then - printf "Sender: %s\n" "${_sender_addr}" >&3 - fi - if [ -n "${SUBJECT}" ]; then - printf "Subject: %s\n" "${SUBJECT}" >&3 - fi - if [ -n "${REPLYTO}" ]; then - # - # XXX TBD proper Reply-To header value checks: - # a comma separated list of full mail addresses - # - printf "Reply-To: %s\n" "${REPLYTO}" >&3 - fi - if [ -n "${CC}" ]; then - # - # XXX TBD proper CC header value checks: - # a comma separated list of full mail addresses - # - printf "Cc: %s\n" "${CC}" >&3 - fi - printf "\n" >&3 - - # preserve leading white space when reading with `read` - _oifs="$IFS" - IFS=" -" - cat "${MAILCONTENT}" | - while read _text; do - printf "%s\n" "$_text" >&3 - done - # not all mailer recognize this - # printf ".\n" >&3 - IFS="$_oifs" - - # close the fd to the pipe: coproc should get EOF and terminate - exec 3>&- - # read eventually remaining stuff from the mailer until EOF - IFS='' read _dummy <&4 - exec 4<&- - - wait $_pid_mailer - _rc=$? - - # we are done with the named pipes - rm -f "${MAILFIFO_STDIN}" - rm -f "${MAILFIFO_STDOUT}" - - return ${_rc} -} - - -while getopts "V8c:d:f:h:l:nr:s:" _opt; do - case ${_opt} in - V) - echo "bsmtp2dma v${VERSION} (rv:@@HGREVISION@@)" - echo "$USAGE" - exit 0; - ;; - 8) - : # VOID - ;; - c) - CC="$OPTARG" - ;; - d) - : # VOID - ;; - f) - FROM="$OPTARG" - ;; - h) - : # VOID - ;; - l) - : # VOID - ;; - r) - REPLYTO="$OPTARG" - ;; - s) - SUBJECT="$OPTARG" - ;; - \?) - exit 2; - ;; - *) - echo "ERROR: inconsistent option handling" >&2 - exit 2; - ;; - esac -done - -# return code -_rc=0 - -MAILTMPDIR="$(mktemp -d)" -MAILFIFO_STDIN="${MAILTMPDIR}/mail-stdin" -MAILFIFO_STDOUT="${MAILTMPDIR}/mail-stdout" -MAILCONTENT="${MAILTMPDIR}/mail-text" - -# -# Clean up existing temporary stuff on all sorts of exit -# (including the "exit" call (signal 0)) -# -trap 'if [ -d "${MAILTMPDIR}" ]; then rm -rf "${MAILTMPDIR}"; fi; exit;' 0 1 2 15 - -test -d "${MAILTMPDIR}" || { echo "ERROR: no existing private tmp dir" >&2; exit 1; } - -# -# Reset the Shell's option handling system to prepare for handling -# other arguments and probably command-local options -# -shift $((OPTIND-1)) -OPTIND=1 - -# early check whether some recipients are given -if [ $# -eq 0 ]; then - echo "ERROR: no recipient given" >&2 - exit 2; -fi - -# -# Collect the mail text from stdin into a temporary file -# -exec 3>"${MAILCONTENT}" -# preserve leading white space when reading with `read` -_oifs="$IFS" -IFS=" -" -while read _text; do - if [ "${_text}" = "." ]; then - break - else - printf "%s\n" "${_text}" >&3 - fi -done -exec 3>&- -IFS="$_oifs" - -# -# Now send the content of the collected mail content to all recipients -# -until [ $# -eq 0 ]; do - send_mail "$1" - _rcsm=$? - if [ \( ${_rcsm} -ne 0 \) -a \( ${_rc} -eq 0 \) ]; then - _rc=${_rcsm} - fi - shift -done - -exit ${_rc}
--- a/pkg-plist Wed Oct 16 00:23:53 2019 +0200 +++ b/pkg-plist Wed Oct 16 00:49:48 2019 +0200 @@ -1,10 +1,10 @@ @comment DIRECTORIES @dir %%ETCDIR%% @comment FILES -bin/bsmtp2dma bin/check-ports bin/fjail bin/fpkg +sbin/bsmtp2dma @sample %%ETCDIR%%/tools.conf.sample @sample %%ETCDIR%%/package-mapping.conf.sample @sample %%ETCDIR%%/bsmtp2dma.conf.sample
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/sbin/bsmtp2dma Wed Oct 16 00:49:48 2019 +0200 @@ -0,0 +1,344 @@ +#!/bin/sh +# -*- indent-tabs-mode: nil; -*- +: 'A simple replacement for Bacula `bsmtp` when the underlying mailer does +not listen on TCP ports (e.g. `dma`, `ssmtp` et al.). + +:Author: Franz Glasner +:Copyright: (c) 2019 Franz Glasner. + All rights reserved. +:License: BSD 3-Clause "New" or "Revised" License. + See LICENSE for details. + If you cannot find LICENSE see + <https://opensource.org/licenses/BSD-3-Clause> +:ID: @(#)@@PKGORIGIN@@ $HGid$ + +' + +VERSION="@@VERSION@@" + +USAGE=' +USAGE: bsmtp2dma [OPTIONS] RECIPIENT ... + +Options: + + -V Show the program version and usage and exit. + + -8 Does nothing. Just a compatibility option for `bsmtp`. + + -c ADDRESS Set then "CC:" header. + + -d n Does nothing. Just a compatibility option for `bsmtp`. + + -f ADDRESS Set the "From:" header. + + -h MAILHOST:PORT Does nothing. Just a compatibility option for `bsmtp`. + + -l NUMBER Does nothing. Just a compatibility option for `bsmtp`. + + -r ADDRESS Set the "Reply-To:" header + + -s SUBJECT Set the "Subject:" header + + +Usage: + + The body of the email message is read from standard input. Message is + ended by sending the `EOF` character (`Ctrl-D` on many systems) on the + start of a new line, much like many `mail` commands. + + +Files: + + The shell style configuration file in + + @@ETCDIR@@/bsmtp2dma.conf is + + sourced in at script start. + +' + +# +# Configuration directory +# +: ${CONFIGDIR:=@@ETCDIR@@} + +test -r "${CONFIGDIR}/bsmtp2dma.conf" && . "${CONFIGDIR}/bsmtp2dma.conf" + + +# +# Default configuration values +# +# `sendmail` is also valid for `dma` because of the mapping within +# `/etc/mail/mailer.conf` +# +: ${MAILER:=/usr/sbin/sendmail} + + +parse_addr() { + : 'Parse an possibly complex email address. + + Addresses can be of the form + + - Name Parts <user@domain.tld> + - user@domain.tld + + `Name Parts` may not contain ``<`` or ``>`` characters. + + Args: + _addr: the complex email address + + Returns: + 0 on success, 1 on errors + + Output (Globals): + email_name: the name part (or empty) + email_addr: the technical address part (or empty) + + ' + local _addr + + _addr="$1" + test -n "${_addr}" || return 1 + + if printf "%s" "${_addr}" | grep -q -E -e '^[^<>]+<[^<>]+@[^<>]+>$'; then + email_name=$(printf '%s' "${_addr}" | sed -E -e 's/[[:space:]]*<.+$//') + email_addr=$(printf '%s' "${_addr}" | sed -E -e 's/^[^<>]+<//' | sed -E -e 's/>$//') + return 0 + fi + if printf "%s" "${_addr}" | grep -q -E -e '^[^<>]+@[^<>]+$'; then + email_name="" + email_addr="${_addr}" + return 0 + fi + return 1 +} + + +send_mail() { + : 'Send the mail via the underlying configured mailer (dma, sendmail et al.). + + Args: + _recipient: The recipient name. + + Will be written into the "To:" header also. + + Input (Globals): + MAILER + MAILCONTENT + MAILFIFO_STDIN + MAILFIFO_STDOUT + CC + FROM + REPLYTO + SUBJECT + + Returns: + 0 on success, other values on errors or the error exit code from the + underlying mailer + + This procedure starts the configured mailer as coproc and sends + email headers and contents to the started mailer. + + ' + local _recipient _rc _oifs _text _pid_mailer _recipient_addr + local _from_from _from_addr _sender_addr _dummy + + _recipient="$1" + _rc=0 + + if parse_addr "${_recipient}"; then + _recipient_addr="${email_addr}" + else + echo "ERROR: unknown recipient address format in \`${_recipient}'" >&2 + return 1 + fi + _sender_addr="$(whoami)@$(hostname -f)" + if [ -z "${FROM}" ]; then + _from_addr="${_sender_addr}" + _from_from="${_from_addr}" + else + if parse_addr "${FROM}"; then + _from_from="${FROM}" + _from_addr="${email_addr}" + else + echo "ERROR: unknown sender name in \`${FROM}'" >&2 + return 1 + fi + fi + + mkfifo -m 0600 "${MAILFIFO_STDIN}" + _rc=$? + if [ ${_rc} -ne 0 ]; then + return ${_rc} + fi + mkfifo -m 0600 "${MAILFIFO_STDOUT}" + _rc=$? + if [ ${_rc} -ne 0 ]; then + rm -f "${MAILFIFO_STDIN}" + return ${_rc} + fi + + # + # Start the mailer **before** opening the pipe; otherwise a + # deadlock occurs + # + "$MAILER" -f "${_sender_addr}" "${_recipient_addr}" <${MAILFIFO_STDIN} >${MAILFIFO_STDOUT} & + _pid_mailer=$! + + exec 3>"${MAILFIFO_STDIN}" + exec 4<"${MAILFIFO_STDOUT}" + + printf "To: %s\n" "${_recipient}" >&3 + printf "From: %s\n" "${_from_from}" >&3 + if [ "${_sender_addr}" != "${_from_addr}" ]; then + printf "Sender: %s\n" "${_sender_addr}" >&3 + fi + if [ -n "${SUBJECT}" ]; then + printf "Subject: %s\n" "${SUBJECT}" >&3 + fi + if [ -n "${REPLYTO}" ]; then + # + # XXX TBD proper Reply-To header value checks: + # a comma separated list of full mail addresses + # + printf "Reply-To: %s\n" "${REPLYTO}" >&3 + fi + if [ -n "${CC}" ]; then + # + # XXX TBD proper CC header value checks: + # a comma separated list of full mail addresses + # + printf "Cc: %s\n" "${CC}" >&3 + fi + printf "\n" >&3 + + # preserve leading white space when reading with `read` + _oifs="$IFS" + IFS=" +" + cat "${MAILCONTENT}" | + while read _text; do + printf "%s\n" "$_text" >&3 + done + # not all mailer recognize this + # printf ".\n" >&3 + IFS="$_oifs" + + # close the fd to the pipe: coproc should get EOF and terminate + exec 3>&- + # read eventually remaining stuff from the mailer until EOF + IFS='' read _dummy <&4 + exec 4<&- + + wait $_pid_mailer + _rc=$? + + # we are done with the named pipes + rm -f "${MAILFIFO_STDIN}" + rm -f "${MAILFIFO_STDOUT}" + + return ${_rc} +} + + +while getopts "V8c:d:f:h:l:nr:s:" _opt; do + case ${_opt} in + V) + echo "bsmtp2dma v${VERSION} (rv:@@HGREVISION@@)" + echo "$USAGE" + exit 0; + ;; + 8) + : # VOID + ;; + c) + CC="$OPTARG" + ;; + d) + : # VOID + ;; + f) + FROM="$OPTARG" + ;; + h) + : # VOID + ;; + l) + : # VOID + ;; + r) + REPLYTO="$OPTARG" + ;; + s) + SUBJECT="$OPTARG" + ;; + \?) + exit 2; + ;; + *) + echo "ERROR: inconsistent option handling" >&2 + exit 2; + ;; + esac +done + +# return code +_rc=0 + +MAILTMPDIR="$(mktemp -d)" +MAILFIFO_STDIN="${MAILTMPDIR}/mail-stdin" +MAILFIFO_STDOUT="${MAILTMPDIR}/mail-stdout" +MAILCONTENT="${MAILTMPDIR}/mail-text" + +# +# Clean up existing temporary stuff on all sorts of exit +# (including the "exit" call (signal 0)) +# +trap 'if [ -d "${MAILTMPDIR}" ]; then rm -rf "${MAILTMPDIR}"; fi; exit;' 0 1 2 15 + +test -d "${MAILTMPDIR}" || { echo "ERROR: no existing private tmp dir" >&2; exit 1; } + +# +# Reset the Shell's option handling system to prepare for handling +# other arguments and probably command-local options +# +shift $((OPTIND-1)) +OPTIND=1 + +# early check whether some recipients are given +if [ $# -eq 0 ]; then + echo "ERROR: no recipient given" >&2 + exit 2; +fi + +# +# Collect the mail text from stdin into a temporary file +# +exec 3>"${MAILCONTENT}" +# preserve leading white space when reading with `read` +_oifs="$IFS" +IFS=" +" +while read _text; do + if [ "${_text}" = "." ]; then + break + else + printf "%s\n" "${_text}" >&3 + fi +done +exec 3>&- +IFS="$_oifs" + +# +# Now send the content of the collected mail content to all recipients +# +until [ $# -eq 0 ]; do + send_mail "$1" + _rcsm=$? + if [ \( ${_rcsm} -ne 0 \) -a \( ${_rc} -eq 0 \) ]; then + _rc=${_rcsm} + fi + shift +done + +exit ${_rc}
