mirror of
https://github.com/limosek/zaf.git
synced 2024-11-21 18:09:06 +01:00
Json parsing based on JSON.sh https://github.com/dominictarr/JSON.sh
This commit is contained in:
parent
941a96208c
commit
c5df621461
@ -39,6 +39,7 @@ fi
|
||||
|
||||
if ! type zaf_version >/dev/null; then
|
||||
. lib/zaf.lib.sh
|
||||
. lib/plugin.lib.sh
|
||||
. lib/os.lib.sh
|
||||
. lib/ctrl.lib.sh
|
||||
. lib/cache.lib.sh
|
||||
@ -278,7 +279,7 @@ zaf_install_all() {
|
||||
rm -rif ${ZAF_TMP_DIR}
|
||||
mkdir -p ${ZAF_TMP_DIR}
|
||||
zaf_install_dir ${ZAF_LIB_DIR}
|
||||
for i in lib/zaf.lib.sh lib/os.lib.sh lib/ctrl.lib.sh lib/cache.lib.sh lib/zbxapi.lib.sh README.md; do
|
||||
for i in lib/zaf.lib.sh lib/plugin.lib.sh lib/os.lib.sh lib/ctrl.lib.sh lib/cache.lib.sh lib/zbxapi.lib.sh lib/JSON.sh README.md; do
|
||||
zaf_install $i ${ZAF_LIB_DIR}/ || zaf_err "Error installing $i"
|
||||
done
|
||||
for i in lib/zaflock lib/zafcache lib/preload.sh; do
|
||||
|
208
lib/JSON.sh
Executable file
208
lib/JSON.sh
Executable file
@ -0,0 +1,208 @@
|
||||
#!/bin/sh
|
||||
|
||||
throw() {
|
||||
echo "$*" >&2
|
||||
exit 1
|
||||
}
|
||||
|
||||
BRIEF=0
|
||||
LEAFONLY=0
|
||||
PRUNE=0
|
||||
NO_HEAD=0
|
||||
NORMALIZE_SOLIDUS=0
|
||||
|
||||
usage() {
|
||||
echo
|
||||
echo "Usage: JSON.sh [-b] [-l] [-p] [-s] [-h]"
|
||||
echo
|
||||
echo "-p - Prune empty. Exclude fields with empty values."
|
||||
echo "-l - Leaf only. Only show leaf nodes, which stops data duplication."
|
||||
echo "-b - Brief. Combines 'Leaf only' and 'Prune empty' options."
|
||||
echo "-n - No-head. Do not show nodes that have no path (lines that start with [])."
|
||||
echo "-s - Remove escaping of the solidus symbol (stright slash)."
|
||||
echo "-h - This help text."
|
||||
echo
|
||||
}
|
||||
|
||||
parse_options() {
|
||||
set -- "$@"
|
||||
local ARGN=$#
|
||||
while [ "$ARGN" -ne 0 ]
|
||||
do
|
||||
case $1 in
|
||||
-h) usage
|
||||
exit 0
|
||||
;;
|
||||
-b) BRIEF=1
|
||||
LEAFONLY=1
|
||||
PRUNE=1
|
||||
;;
|
||||
-l) LEAFONLY=1
|
||||
;;
|
||||
-p) PRUNE=1
|
||||
;;
|
||||
-n) NO_HEAD=1
|
||||
;;
|
||||
-s) NORMALIZE_SOLIDUS=1
|
||||
;;
|
||||
?*) echo "ERROR: Unknown option."
|
||||
usage
|
||||
exit 0
|
||||
;;
|
||||
esac
|
||||
shift 1
|
||||
ARGN=$((ARGN-1))
|
||||
done
|
||||
}
|
||||
|
||||
awk_egrep () {
|
||||
local pattern_string=$1
|
||||
|
||||
gawk '{
|
||||
while ($0) {
|
||||
start=match($0, pattern);
|
||||
token=substr($0, start, RLENGTH);
|
||||
print token;
|
||||
$0=substr($0, start+RLENGTH);
|
||||
}
|
||||
}' pattern="$pattern_string"
|
||||
}
|
||||
|
||||
tokenize () {
|
||||
local GREP
|
||||
local ESCAPE
|
||||
local CHAR
|
||||
|
||||
if echo "test string" | egrep -ao --color=never "test" >/dev/null 2>&1
|
||||
then
|
||||
GREP='egrep -ao --color=never'
|
||||
else
|
||||
GREP='egrep -ao'
|
||||
fi
|
||||
|
||||
if echo "test string" | egrep -o "test" >/dev/null 2>&1
|
||||
then
|
||||
ESCAPE='(\\[^u[:cntrl:]]|\\u[0-9a-fA-F]{4})'
|
||||
CHAR='[^[:cntrl:]"\\]'
|
||||
else
|
||||
GREP=awk_egrep
|
||||
ESCAPE='(\\\\[^u[:cntrl:]]|\\u[0-9a-fA-F]{4})'
|
||||
CHAR='[^[:cntrl:]"\\\\]'
|
||||
fi
|
||||
|
||||
local STRING="\"$CHAR*($ESCAPE$CHAR*)*\""
|
||||
local NUMBER='-?(0|[1-9][0-9]*)([.][0-9]*)?([eE][+-]?[0-9]*)?'
|
||||
local KEYWORD='null|false|true'
|
||||
local SPACE='[[:space:]]+'
|
||||
|
||||
# Force zsh to expand $A into multiple words
|
||||
local is_wordsplit_disabled=$(unsetopt 2>/dev/null | grep -c '^shwordsplit$')
|
||||
if [ $is_wordsplit_disabled != 0 ]; then setopt shwordsplit; fi
|
||||
$GREP "$STRING|$NUMBER|$KEYWORD|$SPACE|." | egrep -v "^$SPACE$"
|
||||
if [ $is_wordsplit_disabled != 0 ]; then unsetopt shwordsplit; fi
|
||||
}
|
||||
|
||||
parse_array () {
|
||||
local index=0
|
||||
local ary=''
|
||||
read -r token
|
||||
case "$token" in
|
||||
']') ;;
|
||||
*)
|
||||
while :
|
||||
do
|
||||
parse_value "$1" "$index"
|
||||
index=$((index+1))
|
||||
ary="$ary""$value"
|
||||
read -r token
|
||||
case "$token" in
|
||||
']') break ;;
|
||||
',') ary="$ary," ;;
|
||||
*) throw "EXPECTED , or ] GOT ${token:-EOF}" ;;
|
||||
esac
|
||||
read -r token
|
||||
done
|
||||
;;
|
||||
esac
|
||||
[ "$BRIEF" -eq 0 ] && value=$(printf '[%s]' "$ary") || value=
|
||||
:
|
||||
}
|
||||
|
||||
parse_object () {
|
||||
local key
|
||||
local obj=''
|
||||
read -r token
|
||||
case "$token" in
|
||||
'}') ;;
|
||||
*)
|
||||
while :
|
||||
do
|
||||
case "$token" in
|
||||
'"'*'"') key=$token ;;
|
||||
*) throw "EXPECTED string GOT ${token:-EOF}" ;;
|
||||
esac
|
||||
read -r token
|
||||
case "$token" in
|
||||
':') ;;
|
||||
*) throw "EXPECTED : GOT ${token:-EOF}" ;;
|
||||
esac
|
||||
read -r token
|
||||
parse_value "$1" "$key"
|
||||
obj="$obj$key:$value"
|
||||
read -r token
|
||||
case "$token" in
|
||||
'}') break ;;
|
||||
',') obj="$obj," ;;
|
||||
*) throw "EXPECTED , or } GOT ${token:-EOF}" ;;
|
||||
esac
|
||||
read -r token
|
||||
done
|
||||
;;
|
||||
esac
|
||||
[ "$BRIEF" -eq 0 ] && value=$(printf '{%s}' "$obj") || value=
|
||||
:
|
||||
}
|
||||
|
||||
parse_value () {
|
||||
local jpath="${1:+$1,}$2" isleaf=0 isempty=0 print=0
|
||||
case "$token" in
|
||||
'{') parse_object "$jpath" ;;
|
||||
'[') parse_array "$jpath" ;;
|
||||
# At this point, the only valid single-character tokens are digits.
|
||||
''|[!0-9]) throw "EXPECTED value GOT ${token:-EOF}" ;;
|
||||
*) value=$token
|
||||
# if asked, replace solidus ("\/") in json strings with normalized value: "/"
|
||||
[ "$NORMALIZE_SOLIDUS" -eq 1 ] && value=$(echo "$value" | sed 's#\\/#/#g')
|
||||
isleaf=1
|
||||
[ "$value" = '""' ] && isempty=1
|
||||
;;
|
||||
esac
|
||||
[ "$value" = '' ] && return
|
||||
[ "$NO_HEAD" -eq 1 ] && [ -z "$jpath" ] && return
|
||||
|
||||
[ "$LEAFONLY" -eq 0 ] && [ "$PRUNE" -eq 0 ] && print=1
|
||||
[ "$LEAFONLY" -eq 1 ] && [ "$isleaf" -eq 1 ] && [ $PRUNE -eq 0 ] && print=1
|
||||
[ "$LEAFONLY" -eq 0 ] && [ "$PRUNE" -eq 1 ] && [ "$isempty" -eq 0 ] && print=1
|
||||
[ "$LEAFONLY" -eq 1 ] && [ "$isleaf" -eq 1 ] && \
|
||||
[ $PRUNE -eq 1 ] && [ $isempty -eq 0 ] && print=1
|
||||
[ "$print" -eq 1 ] && printf "[%s]\t%s\n" "$jpath" "$value"
|
||||
:
|
||||
}
|
||||
|
||||
parse () {
|
||||
read -r token
|
||||
parse_value
|
||||
read -r token
|
||||
case "$token" in
|
||||
'') ;;
|
||||
*) throw "EXPECTED EOF GOT $token" ;;
|
||||
esac
|
||||
}
|
||||
|
||||
if ([ "$0" = "$BASH_SOURCE" ] || ! [ -n "$BASH_SOURCE" ]);
|
||||
then
|
||||
parse_options "$@"
|
||||
tokenize | parse
|
||||
fi
|
||||
|
||||
# vi: expandtab sw=2 ts=2
|
@ -23,11 +23,13 @@ zaf_tocache(){
|
||||
! [ -w $ZAF_CACHE_DIR ] && return 1
|
||||
local key
|
||||
local value
|
||||
local expiry
|
||||
|
||||
key=$(zaf_cache_key "$1")
|
||||
echo "$2" >$ZAF_CACHE_DIR/$key
|
||||
echo "$1" >$ZAF_CACHE_DIR/$key.info
|
||||
touch -m -d "$3 seconds" $ZAF_CACHE_DIR/$key.info
|
||||
expiry=$(zaf_date_add "$3")
|
||||
touch -m -d "$expiry" $ZAF_CACHE_DIR/$key.info
|
||||
zaf_trc "Cache: Saving entry $1($key)"
|
||||
}
|
||||
|
||||
@ -37,13 +39,15 @@ zaf_tocache(){
|
||||
zaf_tocache_stdin(){
|
||||
! [ -w $ZAF_CACHE_DIR ] && return 1
|
||||
local key
|
||||
local expiry
|
||||
|
||||
key=$(zaf_cache_key "$1")
|
||||
cat >$ZAF_CACHE_DIR/$key
|
||||
if [ -s $ZAF_CACHE_DIR/$key ]; then
|
||||
zaf_trc "Cache: Saving entry $1($key)"
|
||||
echo "$1" >$ZAF_CACHE_DIR/$key.info
|
||||
touch -m -d "$2 seconds" $ZAF_CACHE_DIR/$key.info
|
||||
expiry=$(zaf_date_add "$3")
|
||||
touch -m -d "$expiry" $ZAF_CACHE_DIR/$key.info
|
||||
cat $ZAF_CACHE_DIR/$key
|
||||
else
|
||||
rm $ZAF_CACHE_DIR/$key
|
||||
|
259
lib/plugin.lib.sh
Normal file
259
lib/plugin.lib.sh
Normal file
@ -0,0 +1,259 @@
|
||||
# Plugin related functions
|
||||
|
||||
# Update repo
|
||||
zaf_update_repo() {
|
||||
[ "$ZAF_GIT" != 1 ] && { zaf_err "Git is disabled or is not installed. Exiting."; }
|
||||
if [ -z "${ZAF_REPO_GITURL}" ] || [ -z "${ZAF_REPO_DIR}" ]; then
|
||||
zaf_err "This system is not configured for git repository."
|
||||
else
|
||||
[ ! -d "${ZAF_REPO_DIR}" ] && git clone "${ZAF_REPO_GITURL}" "${ZAF_REPO_DIR}"
|
||||
(cd ${ZAF_REPO_DIR} && git pull)
|
||||
fi
|
||||
}
|
||||
|
||||
# Construct url from plugin name
|
||||
# It can be http[s]://url
|
||||
# /path (from file)
|
||||
# name (to try from repo)
|
||||
zaf_get_plugin_url() {
|
||||
local url
|
||||
|
||||
if echo "$1" | grep -q '/'; then
|
||||
url="$1" # plugin with path - from directory
|
||||
else
|
||||
if echo "$1" | grep -q ^http; then
|
||||
url="$1" # plugin with http[s] url
|
||||
else
|
||||
if [ -d "${ZAF_REPO_DIR}/$1" ]; then
|
||||
url="${ZAF_REPO_DIR}/$1"
|
||||
else
|
||||
if [ -n "${ZAF_PREPACKAGED_DIR}" ] && [ -d "${ZAF_PREPACKAGED_DIR}/$1" ]; then
|
||||
url="${ZAF_PREPACKAGED_DIR}/$1"
|
||||
else
|
||||
if [ -n "${ZAF_REPO_URL}" ]; then
|
||||
url="${ZAF_REPO_URL}/$1"
|
||||
else
|
||||
zaf_err "Cannot find plugin $1"
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
echo $url
|
||||
}
|
||||
|
||||
# $1 - control
|
||||
zaf_plugin_info() {
|
||||
local control="$1"
|
||||
|
||||
! [ -f "$control" ] && zaf_err "Control file $control not found."
|
||||
plugin=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Plugin)
|
||||
pdescription=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_moption Description)
|
||||
pmaintainer=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Maintainer)
|
||||
pversion=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Version)
|
||||
purl=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Url)
|
||||
phome=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Home)
|
||||
pitems=$(zaf_ctrl_get_items <"${control}")
|
||||
echo
|
||||
echo -n "Plugin '$plugin' "; [ -n "$pversion" ] && echo -n "version ${pversion}"; echo ":"
|
||||
echo "$pdescription"; echo
|
||||
[ -n "$pmaintainer" ] && echo "Maintainer: $pmaintainer"
|
||||
[ -n "$purl" ] && echo "Url: $purl"
|
||||
[ -n "$phome" ] && echo "Home: $phome"
|
||||
echo
|
||||
if zaf_is_plugin "$(basename $plugin)"; then
|
||||
echo -n "Defined items: "; zaf_list_plugin_items $plugin
|
||||
echo -n "Test items: "; zaf_list_plugin_items $plugin test
|
||||
echo -n "Precache items: "; zaf_list_plugin_items $plugin precache
|
||||
else
|
||||
echo "Items: $pitems"
|
||||
fi
|
||||
echo
|
||||
}
|
||||
|
||||
# Prepare plugin into dir
|
||||
# $1 is url, directory or plugin name (will be searched in default plugin dir).
|
||||
# $2 is directory to prepare.
|
||||
zaf_prepare_plugin() {
|
||||
local url
|
||||
local plugindir
|
||||
local control
|
||||
|
||||
url=$(zaf_get_plugin_url "$1")/control.zaf || exit $?
|
||||
plugindir="$2"
|
||||
control=${plugindir}/control.zaf
|
||||
zaf_install_dir "$plugindir"
|
||||
zaf_dbg "Fetching control file from $url ..."
|
||||
if zaf_fetch_url "$url" >"${control}"; then
|
||||
zaf_ctrl_check_deps "${control}"
|
||||
else
|
||||
zaf_err "prepare_plugin: Cannot fetch or write control file $control from url $url!"
|
||||
fi
|
||||
}
|
||||
|
||||
zaf_install_plugin() {
|
||||
local url
|
||||
local plugin
|
||||
local plugindir
|
||||
local control
|
||||
local version
|
||||
|
||||
if zaf_prepare_plugin "$1" "${ZAF_TMP_DIR}/plugin"; then
|
||||
url=$(zaf_get_plugin_url "$1")
|
||||
control="${ZAF_TMP_DIR}/plugin/control.zaf"
|
||||
plugin=$(zaf_ctrl_get_global_option $control Plugin)
|
||||
version=$(zaf_ctrl_get_global_option $control Version)
|
||||
plugindir="${ZAF_PLUGINS_DIR}"/$plugin
|
||||
if [ -n "$plugin" ] && zaf_prepare_plugin "$1" $plugindir; then
|
||||
zaf_wrn "Installing plugin $plugin version $version"
|
||||
zaf_dbg "Source url: $url, Destination dir: $plugindir"
|
||||
control=${plugindir}/control.zaf
|
||||
[ "$ZAF_DEBUG" -gt 1 ] && zaf_plugin_info "${control}"
|
||||
zaf_ctrl_check_deps "${control}"
|
||||
zaf_ctrl_sudo "$plugin" "${control}" "${plugindir}"
|
||||
zaf_ctrl_cron "$plugin" "${control}" "${plugindir}"
|
||||
zaf_ctrl_generate_cfg "${control}" "${plugin}" \
|
||||
| zaf_far '{PLUGINDIR}' "${plugindir}" >${ZAF_AGENT_CONFIGD}/zaf_${plugin}.conf
|
||||
zaf_dbg "Generated ${ZAF_AGENT_CONFIGD}/zaf_${plugin}.conf"
|
||||
zaf_ctrl_install "$url" "${control}" "${plugindir}"
|
||||
else
|
||||
zaf_err "Cannot install plugin '$plugin' to $plugindir!"
|
||||
fi
|
||||
else
|
||||
zaf_err "Cannot prepare plugin $1"
|
||||
fi
|
||||
}
|
||||
|
||||
# List installed plugins
|
||||
# $1 - plugin
|
||||
zaf_list_plugins() {
|
||||
local cfile
|
||||
local plugin
|
||||
ls -1 ${ZAF_PLUGINS_DIR} | while read p; do
|
||||
zaf_is_plugin "$(basename $p)" && echo $p
|
||||
done
|
||||
}
|
||||
|
||||
zaf_is_plugin() {
|
||||
[ -d "$ZAF_PLUGINS_DIR/$1" ] && [ -f "$ZAF_PLUGINS_DIR/$1/control.zaf" ] && return
|
||||
false
|
||||
}
|
||||
|
||||
zaf_discovery_plugins() {
|
||||
zaf_list_plugins | zaf_discovery '{#PLUGIN}'
|
||||
}
|
||||
|
||||
# $1 plugin
|
||||
# $2 ctrl_option
|
||||
zaf_plugin_option() {
|
||||
local plugindir
|
||||
local cfile
|
||||
|
||||
if [ -z "$1" ]; then
|
||||
zaf_err "Missing plugin name.";
|
||||
fi
|
||||
if zaf_is_plugin "$1"; then
|
||||
plugindir="${ZAF_PLUGINS_DIR}/$1"
|
||||
cfile="$plugindir/control.zaf"
|
||||
zaf_ctrl_get_global_option $cfile $2
|
||||
else
|
||||
zaf_err "Plugin $1 not installed."
|
||||
fi
|
||||
}
|
||||
|
||||
zaf_plugin_version() {
|
||||
zaf_plugin_option "$1" Version
|
||||
}
|
||||
zaf_plugin_maintainer() {
|
||||
zaf_plugin_option "$1" Maintainer
|
||||
}
|
||||
zaf_plugin_url() {
|
||||
zaf_plugin_option "$1" Url
|
||||
}
|
||||
zaf_plugin_web() {
|
||||
zaf_plugin_option "$1" Web
|
||||
}
|
||||
zaf_plugin_template_url() {
|
||||
echo $(zaf_plugin_option "$1" Url)/template.xml
|
||||
}
|
||||
|
||||
# $1 plugin
|
||||
# $2 test to get test items, precache to get items to precache
|
||||
zaf_list_plugin_items() {
|
||||
local items
|
||||
local i
|
||||
local p
|
||||
local key
|
||||
local testparms
|
||||
local precache
|
||||
|
||||
if ! zaf_is_plugin "$1"; then
|
||||
zaf_err "Missing plugin name or plugin $1 unknown. ";
|
||||
fi
|
||||
plugindir="${ZAF_PLUGINS_DIR}/$1"
|
||||
cfile="$plugindir/control.zaf"
|
||||
items=$(zaf_ctrl_get_items <$cfile)
|
||||
for i in $items; do
|
||||
p=$(zaf_ctrl_get_item_option $cfile $i "Parameters")
|
||||
testparms=$(zaf_ctrl_get_item_option $cfile $i "Testparameters")
|
||||
precache=$(zaf_ctrl_get_item_option $cfile $i "Precache")
|
||||
if [ -n "$p" ]; then
|
||||
if [ -n "$testparms" ] && [ "$2" = "test" ]; then
|
||||
for tp in $testparms; do
|
||||
echo -n "$1.$i[$tp] "
|
||||
done
|
||||
else
|
||||
if [ -n "$precache" ] && [ "$2" = "precache" ]; then
|
||||
for tp in $precache; do
|
||||
echo -n "$1.$i[$tp] "
|
||||
done
|
||||
fi
|
||||
[ "$2" != "test" ] && key="$1.$i[]"
|
||||
fi
|
||||
else
|
||||
key="$1.$i"
|
||||
fi
|
||||
[ "$2" != "precache" ] && echo -n "$key "
|
||||
done
|
||||
echo
|
||||
}
|
||||
|
||||
zaf_list_items() {
|
||||
for p in $(zaf_list_plugins); do
|
||||
echo $p: $(zaf_list_plugin_items $p)
|
||||
done
|
||||
}
|
||||
|
||||
zaf_get_item() {
|
||||
if which zabbix_get >/dev/null; then
|
||||
zaf_dbg zabbix_get -s localhost -k "'$1'"
|
||||
(zabbix_get -s localhost -k "$1" | tr '\n' ' '; echo) || zaf_wrn "Cannot reach agent on localhost. Please localhost to Server list."
|
||||
return 11
|
||||
else
|
||||
zaf_wrn "Please install zabbix_get binary to check items over network."
|
||||
return 11
|
||||
fi
|
||||
}
|
||||
|
||||
zaf_test_item() {
|
||||
if $ZAF_AGENT_BIN -t "$1" | grep ZBX_NOTSUPPORTED; then
|
||||
return 1
|
||||
else
|
||||
$ZAF_AGENT_BIN -t "$1" | tr '\n' ' '
|
||||
echo
|
||||
fi
|
||||
}
|
||||
|
||||
zaf_precache_item() {
|
||||
cmd=$(grep "^UserParameter=$item" $ZAF_AGENT_CONFIGD/zaf*.conf | cut -d ',' -f 2- | sed -e "s/_cache/_nocache/")
|
||||
zaf_wrn "Precaching item $item[$(echo $*| tr ' ' ',')] ($cmd)"
|
||||
eval $cmd
|
||||
}
|
||||
|
||||
zaf_remove_plugin() {
|
||||
! zaf_is_plugin $1 && { zaf_err "Plugin $1 not installed!"; }
|
||||
zaf_wrn "Removing plugin $1 (version $(zaf_plugin_version $1))"
|
||||
rm -rf ${ZAF_PLUGINS_DIR}/$1
|
||||
rm -f ${ZAF_AGENT_CONFIGD}/zaf_$1.conf ${ZAF_CROND}/zaf_$1 ${ZAF_SUDOERSD}/zaf_$1
|
||||
}
|
||||
|
263
lib/zaf.lib.sh
263
lib/zaf.lib.sh
@ -186,263 +186,6 @@ zaf_check_agent_config() {
|
||||
${ZAF_AGENT_BIN} -t zaf.version
|
||||
}
|
||||
|
||||
# Update repo
|
||||
zaf_update_repo() {
|
||||
[ "$ZAF_GIT" != 1 ] && { zaf_err "Git is disabled or is not installed. Exiting."; }
|
||||
if [ -z "${ZAF_REPO_GITURL}" ] || [ -z "${ZAF_REPO_DIR}" ]; then
|
||||
zaf_err "This system is not configured for git repository."
|
||||
else
|
||||
[ ! -d "${ZAF_REPO_DIR}" ] && git clone "${ZAF_REPO_GITURL}" "${ZAF_REPO_DIR}"
|
||||
(cd ${ZAF_REPO_DIR} && git pull)
|
||||
fi
|
||||
}
|
||||
|
||||
# Construct url from plugin name
|
||||
# It can be http[s]://url
|
||||
# /path (from file)
|
||||
# name (to try from repo)
|
||||
zaf_get_plugin_url() {
|
||||
local url
|
||||
|
||||
if echo "$1" | grep -q '/'; then
|
||||
url="$1" # plugin with path - from directory
|
||||
else
|
||||
if echo "$1" | grep -q ^http; then
|
||||
url="$1" # plugin with http[s] url
|
||||
else
|
||||
if [ -d "${ZAF_REPO_DIR}/$1" ]; then
|
||||
url="${ZAF_REPO_DIR}/$1"
|
||||
else
|
||||
if [ -n "${ZAF_PREPACKAGED_DIR}" ] && [ -d "${ZAF_PREPACKAGED_DIR}/$1" ]; then
|
||||
url="${ZAF_PREPACKAGED_DIR}/$1"
|
||||
else
|
||||
if [ -n "${ZAF_REPO_URL}" ]; then
|
||||
url="${ZAF_REPO_URL}/$1"
|
||||
else
|
||||
zaf_err "Cannot find plugin $1"
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
echo $url
|
||||
}
|
||||
|
||||
# $1 - control
|
||||
zaf_plugin_info() {
|
||||
local control="$1"
|
||||
|
||||
! [ -f "$control" ] && zaf_err "Control file $control not found."
|
||||
plugin=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Plugin)
|
||||
pdescription=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_moption Description)
|
||||
pmaintainer=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Maintainer)
|
||||
pversion=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Version)
|
||||
purl=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Url)
|
||||
phome=$(zaf_ctrl_get_global_block <"${control}" | zaf_block_get_option Home)
|
||||
pitems=$(zaf_ctrl_get_items <"${control}")
|
||||
echo
|
||||
echo -n "Plugin '$plugin' "; [ -n "$pversion" ] && echo -n "version ${pversion}"; echo ":"
|
||||
echo "$pdescription"; echo
|
||||
[ -n "$pmaintainer" ] && echo "Maintainer: $pmaintainer"
|
||||
[ -n "$purl" ] && echo "Url: $purl"
|
||||
[ -n "$phome" ] && echo "Home: $phome"
|
||||
echo
|
||||
if zaf_is_plugin "$(basename $plugin)"; then
|
||||
echo -n "Defined items: "; zaf_list_plugin_items $plugin
|
||||
echo -n "Test items: "; zaf_list_plugin_items $plugin test
|
||||
echo -n "Precache items: "; zaf_list_plugin_items $plugin precache
|
||||
else
|
||||
echo "Items: $pitems"
|
||||
fi
|
||||
echo
|
||||
}
|
||||
|
||||
# Prepare plugin into dir
|
||||
# $1 is url, directory or plugin name (will be searched in default plugin dir).
|
||||
# $2 is directory to prepare.
|
||||
zaf_prepare_plugin() {
|
||||
local url
|
||||
local plugindir
|
||||
local control
|
||||
|
||||
url=$(zaf_get_plugin_url "$1")/control.zaf || exit $?
|
||||
plugindir="$2"
|
||||
control=${plugindir}/control.zaf
|
||||
zaf_install_dir "$plugindir"
|
||||
zaf_dbg "Fetching control file from $url ..."
|
||||
if zaf_fetch_url "$url" >"${control}"; then
|
||||
zaf_ctrl_check_deps "${control}"
|
||||
else
|
||||
zaf_err "prepare_plugin: Cannot fetch or write control file $control from url $url!"
|
||||
fi
|
||||
}
|
||||
|
||||
zaf_install_plugin() {
|
||||
local url
|
||||
local plugin
|
||||
local plugindir
|
||||
local control
|
||||
local version
|
||||
|
||||
if zaf_prepare_plugin "$1" "${ZAF_TMP_DIR}/plugin"; then
|
||||
url=$(zaf_get_plugin_url "$1")
|
||||
control="${ZAF_TMP_DIR}/plugin/control.zaf"
|
||||
plugin=$(zaf_ctrl_get_global_option $control Plugin)
|
||||
version=$(zaf_ctrl_get_global_option $control Version)
|
||||
plugindir="${ZAF_PLUGINS_DIR}"/$plugin
|
||||
if [ -n "$plugin" ] && zaf_prepare_plugin "$1" $plugindir; then
|
||||
zaf_wrn "Installing plugin $plugin version $version"
|
||||
zaf_dbg "Source url: $url, Destination dir: $plugindir"
|
||||
control=${plugindir}/control.zaf
|
||||
[ "$ZAF_DEBUG" -gt 1 ] && zaf_plugin_info "${control}"
|
||||
zaf_ctrl_check_deps "${control}"
|
||||
zaf_ctrl_sudo "$plugin" "${control}" "${plugindir}"
|
||||
zaf_ctrl_cron "$plugin" "${control}" "${plugindir}"
|
||||
zaf_ctrl_generate_cfg "${control}" "${plugin}" \
|
||||
| zaf_far '{PLUGINDIR}' "${plugindir}" >${ZAF_AGENT_CONFIGD}/zaf_${plugin}.conf
|
||||
zaf_dbg "Generated ${ZAF_AGENT_CONFIGD}/zaf_${plugin}.conf"
|
||||
zaf_ctrl_install "$url" "${control}" "${plugindir}"
|
||||
else
|
||||
zaf_err "Cannot install plugin '$plugin' to $plugindir!"
|
||||
fi
|
||||
else
|
||||
zaf_err "Cannot prepare plugin $1"
|
||||
fi
|
||||
}
|
||||
|
||||
# List installed plugins
|
||||
# $1 - plugin
|
||||
zaf_list_plugins() {
|
||||
local cfile
|
||||
local plugin
|
||||
ls -1 ${ZAF_PLUGINS_DIR} | while read p; do
|
||||
zaf_is_plugin "$(basename $p)" && echo $p
|
||||
done
|
||||
}
|
||||
|
||||
zaf_is_plugin() {
|
||||
[ -d "$ZAF_PLUGINS_DIR/$1" ] && [ -f "$ZAF_PLUGINS_DIR/$1/control.zaf" ] && return
|
||||
false
|
||||
}
|
||||
|
||||
zaf_discovery_plugins() {
|
||||
zaf_list_plugins | zaf_discovery '{#PLUGIN}'
|
||||
}
|
||||
|
||||
# $1 plugin
|
||||
# $2 ctrl_option
|
||||
zaf_plugin_option() {
|
||||
local plugindir
|
||||
local cfile
|
||||
|
||||
if [ -z "$1" ]; then
|
||||
zaf_err "Missing plugin name.";
|
||||
fi
|
||||
if zaf_is_plugin "$1"; then
|
||||
plugindir="${ZAF_PLUGINS_DIR}/$1"
|
||||
cfile="$plugindir/control.zaf"
|
||||
zaf_ctrl_get_global_option $cfile $2
|
||||
else
|
||||
zaf_err "Plugin $1 not installed."
|
||||
fi
|
||||
}
|
||||
|
||||
zaf_plugin_version() {
|
||||
zaf_plugin_option "$1" Version
|
||||
}
|
||||
zaf_plugin_maintainer() {
|
||||
zaf_plugin_option "$1" Maintainer
|
||||
}
|
||||
zaf_plugin_url() {
|
||||
zaf_plugin_option "$1" Url
|
||||
}
|
||||
zaf_plugin_web() {
|
||||
zaf_plugin_option "$1" Web
|
||||
}
|
||||
zaf_plugin_template_url() {
|
||||
echo $(zaf_plugin_option "$1" Url)/template.xml
|
||||
}
|
||||
|
||||
# $1 plugin
|
||||
# $2 test to get test items, precache to get items to precache
|
||||
zaf_list_plugin_items() {
|
||||
local items
|
||||
local i
|
||||
local p
|
||||
local key
|
||||
local testparms
|
||||
local precache
|
||||
|
||||
if ! zaf_is_plugin "$1"; then
|
||||
zaf_err "Missing plugin name or plugin $1 unknown. ";
|
||||
fi
|
||||
plugindir="${ZAF_PLUGINS_DIR}/$1"
|
||||
cfile="$plugindir/control.zaf"
|
||||
items=$(zaf_ctrl_get_items <$cfile)
|
||||
for i in $items; do
|
||||
p=$(zaf_ctrl_get_item_option $cfile $i "Parameters")
|
||||
testparms=$(zaf_ctrl_get_item_option $cfile $i "Testparameters")
|
||||
precache=$(zaf_ctrl_get_item_option $cfile $i "Precache")
|
||||
if [ -n "$p" ]; then
|
||||
if [ -n "$testparms" ] && [ "$2" = "test" ]; then
|
||||
for tp in $testparms; do
|
||||
echo -n "$1.$i[$tp] "
|
||||
done
|
||||
else
|
||||
if [ -n "$precache" ] && [ "$2" = "precache" ]; then
|
||||
for tp in $precache; do
|
||||
echo -n "$1.$i[$tp] "
|
||||
done
|
||||
fi
|
||||
[ "$2" != "test" ] && key="$1.$i[]"
|
||||
fi
|
||||
else
|
||||
key="$1.$i"
|
||||
fi
|
||||
[ "$2" != "precache" ] && echo -n "$key "
|
||||
done
|
||||
echo
|
||||
}
|
||||
|
||||
zaf_list_items() {
|
||||
for p in $(zaf_list_plugins); do
|
||||
echo $p: $(zaf_list_plugin_items $p)
|
||||
done
|
||||
}
|
||||
|
||||
zaf_get_item() {
|
||||
if which zabbix_get >/dev/null; then
|
||||
zaf_dbg zabbix_get -s localhost -k "'$1'"
|
||||
(zabbix_get -s localhost -k "$1" | tr '\n' ' '; echo) || zaf_wrn "Cannot reach agent on localhost. Please localhost to Server list."
|
||||
return 11
|
||||
else
|
||||
zaf_wrn "Please install zabbix_get binary to check items over network."
|
||||
return 11
|
||||
fi
|
||||
}
|
||||
|
||||
zaf_test_item() {
|
||||
if $ZAF_AGENT_BIN -t "$1" | grep ZBX_NOTSUPPORTED; then
|
||||
return 1
|
||||
else
|
||||
$ZAF_AGENT_BIN -t "$1" | tr '\n' ' '
|
||||
echo
|
||||
fi
|
||||
}
|
||||
|
||||
zaf_precache_item() {
|
||||
cmd=$(grep "^UserParameter=$item" $ZAF_AGENT_CONFIGD/zaf*.conf | cut -d ',' -f 2- | sed -e "s/_cache/_nocache/")
|
||||
zaf_wrn "Precaching item $item[$(echo $*| tr ' ' ',')] ($cmd)"
|
||||
eval $cmd
|
||||
}
|
||||
|
||||
zaf_remove_plugin() {
|
||||
! zaf_is_plugin $1 && { zaf_err "Plugin $1 not installed!"; }
|
||||
zaf_wrn "Removing plugin $1 (version $(zaf_plugin_version $1))"
|
||||
rm -rf ${ZAF_PLUGINS_DIR}/$1
|
||||
rm -f ${ZAF_AGENT_CONFIGD}/zaf_$1.conf ${ZAF_CROND}/zaf_$1 ${ZAF_SUDOERSD}/zaf_$1
|
||||
}
|
||||
|
||||
zaf_tolower() {
|
||||
tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'
|
||||
}
|
||||
@ -469,3 +212,9 @@ zaf_strescape() {
|
||||
sed -e 's#\(['"$1"']\)#\\\1#g'
|
||||
}
|
||||
|
||||
# Add seconds to current date and return date in YYYY-MM-DD hh:mm:ss
|
||||
# $1 seconds
|
||||
zaf_date_add() {
|
||||
date -d "$1 seconds" "+%Y-%m-%d %H:%M:%S" 2>/dev/null || date -d "$(expr $(date +%s) + $1)" -D %s "+%Y-%m-%d %H:%M:%S"
|
||||
}
|
||||
|
||||
|
@ -3,45 +3,52 @@
|
||||
# $1 - query string
|
||||
zaf_zbxapi_do() {
|
||||
local result
|
||||
local tmpfile
|
||||
|
||||
tmpfile=$ZAF_TMP_DIR/zapi$$
|
||||
zaf_trc "Zabbix API: $1"
|
||||
result=$(curl -s -f -L -X POST -H 'Content-Type: application/json-rpc' -d "$1" "$ZAF_ZBXAPI_URL")
|
||||
if [ $? = 0 ] && echo $result | grep -q '"result":'; then
|
||||
curl -s -f -L -X POST -H 'Content-Type: application/json-rpc' -d "$1" "$ZAF_ZBXAPI_URL" >$tmpfile
|
||||
if [ $? = 0 ] && $ZAF_LIB_DIR/JSON.sh -b <$tmpfile | grep -q '"result"'; then
|
||||
zaf_trc "API OK"
|
||||
echo $result
|
||||
cat $tmpfile
|
||||
rm -f $tmpfile
|
||||
else
|
||||
zaf_err "Error processing API request. ($?,$result)"
|
||||
zaf_err "Error processing API request. ($?,$tmpfile)"
|
||||
fi
|
||||
}
|
||||
# Call api function and cache results
|
||||
# $1 - query string
|
||||
zaf_zbxapi_do_cache() {
|
||||
local result
|
||||
local tmpfile
|
||||
|
||||
tmpfile=$ZAF_TMP_DIR/zcapi$$
|
||||
if ! zaf_fromcache "$1"; then
|
||||
result=$(zaf_zbxapi_do "$1")
|
||||
[ -n "$result" ] && zaf_tocache "$1" "$result" 60
|
||||
echo $result
|
||||
zaf_zbxapi_do "$1" >$tmpfile
|
||||
[ -s "$tmpfile" ] && cat $tmpfile | zaf_tocache_stdin "$1" 60
|
||||
rm -f $tmpfile
|
||||
fi
|
||||
}
|
||||
|
||||
# Extract result from JSON response
|
||||
# Extract one result from JSON response
|
||||
zaf_zbxapi_getresult() {
|
||||
sed -e 's/\({"jsonrpc":"2.0","result":\)\(.*\),\("id":.*\)/\2/g' | sed -e 's/^\[\]$//'
|
||||
$ZAF_LIB_DIR/JSON.sh -b | grep '\["result"\]' | tr '\t' ' ' | cut -d ' ' -f 2-
|
||||
}
|
||||
|
||||
# Extract XML result from JSON response
|
||||
zaf_zbxapi_getxml() {
|
||||
zaf_zbxapi_getresult | sed -e 's/{"jsonrpc":"2.0","result":"//' | sed -e 's/","id"\:1}//' | zaf_zbxapi_getstring | zaf_strunescape '<">/'
|
||||
zaf_zbxapi_getstring | zaf_strunescape '</">' | zaf_far '\\n' "\n"
|
||||
}
|
||||
|
||||
# Extract string from JSON response result
|
||||
zaf_zbxapi_getstring() {
|
||||
sed -e 's/^"//' -e 's/"$//' -e 's/\\n/'\\n'/g'
|
||||
zaf_zbxapi_getresult | sed -e 's/^"//' -e 's/"$//'
|
||||
}
|
||||
|
||||
# Extract value from JSON response result
|
||||
# $1 key
|
||||
zaf_zbxapi_getvalue() {
|
||||
tr ',' '\n' | grep "\"$1\":" | cut -d '"' -f 4
|
||||
zaf_zbxapi_getvalues() {
|
||||
$ZAF_LIB_DIR/JSON.sh -b | grep '\["result",.*,"'$1'"]' | tr '\t' ' ' | cut -d ' ' -f 2- | sed -e 's/^"//' -e 's/"$//'
|
||||
}
|
||||
|
||||
# Zabbix API related functions
|
||||
@ -68,7 +75,7 @@ zaf_zbxapi_login(){
|
||||
ZAF_ZBXAPI_URL=$(echo $ZAF_ZBXAPI_URL | cut -d '/' -f 1)//$ZAF_ZBXAPI_USER:$ZAF_ZBXAPI_PASS@$(echo $ZAF_ZBXAPI_URL | cut -d '/' -f 3-)
|
||||
fi
|
||||
result=$(zaf_zbxapi_do_cache "$authstr")
|
||||
ZAF_ZBXAPI_AUTH=$(echo $result |zaf_zbxapi_getresult| zaf_zbxapi_getstring)
|
||||
ZAF_ZBXAPI_AUTH=$(echo $result |zaf_zbxapi_getstring)
|
||||
[ -z "$ZAF_ZBXAPI_AUTH" ] && zaf_err "Cannot login into API"
|
||||
zaf_dbg "Logged into zabbix API ($ZAF_ZBXAPI_AUTH)"
|
||||
}
|
||||
@ -102,7 +109,7 @@ zaf_zbxapi_get_object() {
|
||||
params='"params": {'$filter' "output":"'$output'"}';
|
||||
fi
|
||||
str='{ "method": "'$obj'.get", "jsonrpc": "2.0", "auth": "'$ZAF_ZBXAPI_AUTH'",'$params', "id": "'$id'" }'
|
||||
result=$(zaf_zbxapi_do_cache "$str" | zaf_zbxapi_getresult)
|
||||
result=$(zaf_zbxapi_do_cache "$str")
|
||||
[ -z "$result" ] && zaf_dbg "API call result empty or error! ($str)"
|
||||
echo $result
|
||||
}
|
||||
@ -113,7 +120,7 @@ zaf_zbxapi_gethostgroupid() {
|
||||
|
||||
result=$(zaf_zbxapi_get_object "hostgroup" '"name": ["'$1'"]')
|
||||
[ -z "$result" ] && zaf_err "HostGroup $1 not found!"
|
||||
echo $result |zaf_zbxapi_getvalue groupid
|
||||
echo $result |zaf_zbxapi_getvalues groupid
|
||||
}
|
||||
|
||||
# $1 hostid
|
||||
@ -126,7 +133,7 @@ zaf_zbxapi_gethost() {
|
||||
if [ -z "$2" ]; then
|
||||
echo $result
|
||||
else
|
||||
echo $result |zaf_zbxapi_getvalue $2
|
||||
echo $result |zaf_zbxapi_getvalues $2
|
||||
fi
|
||||
}
|
||||
|
||||
@ -136,7 +143,7 @@ zaf_zbxapi_gethostid() {
|
||||
|
||||
result=$(zaf_zbxapi_get_object "host" '"host": ["'$1'"]')
|
||||
[ -z "$result" ] && zaf_err "Host $1 not found!"
|
||||
echo $result |zaf_zbxapi_getvalue hostid
|
||||
echo $result |zaf_zbxapi_getvalues hostid
|
||||
}
|
||||
|
||||
# $1 hostname
|
||||
@ -149,7 +156,7 @@ zaf_zbxapi_gethostinventory() {
|
||||
if [ -z "$2" ]; then
|
||||
echo $result
|
||||
else
|
||||
echo $result |zaf_zbxapi_getvalue $2
|
||||
echo $result |zaf_zbxapi_getvalues $2
|
||||
fi
|
||||
}
|
||||
|
||||
@ -159,7 +166,7 @@ zaf_zbxapi_gettemplateid() {
|
||||
|
||||
result=$(zaf_zbxapi_get_object "template" '"host": ["'$1'"]')
|
||||
[ -z "$result" ] && zaf_err "Template $1 not found!"
|
||||
echo $result |zaf_zbxapi_getvalue templateid
|
||||
echo $result |zaf_zbxapi_getvalues templateid
|
||||
}
|
||||
|
||||
# $1 templateid
|
||||
@ -172,7 +179,7 @@ zaf_zbxapi_gettemplate() {
|
||||
if [ -z "$2" ]; then
|
||||
echo $result
|
||||
else
|
||||
echo $result |zaf_zbxapi_getvalue $2
|
||||
echo $result |zaf_zbxapi_getvalues $2
|
||||
fi
|
||||
}
|
||||
|
||||
@ -182,7 +189,7 @@ zaf_zbxapi_gethostsingroup() {
|
||||
|
||||
result=$(zaf_zbxapi_get_object "host" '' '"groupids": ["'$1'"]')
|
||||
[ -z "$result" ] && zaf_wrn "No hosts in groupid '$1'"
|
||||
echo $result | zaf_zbxapi_getvalue "hostid"
|
||||
echo $result | zaf_zbxapi_getvalues "hostid"
|
||||
}
|
||||
|
||||
# Get all hostids in system
|
||||
@ -190,7 +197,7 @@ zaf_zbxapi_gethostids() {
|
||||
local result
|
||||
|
||||
result=$(zaf_zbxapi_get_object "host")
|
||||
echo $result | zaf_zbxapi_getvalue "hostid"
|
||||
echo $result | zaf_zbxapi_getvalues "hostid"
|
||||
}
|
||||
|
||||
# Get all templateids in system
|
||||
@ -198,7 +205,7 @@ zaf_zbxapi_gettemplateids() {
|
||||
local result
|
||||
|
||||
result=$(zaf_zbxapi_get_object "template")
|
||||
echo $result | zaf_zbxapi_getvalue "templateid"
|
||||
echo $result | zaf_zbxapi_getvalues "templateid"
|
||||
}
|
||||
|
||||
# $1 hostgroupid
|
||||
@ -207,7 +214,7 @@ zaf_zbxapi_gettemplatesingroup() {
|
||||
|
||||
result=$(zaf_zbxapi_get_object "template" '' '"groupids": ["'$1'"]')
|
||||
[ -z "$result" ] && zaf_wrn "No templates in groupid '$1'"
|
||||
echo $result | zaf_zbxapi_getvalue "templateid"
|
||||
echo $result | zaf_zbxapi_getvalues "templateid"
|
||||
}
|
||||
|
||||
# $1 map or null for all
|
||||
@ -220,7 +227,7 @@ zaf_zbxapi_getmapid() {
|
||||
result=$(zaf_zbxapi_get_object "map")
|
||||
fi
|
||||
[ -z "$result" ] && zaf_err "Map $1 not found"
|
||||
echo $result | zaf_zbxapi_getvalue "sysmapid"
|
||||
echo $result | zaf_zbxapi_getvalues "sysmapid"
|
||||
}
|
||||
|
||||
# $1 mapid
|
||||
@ -233,7 +240,7 @@ zaf_zbxapi_getmap() {
|
||||
if [ -z "$2" ]; then
|
||||
echo $result
|
||||
else
|
||||
echo $result |zaf_zbxapi_getvalue $2
|
||||
echo $result |zaf_zbxapi_getvalues $2
|
||||
fi
|
||||
}
|
||||
|
||||
|
4
zaf
4
zaf
@ -44,6 +44,7 @@ fi
|
||||
|
||||
if [ -f ./lib/zaf.lib.sh ]; then
|
||||
. ./lib/zaf.lib.sh
|
||||
. ./lib/plugin.lib.sh
|
||||
. ./lib/os.lib.sh
|
||||
. ./lib/ctrl.lib.sh
|
||||
. ./lib/cache.lib.sh
|
||||
@ -398,6 +399,9 @@ api)
|
||||
zaf_hlp "get-byid-${i} id [property]" "Get $i property from id. Leave empty property for JSON"
|
||||
done
|
||||
zaf_hlp "get-inventory host [fields]" "Get inventory fields [or all fields]"
|
||||
zaf_hlp "get-host-ids [hg]" "Get all hostids or hostids in group hg"
|
||||
zaf_hlp "get-template-ids [hg]" "Get all templateids or templateids in group hg"
|
||||
zaf_hlp "get-map-ids" "Get all mapids"
|
||||
zaf_hlp "export-hosts dir [hg]" "Backup all hosts [in group hg] (get their config from zabbix and save to dir/hostname.xml)"
|
||||
zaf_hlp "export-host host" "Backup host (get config from zabbix to stdout)"
|
||||
zaf_hlp "import-template {plugin|file}" "Import template for plugin or from file"
|
||||
|
Loading…
Reference in New Issue
Block a user