fix(ws connection): fix peer_cert_as_username error when ws connect

This commit is contained in:
zhanghongtong 2021-04-14 10:53:14 +08:00 committed by turtleDeng
parent eda783efd0
commit 446a69c814
3 changed files with 35 additions and 11 deletions

View File

@ -1113,14 +1113,14 @@ listener.tcp.external.access.1 = allow all
## Enable the option for X.509 certificate based authentication. ## Enable the option for X.509 certificate based authentication.
## EMQX will use the common name of certificate as MQTT username. ## EMQX will use the common name of certificate as MQTT username.
## The proxy-protocol protocol can get the certificate CN through tcp ## Only support Proxy Protocol V2, the CN is available in Proxy Protocol V2 additional info
## ##
## Value: cn ## Value: cn
## listener.tcp.external.peer_cert_as_username = cn ## listener.tcp.external.peer_cert_as_username = cn
## Enable the option for X.509 certificate based authentication. ## Enable the option for X.509 certificate based authentication.
## EMQX will use the common name of certificate as MQTT clientid. ## EMQX will use the common name of certificate as MQTT clientid.
## The proxy-protocol protocol can get the certificate CN through tcp ## Only support Proxy Protocol V2, the CN is available in Proxy Protocol V2 additional info
## ##
## Value: cn ## Value: cn
## listener.tcp.external.peer_cert_as_clientid = cn ## listener.tcp.external.peer_cert_as_clientid = cn
@ -1635,6 +1635,20 @@ listener.ws.external.access.1 = allow all
## Value: Duration ## Value: Duration
## listener.ws.external.proxy_protocol_timeout = 3s ## listener.ws.external.proxy_protocol_timeout = 3s
## Enable the option for X.509 certificate based authentication.
## EMQX will use the common name of certificate as MQTT username.
## Only support Proxy Protocol V2, the CN is available in Proxy Protocol V2 additional info
##
## Value: cn
## listener.ws.external.peer_cert_as_username = cn
## Enable the option for X.509 certificate based authentication.
## EMQX will use the common name of certificate as MQTT clientid.
## Only support Proxy Protocol V2, the CN is available in Proxy Protocol V2 additional info
##
## Value: cn
## listener.ws.external.peer_cert_as_clientid = cn
## The TCP backlog of external MQTT/WebSocket Listener. ## The TCP backlog of external MQTT/WebSocket Listener.
## ##
## See: listener.ws.$name.backlog ## See: listener.ws.$name.backlog

View File

@ -1647,7 +1647,11 @@ end}.
]}. ]}.
{mapping, "listener.ws.$name.peer_cert_as_username", "emqx.listeners", [ {mapping, "listener.ws.$name.peer_cert_as_username", "emqx.listeners", [
{datatype, {enum, [cn, dn, crt]}} {datatype, {enum, [cn]}}
]}.
{mapping, "listener.ws.$name.peer_cert_as_clientid", "emqx.listeners", [
{datatype, {enum, [cn]}}
]}. ]}.
{mapping, "listener.ws.$name.check_origin_enable", "emqx.listeners", [ {mapping, "listener.ws.$name.check_origin_enable", "emqx.listeners", [

View File

@ -248,15 +248,21 @@ check_origin_header(Req, Opts) ->
end. end.
websocket_init([Req, Opts]) -> websocket_init([Req, Opts]) ->
Peername = case proplists:get_bool(proxy_protocol, Opts) {Peername, Peercert} =
andalso maps:get(proxy_header, Req) of case proplists:get_bool(proxy_protocol, Opts)
#{src_address := SrcAddr, src_port := SrcPort} -> andalso maps:get(proxy_header, Req) of
{SrcAddr, SrcPort}; #{src_address := SrcAddr, src_port := SrcPort, ssl := SSL} ->
_ -> ProxyName = {SrcAddr, SrcPort},
get_peer(Req, Opts) %% Notice: Only CN is available in Proxy Protocol V2 additional info
end, ProxySSL = case maps:get(cn, SSL, undefined) of
undeined -> nossl;
CN -> [{pp2_ssl_cn, CN}]
end,
{ProxyName, ProxySSL};
_ ->
{get_peer(Req, Opts), cowboy_req:cert(Req)}
end,
Sockname = cowboy_req:sock(Req), Sockname = cowboy_req:sock(Req),
Peercert = cowboy_req:cert(Req),
WsCookie = try cowboy_req:parse_cookies(Req) WsCookie = try cowboy_req:parse_cookies(Req)
catch catch
error:badarg -> error:badarg ->