blob: f2a516791244476b270476189190d74cee304c4e [file] [log] [blame] [raw]
# Copyright 2015-2020 Rivoreo
# Permission is hereby granted, free of charge, to any person obtaining
# a copy of this software and associated documentation files (the
# "Software"), to deal in the Software without restriction, including
# without limitation the rights to use, copy, modify, merge, publish,
# distribute, sublicense, and/or sell copies of the Software, and to
# permit persons to whom the Software is furnished to do so, subject to
# the following conditions:
# The above copyright notice and this permission notice shall be
# included in all copies or substantial portions of the Software.
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
# NONINFRINGEMENT. IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE
# FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
# CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
http_post() {
if [ $# != 2 ]; then
echo "Usage: http_post <url> <data>" 1>&2
return 255
fi
command="${HTTP_CLIENT#*=}"
case "${HTTP_CLIENT%%=*}" in
wget)
[ -z "$command" ] && command=wget
$command --timeout 2 --tries 1 --no-verbose "$1" --post-data "$2" --output-document - &
;;
curl)
[ -z "$command" ] && command=curl
$command "$1" --request POST --data-binary "$2" &
;;
netcat)
[ -z "$HTTP_SERVER_NAME" ] && prepare_http_server_information "$1"
[ -z "$command" ] && command=netcat
#post_data="`printf %s \"$2\" | sed 's/ /%20/g;s/!/%21/g;s/\"/%22/g;s/#/%23/g;s/\\$/%24/g;s/\\&/%26/g;s/'\"'\"'/%27/g;s/(/%28/g;s/)/%29/g;s/:/%3A/g'`"
post_data="$2"
printf 'POST %s HTTP/1.0\r
Host: %s\r
Content-Type: application/x-www-form-urlencoded\r
Content-Length: %s\r\n\r\n%s' "$HTTP_REQUEST_PATH" "$HTTP_SERVER_NAME" \
"`printf %s \"$post_data\" | wc -c`" "$post_data" | \
$command "$HTTP_SERVER_NAME" "$HTTP_SERVER_PORT" > /dev/null &
;;
bash)
[ -z "$HTTP_SERVER_NAME" ] && prepare_http_server_information "$1"
#post_data="`printf %s \"$2\" | sed 's/ /%20/g;s/!/%21/g;s/\"/%22/g;s/#/%23/g;s/\\$/%24/g;s/\\&/%26/g;s/'\"'\"'/%27/g;s/(/%28/g;s/)/%29/g;s/:/%3A/g'`"
post_data="$2"
printf 'POST %s HTTP/1.0\r
Host: %s\r
Content-Type: application/x-www-form-urlencoded\r
Content-Length: %s\r\n\r\n%s' "$HTTP_REQUEST_PATH" "$HTTP_SERVER_NAME" \
"`printf %s \"$post_data\" | wc -c`" "$post_data" > \
"/dev/tcp/$HTTP_SERVER_NAME/$HTTP_SERVER_PORT"
;;
*)
printf "HTTP client type '%s' not recognized\\n" "$HTTP_CLIENT" 1>&2
return 1
;;
esac
}
get_ip_address() {
if [ $# != 1 ]; then
echo "Usage: get_ip_address <interface>" 1>&2
return 255
fi
ifconfig "$1" | grep -Ev '^[[:space:]]+tunnel ' | grep -Eo -m 1 '^[[:space:]]+inet[ a-z:]+([0-9]{1,3}\.){3}[0-9]{1,3}' | sed -r 's/^[[:space:]]+inet[ a-z:]+//'
return 0
}
set_hostname_from_interface() {
HOSTNAME="`get_ip_address \"$1\"`"
if [ -z "$HOSTNAME" ]; then
printf "Cannot get IP address from interface '%s'\\n" "$1" 1>&2
exit 1
fi
}
load_config_file() {
[ -f "$1" ] || return
eval "`grep -Eo '^[A-Z0-9_]+=[-A-Za-z0-9_@\" .:=/\\]+' \"$1\"`"
}
check_config() {
if { [ -z "$INFLUXDB_BASE_URL" ] || [ -z "$INFLUXDB_DB_NAME" ]; } && [ -z "$CARBON_SERVER" ]; then
echo "INFLUXDB_BASE_URL and INFLUXDB_DB_NAME must be set, or CARBON_SERVER must be set" 1>&2
exit 1
fi
if [ -n "$INFLUXDB_BASE_URL" ] && [ -z "$INFLUXDB_DB_NAME" ]; then
echo "Set INFLUXDB_BASE_URL but INFLUXDB_DB_NAME is not set" 1>&2
exit 1
fi
if [ -n "$INFLUXDB_BASE_URL" ]; then
if ! printf %s "$INFLUXDB_BASE_URL" | grep -q -e "^http://" -e "^https://"; then
echo "INFLUXDB_BASE_URL doesn't contain a supported protocol" 1>&2
exit 1
fi
[ -n "${INFLUXDB_BASE_URL##*/}" ] && INFLUXDB_BASE_URL="$INFLUXDB_BASE_URL/"
fi
[ -z "$HTTP_CLIENT" ] && check_http_client
if [ -n "$INTERVAL" ]; then
if ! [ "$INTERVAL" -gt 0 ]; then
echo "Invalid INTERVAL setting; it must be a positive integer" 1>&2
exit 1
fi
else
INTERVAL=5
fi
[ -n "$INTERFACE" ] && set_hostname_from_interface "$INTERFACE"
[ -z "$HOSTNAME" ] && HOSTNAME="`hostname -s`"
HOSTNAME_FOR_CARBON="`printf %s \"$HOSTNAME\" | sed -r 's [.:;/\\] \\- g'`"
if [ -n "$CARBON_SERVER" ]; then
case "$CARBON_OVER_SSH" in
[Oo][Ff][Ff]|[Nn][Oo]|[Ff][Aa][Ll][Ss][Ee]|0|"")
CARBON_OVER_SSH=
;;
[Oo][Nn]|[Yy][Ee][Ss]|[Tt][Rr][Uu][Ee]|1)
CARBON_OVER_SSH=1
;;
*)
printf "current CARBON_OVER_SSH setting '%s' can't be recognized\\n" "$CARBON_OVER_SSH" 1>&2
exit 1
;;
esac
if [ -n "$CARBON_OVER_SSH" ]; then
[ -n "$CARBON_PORT" ] || CARBON_PORT=22
[ -n "$CARBON_OVER_SSH_USER_NAME" ] || CARBON_OVER_SSH_USER_NAME=carbon
else
[ -n "$CARBON_PORT" ] || CARBON_PORT=2003
fi
fi
}
handle_command_line_options() {
while getopts i:I:n: c
do case "$c" in
i)
INTERVAL="$OPTARG"
;;
I)
INTERFACE="$OPTARG"
;;
n)
HOSTNAME="$1"
;;
\?)
printf "Usage: %s [-i <interval>] [-I <interface>] [-n <hostname>]\\n" "$0" 1>&2
exit 255
;;
esac done
check_config
}
check_http_client() {
[ -z "$INFLUXDB_BASE_URL" ] && return
if wget --version 2> /dev/null | grep -q "^GNU Wget "; then
HTTP_CLIENT=wget
elif curl --version 2> /dev/null | grep -q "^curl "; then
HTTP_CLIENT=curl
elif printf %s "$INFLUXDB_BASE_URL" | grep -q "^http://"; then
if ncat --version 2>&1 | grep -q "^Ncat: "; then
HTTP_CLIENT=netcat=ncat
else
for nc in netcat nc; do case "`$nc --version 2>&1 | sed 1!d`" in
"Ncat: "*|*"The GNU Netcat"*)
HTTP_CLIENT=netcat=$nc
return
;;
esac done
if nc -h 2>&1 | grep -Eq '^\[v1\..+\]$'; then
HTTP_CLIENT=netcat=nc
elif [ -n "$BASH" ]; then
HTTP_CLIENT=bash
else
echo "Need a HTTP client tool to post data via HTTP" 1>&2
exit 1
fi
fi
else
echo "Need a HTTP client tool to post data via HTTPS" 1>&2
echo "Please install wget(1) or curl(1)" 1>&2
exit 1
fi
}
prepare_http_server_information() {
HTTP_SERVER_NAME="${1#http://}"
HTTP_REQUEST_PATH="/${HTTP_SERVER_NAME#*/}"
HTTP_SERVER_NAME="${HTTP_SERVER_NAME%%/*}"
HTTP_SERVER_PORT="${HTTP_SERVER_NAME##*:}"
if [ "$HTTP_SERVER_PORT" = "$HTTP_SERVER_NAME" ]; then
HTTP_SERVER_PORT=80
else
HTTP_SERVER_NAME="${HTTP_SERVER_NAME%:[0-9]*}"
fi
}
check_netcat_for_carbon() {
if ncat --version 2>&1 | grep -q "^Ncat: "; then
NETCAT_FOR_CARBON="ncat -n"
return 0
fi
for nc in netcat nc; do case "`$nc --version 2>&1 | sed 1!d`" in
"Ncat: "*|*"The GNU Netcat"*)
NETCAT_FOR_CARBON="$nc -n"
return 0
;;
esac done
if nc -h 2>&1 | grep -Eq '^\[v1\..+\]$'; then
NETCAT_FOR_CARBON="nc -n -q 1"
return 0
fi
if [ -n "$BASH" ] || bash --version | grep -q "^GNU bash"; then
if [ -n "$BASH" ]; then
bash_netcat() {
cat > /dev/tcp/$1/$2
}
else
bash_netcat() {
bash -c 'exec cat > /dev/tcp/$0/$1' "$@"
}
fi
NETCAT_FOR_CARBON=bash_netcat
return 0
fi
}
send_carbon_lines() {
[ -n "$CARBON_SERVER" ] || exec cat > /dev/null
if [ -n "$CARBON_OVER_SSH" ]; then
#ssh_command_line="ssh -o BatchMode=yes -o ConnectionAttempts=4 -o ServerAliveInterval=60
SSH_COMMAND_LINE="ssh -o BatchMode=yes -o ConnectionAttempts=4 -o ServerAliveInterval=60 $CARBON_SERVER -p $CARBON_PORT -l $CARBON_OVER_SSH_USER_NAME -T"
[ -n "$CARBON_OVER_SSH_IDENTITY_FILE" ] && SSH_COMMAND_LINE="$SSH_COMMAND_LINE -i $CARBON_OVER_SSH_IDENTITY_FILE"
until $SSH_COMMAND_LINE; do sleep 4; done
else
if [ -n "$BASH" ]; then
until cat > "/dev/tcp/$CARBON_SERVER/$CARBON_PORT"; do sleep 4; done
else
[ -n "$NETCAT_FOR_CARBON" ] || check_netcat_for_carbon || exit
until $NETCAT_FOR_CARBON "$CARBON_SERVER" "$CARBON_PORT"; do sleep 4; done
fi
fi
}