[英]Elixir httpc error on production
I want to use :httpc
as my HTTP client. 我想使用:httpc
作为我的HTTP客户端。
I use edeliver for my release management and such. 我将edeliver用于发布管理等。 I have :inets
and :httpc
in my .deliver/config.exs
like: 我的.deliver/config.exs
有:inets
和:httpc
:
set applications: [
:runtime_tools,
:inets,
:httpc
]
I also added :inets
to :extra_applications
in mix.exs
. 我还补充:inets
到:extra_applications
在mix.exs
。
Here is how I use :httpc
: 这是我的使用方式:httpc
:
headers =
if apikey,
do: [{'Content-Type', 'application/json'}, {'apikey', to_charlist(apikey)}],
else: [{'Content-Type', 'application/json'}]
http_options = [timeout: @timeout, connect_timeout: @timeout]
options = []
request = {
to_charlist(url),
headers,
'application/json',
to_charlist(encoded_obj)
}
:post
|> :httpc.request(request, http_options, options)
|> handle_response()
I get a lot of errors like: 我收到很多错误,例如:
=SUPERVISOR REPORT==== 6-Mar-2018::15:44:11 ===
Supervisor: {local,httpc_handler_sup}
Context: child_terminated
Reason: {function_clause,
[{http_transport,close,
[undefined,#Port<0.21557>],
[{file,"http_transport.erl"},{line,346}]},
{gen_server,try_terminate,3,
[{file,"gen_server.erl"},{line,648}]},
{gen_server,terminate,10,
[{file,"gen_server.erl"},{line,833}]},
{proc_lib,init_p_do_apply,3,
[{file,"proc_lib.erl"},{line,247}]}]}
Offender: [{pid,<0.2596.1>},
{id,undefined},
{mfargs,{httpc_handler,start_link,undefined}},
{restart_type,temporary},
{shutdown,4000},
{child_type,worker}]
and also 并且
15:44:11.743 [error] GenServer #PID<0.2595.1> terminating
** (FunctionClauseError) no function clause matching in :http_transport.close/2
(inets) http_transport.erl:346: :http_transport.close(:undefined, #Port<0.21559>)
(stdlib) gen_server.erl:648: :gen_server.try_terminate/3
(stdlib) gen_server.erl:833: :gen_server.terminate/10
(stdlib) proc_lib.erl:247: :proc_lib.init_p_do_apply/3
Last message: {:init_error, :error_sending, {#Reference<0.18155839.2531262466.203553>, {:error, :einval}}}
which are the same error reported differently. 相同错误报告的方式有所不同。
This line says something that I don't get too: 这行说的话我也不太明白:
15:44:11.741 [error] Bad value on output port 'tcp_inet'
I don't actually get why this happens. 我真的不明白为什么会这样。
I was using HTTPotion
and that did not have this problem (had others though). 我正在使用HTTPotion
,但是没有这个问题(尽管有其他问题)。
The thing is this works on my dev machine. 问题是这可以在我的开发机器上工作。 It also works on a production-like VM that is on my machine too. 它也可以在我的机器上的类似生产的VM上运行。 But it throws this error when it goes on real production server. 但是当它在实际生产服务器上运行时会引发此错误。
I'm so confused! 我很混乱!
In erlang, there is a Request parameter variable for the httpc:request()
function: 在erlang中, httpc:request()
函数有一个Request参数变量:
request(Method, Request, HTTPOptions, Options) ->
The type of the Request parameter variable is specified as: Request参数变量的类型指定为:
Request = request()
request() = {url(), headers()}
where url() = string()
and headers() = [header()]
, ie a list, so the shape of the Request argument needs to be: 其中url() = string()
和headers() = [header()]
,即一个列表,因此Request参数的形状需要为:
{string, []}
But, you are doing this: 但是,您正在这样做:
request = {
to_charlist(url),
headers,
'application/json',
to_charlist(encoded_obj)
}
which looks like it has a shape of: 看起来像是:
{string, [], string, string}
I have no idea why you are duplicating the Content-Type of 'application/json' outside the headers list, and it's not clear to me what to_charlist(encoded_obj)
is supposed to be. 我不知道为什么要在标头列表之外复制“ application / json”的Content-Type,而且我不清楚to_charlist(encoded_obj)
应该是什么。 I would try: 我会尝试:
request = {
to_charlist(url),
headers
}
If to_charlist(encoded_obj)
needs to be in an http header, then add an appropriate key/value pair to your headers list. 如果to_charlist(encoded_obj)
必须位于http标头中,则将适当的键/值对添加到标头列表中。 Potential http headers here . 可能的http标头在这里 。 Maybe you need: 也许您需要:
headers =
if api,
do: [{'Content-Type', 'application/json'},
{'apikey', to_charlist(apikey)},
{'Authorization, to_charlist(encoded_obj)} ],
else: [{'Content-Type', 'application/json'},
{'Authorization, to_charlist(encoded_obj)} ]
which could probably be better written as: 最好写成:
base_headers = [
{'Content-Type', 'application/json'},
{'Authorization', to_charlist(encoded_obj)}
]
request_headers =
if apikey,
do: [ {'apikey', to_charlist(apikey)} | base_headers ],
else: base_headers
The thing is this works on my dev machine. 问题是这可以在我的开发机器上工作。 It also works on a production-like VM that is on my machine too. 它也可以在我的机器上的类似生产的VM上运行。 But it throws this error when it goes on real production server. 但是当它在实际生产服务器上运行时会引发此错误。
Well, then see here: 好吧,然后看这里:
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.