Skip to content
Snippets Groups Projects
Commit b04c0aca authored by Hahn Axel (hahn)'s avatar Hahn Axel (hahn)
Browse files

handle multiple files with spaces; long param options; update help

parent 1e24240b
Branches
No related tags found
1 merge request!2Multiple files with spaces
...@@ -23,20 +23,22 @@ ...@@ -23,20 +23,22 @@
# 2019-10-21 v1.03 <axel.hahn@iml.unibe.ch> use stat as default # 2019-10-21 v1.03 <axel.hahn@iml.unibe.ch> use stat as default
# 2022-03-11 v1.04 <axel.hahn@iml.unibe.ch> shell fixes # 2022-03-11 v1.04 <axel.hahn@iml.unibe.ch> shell fixes
# 2022-03-11 v1.05 <axel.hahn@iml.unibe.ch> fix: behaviur when trigger command fails; shell fixes; update docs # 2022-03-11 v1.05 <axel.hahn@iml.unibe.ch> fix: behaviur when trigger command fails; shell fixes; update docs
# 2025-01-17 v1.06 <axel.hahn@unibe.ch> handle multiple files with spaces; long param options; update help
# ====================================================================== # ======================================================================
# ---------------------------------------------------------------------- # ----------------------------------------------------------------------
# CONFIG # CONFIG
# ---------------------------------------------------------------------- # ----------------------------------------------------------------------
bDebug=0 FLAG_DEBUG=0
iSleep=5 typeset -i iSleep=5
sCommand= sCommand=
sWatchFile=
sMode= sMode=
aWatchFiles=()
# ---- below are some internal variables # ---- below are some internal variables
_version=1.05 _version=1.06
# ---------------------------------------------------------------------- # ----------------------------------------------------------------------
...@@ -47,38 +49,55 @@ _version=1.05 ...@@ -47,38 +49,55 @@ _version=1.05
function showHelp(){ function showHelp(){
local _self=$( basename $0 ) local _self=$( basename $0 )
cat <<ENDOFHELP cat <<ENDOFHELP
HELP: HELP:
This script checks the change of a given fileobjects and triggers
a command if it changes ${_self} checks the change of a given fileobjects and triggers
a command on file changes.
It can use stat or inotifywait to watch a file change. preferred is stat
because it can be used for not yet existing files.
SYNTAX:
${_self} OPTIONS -c COMAND [FILE] [[... FILE N]]
PRAMETERS: PRAMETERS:
-c [command]
command to execute on a file change
-f [fileobject(s)]
filenames or directories to watch; separate multiple files with
space and put all in quotes
-h
show this help
-i
force inotifywait command
-s
force stat command (default mode)
-v
verbose mode; enable showing debug output
-w [integer]
for stat mode: wait time in seconds betweeen each test or on
missing file; default: 5 sec
EXAMPLES: -c|--command COMMAND
$_self -f /home/me/touchfile.txt -c "ls -l" A command to execute on a file change
watch touchfile.txt and make a file listing on change
-f|--file FILENAME
Filenames or directories to watch; separate multiple files with
space and put all in quotes
DEPRECATED: add all files to watch as parameters
$_self -f "/home/me/touchfile.txt home/me/touchfile2.txt" -c "ls -l" -h|--help
watch touchfile.txt and touchfile2.txt show this help
$_self -f /home/me/touchfile.txt -s -w 10 -c "echo hello" -i|--inotifywait
watch touchfile.txt every 10 sec with stat and show "hello" on a force inotifywait command
change
-s|--stat
force stat command (default mode)
-v
verbose mode; enable showing debug output; it should be the first option
to see handling of other options
-w|--wait SLEEPTIME
for stat mode: wait time in seconds betweeen each test or on
missing file; default: 5 sec
EXAMPLES:
$_self -c "ls -l" /home/me/touchfile.txt
watch touchfile.txt and make a file listing on change
$_self -c "ls -l" "/home/me/touchfile.txt" "home/me/touchfile2.txt"
watch touchfile.txt and touchfile2.txt
$_self -s -w 10 -c "echo hello" /home/me/touchfile.txt
watch touchfile.txt every 10 sec with stat and show "hello" on a change
ENDOFHELP ENDOFHELP
...@@ -86,28 +105,28 @@ ENDOFHELP ...@@ -86,28 +105,28 @@ ENDOFHELP
# write debug output ... if debug is enabled only # write debug output ... if debug is enabled only
# #
# global (bool) $bDebug # global (bool) $FLAG_DEBUG
# param string text message to show # param string text message to show
function wd(){ function wd(){
if [ $bDebug -ne 0 ]; then if [ $FLAG_DEBUG -ne 0 ]; then
echo "[$(date)] DEBUG |" $* echo "$*" | while read -r l; do echo "[$(date)] DEBUG | ${l}"; done
fi fi
} }
# list watched files # list watched files
# #
# global (string) filename(s) to watch # global (string) filesAsString list of all files to watch
function listFiles(){ function listFiles(){
echo echo
echo ">>>>> watched files" echo ">>>>> watched files"
ls -ld ${sWatchFile} 2>&1 eval "ls -ld $filesAsString"
} }
# for stat: helper to get current file status # for stat: helper to get current file status
# #
# global (string) $sWatchFile # global (array) $aWatchFiles array of watched files
function getFilestatus(){ function getFilestatus(){
for myfile in ${sWatchFile} for myfile in "${aWatchFiles[@]}"
do do
stat -c "%F %n | perms: %A; user %u (%U) group %g (%G) | size: %s byte | last modification %y" "${myfile}" 2>&1 stat -c "%F %n | perms: %A; user %u (%U) group %g (%G) | size: %s byte | last modification %y" "${myfile}" 2>&1
done done
...@@ -129,9 +148,9 @@ function initFilestatus(){ ...@@ -129,9 +148,9 @@ function initFilestatus(){
# global (string) $sTmpFile2 current file status # global (string) $sTmpFile2 current file status
# global (string) $sCommand command to execute # global (string) $sCommand command to execute
function compareFilestatus(){ function compareFilestatus(){
getFilestatus >${sTmpFile2} getFilestatus >"${sTmpFile2}"
wd "$(cat ${sTmpFile2})" wd "$(cat "${sTmpFile2}")"
if diff ${sTmpFile} ${sTmpFile2}; then if diff "${sTmpFile}" "${sTmpFile2}"; then
wd "No Change" wd "No Change"
else else
wd "Change detected." wd "Change detected."
...@@ -141,7 +160,7 @@ function compareFilestatus(){ ...@@ -141,7 +160,7 @@ function compareFilestatus(){
echo rc=$? FAILED. echo rc=$? FAILED.
fi fi
wd "Re-Init File status" wd "Re-Init File status"
mv ${sTmpFile2} ${sTmpFile} mv "${sTmpFile2}" "${sTmpFile}"
echo echo
echo ">>>>> waiting for the next change ..." echo ">>>>> waiting for the next change ..."
fi fi
...@@ -168,15 +187,12 @@ _______________________________________________________________________| v${_ver ...@@ -168,15 +187,12 @@ _______________________________________________________________________| v${_ver
ENDOFHEAD ENDOFHEAD
if which stat >/dev/null 2>&1; then if which stat >/dev/null 2>&1; then
echo "INFO: stat command detected"
sMode=stat sMode=stat
else else
echo ERROR: the command stat was not found on your system.
if ! which inotifywait >/dev/null 2>&1; then if ! which inotifywait >/dev/null 2>&1; then
echo ERROR: the command inotifywait was not found on your system. echo ERROR: the command inotifywait was not found on your system.
exit 2 exit 2
fi fi
echo "INFO: enabling inotifywait command"
sMode=inotifywait sMode=inotifywait
fi fi
...@@ -184,52 +200,29 @@ if [ $# -eq 0 ]; then ...@@ -184,52 +200,29 @@ if [ $# -eq 0 ]; then
showHelp showHelp
exit 0 exit 0
fi fi
while [[ "$#" -gt 0 ]]; do case $1 in
while getopts ":c: :v :f: :h :i :s :w:" opt -h|--help) showHelp; exit 0;;
do -c|--command) sCommand="$2"; wd "command is now ${sCommand}"; shift; shift;;
case $opt in -f|--file) aWatchFiles+=("$2"); echo "DEPPRECATED: Add all files as parameter instead of using -f option."; wd "watch file $2 was added" ;shift;shift;;
h) -i|--inotifywait) sMode=inotifywait; wd "forcing mode with inotifywait command"; shift;;
showHelp -s|--stat) sMode=stat; wd "forcing mode with inotifywait command"; shift;;
exit 0 -w|--wait) iSleep=$OPTARG; wd "sleep $iSleep sec"; shift;shift;;
;; -v|--verbose) FLAG_DEBUG=1; shift;;
v) *) if grep "^-" <<< "$1" >/dev/null ; then
bDebug=1 echo; echo "ERROR: Unknown parameter: $1"; echo; _showHelp; exit 2
wd "debug is now ${bDebug}" fi
;; # break;
c) aWatchFiles+=("$1"); wd "watch file $1 was added" ;shift;;
sCommand=$OPTARG
wd "command is now ${sCommand}" esac; done
;;
f)
sWatchFile=$OPTARG
wd "watch file is now ${sWatchFile}"
;;
i)
sMode=inotifywait
wd "forcing mode with inotifywait command"
;;
s)
sMode=stat
wd "forcing mode with stat command"
;;
w)
typeset -i iSleep=$OPTARG
wd "sleep $iSleep sec"
;;
:)
echo "ERROR: Option -$opt requires an argument." >&2
showHelp
exit 1
esac
done
cat <<ENDOFINFO cat <<ENDOFINFO
--- summary --- summary
checking file [${sWatchFile}] checking file(s): ${aWatchFiles[@]}
with command [${sMode}] with command [${sMode}]
with a sleep time of [${iSleep}] seconds with a sleep time of [${iSleep}] seconds
and on change I start the command [${sCommand}] on change execute command [${sCommand}]
............................................................................... ...............................................................................
...@@ -240,19 +233,23 @@ ENDOFINFO ...@@ -240,19 +233,23 @@ ENDOFINFO
# CHECKS # CHECKS
# ---------------------------------------------------------------------- # ----------------------------------------------------------------------
filesAsString=
for myfile in "${aWatchFiles[@]}"
do
filesAsString+="'${myfile}' "
done
wd "--- checks" wd "--- checks"
if [ -z "${sWatchFile}" ]; then if [ -z "${filesAsString}" ]; then
echo ERROR: set a check file with param -f echo "ERROR: Add one or more files / directories to watch as parameter"
exit 1 exit 1
fi fi
if ! listFiles; then if ! listFiles; then
echo "INFO: file ${sWatchFile} (or one of them) does not exist yet" echo "INFO: file ${filesAsString} (or one of them) does not exist yet"
# echo "ERROR: file ${sWatchFile} (or one of them) does not exist yet"
# exit 1
fi fi
if [ -z "${sCommand}" ]; then if [ -z "${sCommand}" ]; then
echo ERROR: set a ${sCommand} with param -s echo ERROR: set a command with option -c first.
exit 1 exit 1
fi fi
echo echo
...@@ -262,7 +259,7 @@ echo ...@@ -262,7 +259,7 @@ echo
# ---------------------------------------------------------------------- # ----------------------------------------------------------------------
echo ">>>>> start" echo ">>>>> start"
myset=$(echo "${sWatchFile}" | sha1sum | cut -f 1 -d " ") myset=$(echo "${aWatchFiles[*]}" | sha1sum | cut -f 1 -d " ")
sTmpFile="/tmp/$(basename $0)-${myset}-last.tmp" sTmpFile="/tmp/$(basename $0)-${myset}-last.tmp"
sTmpFile2="/tmp/$(basename $0)-${myset}-current.tmp" sTmpFile2="/tmp/$(basename $0)-${myset}-current.tmp"
...@@ -270,7 +267,7 @@ case $sMode in ...@@ -270,7 +267,7 @@ case $sMode in
"inotifywait") "inotifywait")
while true; do while true; do
if listFiles >/dev/null 2>&1; then if listFiles >/dev/null 2>&1; then
inotifywait -e attrib -e modify "${sWatchFile}" && execCommand eval inotifywait -e attrib -e modify "${filesAsString}" && execCommand || exit 1
else else
echo "ERROR: inotifywait only can notify if all watched files exist." echo "ERROR: inotifywait only can notify if all watched files exist."
echo "Use parameter -s to use stat for file detection, This mode also allows that a file is deleted." echo "Use parameter -s to use stat for file detection, This mode also allows that a file is deleted."
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment