diff --git a/lib/ulib/multiconf b/lib/ulib/multiconf index 0fda462..2624a36 100644 --- a/lib/ulib/multiconf +++ b/lib/ulib/multiconf @@ -9,7 +9,7 @@ function conf_local() { # par les fonctions conf_* # cela permet d'utiliser ces fonctions à l'intérieur d'autres fonctions sans # polluer l'espace de nom - echo "local -a __CONF_ARRAY_VARS" + echo "local -a __CONF_ARRAY_VARS __CONF_PATH_VARS" } function conf_auto() { @@ -50,27 +50,41 @@ function conf_init() { # par défaut, les variables sont en mode scalaire: la définition d'une # variable écrase la valeur précédente. Avec l'option -a les variables sont # en mode tableau: les nouvelles valeurs sont rajoutées à la fin du tableau. + # Avec l'option -p les variables sont en mode chemin: les nouvelles valeurs + # sont ajoutées si elles n'existe pas déjà avec le séparateur ':' # dans l'exemple suivant: - # conf_init NAME VALUE -a SRCDIRS DESTDIRS - # NAME et VALUE sont scalaires alors que SRCDIRS et DESTDIRS sont tableaux - # Les variables scalaires sont initialisées à la valeur vide ou à la valeur - # spécifiée e.g.: - # conf_init VAR=value + # conf_init NAME VALUE -a SRCDIRS DESTDIRS -p LIBPATH + # NAME et VALUE sont scalaires, SRCDIRS et DESTDIRS sont des tableaux et + # LIBPATH est de type chemin + # Les variables scalaires et chemin sont initialisées à la valeur vide ou à + # la valeur spécifiée e.g.: + # conf_init VAR=value MYPATH=a:b:c # Les variables tableaux sont toujours initialisées à la valeur vide # L'option -s permet de revenir au mode scalaire __CONF_ARRAY_VARS=() - local __var __array + __CONF_PATH_VARS=() + local __var __type=scalar while [ $# -gt 0 ]; do case "$1" in - -a|--array) __array=1;; - -s|--scalar) __array=;; + -a|--array) __type=array;; + -p|--path) __type=path;; + -s|--scalar) __type=scalar;; *) - if [ -n "$__array" ]; then + case "$__type" in + array) eval "${1%%=*}=()" array_addu __CONF_ARRAY_VARS "${1%%=*}" - else + array_del __CONF_PATH_VARS "${1%%=*}" + ;; + path) setv "$1" - fi + array_addu __CONF_PATH_VARS "${1%%=*}" + array_del __CONF_ARRAY_VARS "${1%%=*}" + ;; + scalar) + setv "$1" + ;; + esac ;; esac shift @@ -118,26 +132,55 @@ function conf_load_files() { # sourcer les fichiers spécifiés en faisant ce qui est nécessaire pour que # les variables de __CONF_ARRAY_VARS soient correctement traitées. local -a __conf_backups __conf_values - local __conf_file __conf_name __conf_i __conf_backup + local __conf_file __conf_name __conf_i __conf_backup __conf_bn __conf_bv for __conf_file in "$@"; do # faire une copie de sauvegarde puis supprimer les variables tableaux __conf_backups=() - for __conf_name in "${__CONF_ARRAY_VARS[@]}"; do - __conf_backups=("${__conf_backups[@]}" "$(declare -p "$__conf_name")") + for __conf_name in "${__CONF_ARRAY_VARS[@]}" "${__CONF_PATH_VARS[@]}"; do + __conf_backup="$(declare -p "$__conf_name" 2>/dev/null)" + if [ -z "$__conf_backup" ]; then + __conf_backup="$__conf_name=" + else + # faire une correction de l'expression parce que la commande + # affichée par declare -p est différente entre bash 4.3 et bash + # 4.4 pour les tableaux. pour le tableau array=(a b) on aura: + # - bash 4.3 affiche declare -a array='([0]="a" [1]="b")' + # - bash 4.4 affiche declare -a array=([0]="a" [1]="b") + __conf_backup="${__conf_backup#declare }" + __conf_bn="${__conf_backup%% *}" + __conf_bv="${__conf_backup#* }" + if [[ "$__conf_bn" == -*a* ]]; then + __conf_bn="${__conf_bv%%=*}" + __conf_bv="${__conf_bv#*=}" + if [ "${__conf_bv:0:2}" == "'(" -a "${__conf_bv: -2:2}" == ")'" ]; then + __conf_backup="$__conf_bn=${__conf_bv:1: -1}" + else + __conf_backup="$__conf_bn=$__conf_bv" + fi + else + __conf_backup="$__conf_bv" + fi + fi + __conf_backups=("${__conf_backups[@]}" "$__conf_backup") unset "$__conf_name" done # charger le fichier source "$__conf_file" # puis restaurer les variables ou les fusionner avec une éventuelle nouvelle valeur __conf_i=0 - for __conf_name in "${__CONF_ARRAY_VARS[@]}"; do + for __conf_name in "${__CONF_ARRAY_VARS[@]}" "${__CONF_PATH_VARS[@]}"; do __conf_backup="${__conf_backups[$__conf_i]}" - __conf_backup="${__conf_backup#declare * }" if [ -n "$(declare -p "$__conf_name" 2>/dev/null)" ]; then # la variable a été redéfinie, la fusionner avec la précédente valeur - array_copy __conf_values "$__conf_name" - eval "$__conf_backup" - array_extend "$__conf_name" __conf_values + if array_contains __CONF_ARRAY_VARS "$__conf_name"; then + array_copy __conf_values "$__conf_name" + eval "$__conf_backup" + array_extend "$__conf_name" __conf_values + elif array_contains __CONF_PATH_VARS "$__conf_name"; then + __conf_values="${!__conf_name}" + eval "$__conf_backup" + uaddpath "$__conf_values" "$__conf_name" + fi else # la variable n'a pas été redéfinie, restaurer la précédente valeur eval "$__conf_backup"