Thursday, October 6, 2022

[SOLVED] Bash/sh: Reading and saving the number of root keys of a yaml file

Issue

I am using the script from here in order to read a yaml file that contains some local paths of my system. The script does what is intended to do but I would also like to keep count of how many paths are there.

YAML example:

path1: ../
path2: /bin
path3: ../src

.sh example:

#!/bin/bash

paths=0;

parse_yaml() {
   local prefix=$2
   local s='[[:space:]]*' w='[a-zA-Z0-9_]*' fs=$(echo @|tr @ '\034')
   sed -ne "s|^\($s\):|\1|" \
        -e "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"  $1 |
   awk -F$fs '{
      indent = length($1)/2;
      vname[indent] = $2;
      echo $indent
      for (i in vname) {if (i > indent) {delete vname[i]}}
      if (length($3) > 0) {
         vn=""; for (i=0; i<indent; i++) {
         vn=(vn)(vname[i])("_")
     }
         printf("%s%s%s=\"%s\"\n", "'$prefix'",vn, $2, $3);
     printf(vn);
      }
   }'
}

eval $(parse_yaml paths.yaml)



echo $path1
echo $path2
echo $path3

OUTPUT:

../
/bin
../src

I would like to have in paths variable declared at top saved the number of keys(in other words paths) declared in that yaml file. I tried to increment it inside the for loops but it did not work.


Solution

If you cannot use a proper YAML parser, one option would be to read the paths into an array:

IFS=$'\n' read -r -d '' -a paths < <(awk '{print $2}' sample.yaml  && printf '\0')
printf "Number of paths: %s\n" "${#paths[@]}" 

To print each path:

printf "%s\n" "${paths[@]}"


Answered By - j_b
Answer Checked By - Clifford M. (WPSolving Volunteer)