Matriz associativa de querystring no bash?
-
21-12-2019 - |
Pergunta
Como obtenho um array associativo de uma string de consulta no Bash?- Tentar:
#!/usr/bin/env bash
# Querystring (implementation stolen from http://stackoverflow.com/q/3919755)
function populate_querystring_array ()
{
param="$1"
query_dict="$2"
#for i in "${array[@]}"; do IFS="=" ; set -- $i; query_dict[$1]=$2; done
for ((i=0; i<${#param[@]}; i+=2))
do
query_dict[${param[i]}]=${param[i+1]}
done
}
q0='email=foo@bar.com&password=dfsa54'
declare -A querydict
populate_querystring_array "$q0" "$querydict"
printf "$querydict[email]"
Solução
Abaixo deve funcionar:
#!/bin/bash
function qrystring() {
qry=$1
while read key value; do
arr+=(["$key"]="$value")
done < <(awk -F'&' '{for(i=1;i<=NF;i++) {print $i}}' <<< $qry | awk -F'=' '{print $1" "$2}')
}
q='email=foo@bar.com&password=dfsa54'
declare -A arr
qrystring "$q"
for k in ${!arr[@]}; do
echo "$k -> ${arr[$k]}"
done
Explicação:
Estou usando uma combinação de comandos awk para dividir a string em registros individuais primeiro e depois dividir no sinal = para o par kv.
Estou usando a substituição de processo aqui, caso contrário estaria preenchendo uma cópia do array.
EDITAR:
Usando uma variável global para abrigar o array.
Outras dicas
#!/usr/bin/env bash
q0='email=foo@bar.com&password=dfsa54'
declare -A querydict
while IFS== read key value
do
querydict["$key"]="$value"
done < <(echo "$q0" | sed 's/&/\n/g' )
printf "${querydict[email]}\n"
No acima, 's/&/\n/g'
é um sed
comando que substitui cada ocorrência de &
com uma nova linha.Aplicamos isso a q0
para que cada atribuição de parâmetro esteja em uma linha separada.As atribuições de parâmetros são então lidas no while
laço.Para ler cada tarefa, IFS== read key value
é usado. IFS==
diz read
para tratar o sinal de igual como um separador de palavras.Assim, cada tarefa é dividida em duas palavras:a primeira é a chave e a segunda é o valor.Estes são então atribuídos à matriz associativa querydict
com a declaração querydict["$key"]="$value"
.
Colocando isso em uma função
bash
difere da maioria das linguagens de programação modernas porque suas facilidades para passar dados complexos para dentro e fora de funções são extremamente limitadas.No método mostrado abaixo, a matriz associativa, querydict
, é uma variável global:
#!/usr/bin/env bash
declare -A querydict
populate_querystring_array () {
query="$1"
while IFS== read arg value
do
querydict["$arg"]="$value"
done < <(echo "$query" | sed 's/&/\n/g' )
}
q0='email=foo@bar.com&password=dfsa54'
populate_querystring_array "$q0"
printf "${querydict[email]}\n"
Pegando a resposta de @ John1024 eu a uso em uma função que retorna o array associativo por valor, simplesmente imprimindo o conteúdo usando a sintaxe do array:
function parseQuery {
local querystring="$*"
echo -n "("
echo "${querystring}" | sed 's/&/\n/g' | while IFS== read arg value
do
echo -n "[${arg}]='${value}' "
done
echo ")"
}
declare -A querydict=$(parseQuery "${QUERY_STRING}" )