$ ary=($(echo '{"crew":[{"name":"kirk"},{"name":"bones"},{"name":"mr spock"}]}' | jq -r '.crew[].name | @sh'))
$ declare -p ary
declare -a ary=([0]="'kirk'" [1]="'bones'" [2]="'mr" [3]="spock'")
This does not work as expected because the command substitution is unquoted, bash will perform word splitting on the output. It doesn't matter that the actual output contains quote characters. Refer to 3.5 Shell Expansions in the manual
You need to delay the array assignment until the contents of the output can be examined by the shell. This could be done with eval, but for variable assignment it's better done with declare:
$ declare -a "ary=($(echo '{"crew":[{"name":"kirk"},{"name":"bones"},{"name":"mr spock"}]}' | jq -r '.crew[].name | @sh'))"
$ declare -p ary
declare -a ary=([0]="kirk" [1]="bones" [2]="mr spock")
For readability, split that into steps:
$ jq_out=$(echo '{"crew":[{"name":"kirk"},{"name":"bones"},{"name":"mr spock"}]}' | jq -r '.crew[].name | @sh')
$ declare -a "ary=( $jq_out )"
$ declare -p ary
declare -a ary=([0]="kirk" [1]="bones" [2]="mr spock")
@shescapes the output, as per the jq manual: "The input is escaped suitable for use in a command-line for a POSIX shell. If the input is an array, the output will be a series of space-separated strings."readarrayseems to work. Thank you. However, I am still interested to know why bash seems to remove/ignore the quotes that jq is wrapping the values in.