Packages
plug
0.5.2
1.20.3
1.20.2
1.20.1
retired
1.20.0
retired
1.19.5
1.19.4
1.19.3
1.19.2
1.19.1
1.19.0
1.18.5
1.18.4
1.18.3
1.18.2
1.18.1
1.18.0
1.17.4
1.17.3
1.17.2
1.17.1
1.17.0
1.16.6
1.16.5
1.16.4
1.16.3
1.16.2
1.16.1
1.16.0
1.15.6
1.15.5
1.15.4
1.15.3
1.15.2
1.15.1
1.15.0
1.14.2
1.14.1
1.14.0
1.13.6
1.13.5
1.13.4
1.13.3
1.13.2
1.13.1
retired
1.13.0
retired
1.12.1
1.12.0
1.11.1
1.11.0
1.10.4
1.10.3
1.10.2
1.10.1
1.10.0
1.9.0
1.8.3
1.8.2
1.8.1
1.8.0
1.7.2
1.7.1
1.7.0
1.6.4
1.6.3
1.6.2
1.6.1
1.6.0
1.5.1
1.5.0
1.5.0-rc.2
1.5.0-rc.1
1.5.0-rc.0
1.4.5
1.4.4
1.4.3
1.4.2
1.4.1
1.4.0
1.4.0-rc.0
1.3.6
1.3.5
1.3.4
1.3.3
1.3.2
1.3.1
1.3.0
1.2.6
1.2.5
1.2.4
1.2.3
1.2.2
1.2.1
1.2.0
1.2.0-rc.0
1.1.9
1.1.8
1.1.7
1.1.6
1.1.5
1.1.4
1.1.3
1.1.2
1.1.1
1.1.0
1.0.6
1.0.5
1.0.4
1.0.3
1.0.2
1.0.1
1.0.0
0.14.0
0.13.1
0.13.0
0.12.2
0.12.1
0.12.0
0.11.3
0.11.2
0.11.1
0.11.0
0.10.0
0.9.0
0.8.4
0.8.3
0.8.2
0.8.1
0.8.0
0.7.0
0.6.0
0.5.3
0.5.2
0.5.1
0.5.0
0.4.4
0.4.3
0.4.2
0.4.1
Compose web applications with functions
Security advisory:
This version has known vulnerabilities.
View advisories
Current section
Files
Jump to
Current section
Files
lib/plug/adapters/cowboy/conn.ex
defmodule Plug.Adapters.Cowboy.Conn do
@behaviour Plug.Conn.Adapter
@moduledoc false
alias :cowboy_req, as: Request
def conn(req, transport) do
{path, req} = Request.path req
{host, req} = Request.host req
{port, req} = Request.port req
{meth, req} = Request.method req
{hdrs, req} = Request.headers req
{qs, req} = Request.qs req
%Plug.Conn{
adapter: {__MODULE__, req},
host: host,
method: meth,
path_info: split_path(path),
port: port,
query_string: qs,
req_headers: hdrs,
scheme: scheme(transport)
}
end
def send_resp(req, status, headers, body) do
{:ok, req} = Request.reply(status, headers, body, req)
{:ok, nil, req}
end
def send_file(req, status, headers, path) do
%File.Stat{type: :regular, size: size} = File.stat!(path)
body_fun = fn(socket, transport) -> transport.sendfile(socket, path) end
{:ok, req} = Request.reply(status, headers, Request.set_resp_body_fun(size, body_fun, req))
{:ok, nil, req}
end
def send_chunked(req, status, headers) do
{:ok, req} = Request.chunked_reply(status, headers, req)
{:ok, nil, req}
end
def chunk(req, body) do
Request.chunk(body, req)
end
def read_req_body(req, opts \\ []) do
Request.body(req, opts)
end
def parse_req_multipart(req, opts, callback) do
limit = Keyword.get(opts, :length, 8_000_000)
{:ok, limit, acc, req} = parse_multipart(Request.part(req), limit, opts, %{}, callback)
params = Enum.reduce(acc, %{}, &Plug.Conn.Query.decode_pair/2)
if limit > 0 do
{:ok, params, req}
else
{:more, params, req}
end
end
## Helpers
defp scheme(:tcp), do: :http
defp scheme(:ssl), do: :https
defp split_path(path) do
segments = :binary.split(path, "/", [:global])
for segment <- segments, segment != "", do: segment
end
## Multipart
defp parse_multipart({:ok, headers, req}, limit, opts, acc, callback) when limit >= 0 do
case callback.(headers) do
{:binary, name} ->
{:ok, limit, body, req} = parse_multipart_body(Request.part_body(req, opts), limit, opts, "")
parse_multipart(Request.part(req), limit, opts, Map.put(acc, name, body), callback)
{:file, name, file, %Plug.Upload{} = uploaded} ->
{:ok, limit, req} = parse_multipart_file(Request.part_body(req, opts), limit, opts, file)
parse_multipart(Request.part(req), limit, opts, Map.put(acc, name, uploaded), callback)
:skip ->
{:ok, req} = Request.multipart_skip(req)
parse_multipart(Request.part(req), limit, opts, acc, callback)
end
end
defp parse_multipart({:ok, _headers, req}, limit, _opts, acc, _callback) do
{:ok, limit, acc, req}
end
defp parse_multipart({:done, req}, limit, _opts, acc, _callback) do
{:ok, limit, acc, req}
end
defp parse_multipart_body({:more, tail, req}, limit, opts, body) when limit >= 0 do
parse_multipart_body(Request.part_body(req), limit - byte_size(tail), opts, body <> tail)
end
defp parse_multipart_body({:more, _tail, req}, limit, _opts, body) do
{:ok, limit, body, req}
end
defp parse_multipart_body({:ok, tail, req}, limit, _opts, body) when limit >= byte_size(tail) do
{:ok, limit, body <> tail, req}
end
defp parse_multipart_body({:ok, _tail, req}, limit, _opts, body) do
{:ok, limit, body, req}
end
defp parse_multipart_file({:more, tail, req}, limit, opts, file) when limit >= 0 do
:file.write(file, tail)
parse_multipart_file(Request.part_body(req, opts), limit - byte_size(tail), opts, file)
end
defp parse_multipart_file({:more, _tail, req}, limit, _opts, file) do
:file.close(file)
{:ok, limit, req}
end
defp parse_multipart_file({:ok, tail, req}, limit, _opts, file) when limit >= byte_size(tail) do
:file.write(file, tail)
:file.close(file)
{:ok, limit, req}
end
defp parse_multipart_file({:ok, _tail, req}, limit, _opts, file) do
:file.close(file)
{:ok, limit, req}
end
end