Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix invalid query string for array params #1908

Merged
merged 3 commits into from
Aug 12, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 20 additions & 0 deletions spec/lucky/base_http_client_spec.cr
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,23 @@ require "../spec_helper"
class HelloWorldAction < TestAction
accepted_formats [:plain_text]

param codes : Array(String)?

post "/hello" do
plain_text "world"
end
end

class ArrayParamAction < TestAction
accepted_formats [:plain_text]

param codes : Array(String)

post "/array_param" do
plain_text codes.join("--")
end
end

class MyClient < Lucky::BaseHTTPClient
app TestServer.new
end
Expand Down Expand Up @@ -46,6 +58,14 @@ describe Lucky::BaseHTTPClient do
request = TestServer.last_request
request.body.to_s.should eq({foo: "bar"}.to_json)
end

it "works with array query params" do
response = MyClient.new.exec ArrayParamAction.with(codes: ["ab", "xy"])
response.body.should eq "ab--xy"

request = TestServer.last_request
request.query.should eq("codes%5B%5D=ab&codes%5B%5D=xy")
end
end

describe "with a Lucky::RouteHelper" do
Expand Down
28 changes: 17 additions & 11 deletions src/lucky/routable.cr
Original file line number Diff line number Diff line change
Expand Up @@ -298,19 +298,25 @@ module Lucky::Routable
{{ param.gsub(/^\?:/, "").id }},
{% end %}
)
query_params = {} of String => String
{% for param in PARAM_DECLARATIONS %}
# add query param if given and not nil
query_params["{{ param.var }}"] = {{ param.var }}.to_s unless {{ param.var }}.nil?
{% end %}

query_params = URI::Params.build do |builder|
{% for param in PARAM_DECLARATIONS %}
_param = {{ param.var }}

# add query param if given and not nil
unless _param.nil?
if _param.is_a?(Array)
builder.add("{{ param.var }}[]", _param.map(&.to_s))
else
builder.add("{{ param.var }}", _param.to_s)
end
end
{% end %}
end

unless query_params.empty?
io << '?'
{% if compare_versions(Crystal::VERSION, "1.10.0") < 0 %}
{% @type.warning("[Deprecated] Please update your Crystal version #{Crystal::VERSION}. Using Lucky with a version below 1.10.0 is deprecated.") %}
io << HTTP::Params.encode(query_params)
{% else %}
HTTP::Params.encode(io, query_params)
{% end %}
io << query_params
end

anchor.try do |value|
Expand Down
Loading