mirror of
https://github.com/ninenines/cowboy.git
synced 2025-07-15 12:40:25 +00:00
Merge branch 'ipv6-literal' of git://github.com/yamt/cowboy
This commit is contained in:
commit
67410731e0
5 changed files with 131 additions and 40 deletions
|
@ -93,16 +93,19 @@ request(Method, URL, Headers, Body, Client=#client{
|
|||
end,
|
||||
VersionBin = atom_to_binary(Version, latin1),
|
||||
%% @todo do keepalive too, allow override...
|
||||
Headers2 = [
|
||||
{<<"host">>, FullHost},
|
||||
Headers2 = case lists:keyfind(<<"host">>, 1, Headers) of
|
||||
false -> [{<<"host">>, FullHost}|Headers];
|
||||
_ -> Headers
|
||||
end,
|
||||
Headers3 = [
|
||||
{<<"user-agent">>, <<"Cow">>}
|
||||
|Headers],
|
||||
Headers3 = case iolist_size(Body) of
|
||||
0 -> Headers2;
|
||||
Length -> [{<<"content-length">>, integer_to_list(Length)}|Headers2]
|
||||
|Headers2],
|
||||
Headers4 = case iolist_size(Body) of
|
||||
0 -> Headers3;
|
||||
Length -> [{<<"content-length">>, integer_to_list(Length)}|Headers3]
|
||||
end,
|
||||
HeadersData = [[Name, <<": ">>, Value, <<"\r\n">>]
|
||||
|| {Name, Value} <- Headers3],
|
||||
|| {Name, Value} <- Headers4],
|
||||
Data = [Method, <<" ">>, Path, <<" ">>, VersionBin, <<"\r\n">>,
|
||||
HeadersData, <<"\r\n">>, Body],
|
||||
raw_request(Data, Client2).
|
||||
|
|
|
@ -54,7 +54,7 @@
|
|||
%% Internal.
|
||||
-export([init/4]).
|
||||
-export([parse_request/3]).
|
||||
-export([parse_host/2]).
|
||||
-export([parse_host/3]).
|
||||
-export([resume/6]).
|
||||
|
||||
-type opts() :: [{compress, boolean()}
|
||||
|
@ -426,7 +426,7 @@ request(B, State=#state{transport=Transport}, M, P, Q, Version, Headers) ->
|
|||
request(B, State, M, P, Q, Version, Headers,
|
||||
<<>>, default_port(Transport:name()));
|
||||
{_, RawHost} ->
|
||||
case catch parse_host(RawHost, <<>>) of
|
||||
case catch parse_host(RawHost, false, <<>>) of
|
||||
{'EXIT', _} ->
|
||||
error_terminate(400, State);
|
||||
{Host, undefined} ->
|
||||
|
@ -443,39 +443,43 @@ default_port(ssl) -> 443;
|
|||
default_port(_) -> 80.
|
||||
|
||||
%% Another hurtful block of code. :)
|
||||
parse_host(<<>>, Acc) ->
|
||||
parse_host(<< $[, Rest/bits >>, false, <<>>) ->
|
||||
parse_host(Rest, true, << $[ >>);
|
||||
parse_host(<<>>, false, Acc) ->
|
||||
{Acc, undefined};
|
||||
parse_host(<< $:, Rest/bits >>, Acc) ->
|
||||
parse_host(<< $:, Rest/bits >>, false, Acc) ->
|
||||
{Acc, list_to_integer(binary_to_list(Rest))};
|
||||
parse_host(<< C, Rest/bits >>, Acc) ->
|
||||
parse_host(<< $], Rest/bits >>, true, Acc) ->
|
||||
parse_host(Rest, false, << Acc/binary, $] >>);
|
||||
parse_host(<< C, Rest/bits >>, E, Acc) ->
|
||||
case C of
|
||||
$A -> parse_host(Rest, << Acc/binary, $a >>);
|
||||
$B -> parse_host(Rest, << Acc/binary, $b >>);
|
||||
$C -> parse_host(Rest, << Acc/binary, $c >>);
|
||||
$D -> parse_host(Rest, << Acc/binary, $d >>);
|
||||
$E -> parse_host(Rest, << Acc/binary, $e >>);
|
||||
$F -> parse_host(Rest, << Acc/binary, $f >>);
|
||||
$G -> parse_host(Rest, << Acc/binary, $g >>);
|
||||
$H -> parse_host(Rest, << Acc/binary, $h >>);
|
||||
$I -> parse_host(Rest, << Acc/binary, $i >>);
|
||||
$J -> parse_host(Rest, << Acc/binary, $j >>);
|
||||
$K -> parse_host(Rest, << Acc/binary, $k >>);
|
||||
$L -> parse_host(Rest, << Acc/binary, $l >>);
|
||||
$M -> parse_host(Rest, << Acc/binary, $m >>);
|
||||
$N -> parse_host(Rest, << Acc/binary, $n >>);
|
||||
$O -> parse_host(Rest, << Acc/binary, $o >>);
|
||||
$P -> parse_host(Rest, << Acc/binary, $p >>);
|
||||
$Q -> parse_host(Rest, << Acc/binary, $q >>);
|
||||
$R -> parse_host(Rest, << Acc/binary, $r >>);
|
||||
$S -> parse_host(Rest, << Acc/binary, $s >>);
|
||||
$T -> parse_host(Rest, << Acc/binary, $t >>);
|
||||
$U -> parse_host(Rest, << Acc/binary, $u >>);
|
||||
$V -> parse_host(Rest, << Acc/binary, $v >>);
|
||||
$W -> parse_host(Rest, << Acc/binary, $w >>);
|
||||
$X -> parse_host(Rest, << Acc/binary, $x >>);
|
||||
$Y -> parse_host(Rest, << Acc/binary, $y >>);
|
||||
$Z -> parse_host(Rest, << Acc/binary, $z >>);
|
||||
_ -> parse_host(Rest, << Acc/binary, C >>)
|
||||
$A -> parse_host(Rest, E, << Acc/binary, $a >>);
|
||||
$B -> parse_host(Rest, E, << Acc/binary, $b >>);
|
||||
$C -> parse_host(Rest, E, << Acc/binary, $c >>);
|
||||
$D -> parse_host(Rest, E, << Acc/binary, $d >>);
|
||||
$E -> parse_host(Rest, E, << Acc/binary, $e >>);
|
||||
$F -> parse_host(Rest, E, << Acc/binary, $f >>);
|
||||
$G -> parse_host(Rest, E, << Acc/binary, $g >>);
|
||||
$H -> parse_host(Rest, E, << Acc/binary, $h >>);
|
||||
$I -> parse_host(Rest, E, << Acc/binary, $i >>);
|
||||
$J -> parse_host(Rest, E, << Acc/binary, $j >>);
|
||||
$K -> parse_host(Rest, E, << Acc/binary, $k >>);
|
||||
$L -> parse_host(Rest, E, << Acc/binary, $l >>);
|
||||
$M -> parse_host(Rest, E, << Acc/binary, $m >>);
|
||||
$N -> parse_host(Rest, E, << Acc/binary, $n >>);
|
||||
$O -> parse_host(Rest, E, << Acc/binary, $o >>);
|
||||
$P -> parse_host(Rest, E, << Acc/binary, $p >>);
|
||||
$Q -> parse_host(Rest, E, << Acc/binary, $q >>);
|
||||
$R -> parse_host(Rest, E, << Acc/binary, $r >>);
|
||||
$S -> parse_host(Rest, E, << Acc/binary, $s >>);
|
||||
$T -> parse_host(Rest, E, << Acc/binary, $t >>);
|
||||
$U -> parse_host(Rest, E, << Acc/binary, $u >>);
|
||||
$V -> parse_host(Rest, E, << Acc/binary, $v >>);
|
||||
$W -> parse_host(Rest, E, << Acc/binary, $w >>);
|
||||
$X -> parse_host(Rest, E, << Acc/binary, $x >>);
|
||||
$Y -> parse_host(Rest, E, << Acc/binary, $y >>);
|
||||
$Z -> parse_host(Rest, E, << Acc/binary, $z >>);
|
||||
_ -> parse_host(Rest, E, << Acc/binary, C >>)
|
||||
end.
|
||||
|
||||
%% End of request parsing.
|
||||
|
@ -589,3 +593,24 @@ error_terminate(Status, Req, State) ->
|
|||
terminate(#state{socket=Socket, transport=Transport}) ->
|
||||
Transport:close(Socket),
|
||||
ok.
|
||||
|
||||
%% Tests.
|
||||
|
||||
-ifdef(TEST).
|
||||
|
||||
parse_host(RawHost) ->
|
||||
parse_host(RawHost, false, <<>>).
|
||||
|
||||
parse_host_test() ->
|
||||
{<<"example.org">>, 8080} = parse_host(<<"example.org:8080">>),
|
||||
{<<"example.org">>, undefined} = parse_host(<<"example.org">>),
|
||||
{<<"192.0.2.1">>, 8080} = parse_host(<<"192.0.2.1:8080">>),
|
||||
{<<"192.0.2.1">>, undefined} = parse_host(<<"192.0.2.1">>),
|
||||
{<<"[2001:db8::1]">>, 8080} = parse_host(<<"[2001:db8::1]:8080">>),
|
||||
{<<"[2001:db8::1]">>, undefined} = parse_host(<<"[2001:db8::1]">>),
|
||||
{<<"[::ffff:192.0.2.1]">>, 8080} =
|
||||
parse_host(<<"[::ffff:192.0.2.1]:8080">>),
|
||||
{<<"[::ffff:192.0.2.1]">>, undefined} =
|
||||
parse_host(<<"[::ffff:192.0.2.1]">>).
|
||||
|
||||
-endif.
|
||||
|
|
|
@ -346,7 +346,7 @@ data_from_file(Socket, Transport, StreamID, IoDevice) ->
|
|||
request_init(FakeSocket, Peer, OnRequest, OnResponse,
|
||||
Env, Middlewares, Method, Host, Path, Version, Headers) ->
|
||||
Version2 = parse_version(Version),
|
||||
{Host2, Port} = cowboy_protocol:parse_host(Host, <<>>),
|
||||
{Host2, Port} = cowboy_protocol:parse_host(Host, false, <<>>),
|
||||
{Path2, Query} = parse_path(Path, <<>>),
|
||||
Req = cowboy_req:new(FakeSocket, ?MODULE, Peer,
|
||||
Method, Path2, Query, Version2, Headers,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue