mirror of
https://github.com/hassio-addons/bashio.git
synced 2025-05-03 10:31:25 +00:00
631 lines
21 KiB
Bash
631 lines
21 KiB
Bash
#!/usr/bin/env bash
|
|
# ==============================================================================
|
|
# Home Assistant Community Add-ons: Bashio
|
|
# Bashio is a bash function library for use with Home Assistant add-ons.
|
|
#
|
|
# It contains a set of commonly used operations and can be used
|
|
# to be included in add-on scripts to reduce code duplication across add-ons.
|
|
# ==============================================================================
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Fetches a configuration value from the add-on config file.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# $2 Default value for not set config option (optional: defaults to 'null')
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config() {
|
|
local key=${1}
|
|
local default_value=${2:-null}
|
|
local query
|
|
local result
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
read -r -d '' query << QUERY
|
|
if (.${key} == null) then
|
|
null
|
|
elif (.${key} | type == "string") then
|
|
.${key} // empty
|
|
elif (.${key} | type == "boolean") then
|
|
.${key} // false
|
|
elif (.${key} | type == "array") then
|
|
if (.${key} == []) then
|
|
empty
|
|
else
|
|
.${key}[]
|
|
end
|
|
elif (.${key} | type == "object") then
|
|
if (.${key} == {}) then
|
|
empty
|
|
else
|
|
.${key}
|
|
end
|
|
else
|
|
.${key}
|
|
end
|
|
QUERY
|
|
|
|
options=$(bashio::addon.config)
|
|
result=$(bashio::jq "${options}" "${query}")
|
|
|
|
if [[ "${result}" == "null" ]];
|
|
then
|
|
echo "${default_value}"
|
|
else
|
|
printf "%s" "${result}"
|
|
fi
|
|
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Checks if a configuration option exists in the config file
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.exists() {
|
|
local key=${1}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if [[ $(bashio::config "${key}") == "null" ]]; then
|
|
return "${__BASHIO_EXIT_NOK}"
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Checks if a configuration option has an actual value.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.has_value() {
|
|
local key=${1}
|
|
local value
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
value=$(bashio::config "${key}")
|
|
if [[ "${value}" == "null" ]]; then
|
|
return "${__BASHIO_EXIT_NOK}"
|
|
fi
|
|
|
|
if ! bashio::var.has_value "${value}"; then
|
|
return "${__BASHIO_EXIT_NOK}"
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Checks if a configuration option has an empty value.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.is_empty() {
|
|
local key=${1}
|
|
local value
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
value=$(bashio::config "${key}")
|
|
if bashio::var.is_empty "${value}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
if [[ "${value}" == "null" ]]; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_NOK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Checks if a configuration option equals a value.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# $2 Checks if the configuration option matches
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.equals() {
|
|
local key=${1}
|
|
local equals=${2}
|
|
local value
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
value=$(bashio::config "${key}")
|
|
if ! bashio::var.equals "${value}" "${equals}"; then
|
|
return "${__BASHIO_EXIT_NOK}"
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Checks if a configuration option is true.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.true() {
|
|
local key=${1}
|
|
local value
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
value=$(bashio::config "${key}")
|
|
if ! bashio::var.true "${value}"; then
|
|
return "${__BASHIO_EXIT_NOK}"
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Checks if a configuration option is false.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.false() {
|
|
local key=${1}
|
|
local value
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
value=$(bashio::config "${key}")
|
|
if ! bashio::var.false "${value}"; then
|
|
return "${__BASHIO_EXIT_NOK}"
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Checks if a password is safe to use, using IHaveBeenPwned.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.is_safe_password() {
|
|
local key=${1}
|
|
local password
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
# If the password is safe, we'll accept it anyways.
|
|
password=$(bashio::config "${key}")
|
|
if bashio::pwned.is_safe_password "${password}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
# If the bypass is enabled, we'll return OK.
|
|
if bashio::config.true "i_like_to_be_pwned"; then
|
|
bashio::log.warning "Have I Been Pwned bypass enabled."
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
# If we reach this point, we'll just fail.
|
|
return "${__BASHIO_EXIT_NOK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Require a configuration option to be set by the user.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# $2 Addition reason why this is needed
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.require() {
|
|
local key=${1}
|
|
local reason=${2:-}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if bashio::config.has_value "${key}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
bashio::log.fatal
|
|
bashio::log.fatal "A required add-on configuration option is missing!"
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Please set a value for the '${key}' option."
|
|
if bashio::var.has_value "${reason}"; then
|
|
bashio::log.fatal
|
|
bashio::log.fatal "This option is required because:"
|
|
bashio::log.fatal "${reason}"
|
|
fi
|
|
bashio::log.fatal
|
|
bashio::log.fatal "If unsure, check the add-on manual for more information."
|
|
bashio::log.fatal
|
|
|
|
bashio::exit.nok
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Suggest on setting a configuration option to the user.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# $2 Addition reason why this is needed
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.suggest() {
|
|
local key=${1}
|
|
local reason=${2:-}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if ! bashio::config.has_value "${key}"; then
|
|
bashio::log.warning
|
|
bashio::log.warning \
|
|
"A recommended add-on configuration option is not set."
|
|
bashio::log.warning
|
|
bashio::log.warning "The configuration key '${key}' seems to be empty."
|
|
bashio::log.warning
|
|
if bashio::var.has_value "${reason}"; then
|
|
bashio::log.warning
|
|
bashio::log.warning "Consider configuring this because:"
|
|
bashio::log.warning "${reason}"
|
|
fi
|
|
bashio::log.warning "Check the add-on manual for more information."
|
|
bashio::log.warning
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Suggest on enabling a configuration option to the user.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# $2 Addition reason why this is needed
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.suggest.true() {
|
|
local key=${1}
|
|
local reason=${2:-}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if ! bashio::config.true "${key}"; then
|
|
bashio::log.warning
|
|
bashio::log.warning \
|
|
"A recommended add-on configuration option is not enabled."
|
|
if bashio::var.has_value "${reason}"; then
|
|
bashio::log.warning
|
|
bashio::log.warning "Consider enabling this because:"
|
|
bashio::log.warning "${reason}"
|
|
fi
|
|
bashio::log.warning
|
|
bashio::log.warning "Enable config option '${key}' hide this message."
|
|
bashio::log.warning
|
|
bashio::log.warning "Check the add-on manual for more information."
|
|
bashio::log.warning
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Suggest on disabling a configuration option to the user.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option
|
|
# $2 Addition reason why this is needed
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.suggest.false() {
|
|
local key=${1}
|
|
local reason=${2:-}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if ! bashio::config.false "${key}"; then
|
|
bashio::log.warning
|
|
bashio::log.warning \
|
|
"A recommended add-on configuration option is not disabled."
|
|
if bashio::var.has_value "${reason}"; then
|
|
bashio::log.warning
|
|
bashio::log.warning "Consider disabling this because:"
|
|
bashio::log.warning "${reason}"
|
|
fi
|
|
bashio::log.warning
|
|
bashio::log.warning "Disable config option '${key}' hide this message."
|
|
bashio::log.warning
|
|
bashio::log.warning "Check the add-on manual for more information."
|
|
bashio::log.warning
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Require the user to configure a username.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option (optional: defaults to 'username')
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.require.username() {
|
|
local key=${1:-"username"}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if bashio::config.has_value "${key}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Setting a username is required!"
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Please username in the '${key}' option."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "If unsure, check the add-on manual for more information."
|
|
bashio::log.fatal
|
|
|
|
bashio::exit.nok
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Suggest to the user to set a username, in case it is not.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option (optional: defaults to 'username')
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.suggest.username() {
|
|
local key=${1}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if ! bashio::config.has_value "${key}"; then
|
|
bashio::log.warning
|
|
bashio::log.warning \
|
|
"Setting a username is highly recommended!"
|
|
bashio::log.warning
|
|
bashio::log.warning "Define a username in the '${key}' option."
|
|
bashio::log.warning
|
|
bashio::log.warning "Check the add-on manual for more information."
|
|
bashio::log.warning
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Checks if the password has been set and exits when it is not.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option (optional: defaults to 'password')
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.require.password() {
|
|
local key=${1:-"password"}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if bashio::config.has_value "${key}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Setting a password is required!"
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Please set a password in the '${key}' option."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "If unsure, check the add-on manual for more information."
|
|
bashio::log.fatal
|
|
|
|
bashio::exit.nok
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Suggest to set a password if it was not set.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option (optional: defaults to 'password')
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.suggest.password() {
|
|
local key=${1:-"password"}
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if bashio::config.has_value "${key}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
bashio::log.warning
|
|
bashio::log.warning "Setting a password is highly recommended!"
|
|
bashio::log.warning
|
|
bashio::log.warning "Please set a password in the '${key}' option."
|
|
bashio::log.warning
|
|
bashio::log.warning \
|
|
"If unsure, check the add-on manual for more information."
|
|
bashio::log.warning
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Require to set a password which is not in HaveIBeenPwned database.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option (optional: defaults to 'password')
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.require.safe_password() {
|
|
local key=${1:-"password"}
|
|
local password
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
bashio::config.require.password "${key}"
|
|
|
|
password=$(bashio::config "${key}")
|
|
|
|
if bashio::pwned.is_safe_password "${password}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
bashio::log.fatal
|
|
bashio::log.fatal "We are trying to help you to protect your system the"
|
|
bashio::log.fatal "best we can. Therefore, this add-on checks your"
|
|
bashio::log.fatal "configured password against the HaveIBeenPwned database."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Unfortunately, your configured password is considered"
|
|
bashio::log.fatal "unsafe. We highly recommend you to pick a different one."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Please change the password in the '${key}' option."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Check the add-on manual for more information."
|
|
bashio::log.fatal
|
|
|
|
bashio::exit.nok
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Suggest to set a password which is not in HaveIBeenPwned database.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the config option (optional: defaults to 'password')
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.suggest.safe_password() {
|
|
local key=${1:-"password"}
|
|
local password
|
|
|
|
bashio::log.trace "${FUNCNAME[0]}:" "$@"
|
|
|
|
if ! bashio::config.has_value "${key}"; then
|
|
bashio::config.suggest.password "${key}"
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
password=$(bashio::config "${key}")
|
|
|
|
if bashio::pwned.is_safe_password "${password}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
bashio::log.warning
|
|
bashio::log.warning "We are trying to help you to protect your system the"
|
|
bashio::log.warning "best we can. Therefore, this add-on checks your"
|
|
bashio::log.warning "configured password against the HaveIBeenPwned database."
|
|
bashio::log.warning
|
|
bashio::log.warning "Unfortunately, your configured password is considered"
|
|
bashio::log.warning "unsafe. It is recommended to pick a different one."
|
|
bashio::log.warning
|
|
bashio::log.warning "Please change the password in the '${key}' option."
|
|
bashio::log.warning
|
|
bashio::log.warning "Check the add-on manual for more information."
|
|
bashio::log.warning
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# Check if certificate files exists when SSL is enabled.
|
|
#
|
|
# Arguments:
|
|
# $1 Key of the ssl config option (optional: defaults to 'ssl')
|
|
# $2 Key of the cert file config option (optional: defaults to 'certfile')
|
|
# $3 Key of the cert key file config option (optional: defaults to 'keyfile')
|
|
# ------------------------------------------------------------------------------
|
|
function bashio::config.require.ssl() {
|
|
local key=${1:-"ssl"}
|
|
local certfile=${2:-"certfile"}
|
|
local keyfile=${3:-"keyfile"}
|
|
|
|
if ! bashio::config.true "${key}"; then
|
|
return "${__BASHIO_EXIT_OK}"
|
|
fi
|
|
|
|
if bashio::config.is_empty "${certfile}"; then
|
|
bashio::log.fatal
|
|
bashio::log.fatal "SSL has been enabled using the '${key}' option,"
|
|
bashio::log.fatal "this requires an SSL certificate file which is"
|
|
bashio::log.fatal "configured using the '${certfile}' option in the"
|
|
bashio::log.fatal "add-on configuration."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Unfortunately, the '${certfile}' option is empty."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Consider configuring or getting an SSL certificate"
|
|
bashio::log.fatal "or setting the '${key}' option to 'false' in case"
|
|
bashio::log.fatal "you are not planning on using SSL with this add-on."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Check the add-on manual for more information."
|
|
bashio::log.fatal
|
|
|
|
bashio::exit.nok
|
|
fi
|
|
|
|
if bashio::config.is_empty "${keyfile}"; then
|
|
bashio::log.fatal
|
|
bashio::log.fatal "SSL has been enabled using the '${key}' option,"
|
|
bashio::log.fatal "this requires an SSL certificate key file which is"
|
|
bashio::log.fatal "configured using the '${keyfile}' option in the"
|
|
bashio::log.fatal "add-on configuration."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Unfortunately, the '${keyfile}' option is empty."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Consider configuring or getting an SSL certificate"
|
|
bashio::log.fatal "or setting the '${key}' option to 'false' in case"
|
|
bashio::log.fatal "you are not planning on using SSL with this add-on."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Check the add-on manual for more information."
|
|
bashio::log.fatal
|
|
|
|
bashio::exit.nok
|
|
fi
|
|
|
|
if ! bashio::fs.file_exists "/ssl/$(bashio::config "${certfile}")"; then
|
|
bashio::log.fatal
|
|
bashio::log.fatal "SSL has been enabled using the '${key}' option,"
|
|
bashio::log.fatal "this requires an SSL certificate file which is"
|
|
bashio::log.fatal "configured using the '${certfile}' option in the"
|
|
bashio::log.fatal "add-on configuration."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Unfortunately, the file specified in the"
|
|
bashio::log.fatal "'${certfile}' option does not exist."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Please ensure the certificate file exists and"
|
|
bashio::log.fatal "is placed in the '/ssl/' directory."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "In case you don't have SSL yet, consider getting"
|
|
bashio::log.fatal "an SSL certificate or setting the '${key}' option"
|
|
bashio::log.fatal "to 'false' in case you are not planning on using"
|
|
bashio::log.fatal "SSL with this add-on."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Check the add-on manual for more information."
|
|
bashio::log.fatal
|
|
|
|
bashio::exit.nok
|
|
fi
|
|
|
|
if ! bashio::fs.file_exists "/ssl/$(bashio::config "${keyfile}")"; then
|
|
bashio::log.fatal
|
|
bashio::log.fatal "SSL has been enabled using the '${key}' option,"
|
|
bashio::log.fatal "this requires an SSL certificate key file which is"
|
|
bashio::log.fatal "configured using the '${keyfile}' option in the"
|
|
bashio::log.fatal "add-on configuration."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Unfortunately, the file specified in the"
|
|
bashio::log.fatal "'${keyfile}' option does not exist."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Please ensure the certificate key file exists and"
|
|
bashio::log.fatal "is placed in the '/ssl/' directory."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "In case you don't have SSL yet, consider getting"
|
|
bashio::log.fatal "an SSL certificate or setting the '${key}' option"
|
|
bashio::log.fatal "to 'false' in case you are not planning on using"
|
|
bashio::log.fatal "SSL with this add-on."
|
|
bashio::log.fatal
|
|
bashio::log.fatal "Check the add-on manual for more information."
|
|
bashio::log.fatal
|
|
|
|
bashio::exit.nok
|
|
fi
|
|
|
|
return "${__BASHIO_EXIT_OK}"
|
|
}
|