Skip to content

Commit

Permalink
Support profile for httpc adapter (#655)
Browse files Browse the repository at this point in the history
Support profile for httpc adapter

Co-authored-by: Yordis Prieto <[email protected]>
  • Loading branch information
tanguilp and yordis authored Apr 25, 2024
1 parent 7579d9f commit 0ca1e59
Show file tree
Hide file tree
Showing 2 changed files with 47 additions and 11 deletions.
34 changes: 23 additions & 11 deletions lib/tesla/adapter/httpc.ex
Original file line number Diff line number Diff line change
Expand Up @@ -55,33 +55,33 @@ defmodule Tesla.Adapter.Httpc do
Enum.map(env.headers, fn {k, v} -> {to_charlist(k), to_charlist(v)} end),
content_type,
env.body,
Keyword.split(opts, @http_opts)
opts
)
)
end

# fix for # see https://github.com/teamon/tesla/issues/147
defp request(:delete, url, headers, content_type, nil, {http_opts, opts}) do
request(:delete, url, headers, content_type, "", {http_opts, opts})
defp request(:delete, url, headers, content_type, nil, opts) do
request(:delete, url, headers, content_type, "", opts)
end

defp request(method, url, headers, _content_type, nil, {http_opts, opts}) do
:httpc.request(method, {url, headers}, http_opts, opts)
defp request(method, url, headers, _content_type, nil, opts) do
:httpc.request(method, {url, headers}, http_opts(opts), adapter_opts(opts), profile(opts))
end

# These methods aren't able to contain a content_type and body
defp request(method, url, headers, _content_type, _body, {http_opts, opts})
defp request(method, url, headers, _content_type, _body, opts)
when method in [:get, :options, :head, :trace] do
:httpc.request(method, {url, headers}, http_opts, opts)
:httpc.request(method, {url, headers}, http_opts(opts), adapter_opts(opts), profile(opts))
end

defp request(method, url, headers, _content_type, %Multipart{} = mp, opts) do
headers = headers ++ Multipart.headers(mp)
headers = for {key, value} <- headers, do: {to_charlist(key), to_charlist(value)}

{content_type, headers} =
case List.keytake(headers, 'content-type', 0) do
nil -> {'text/plain', headers}
case List.keytake(headers, ~c"content-type", 0) do
nil -> {~c"text/plain", headers}
{{_, ct}, headers} -> {ct, headers}
end

Expand All @@ -100,10 +100,22 @@ defmodule Tesla.Adapter.Httpc do
request(method, url, headers, content_type, body, opts)
end

defp request(method, url, headers, content_type, body, {http_opts, opts}) do
:httpc.request(method, {url, headers, content_type, body}, http_opts, opts)
defp request(method, url, headers, content_type, body, opts) do
:httpc.request(
method,
{url, headers, content_type, body},
http_opts(opts),
adapter_opts(opts),
profile(opts)
)
end

defp handle({:error, {:failed_connect, _}}), do: {:error, :econnrefused}
defp handle(response), do: response

defp http_opts(opts), do: opts |> Keyword.take(@http_opts) |> Keyword.delete(:profile)

defp adapter_opts(opts), do: opts |> Keyword.drop(@http_opts) |> Keyword.delete(:profile)

defp profile(opts), do: opts[:profile] || :default
end
24 changes: 24 additions & 0 deletions test/tesla/adapter/httpc_test/profile.ex
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
defmodule Tesla.Adapter.HttpcTest.Profile do
@profile :test_profile

use ExUnit.Case
use Tesla.AdapterCase, adapter: {Tesla.Adapter.Httpc, profile: @profile}

alias Tesla.Env

setup do
{:ok, _pid} = :inets.start(:httpc, profile: @profile)

on_exit(fn -> :inets.stop(:httpc, @profile) end)
end

test "a non-default profile is used" do
request = %Env{
method: :get,
url: "#{@http}/ip"
}

assert {:ok, %Env{} = response} = call(request)
assert response.status == 200
end
end

0 comments on commit 0ca1e59

Please sign in to comment.