| ... | ... |
@@ -119,6 +119,33 @@ function ini_has_option {
|
| 119 | 119 |
[ -n "$line" ] |
| 120 | 120 |
} |
| 121 | 121 |
|
| 122 |
+# Add another config line for a multi-line option. |
|
| 123 |
+# It's normally called after iniset of the same option and assumes |
|
| 124 |
+# that the section already exists. |
|
| 125 |
+# |
|
| 126 |
+# Note that iniset_multiline requires all the 'lines' to be supplied |
|
| 127 |
+# in the argument list. Doing that will cause incorrect configuration |
|
| 128 |
+# if spaces are used in the config values. |
|
| 129 |
+# |
|
| 130 |
+# iniadd_literal config-file section option value |
|
| 131 |
+function iniadd_literal {
|
|
| 132 |
+ local xtrace=$(set +o | grep xtrace) |
|
| 133 |
+ set +o xtrace |
|
| 134 |
+ local file=$1 |
|
| 135 |
+ local section=$2 |
|
| 136 |
+ local option=$3 |
|
| 137 |
+ local value=$4 |
|
| 138 |
+ |
|
| 139 |
+ [[ -z $section || -z $option ]] && return |
|
| 140 |
+ |
|
| 141 |
+ # Add it |
|
| 142 |
+ sed -i -e "/^\[$section\]/ a\\ |
|
| 143 |
+$option = $value |
|
| 144 |
+" "$file" |
|
| 145 |
+ |
|
| 146 |
+ $xtrace |
|
| 147 |
+} |
|
| 148 |
+ |
|
| 122 | 149 |
# Set an option in an INI file |
| 123 | 150 |
# iniset config-file section option value |
| 124 | 151 |
function iniset {
|
| ... | ... |
@@ -86,7 +86,11 @@ function merge_config_file {
|
| 86 | 86 |
# having to do nasty quoting games |
| 87 | 87 |
get_meta_section $file $matchgroup $configfile | \ |
| 88 | 88 |
$CONFIG_AWK_CMD -v configfile=$configfile ' |
| 89 |
- BEGIN { section = "" }
|
|
| 89 |
+ BEGIN {
|
|
| 90 |
+ section = "" |
|
| 91 |
+ last_section = "" |
|
| 92 |
+ section_count = 0 |
|
| 93 |
+ } |
|
| 90 | 94 |
/^\[.+\]/ {
|
| 91 | 95 |
gsub("[][]", "", $1);
|
| 92 | 96 |
section=$1 |
| ... | ... |
@@ -106,10 +110,48 @@ function merge_config_file {
|
| 106 | 106 |
# need to strip leading & trailing whitespace from value |
| 107 | 107 |
sub(/^[ \t]*/, "", value) |
| 108 | 108 |
sub(/[ \t]*$/, "", value) |
| 109 |
- print "iniset " configfile " " section " " attr " \x27" value "\x27" |
|
| 109 |
+ |
|
| 110 |
+ # cfg_attr_count: number of config lines per [section, attr] |
|
| 111 |
+ # cfg_attr: three dimensional array to keep all the config lines per [section, attr] |
|
| 112 |
+ # cfg_section: keep the section names in the same order as they appear in local.conf |
|
| 113 |
+ # cfg_sec_attr_name: keep the attr names in the same order as they appear in local.conf |
|
| 114 |
+ if (! (section, attr) in cfg_attr_count) {
|
|
| 115 |
+ if (section != last_section) {
|
|
| 116 |
+ cfg_section[section_count++] = section |
|
| 117 |
+ last_section = section |
|
| 118 |
+ } |
|
| 119 |
+ attr_count = cfg_sec_attr_count[section_count - 1]++ |
|
| 120 |
+ cfg_sec_attr_name[section_count - 1, attr_count] = attr |
|
| 121 |
+ |
|
| 122 |
+ cfg_attr[section, attr, 0] = value |
|
| 123 |
+ cfg_attr_count[section, attr] = 1 |
|
| 124 |
+ } else {
|
|
| 125 |
+ lno = cfg_attr_count[section, attr]++ |
|
| 126 |
+ cfg_attr[section, attr, lno] = value |
|
| 127 |
+ } |
|
| 128 |
+ } |
|
| 129 |
+ END {
|
|
| 130 |
+ # Process each section in order |
|
| 131 |
+ for (sno = 0; sno < section_count; sno++) {
|
|
| 132 |
+ section = cfg_section[sno] |
|
| 133 |
+ # The ini routines simply append a config item immediately |
|
| 134 |
+ # after the section header. To keep the same order as defined |
|
| 135 |
+ # in local.conf, invoke the ini routines in the reverse order |
|
| 136 |
+ for (attr_no = cfg_sec_attr_count[sno] - 1; attr_no >=0; attr_no--) {
|
|
| 137 |
+ attr = cfg_sec_attr_name[sno, attr_no] |
|
| 138 |
+ if (cfg_attr_count[section, attr] == 1) |
|
| 139 |
+ print "iniset " configfile " " section " " attr " \x27" cfg_attr[section, attr, 0] "\x27" |
|
| 140 |
+ else {
|
|
| 141 |
+ # For multiline, invoke the ini routines in the reverse order |
|
| 142 |
+ count = cfg_attr_count[section, attr] |
|
| 143 |
+ print "iniset " configfile " " section " " attr " \x27" cfg_attr[section, attr, count - 1] "\x27" |
|
| 144 |
+ for (l = count -2; l >= 0; l--) |
|
| 145 |
+ print "iniadd_literal " configfile " " section " " attr " \x27" cfg_attr[section, attr, l] "\x27" |
|
| 146 |
+ } |
|
| 147 |
+ } |
|
| 148 |
+ } |
|
| 110 | 149 |
} |
| 111 | 150 |
' | while read a; do eval "$a"; done |
| 112 |
- |
|
| 113 | 151 |
} |
| 114 | 152 |
|
| 115 | 153 |
|
| ... | ... |
@@ -108,6 +108,27 @@ attr = strip_trailing_space |
| 108 | 108 |
[[test7|test-colon.conf]] |
| 109 | 109 |
[DEFAULT] |
| 110 | 110 |
servers=10.11.12.13:80 |
| 111 |
+ |
|
| 112 |
+[[test-multi-sections|test-multi-sections.conf]] |
|
| 113 |
+[sec-1] |
|
| 114 |
+cfg_item1 = abcd |
|
| 115 |
+cfg_item2 = efgh |
|
| 116 |
+ |
|
| 117 |
+[sec-2] |
|
| 118 |
+cfg_item1 = abcd |
|
| 119 |
+cfg_item3 = /1/2/3/4:5 |
|
| 120 |
+cfg_item4 = end |
|
| 121 |
+ |
|
| 122 |
+[sec-3] |
|
| 123 |
+cfg_item5 = 5555 |
|
| 124 |
+cfg_item6 = 6666 |
|
| 125 |
+cfg_item5 = 5555another |
|
| 126 |
+ |
|
| 127 |
+[[test-multiline|test-multiline.conf]] |
|
| 128 |
+[multi] |
|
| 129 |
+cfg_item1 = "ab":"cd", "ef": "gh" |
|
| 130 |
+cfg_item1 = abcd |
|
| 131 |
+cfg_item2 = efgh |
|
| 111 | 132 |
EOF |
| 112 | 133 |
|
| 113 | 134 |
echo -n "get_meta_section_files: test0 doesn't exist: " |
| ... | ... |
@@ -189,8 +210,39 @@ VAL=$(cat test2a.conf) |
| 189 | 189 |
# iniset adds a blank line if it creates the file... |
| 190 | 190 |
EXPECT_VAL=" |
| 191 | 191 |
[ddd] |
| 192 |
-additional = true |
|
| 193 |
-type = new" |
|
| 192 |
+type = new |
|
| 193 |
+additional = true" |
|
| 194 |
+check_result "$VAL" "$EXPECT_VAL" |
|
| 195 |
+ |
|
| 196 |
+echo -n "merge_config_file test-multi-sections: " |
|
| 197 |
+rm -f test-multi-sections.conf |
|
| 198 |
+merge_config_file test.conf test-multi-sections test-multi-sections.conf |
|
| 199 |
+VAL=$(cat test-multi-sections.conf) |
|
| 200 |
+EXPECT_VAL=' |
|
| 201 |
+[sec-1] |
|
| 202 |
+cfg_item1 = abcd |
|
| 203 |
+cfg_item2 = efgh |
|
| 204 |
+ |
|
| 205 |
+[sec-2] |
|
| 206 |
+cfg_item1 = abcd |
|
| 207 |
+cfg_item3 = /1/2/3/4:5 |
|
| 208 |
+cfg_item4 = end |
|
| 209 |
+ |
|
| 210 |
+[sec-3] |
|
| 211 |
+cfg_item5 = 5555 |
|
| 212 |
+cfg_item5 = 5555another |
|
| 213 |
+cfg_item6 = 6666' |
|
| 214 |
+check_result "$VAL" "$EXPECT_VAL" |
|
| 215 |
+ |
|
| 216 |
+echo -n "merge_config_file test-multiline: " |
|
| 217 |
+rm -f test-multiline.conf |
|
| 218 |
+merge_config_file test.conf test-multiline test-multiline.conf |
|
| 219 |
+VAL=$(cat test-multiline.conf) |
|
| 220 |
+EXPECT_VAL=' |
|
| 221 |
+[multi] |
|
| 222 |
+cfg_item1 = "ab":"cd", "ef": "gh" |
|
| 223 |
+cfg_item1 = abcd |
|
| 224 |
+cfg_item2 = efgh' |
|
| 194 | 225 |
check_result "$VAL" "$EXPECT_VAL" |
| 195 | 226 |
|
| 196 | 227 |
echo -n "merge_config_group test2: " |
| ... | ... |
@@ -200,8 +252,8 @@ VAL=$(cat test2a.conf) |
| 200 | 200 |
# iniset adds a blank line if it creates the file... |
| 201 | 201 |
EXPECT_VAL=" |
| 202 | 202 |
[ddd] |
| 203 |
-additional = true |
|
| 204 |
-type = new" |
|
| 203 |
+type = new |
|
| 204 |
+additional = true" |
|
| 205 | 205 |
check_result "$VAL" "$EXPECT_VAL" |
| 206 | 206 |
|
| 207 | 207 |
echo -n "merge_config_group test2 no conf file: " |
| ... | ... |
@@ -281,4 +333,5 @@ servers = 10.11.12.13:80" |
| 281 | 281 |
check_result "$VAL" "$EXPECT_VAL" |
| 282 | 282 |
|
| 283 | 283 |
rm -f test.conf test1c.conf test2a.conf test-quote.conf test-space.conf test-equals.conf test-strip.conf test-colon.conf |
| 284 |
+rm -f test-multiline.conf test-multi-sections.conf |
|
| 284 | 285 |
rm -rf test-etc |