Issue
I have this data from an API:
[{"name":"***.com","id":"***-0a5864441f49","type":"NATIVE"},{"name":"***.de","id":"***-0a5864441f49","type":"NATIVE"},{"name":"***.com","id":"***-0a5864440f67","type":"NATIVE"},{"name":"***.de","id":"***-0a5864441314","type":"NATIVE"},{"name":"***.com","id":"***-0a586444968b","type":"NATIVE"},{"name":"***.de","id":"***-0a5864441314","type":"NATIVE"},{"name":"***.de","id":"***-0a5864441f49","type":"NATIVE"},{"name":"***.de","id":"***-0a5864441f49","type":"NATIVE"},{"name":"***.de","id":"***-0a58644406ac","type":"NATIVE"},{"name":"***.de","id":"***-0a58644435f4","type":"NATIVE"}]
and I want to create a menu from it looking like this:
Choose one:
1. ***.com ***-0a5864441f49
2. ***.de ***-0a5864441f49
and so on...
And I would like to then use the input further. What is the most efficient method to do this in bash?
I'm thinking of an array but I think IFS would not like me using },{
as a delimiter, right?
I tried using IFS but that didn't work out.
Solution
You could use jq to transform the input to look something like this (see playground):
$ jq -r 'map("\(.name) \(.id)")[]' infile.json
***.com ***-0a5864441f49
***.de ***-0a5864441f49
***.com ***-0a5864440f67
***.de ***-0a5864441314
-->8--
Based on that, you could read this output into an array, and then use the select
built-in to present a menu:
readarray -t opts < <(jq -r 'map("\(.name) \(.id)")[]' infile.json)
PS3='Choose one: '
select opt in "${opts[@]}"; do
echo "Do something with $opt"
break
done
resulting in a prompt like
1) ***.com ***-0a5864441f49 6) ***.de ***-0a5864441314
2) ***.de ***-0a5864441f49 7) ***.de ***-0a5864441f49
3) ***.com ***-0a5864440f67 8) ***.de ***-0a5864441f49
4) ***.de ***-0a5864441314 9) ***.de ***-0a58644406ac
5) ***.com ***-0a586444968b 10) ***.de ***-0a58644435f4
Choose one:
Answered By - Benjamin W. Answer Checked By - Clifford M. (WPSolving Volunteer)