Isso é bem fácil com um hash simples como
{:a => "a", :b => "b"}
o que se traduziria em
"a=a&b=b"
Mas o que você faz com algo mais complexo como
{:a => "a", :b => ["c", "d", "e"]}
que deve se traduzir em
"a=a&b[0]=c&b[1]=d&b[2]=e"
Ou pior ainda, (o que fazer) com algo como:
{:a => "a", :b => [{:c => "c", :d => "d"}, {:e => "e", :f => "f"}]
Obrigado pela ajuda muito apreciada com isso!
ruby
http
parameters
hashmap
Julien Genestoux
fonte
fonte
Respostas:
Atualizar: essa funcionalidade foi removida da gema.
Julien, sua resposta é boa, e eu tenho vergonhosamente a emprestado, mas ela não escapa de maneira adequada aos caracteres reservados, e há outros casos extremos em que ocorre.
A gema é ' endereçável '
fonte
query_values
mutador.Para hashes básicos e não aninhados, o Rails / ActiveSupport possui
Object#to_query
.http://api.rubyonrails.org/classes/Object.html#method-i-to_query
fonte
require 'active_support/all'
é necessárioto_query
não lida com valores nulos adequadamente.{ a: nil, b: '1'}.to_query == "a=&b=1"
, mas Rack e CGI analisama=
como uma sequência vazia, nãonil
. Não tenho certeza sobre o suporte a outros servidores, mas com os trilhos, a string de consulta correta deve sera&b=1
. Eu acho errado que o Rails não possa produzir uma string de consulta que seja corretamente analisada por si mesma ...Se você estiver usando Ruby 1.9.2 ou posterior, poderá usar
URI.encode_www_form
lo se não precisar de matrizes.Por exemplo (dos documentos Ruby em 1.9.3):
Você notará que os valores da matriz não são definidos com nomes de chaves que contêm
[]
como todos nos acostumamos nas cadeias de consulta. A especificaçãoencode_www_form
usada está de acordo com a definição deapplication/x-www-form-urlencoded
dados HTML5 .fonte
{:c => "c", :d => true}
parece ser inspecionado, então enviado como uma string.ruby -ruri -e 'puts RUBY_VERSION; puts URI.encode_www_form({:a => "a", :b => {:c => "c", :d => true}, :e => []})' # outputs 2.0.0 a=a&b=%7B%3Ac%3D%3E%22c%22%2C+%3Ad%3D%3Etrue%7D&
Addressable::URI
ActiveSupportObject#to_query
.Não há necessidade de carregar o ActiveSupport inchado ou rolar o seu próprio, você pode usar
Rack::Utils.build_query
eRack::Utils.build_nested_query
. Aqui está uma postagem de blog que dá um bom exemplo:Ele até lida com matrizes:
Ou as coisas aninhadas mais difíceis:
fonte
:b
é uma matriz de dois hashes. Você acaba:b
sendo uma matriz de um hash maior.require 'rack'
? Ele deve estar lá, considerando que todas as principais estruturas da Web Ruby são construídas sobre o Rack agora.to_query
também mescla as duas matrizes (v4.2).Roubar do Merb:
Consulte http://noobkit.com/show/ruby/gems/development/merb/hash/to_params.html
fonte
Aqui está um liner curto e agradável se você precisar apenas suportar cadeias de consulta de chave / valor ASCII simples:
fonte
fonte
Aqui está outra maneira. Para consultas simples.
fonte
Sei que essa é uma pergunta antiga, mas eu só queria postar esse código, pois não consegui encontrar uma solução simples para executar essa tarefa por mim.
Enrolado como gema aqui: https://github.com/simen/queryparams
fonte
URI.escape != CGI.escape
e para o URL que você deseja o primeiro.CGI.escape("http://localhost/search?q=banana&limit=7")
=> "http%3A%2F%2Flocalhost%2Fsearch%3Fq%3Dbanana%26limit%3D7"
URI.escape("http://localhost/search?q=banana&limit=7")
=> "http://localhost/search?q=banana&limit=7"
A melhor abordagem é usar Hash.to_params, que funciona bem com matrizes.
fonte
require 'active_support/all'
é necessárioSe você estiver no contexto de uma solicitação do Faraday, também poderá passar o hash params como o segundo argumento e o faraday se encarrega de fazer parte do URL param apropriado:
fonte
Eu gosto de usar esta gema:
https://rubygems.org/gems/php_http_build_query
Uso da amostra:
fonte
fonte