Skip to content

Commit

Permalink
Req.update: Do not duplicate headers, closes #165
Browse files Browse the repository at this point in the history
  • Loading branch information
wojtekmach committed Aug 19, 2023
1 parent 7e451e2 commit 939a50c
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 21 deletions.
39 changes: 20 additions & 19 deletions lib/req.ex
Original file line number Diff line number Diff line change
Expand Up @@ -321,6 +321,12 @@ defmodule Req do
iex> req.headers
[{"point-x", "1"}, {"point-y", "2"}]
The same header names are overwritten however:
iex> req = Req.new(headers: [authorization: "bearer foo"])
iex> req = Req.update(req, headers: [authorization: "bearer bar"])
iex> req.headers
[{"authorization", "bearer bar"}]
"""
@spec update(Req.Request.t(), options :: keyword()) :: Req.Request.t()
def update(%Req.Request{} = request, options) when is_list(options) do
Expand All @@ -336,28 +342,23 @@ defmodule Req do

Req.Request.validate_options(options, registered)

request_options =
if request_options[:headers] do
update_in(request_options[:headers], &encode_headers/1)
else
request_options
end

request =
Map.merge(request, Map.new(request_options), fn
:url, _, url ->
URI.parse(url)

:headers, old, new ->
old ++ new

_, _, value ->
value
Enum.reduce(request_options, request, fn
{:url, url}, acc ->
put_in(acc.url, URI.parse(url))

{:headers, new_headers}, acc ->
update_in(acc.headers, fn old_headers ->
new_headers = encode_headers(new_headers)
new_header_names = Enum.map(new_headers, &elem(&1, 0))
Enum.reject(old_headers, &(elem(&1, 0) in new_header_names)) ++ new_headers
end)

{name, value}, acc ->
%{acc | name => value}
end)

request = update_in(request.options, &Map.merge(&1, Map.new(options)))

request
update_in(request.options, &Map.merge(&1, Map.new(options)))
end

@doc """
Expand Down
4 changes: 2 additions & 2 deletions test/req_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -40,10 +40,10 @@ defmodule ReqTest do
assert_receive {:headers, headers}
assert headers == [{"x-a", "1, 2"}]

req = Req.new(headers: [x_a: 1])
req = Req.new(headers: [x_a: 1, x_b: 1])
Req.get!(req, url: c.url, headers: [x_a: 2])
assert_receive {:headers, headers}
assert headers == [{"x-a", "1, 2"}]
assert headers == [{"x-a", "2"}, {"x-b", "1"}]
end

test "redact" do
Expand Down

0 comments on commit 939a50c

Please sign in to comment.