Skip to content

Instantly share code, notes, and snippets.

@webevt
Last active October 27, 2017 08:01
Show Gist options
  • Save webevt/643e05171a8e0afa6f39b44aa72f6b9b to your computer and use it in GitHub Desktop.
Save webevt/643e05171a8e0afa6f39b44aa72f6b9b to your computer and use it in GitHub Desktop.
Parse YAML in BASH with support of plain arrays and arrays of hashes
#!/usr/bin/env bash
parse_yml() {
[ -n "$2" ] && local prefix="$2" || {
local prefix=$(basename "$1"); prefix=${prefix%%.*}
}
local file="$1"
local s='[[:space:]]*'
local w='[a-zA-Z0-9_]*'
local fs="$(echo @|tr @ '\034')"
sed -ne "s|^\($s\)\($w\)$s[:-]$s[\"']\(.*\)[\"']$s\$|\1$fs\2$fs\3|p" \
-e "s|^\($s\)\($w\)$s[:-]$s[\"']*\(.*\)[\"']*$s\$|\1$fs\2$fs\3|p" "$file" |
awk -F"$fs" '{
if (!step && length($1)) {
step = length($1);
}
indent = step > 0 ? length($1)/step : 0;
key = $2;
value = $3;
keys[indent] = key;
for (i in keys) {
if (i > indent) {
delete keys[i];
}
}
if (length(value) > 0) {
var = "'"$prefix"'";
is_array = 0;
for (i = 0; i <= indent; i++) {
if (length(keys[i]) == 0) {
is_array = 1;
} else {
var=(var)("_")(keys[i]);
}
}
if (is_array == 1) {
printf("%s+=(\"%s\")\n", var, value);
} else {
printf("%s=\"%s\"\n", var, value);
}
}
}'
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment