| #!/bin/bash |
| # |
| # **inc/ini-config** - Configuration/INI functions |
| # |
| # Support for manipulating INI-style configuration files |
| # |
| # These functions have no external dependencies and no side-effects |
| |
| # Save trace setting |
| INC_CONF_TRACE=$(set +o | grep xtrace) |
| set +o xtrace |
| |
| |
| # Config Functions |
| # ================ |
| |
| # Append a new option in an ini file without replacing the old value |
| # iniadd [-sudo] config-file section option value1 value2 value3 ... |
| function iniadd { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sudo="" |
| if [ $1 == "-sudo" ]; then |
| sudo="-sudo " |
| shift |
| fi |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| shift 3 |
| |
| local values |
| values="$(iniget_multiline $file $section $option) $@" |
| iniset_multiline $sudo $file $section $option $values |
| $xtrace |
| } |
| |
| # Comment an option in an INI file |
| # inicomment [-sudo] config-file section option |
| function inicomment { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sudo="" |
| if [ $1 == "-sudo" ]; then |
| sudo="sudo " |
| shift |
| fi |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| |
| $sudo sed -i -e "/^\[$section\]/,/^\[.*\]/ s|^\($option[ \t]*=.*$\)|#\1|" "$file" |
| $xtrace |
| } |
| |
| # Get an option from an INI file |
| # iniget config-file section option |
| function iniget { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| local line |
| |
| line=$(sed -ne "/^\[$section\]/,/^\[.*\]/ { /^$option[ \t]*=/ p; }" "$file") |
| echo ${line#*=} |
| $xtrace |
| } |
| |
| # Get a multiple line option from an INI file |
| # iniget_multiline config-file section option |
| function iniget_multiline { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| local values |
| |
| values=$(sed -ne "/^\[$section\]/,/^\[.*\]/ { s/^$option[ \t]*=[ \t]*//gp; }" "$file") |
| echo ${values} |
| $xtrace |
| } |
| |
| # Determinate is the given option present in the INI file |
| # ini_has_option [-sudo] config-file section option |
| function ini_has_option { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sudo="" |
| if [ $1 == "-sudo" ]; then |
| sudo="sudo " |
| shift |
| fi |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| local line |
| |
| line=$($sudo sed -ne "/^\[$section\]/,/^\[.*\]/ { /^$option[ \t]*=/ p; }" "$file") |
| $xtrace |
| [ -n "$line" ] |
| } |
| |
| # Add another config line for a multi-line option. |
| # It's normally called after iniset of the same option and assumes |
| # that the section already exists. |
| # |
| # Note that iniset_multiline requires all the 'lines' to be supplied |
| # in the argument list. Doing that will cause incorrect configuration |
| # if spaces are used in the config values. |
| # |
| # iniadd_literal [-sudo] config-file section option value |
| function iniadd_literal { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sudo="" |
| if [ $1 == "-sudo" ]; then |
| sudo="sudo " |
| shift |
| fi |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| local value=$4 |
| |
| if [[ -z $section || -z $option ]]; then |
| $xtrace |
| return |
| fi |
| |
| # Add it |
| $sudo sed -i -e "/^\[$section\]/ a\\ |
| $option = $value |
| " "$file" |
| |
| $xtrace |
| } |
| |
| # Remove an option from an INI file |
| # inidelete [-sudo] config-file section option |
| function inidelete { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sudo="" |
| if [ $1 == "-sudo" ]; then |
| sudo="sudo " |
| shift |
| fi |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| |
| if [[ -z $section || -z $option ]]; then |
| $xtrace |
| return |
| fi |
| |
| # Remove old values |
| $sudo sed -i -e "/^\[$section\]/,/^\[.*\]/ { /^$option[ \t]*=/ d; }" "$file" |
| |
| $xtrace |
| } |
| |
| # Set an option in an INI file |
| # iniset [-sudo] config-file section option value |
| # - if the file does not exist, it is created |
| function iniset { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sudo="" |
| local sudo_option="" |
| if [ $1 == "-sudo" ]; then |
| sudo="sudo " |
| sudo_option="-sudo " |
| shift |
| fi |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| local value=$4 |
| |
| # Escape the ampersand character (&) |
| value=$(echo $value | sed -e 's/&/\\&/g') |
| |
| if [[ -z $section || -z $option ]]; then |
| $xtrace |
| return |
| fi |
| |
| if ! $sudo grep -q "^\[$section\]" "$file" 2>/dev/null; then |
| # Add section at the end |
| echo -e "\n[$section]" | $sudo tee --append "$file" > /dev/null |
| fi |
| if ! ini_has_option $sudo_option "$file" "$section" "$option"; then |
| # Add it |
| $sudo sed -i -e "/^\[$section\]/ a\\ |
| $option = $value |
| " "$file" |
| else |
| local sep |
| sep=$(echo -ne "\x01") |
| # Replace it |
| $sudo sed -i -e '/^\['${section}'\]/,/^\[.*\]/ s'${sep}'^\('"${option}"'[ \t]*=[ \t]*\).*$'${sep}'\1'"${value}"${sep} "$file" |
| fi |
| $xtrace |
| } |
| |
| # Set a multiple line option in an INI file |
| # iniset_multiline [-sudo] config-file section option value1 value2 value3 ... |
| function iniset_multiline { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sudo="" |
| if [ $1 == "-sudo" ]; then |
| sudo="sudo " |
| shift |
| fi |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| |
| shift 3 |
| local values |
| for v in $@; do |
| # The later sed command inserts each new value in the line next to |
| # the section identifier, which causes the values to be inserted in |
| # the reverse order. Do a reverse here to keep the original order. |
| values="$v ${values}" |
| done |
| if ! $sudo grep -q "^\[$section\]" "$file"; then |
| # Add section at the end |
| echo -e "\n[$section]" | $sudo tee --append "$file" > /dev/null |
| else |
| # Remove old values |
| $sudo sed -i -e "/^\[$section\]/,/^\[.*\]/ { /^$option[ \t]*=/ d; }" "$file" |
| fi |
| # Add new ones |
| for v in $values; do |
| $sudo sed -i -e "/^\[$section\]/ a\\ |
| $option = $v |
| " "$file" |
| done |
| $xtrace |
| } |
| |
| # Uncomment an option in an INI file |
| # iniuncomment config-file section option |
| function iniuncomment { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sudo="" |
| if [ $1 == "-sudo" ]; then |
| sudo="sudo " |
| shift |
| fi |
| local file=$1 |
| local section=$2 |
| local option=$3 |
| $sudo sed -i -e "/^\[$section\]/,/^\[.*\]/ s|[^ \t]*#[ \t]*\($option[ \t]*=.*$\)|\1|" "$file" |
| $xtrace |
| } |
| |
| # Get list of sections from an INI file |
| # iniget_sections config-file |
| function iniget_sections { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local file=$1 |
| |
| echo $(sed -ne "s/^\[\(.*\)\]/\1/p" "$file") |
| $xtrace |
| } |
| |
| # Set a localrc var |
| function localrc_set { |
| local file=$1 |
| local group="local" |
| local conf="localrc" |
| local section="" |
| local option=$2 |
| local value=$3 |
| localconf_set "$file" "$group" "$conf" "$section" "$option" "$value" |
| } |
| |
| # Check if local.conf has section. |
| function localconf_has_section { |
| local file=$1 |
| local group=$2 |
| local conf=$3 |
| local section=$4 |
| local sep |
| sep=$(echo -ne "\x01") |
| local line |
| line=$(sed -ne "\\${sep}^\[\[${group}|${conf}\]\]${sep},\\${sep}\[\[.*\]\]${sep}{ |
| /\[${section}\]/p |
| }" "$file") |
| [ -n "$line" ] |
| } |
| |
| # Check if local.conf has option. |
| function localconf_has_option { |
| local file=$1 |
| local group=$2 |
| local conf=$3 |
| local section=$4 |
| local option=$5 |
| local sep |
| sep=$(echo -ne "\x01") |
| local line |
| if [[ -z "$section" ]]; then |
| line=$(sed -ne "\\${sep}^\[\[${group}|${conf}\]\]${sep},\\${sep}\[\[.*\]\]${sep}{ |
| /${option}[ \t]*=.*$/p |
| }" "$file") |
| else |
| line=$(sed -ne "\\${sep}^\[\[${group}|${conf}\]\]${sep},\\${sep}\[\[.*\]\]${sep}{ |
| /\[${section}\]/,/\[\[.*\]\]\|\[.*\]/{ |
| /${option}[ \t]*=.*$/p} |
| }" "$file") |
| fi |
| [ -n "$line" ] |
| } |
| |
| # Update option in local.conf. |
| function localconf_update_option { |
| local sudo=$1 |
| local file=$2 |
| local group=$3 |
| local conf=$4 |
| local section=$5 |
| local option=$6 |
| local value=$7 |
| local sep |
| sep=$(echo -ne "\x01") |
| if [[ -z "$section" ]]; then |
| $sudo sed -i -e "\\${sep}^\[\[${group}|${conf}\]\]${sep},\\${sep}\[\[.*\]\]${sep}{ |
| s${sep}^\(${option}[ \t]*=[ \t]*\).*\$${sep}\1${value}${sep} |
| }" "$file" |
| else |
| $sudo sed -i -e "\\${sep}^\[\[${group}|${conf}\]\]${sep},\\${sep}\[\[.*\]\]${sep}{ |
| /\[${section}\]/,/\[\[.*\]\]\|\[.*\]/s${sep}^\(${option}[ \t]*=[ \t]*\).*\$${sep}\1${value}${sep} |
| }" "$file" |
| fi |
| } |
| |
| # Add option in local.conf. |
| function localconf_add_option { |
| local sudo=$1 |
| local file=$2 |
| local group=$3 |
| local conf=$4 |
| local section=$5 |
| local option=$6 |
| local value=$7 |
| local sep |
| sep=$(echo -ne "\x01") |
| if [[ -z "$section" ]]; then |
| $sudo sed -i -e "\\${sep}^\[\[${group}|${conf}\]\]${sep} a $option=$value" "$file" |
| else |
| $sudo sed -i -e "\\${sep}^\[\[${group}|${conf}\]\]${sep},\\${sep}\[\[.*\]\]${sep}{ |
| /\[${section}\]/ a $option=$value |
| }" "$file" |
| fi |
| } |
| |
| # Add section and option in local.conf. |
| function localconf_add_section_and_option { |
| local sudo=$1 |
| local file=$2 |
| local group=$3 |
| local conf=$4 |
| local section=$5 |
| local option=$6 |
| local value=$7 |
| local sep |
| sep=$(echo -ne "\x01") |
| $sudo sed -i -e "\\${sep}^\[\[${group}|${conf}\]\]${sep} { |
| a [$section] |
| a $option=$value |
| }" "$file" |
| } |
| |
| # Set an option in a local.conf file. |
| # localconf_set [-sudo] config-file group conf-name section option value |
| # - if the file does not exist, it is created |
| function localconf_set { |
| local xtrace |
| xtrace=$(set +o | grep xtrace) |
| set +o xtrace |
| local sep |
| sep=$(echo -ne "\x01") |
| local sudo="" |
| if [ $1 == "-sudo" ]; then |
| sudo="sudo " |
| shift |
| fi |
| local file=$1 |
| local group=$2 |
| local conf=$3 |
| local section=$4 |
| local option=$5 |
| local value=$6 |
| |
| if [[ -z $group || -z $conf || -z $option || -z $value ]]; then |
| $xtrace |
| return |
| fi |
| |
| if ! grep -q "^\[\[${group}|${conf}\]\]" "$file" 2>/dev/null; then |
| # Add meta section at the end if it does not exist |
| echo -e "\n[[${group}|${conf}]]" | $sudo tee --append "$file" > /dev/null |
| # Add section at the end |
| if [[ -n "$section" ]]; then |
| echo -e "[$section]" | $sudo tee --append "$file" > /dev/null |
| fi |
| # Add option at the end |
| echo -e "$option=$value" | $sudo tee --append "$file" > /dev/null |
| elif [[ -z "$section" ]]; then |
| if ! localconf_has_option "$file" "$group" "$conf" "$section" "$option"; then |
| # Add option |
| localconf_add_option "$sudo" "$file" "$group" "$conf" "$section" "$option" "$value" |
| else |
| # Replace it |
| localconf_update_option "$sudo" "$file" "$group" "$conf" "$section" "$option" "$value" |
| fi |
| elif ! localconf_has_section "$file" "$group" "$conf" "$section"; then |
| # Add section and option in specified meta section |
| localconf_add_section_and_option "$sudo" "$file" "$group" "$conf" "$section" "$option" "$value" |
| elif ! localconf_has_option "$file" "$group" "$conf" "$section" "$option"; then |
| # Add option |
| localconf_add_option "$sudo" "$file" "$group" "$conf" "$section" "$option" "$value" |
| else |
| # Replace it |
| localconf_update_option "$sudo" "$file" "$group" "$conf" "$section" "$option" "$value" |
| fi |
| $xtrace |
| } |
| |
| # Restore xtrace |
| $INC_CONF_TRACE |
| |
| # Local variables: |
| # mode: shell-script |
| # End: |