fix(http authn): fix bugs for http authn and http connector

This commit is contained in:
zhouzb 2021-07-14 18:20:46 +08:00
parent 6a8e35ce3a
commit 42c5432514
3 changed files with 26 additions and 15 deletions

View File

@ -3,7 +3,7 @@
{vsn, "0.1.0"},
{modules, []},
{registered, [emqx_authn_sup, emqx_authn_registry]},
{applications, [kernel,stdlib]},
{applications, [kernel,stdlib,emqx_resource,ehttpc,epgsql,mysql]},
{mod, {emqx_authn_app,[]}},
{env, []},
{licenses, ["Apache-2.0"]},

View File

@ -72,7 +72,7 @@ common_fields() ->
] ++ proplists:delete(base_url, emqx_connector_http:fields(config)).
validations() ->
[ {check_ssl_opts, fun emqx_connector_http:check_ssl_opts/1} ].
[ {check_ssl_opts, fun check_ssl_opts/1} ].
url(type) -> binary();
url(nullable) -> false;
@ -108,26 +108,30 @@ create(ChainID, AuthenticatorName,
#{method := Method,
url := URL,
accept := Accept,
content_type := ContentType,
headers := Headers,
form_data := FormData,
request_timeout := RequestTimeout} = Config) ->
NHeaders = maps:merge(#{<<"accept">> => atom_to_binary(Accept, utf8),
<<"content-type">> => atom_to_binary(ContentType, utf8)}, Headers),
ContentType = maps:get(content_type, Config, undefined),
DefaultHeader0 = case ContentType of
undefined -> #{};
_ -> #{<<"content-type">> => atom_to_binary(ContentType, utf8)}
end,
DefaultHeader = DefaultHeader0#{<<"accept">> => atom_to_binary(Accept, utf8)},
NHeaders = maps:to_list(maps:merge(DefaultHeader, maps:from_list(Headers))),
NFormData = preprocess_form_data(FormData),
#{path := Path,
query := Query} = URIMap = parse_url(URL),
BaseURL = generate_base_url(URIMap),
State = #{method => Method,
path => Path,
base_query => cow_qs:parse_qs(Query),
base_query => cow_qs:parse_qs(list_to_binary(Query)),
accept => Accept,
content_type => ContentType,
headers => NHeaders,
form_data => NFormData,
request_timeout => RequestTimeout},
ResourceID = <<ChainID/binary, "/", AuthenticatorName/binary>>,
case emqx_resource:create_local(ResourceID, emqx_connector_http, Config#{base_url := BaseURL}) of
case emqx_resource:create_local(ResourceID, emqx_connector_http, Config#{base_url => BaseURL}) of
{ok, _} ->
{ok, State#{resource_id => ResourceID}};
{error, already_created} ->
@ -192,6 +196,9 @@ check_form_data(FormData) ->
false
end.
check_ssl_opts(Conf) ->
emqx_connector_http:check_ssl_opts("url", Conf).
preprocess_form_data(FormData) ->
KVs = binary:split(FormData, [<<"&">>], [global]),
[list_to_tuple(binary:split(KV, [<<"=">>], [global])) || KV <- KVs].

View File

@ -32,7 +32,7 @@
, fields/1
, validations/0]).
-export([ check_ssl_opts/1 ]).
-export([ check_ssl_opts/2 ]).
-type connect_timeout() :: non_neg_integer() | infinity.
-type pool_type() :: random | hash.
@ -57,7 +57,7 @@ fields(config) ->
, {pool_type, fun pool_type/1}
, {pool_size, fun pool_size/1}
, {ssl_opts, #{type => hoconsc:ref(?MODULE, ssl_opts),
nullable => true}}
default => #{}}}
];
fields(ssl_opts) ->
@ -107,8 +107,9 @@ keyfile(type) -> string();
keyfile(nullable) -> true;
keyfile(_) -> undefined.
%% TODO: certfile is required
certfile(type) -> string();
certfile(nullable) -> false;
certfile(nullable) -> true;
certfile(_) -> undefined.
verify(type) -> boolean();
@ -178,7 +179,7 @@ on_query(InstId, {KeyOrNum, Method, Request, Timeout}, AfterQuery, #{pool_name :
end,
Result.
on_health_check(_InstId, #{server := {Host, Port}} = State) ->
on_health_check(_InstId, #{host := Host, port := Port} = State) ->
case gen_tcp:connect(Host, Port, emqx_misc:ipv6_probe([]), 3000) of
{ok, Sock} ->
gen_tcp:close(Sock),
@ -199,13 +200,16 @@ check_base_url(URL) ->
end.
check_ssl_opts(Conf) ->
URL = hocon_schema:get_value("url", Conf),
check_ssl_opts("base_url", Conf).
check_ssl_opts(URLFrom, Conf) ->
URL = hocon_schema:get_value(URLFrom, Conf),
{ok, #{scheme := Scheme}} = emqx_http_lib:uri_parse(URL),
SSLOpts = hocon_schema:get_value("ssl_opts", Conf),
case {Scheme, SSLOpts} of
{http, undefined} -> true;
case {Scheme, maps:size(SSLOpts)} of
{http, 0} -> true;
{http, _} -> false;
{https, undefined} -> false;
{https, 0} -> false;
{https, _} -> true
end.