Provide installable man pages
make docs: generate Markdown and man pages in doc/ make install-docs: install man pages to be usable directly Docs are generated from the ezdoc files in doc/src/.
3
.gitignore
vendored
|
@ -2,6 +2,9 @@
|
|||
.erlang.mk.packages.*
|
||||
_rel
|
||||
deps
|
||||
doc/man3
|
||||
doc/man7
|
||||
doc/markdown
|
||||
ebin
|
||||
logs
|
||||
relx
|
||||
|
|
52
Makefile
|
@ -24,3 +24,55 @@ dep_gun = pkg://gun master
|
|||
# Standard targets.
|
||||
|
||||
include erlang.mk
|
||||
|
||||
# Documentation.
|
||||
|
||||
dep_ezdoc = https://github.com/ninenines/ezdoc master
|
||||
$(eval $(call dep_target,ezdoc))
|
||||
|
||||
build-doc-deps: $(DEPS_DIR)/ezdoc
|
||||
$(MAKE) -C $(DEPS_DIR)/ezdoc
|
||||
|
||||
define ezdoc_script
|
||||
io:format("Building manual~n"),
|
||||
[begin
|
||||
AST = ezdoc:parse_file(F),
|
||||
BF = filename:rootname(filename:basename(F)),
|
||||
io:format(" ~s~n", [BF]),
|
||||
file:write_file("doc/markdown/manual/" ++ BF ++ ".md", ezdoc_markdown:export(AST)),
|
||||
case BF of
|
||||
"cowboy" ++ _ when BF =/= "cowboy_app" ->
|
||||
file:write_file("doc/man3/" ++ BF ++ ".3", ezdoc_man:export(3, AST));
|
||||
_ when BF =/= "index" ->
|
||||
file:write_file("doc/man7/" ++ BF ++ ".7", ezdoc_man:export(7, AST));
|
||||
_ ->
|
||||
ok
|
||||
end
|
||||
end || F <- filelib:wildcard("doc/src/manual/*.ezdoc")],
|
||||
io:format("Building guide~n"),
|
||||
[begin
|
||||
AST = ezdoc:parse_file(F),
|
||||
BF = filename:rootname(filename:basename(F)),
|
||||
io:format(" ~s~n", [BF]),
|
||||
file:write_file("doc/markdown/guide/" ++ BF ++ ".md", ezdoc_markdown:export(AST))
|
||||
end || F <- filelib:wildcard("doc/src/guide/*.ezdoc")],
|
||||
io:format("Done.~n"),
|
||||
init:stop().
|
||||
endef
|
||||
export ezdoc_script
|
||||
|
||||
docs: clean-docs build-doc-deps
|
||||
@mkdir -p doc/man3 doc/man7 doc/markdown/guide doc/markdown/manual
|
||||
$(gen_verbose) erl -noinput -pa ebin deps/ezdoc/ebin -eval "$$ezdoc_script"
|
||||
@gzip doc/man3/*.3 doc/man7/*.7
|
||||
@cp doc/src/guide/*.png doc/markdown/guide
|
||||
|
||||
clean-docs:
|
||||
$(gen_verbose) rm -rf doc/man3 doc/man7 doc/markdown
|
||||
|
||||
MAN_INSTALL_PATH ?= /usr/local/share/man
|
||||
|
||||
install-docs:
|
||||
mkdir -p $(MAN_INSTALL_PATH)/man3/ $(MAN_INSTALL_PATH)/man7/
|
||||
install -g 0 -o 0 -m 0644 doc/man3/*.gz $(MAN_INSTALL_PATH)/man3/
|
||||
install -g 0 -o 0 -m 0644 doc/man7/*.gz $(MAN_INSTALL_PATH)/man7/
|
||||
|
|
22
README.md
|
@ -27,15 +27,23 @@ The SPDY implementation was sponsored by
|
|||
The project is currently sponsored by
|
||||
[Kato.im](https://kato.im).
|
||||
|
||||
Getting Started
|
||||
---------------
|
||||
Online documentation
|
||||
--------------------
|
||||
|
||||
* [Read the guide](http://ninenines.eu/docs/en/cowboy/HEAD/guide)
|
||||
* [Check the manual](http://ninenines.eu/docs/en/cowboy/HEAD/manual)
|
||||
* Look at the examples in the `examples/` directory
|
||||
* [User guide](http://ninenines.eu/docs/en/cowboy/HEAD/guide)
|
||||
* [Function reference](http://ninenines.eu/docs/en/cowboy/HEAD/manual)
|
||||
|
||||
Support
|
||||
-------
|
||||
Offline documentation
|
||||
---------------------
|
||||
|
||||
* While still online, run `make docs`
|
||||
* Function reference man pages available in `doc/man3/` and `doc/man7/`
|
||||
* Run `make install-docs` to install man pages on your system
|
||||
* Full documentation in Markdown available in `doc/markdown/`
|
||||
* Examples available in `examples/`
|
||||
|
||||
Getting help
|
||||
------------
|
||||
|
||||
* Official IRC Channel: #ninenines on irc.freenode.net
|
||||
* [Mailing Lists](http://lists.ninenines.eu)
|
||||
|
|
|
@ -1,13 +1,11 @@
|
|||
Architecture
|
||||
============
|
||||
::: Architecture
|
||||
|
||||
Cowboy is a lightweight HTTP server.
|
||||
|
||||
It is built on top of Ranch. Please see the Ranch guide for more
|
||||
information.
|
||||
|
||||
One process per connection
|
||||
--------------------------
|
||||
:: One process per connection
|
||||
|
||||
It uses only one process per connection. The process where your
|
||||
code runs is the process controlling the socket. Using one process
|
||||
|
@ -22,8 +20,7 @@ up before terminating the handling of the current request. This may
|
|||
include cleaning up the process dictionary, timers, monitoring and
|
||||
more.
|
||||
|
||||
Binaries
|
||||
--------
|
||||
:: Binaries
|
||||
|
||||
It uses binaries. Binaries are more efficient than lists for
|
||||
representing strings because they take less memory space. Processing
|
||||
|
@ -31,16 +28,14 @@ performance can vary depending on the operation. Binaries are known
|
|||
for generally getting a great boost if the code is compiled natively.
|
||||
Please see the HiPE documentation for more details.
|
||||
|
||||
Date header
|
||||
-----------
|
||||
:: Date header
|
||||
|
||||
Because querying for the current date and time can be expensive,
|
||||
Cowboy generates one `Date` header value every second, shares it
|
||||
to all other processes, which then simply copy it in the response.
|
||||
This allows compliance with HTTP/1.1 with no actual performance loss.
|
||||
|
||||
Max connections
|
||||
---------------
|
||||
:: Max connections
|
||||
|
||||
By default the maximum number of active connections is set to a
|
||||
generally accepted big enough number. This is meant to prevent having
|
|
@ -1,5 +1,4 @@
|
|||
Dealing with broken clients
|
||||
===========================
|
||||
::: Dealing with broken clients
|
||||
|
||||
There exists a very large number of implementations for the
|
||||
HTTP protocol. Most widely used clients, like browsers,
|
||||
|
@ -16,8 +15,7 @@ That means clients that ignore the HTTP standard completely
|
|||
may fail to understand Cowboy's responses. There are of
|
||||
course workarounds. This chapter aims to cover them.
|
||||
|
||||
Lowercase headers
|
||||
-----------------
|
||||
:: Lowercase headers
|
||||
|
||||
Cowboy converts all headers it receives to lowercase, and
|
||||
similarly sends back headers all in lowercase. Some broken
|
||||
|
@ -39,8 +37,7 @@ because the specification explicitly says all headers are
|
|||
lowercase, unlike HTTP which allows any case but treats
|
||||
them as case insensitive.
|
||||
|
||||
Camel-case headers
|
||||
------------------
|
||||
:: Camel-case headers
|
||||
|
||||
Sometimes it is desirable to keep the actual case used by
|
||||
clients, for example when acting as a proxy between two broken
|
||||
|
@ -48,8 +45,7 @@ implementations. There is no easy solution for this other than
|
|||
forking the project and editing the `cowboy_protocol` file
|
||||
directly.
|
||||
|
||||
Chunked transfer-encoding
|
||||
-------------------------
|
||||
:: Chunked transfer-encoding
|
||||
|
||||
Sometimes an HTTP client advertises itself as HTTP/1.1 but
|
||||
does not support chunked transfer-encoding. This is invalid
|
|
@ -1,5 +1,4 @@
|
|||
Using cookies
|
||||
=============
|
||||
::: Using cookies
|
||||
|
||||
Cookies are a mechanism allowing applications to maintain
|
||||
state on top of the stateless HTTP protocol.
|
||||
|
@ -49,8 +48,7 @@ that run from HTTPS webpages.
|
|||
Finally, cookies can be restricted to HTTP and HTTPS requests,
|
||||
essentially disabling their access from client-side scripts.
|
||||
|
||||
Setting cookies
|
||||
---------------
|
||||
:: Setting cookies
|
||||
|
||||
By default, cookies you set are defined for the session.
|
||||
|
||||
|
@ -112,8 +110,7 @@ Req2 = cowboy_req:set_resp_cookie(<<"sessionid">>, SessionID, [
|
|||
Cookies may also be set client-side, for example using
|
||||
Javascript.
|
||||
|
||||
Reading cookies
|
||||
---------------
|
||||
:: Reading cookies
|
||||
|
||||
As we said, the client sends cookies with every request.
|
||||
But unlike the server, the client only sends the cookie
|
|
@ -1,5 +1,4 @@
|
|||
Erlang for beginners
|
||||
====================
|
||||
::: Erlang for beginners
|
||||
|
||||
Chances are you are interested in using Cowboy, but have
|
||||
no idea how to write an Erlang program. Fear not! This
|
||||
|
@ -9,11 +8,10 @@ We recommend two books for beginners. You should read them
|
|||
both at some point, as they cover Erlang from two entirely
|
||||
different perspectives.
|
||||
|
||||
Learn You Some Erlang for Great Good!
|
||||
-------------------------------------
|
||||
:: Learn You Some Erlang for Great Good!
|
||||
|
||||
The quickest way to get started with Erlang is by reading
|
||||
a book with the funny name of [LYSE](http://learnyousomeerlang.com),
|
||||
a book with the funny name of ^"LYSE^http://learnyousomeerlang.com^,
|
||||
as we affectionately call it.
|
||||
|
||||
It will get right into the syntax and quickly answer the questions
|
||||
|
@ -24,13 +22,12 @@ You can read an early version of the book online for free,
|
|||
but you really should buy the much more refined paper and
|
||||
ebook versions.
|
||||
|
||||
Programming Erlang
|
||||
------------------
|
||||
:: Programming Erlang
|
||||
|
||||
After writing some code, you will probably want to understand
|
||||
the very concepts that make Erlang what it is today. These
|
||||
are best explained by Joe Armstrong, the godfather of Erlang,
|
||||
in his book [Programming Erlang](http://pragprog.com/book/jaerlang2/programming-erlang).
|
||||
in his book ^"Programming Erlang^http://pragprog.com/book/jaerlang2/programming-erlang^.
|
||||
|
||||
Instead of going into every single details of the language,
|
||||
Joe focuses on the central concepts behind Erlang, and shows
|
|
@ -1,8 +1,6 @@
|
|||
Erlang and the Web
|
||||
==================
|
||||
::: Erlang and the Web
|
||||
|
||||
The Web is concurrent
|
||||
---------------------
|
||||
:: The Web is concurrent
|
||||
|
||||
When you access a website there is little concurrency
|
||||
involved. A few connections are opened and requests
|
||||
|
@ -55,8 +53,7 @@ will also connect to various applications on the Internet.
|
|||
|
||||
Only Erlang is prepared to deal with what's coming.
|
||||
|
||||
The Web is soft real time
|
||||
-------------------------
|
||||
:: The Web is soft real time
|
||||
|
||||
What does soft real time mean, you ask? It means we want the
|
||||
operations done as quickly as possible, and in the case of
|
||||
|
@ -85,8 +82,7 @@ can guarantee stable low latency of operations.
|
|||
Erlang provides the guarantees that the soft real time Web
|
||||
requires.
|
||||
|
||||
The Web is asynchronous
|
||||
-----------------------
|
||||
:: The Web is asynchronous
|
||||
|
||||
Long ago, the Web was synchronous because HTTP was synchronous.
|
||||
You fired a request, and then waited for a response. Not anymore.
|
||||
|
@ -118,8 +114,7 @@ Erlang is by nature asynchronous and really good at it thanks to the
|
|||
great engineering that has been done in the VM over the years. It's
|
||||
only natural that it's so good at dealing with the asynchronous Web.
|
||||
|
||||
The Web is omnipresent
|
||||
----------------------
|
||||
:: The Web is omnipresent
|
||||
|
||||
The Web has taken a very important part of our lives. We're
|
||||
connected at all times, when we're on our phone, using our computer,
|
||||
|
@ -172,8 +167,7 @@ down, or even a data center entirely.
|
|||
Fault tolerance and distribution are important today, and will be
|
||||
vital in the future of the Web. Erlang is ready.
|
||||
|
||||
Erlang is the ideal platform for the Web
|
||||
----------------------------------------
|
||||
:: Erlang is the ideal platform for the Web
|
||||
|
||||
Erlang provides all the important features that the Web requires
|
||||
or will require in the near future. Erlang is a perfect match
|
|
@ -1,5 +1,4 @@
|
|||
Getting started
|
||||
===============
|
||||
::: Getting started
|
||||
|
||||
Erlang is more than a language, it is also an operating system
|
||||
for your applications. Erlang developers rarely write standalone
|
||||
|
@ -13,14 +12,13 @@ Cowboy, writing your first application and generating your first
|
|||
release. At the end of this chapter you should know everything
|
||||
you need to push your first Cowboy application to production.
|
||||
|
||||
Application skeleton
|
||||
--------------------
|
||||
:: Application skeleton
|
||||
|
||||
Let's start by creating this application. We will simply call it
|
||||
`hello_erlang`. This application will have the following directory
|
||||
structure:
|
||||
|
||||
```
|
||||
``` bash
|
||||
hello_erlang/
|
||||
src/
|
||||
hello_erlang.app.src
|
||||
|
@ -35,7 +33,7 @@ hello_erlang/
|
|||
Once the release is generated, we will also have the following
|
||||
files added:
|
||||
|
||||
```
|
||||
``` bash
|
||||
hello_erlang/
|
||||
ebin/
|
||||
hello_erlang.app
|
||||
|
@ -54,11 +52,11 @@ The `.app` file contains various informations about the application.
|
|||
It contains its name, a description, a version, a list of modules,
|
||||
default configuration and more.
|
||||
|
||||
Using a build system like [erlang.mk](https://github.com/extend/erlang.mk),
|
||||
Using a build system like ^"erlang.mk^https://github.com/extend/erlang.mk^,
|
||||
the list of modules will be included automatically in the `.app` file,
|
||||
so you don't need to manually put them in your `.app.src` file.
|
||||
|
||||
For generating the release, we will use [relx](https://github.com/erlware/relx)
|
||||
For generating the release, we will use ^"relx^https://github.com/erlware/relx
|
||||
as it is a much simpler alternative to the tool coming with Erlang.
|
||||
|
||||
First, create the `hello_erlang` directory. It should have the same name
|
||||
|
@ -129,8 +127,7 @@ That's not enough however. Since we are building a Cowboy based
|
|||
application, we also need to initialize Cowboy when we start our
|
||||
application.
|
||||
|
||||
Setting up Cowboy
|
||||
-----------------
|
||||
:: Setting up Cowboy
|
||||
|
||||
Cowboy does nothing by default.
|
||||
|
||||
|
@ -145,7 +142,7 @@ Listeners are a group of processes that are used to accept and manage
|
|||
connections. The processes used specifically for accepting connections
|
||||
are called acceptors. The number of acceptor processes is unrelated to
|
||||
the maximum number of connections Cowboy can handle. Please refer to
|
||||
the [Ranch guide](http://ninenines.eu/docs/en/ranch/HEAD/guide/)
|
||||
the ^"Ranch guide^http://ninenines.eu/docs/en/ranch/HEAD/guide/
|
||||
for in-depth information.
|
||||
|
||||
Listeners are named. They spawn a given number of acceptors, listen for
|
||||
|
@ -154,7 +151,7 @@ options to the connection processes. The protocol options must include
|
|||
the dispatch list for routing requests to handlers.
|
||||
|
||||
The dispatch list is explained in greater details in the
|
||||
[Routing](routing.md) chapter. For the purpose of this example
|
||||
^"Routing^routing^ chapter. For the purpose of this example
|
||||
we will simply map all URLs to our handler `hello_handler`,
|
||||
using the wildcard `_` for both the hostname and path parts
|
||||
of the URL.
|
||||
|
@ -200,15 +197,14 @@ init([]) ->
|
|||
|
||||
Finally, we need to write the code for handling incoming requests.
|
||||
|
||||
Handling HTTP requests
|
||||
----------------------
|
||||
:: Handling HTTP requests
|
||||
|
||||
Cowboy features many kinds of handlers. For this simple example,
|
||||
we will just use the plain HTTP handler, which has three callback
|
||||
functions: `init/3`, `handle/2` and `terminate/3`. You can find more
|
||||
information about the arguments and possible return values of these
|
||||
callbacks in the
|
||||
[cowboy_http_handler function reference](http://ninenines.eu/docs/en/cowboy/HEAD/manual/cowboy_http_handler).
|
||||
^"cowboy_http_handler function reference^http://ninenines.eu/docs/en/cowboy/HEAD/manual/cowboy_http_handler^.
|
||||
|
||||
Our handler will only send a friendly hello back to the client.
|
||||
|
||||
|
@ -236,12 +232,11 @@ terminate(_Reason, _Req, _State) ->
|
|||
The `Req` variable above is the Req object, which allows the developer
|
||||
to obtain information about the request and to perform a reply.
|
||||
Its usage is documented in the
|
||||
[cowboy_req function reference](http://ninenines.eu/docs/en/cowboy/HEAD/manual/cowboy_req).
|
||||
^"cowboy_req function reference^http://ninenines.eu/docs/en/cowboy/HEAD/manual/cowboy_req^.
|
||||
|
||||
The code for our application is ready, so let's build a release!
|
||||
|
||||
Compiling
|
||||
---------
|
||||
:: Compiling
|
||||
|
||||
First we need to download `erlang.mk`.
|
||||
|
||||
|
@ -279,8 +274,7 @@ haven't made any typo when creating the previous files.
|
|||
$ make
|
||||
```
|
||||
|
||||
Generating the release
|
||||
----------------------
|
||||
:: Generating the release
|
||||
|
||||
That's not all however, as we want to create a working release.
|
||||
For that purpose, we need to create a `relx.config` file. When
|
|
@ -1,12 +1,10 @@
|
|||
Hooks
|
||||
=====
|
||||
::: Hooks
|
||||
|
||||
Cowboy provides two hooks. `onrequest` is called once the request
|
||||
line and headers have been received. `onresponse` is called just
|
||||
before sending the response.
|
||||
|
||||
Onrequest
|
||||
---------
|
||||
:: Onrequest
|
||||
|
||||
The `onrequest` hook is called as soon as Cowboy finishes fetching
|
||||
the request headers. It occurs before any other processing, including
|
||||
|
@ -43,8 +41,7 @@ debug_hook(Req) ->
|
|||
|
||||
Make sure to always return the last request object obtained.
|
||||
|
||||
Onresponse
|
||||
----------
|
||||
:: Onresponse
|
||||
|
||||
The `onresponse` hook is called right before sending the response
|
||||
to the socket. It can be used for the purposes of logging responses,
|
|
@ -1,13 +1,11 @@
|
|||
Handling plain HTTP requests
|
||||
============================
|
||||
::: Handling plain HTTP requests
|
||||
|
||||
The simplest way to handle a request is by writing a
|
||||
plain HTTP handler. It is modeled after Erlang/OTP's
|
||||
gen_server behaviour, although simplified, as Cowboy
|
||||
will simply call the three callbacks sequentially.
|
||||
|
||||
Initialization
|
||||
--------------
|
||||
:: Initialization
|
||||
|
||||
The first callback, `init/3`, is common to all handlers,
|
||||
as it is used to identify the type of handler. Plain
|
||||
|
@ -92,8 +90,7 @@ init(_Type, Req, Opts) ->
|
|||
{ok, Req, #state{lang=Lang}}.
|
||||
```
|
||||
|
||||
Handling the request
|
||||
--------------------
|
||||
:: Handling the request
|
||||
|
||||
The second callback, `handle/2`, is specific to plain HTTP
|
||||
handlers. It's where you, wait for it, handle the request.
|
||||
|
@ -119,8 +116,7 @@ handle(Req, State) ->
|
|||
{ok, Req2, State}.
|
||||
```
|
||||
|
||||
Cleaning up
|
||||
-----------
|
||||
:: Cleaning up
|
||||
|
||||
The third and last callback, `terminate/3`, will most likely
|
||||
be empty in your handler.
|
|
@ -1,12 +1,10 @@
|
|||
The life of a request
|
||||
=====================
|
||||
::: The life of a request
|
||||
|
||||
This chapter explains the different steps a request
|
||||
goes through until a response is sent, along with
|
||||
details of the Cowboy implementation.
|
||||
|
||||
Request/response
|
||||
----------------
|
||||
:: Request/response
|
||||
|
||||
As you already know, HTTP clients connect to the server and
|
||||
send a request for a resource; the server then sends a
|
||||
|
@ -20,7 +18,7 @@ add like writing logs.
|
|||
|
||||
Requests take the following route in Cowboy:
|
||||
|
||||

|
||||
^"HTTP request/response flowchart^!http_req_resp.png
|
||||
|
||||
This shows the default middlewares, but they may be
|
||||
configured differently in your setup. The dark green
|
||||
|
@ -44,8 +42,7 @@ When a response is sent, you can optionally modify it
|
|||
or act upon it by enabling the `onresponse` hook. By
|
||||
default the response is sent directly to the client.
|
||||
|
||||
And then?
|
||||
---------
|
||||
:: And then?
|
||||
|
||||
Behavior depends on what protocol is in use.
|
||||
|
||||
|
@ -62,8 +59,7 @@ asynchronously on the same connection. Details on what
|
|||
this means for your application is described in this
|
||||
chapter.
|
||||
|
||||
Keep-alive (HTTP/1.1)
|
||||
---------------------
|
||||
:: Keep-alive (HTTP/1.1)
|
||||
|
||||
With HTTP/1.1, the connection may be left open for
|
||||
subsequent requests to come. This mechanism is called
|
||||
|
@ -110,8 +106,7 @@ But it also means you need to clean up if you do have
|
|||
code with side effects. The `terminate/3` function can
|
||||
be used for this purpose.
|
||||
|
||||
Pipelining (HTTP/1.1)
|
||||
---------------------
|
||||
:: Pipelining (HTTP/1.1)
|
||||
|
||||
While HTTP is designed as a sequential protocol, with
|
||||
the client sending a request and then waiting for the
|
||||
|
@ -128,8 +123,7 @@ static files for example.
|
|||
|
||||
This is handled automatically by the server.
|
||||
|
||||
Asynchronous requests (SPDY)
|
||||
----------------------------
|
||||
:: Asynchronous requests (SPDY)
|
||||
|
||||
In SPDY, the client can send a request at any time.
|
||||
And the server can send a response at any time too.
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
Before Width: | Height: | Size: 21 KiB After Width: | Height: | Size: 21 KiB |
58
doc/src/guide/index.ezdoc
Normal file
|
@ -0,0 +1,58 @@
|
|||
::: Cowboy User Guide
|
||||
|
||||
The Cowboy User Guide explores the modern Web and how to make
|
||||
best use of Cowboy for writing powerful web applications.
|
||||
|
||||
:: Introducing Cowboy
|
||||
|
||||
* ^"Introduction^introduction
|
||||
* ^"The modern Web^modern_web
|
||||
* ^"Erlang and the Web^erlang_web
|
||||
* ^"Erlang for beginners^erlang_beginners
|
||||
* ^"Getting started^getting_started
|
||||
|
||||
:: HTTP
|
||||
|
||||
* ^"The life of a request^http_req_life
|
||||
* ^"Routing^routing
|
||||
* ^"Handling plain HTTP requests^http_handlers
|
||||
* ^"The Req object^req
|
||||
* ^"Reading the request body^req_body
|
||||
* ^"Sending a response^resp
|
||||
* ^"Using cookies^cookies
|
||||
|
||||
:: Multipart
|
||||
|
||||
* ^"Introduction to multipart^multipart_intro
|
||||
* ^"Multipart requests^multipart_req
|
||||
|
||||
:: Static files
|
||||
|
||||
* ^"Static handler^static_handlers
|
||||
|
||||
:: REST
|
||||
|
||||
* ^"REST principles^rest_principles
|
||||
* ^"Handling REST requests^rest_handlers
|
||||
* ^"REST flowcharts^rest_flowcharts
|
||||
* ^"Designing a resource handler^resource_design
|
||||
|
||||
:: Websocket
|
||||
|
||||
* ^"The Websocket protocol^ws_protocol
|
||||
* ^"Handling Websocket connections^ws_handlers
|
||||
|
||||
:: Server push
|
||||
|
||||
* ^"Loop handlers^loop_handlers
|
||||
|
||||
:: Pluggable interface
|
||||
|
||||
* ^"Middlewares^middlewares
|
||||
* ^"Protocol upgrades^upgrade_protocol
|
||||
* ^"Hooks^hooks
|
||||
|
||||
:: Internals
|
||||
|
||||
* ^"Architecture^architecture
|
||||
* ^"Dealing with broken clients^broken_clients
|
|
@ -1,5 +1,4 @@
|
|||
Introduction
|
||||
============
|
||||
::: Introduction
|
||||
|
||||
Cowboy is a small, fast and modular HTTP server written in Erlang.
|
||||
|
||||
|
@ -15,8 +14,7 @@ Cowboy is clean Erlang code. It includes hundreds of tests and its code
|
|||
is fully compliant with the Dialyzer. It is also well documented and
|
||||
features both a Function Reference and a User Guide.
|
||||
|
||||
Prerequisites
|
||||
-------------
|
||||
:: Prerequisites
|
||||
|
||||
No Erlang knowledge is required for reading this guide. The reader will
|
||||
be introduced to Erlang concepts and redirected to reference material
|
||||
|
@ -25,8 +23,7 @@ whenever necessary.
|
|||
Knowledge of the HTTP protocol is recommended but not required, as it
|
||||
will be detailed throughout the guide.
|
||||
|
||||
Supported platforms
|
||||
-------------------
|
||||
:: Supported platforms
|
||||
|
||||
Cowboy is tested and supported on Linux.
|
||||
|
||||
|
@ -40,8 +37,7 @@ Cowboy is developed for Erlang R15B+.
|
|||
Cowboy may be compiled on earlier Erlang versions with small source code
|
||||
modifications but there is no guarantee that it will work as expected.
|
||||
|
||||
Conventions
|
||||
-----------
|
||||
:: Conventions
|
||||
|
||||
In the HTTP protocol, the method name is case sensitive. All standard
|
||||
method names are uppercase.
|
|
@ -1,5 +1,4 @@
|
|||
Loop handlers
|
||||
=============
|
||||
::: Loop handlers
|
||||
|
||||
Loop handlers are a special kind of HTTP handlers used when the
|
||||
response can not be sent right away. The handler enters instead
|
||||
|
@ -25,8 +24,7 @@ and feed these messages to the `info/3` callback. It also features
|
|||
the `init/3` and `terminate/3` callbacks which work the same as
|
||||
for plain HTTP handlers.
|
||||
|
||||
Initialization
|
||||
--------------
|
||||
:: Initialization
|
||||
|
||||
The `init/3` function must return a `loop` tuple to enable
|
||||
loop handler behavior. This tuple may optionally contain
|
||||
|
@ -49,8 +47,7 @@ init(_Type, Req, _Opts) ->
|
|||
{loop, Req, undefined_state, 30000, hibernate}.
|
||||
```
|
||||
|
||||
Receive loop
|
||||
------------
|
||||
:: Receive loop
|
||||
|
||||
Once initialized, Cowboy will wait for messages to arrive
|
||||
in the process' mailbox. When a message arrives, Cowboy
|
||||
|
@ -84,8 +81,7 @@ This will instruct Cowboy to end the request.
|
|||
|
||||
Otherwise a `loop` tuple should be returned.
|
||||
|
||||
Streaming loop
|
||||
--------------
|
||||
:: Streaming loop
|
||||
|
||||
Another common case well suited for loop handlers is
|
||||
streaming data received in the form of Erlang messages.
|
||||
|
@ -111,18 +107,16 @@ info(_Msg, Req, State) ->
|
|||
{loop, Req, State}.
|
||||
```
|
||||
|
||||
Cleaning up
|
||||
-----------
|
||||
:: Cleaning up
|
||||
|
||||
It is recommended that you set the connection header to
|
||||
`close` when replying, as this process may be reused for
|
||||
a subsequent request.
|
||||
|
||||
Please refer to the [HTTP handlers chapter](http_handlers.md)
|
||||
Please refer to the ^"HTTP handlers chapter^http_handlers
|
||||
for general instructions about cleaning up.
|
||||
|
||||
Timeout
|
||||
-------
|
||||
:: Timeout
|
||||
|
||||
By default Cowboy will not attempt to close the connection
|
||||
if there is no activity from the client. This is not always
|
||||
|
@ -138,8 +132,7 @@ so there is a configurable limit for it. The default buffer
|
|||
size is of 5000 bytes, but it may be changed by setting the
|
||||
`loop_max_buffer` middleware environment value.
|
||||
|
||||
Hibernate
|
||||
---------
|
||||
:: Hibernate
|
||||
|
||||
To save memory, you may hibernate the process in between
|
||||
messages received. This is done by returning the atom
|
|
@ -1,5 +1,4 @@
|
|||
Middlewares
|
||||
===========
|
||||
::: Middlewares
|
||||
|
||||
Cowboy delegates the request processing to middleware components.
|
||||
By default, two middlewares are defined, for the routing and handling
|
||||
|
@ -12,8 +11,7 @@ change the chain of middlewares as needed.
|
|||
Cowboy will execute all middlewares in the given order, unless one
|
||||
of them decides to stop processing.
|
||||
|
||||
Usage
|
||||
-----
|
||||
:: Usage
|
||||
|
||||
Middlewares only need to implement a single callback: `execute/2`.
|
||||
It is defined in the `cowboy_middleware` behavior.
|
||||
|
@ -22,6 +20,7 @@ This callback has two arguments. The first is the `Req` object.
|
|||
The second is the environment.
|
||||
|
||||
Middlewares can return one of four different values:
|
||||
|
||||
* `{ok, Req, Env}` to continue the request processing
|
||||
* `{suspend, Module, Function, Args}` to hibernate
|
||||
* `{halt, Req}` to stop processing and move on to the next request
|
||||
|
@ -36,8 +35,7 @@ to send an error back to the socket, the process will just crash. It
|
|||
is up to the middleware to make sure that a reply is sent if something
|
||||
goes wrong.
|
||||
|
||||
Configuration
|
||||
-------------
|
||||
:: Configuration
|
||||
|
||||
The middleware environment is defined as the `env` protocol option.
|
||||
In the previous chapters we saw it briefly when we needed to pass
|
||||
|
@ -45,6 +43,7 @@ the routing information. It is a list of tuples with the first
|
|||
element being an atom and the second any Erlang term.
|
||||
|
||||
Two values in the environment are reserved:
|
||||
|
||||
* `listener` contains the name of the listener
|
||||
* `result` contains the result of the processing
|
||||
|
||||
|
@ -58,15 +57,13 @@ environment values to perform.
|
|||
You can update the environment by calling the `cowboy:set_env/3`
|
||||
convenience function, adding or replacing a value in the environment.
|
||||
|
||||
Routing middleware
|
||||
------------------
|
||||
:: Routing middleware
|
||||
|
||||
The routing middleware requires the `dispatch` value. If routing
|
||||
succeeds, it will put the handler name and options in the `handler`
|
||||
and `handler_opts` values of the environment, respectively.
|
||||
|
||||
Handler middleware
|
||||
------------------
|
||||
:: Handler middleware
|
||||
|
||||
The handler middleware requires the `handler` and `handler_opts`
|
||||
values. It puts the result of the request handling into `result`.
|
|
@ -1,5 +1,4 @@
|
|||
The modern Web
|
||||
==============
|
||||
::: The modern Web
|
||||
|
||||
Let's take a look at various technologies from the beginnings
|
||||
of the Web up to this day, and get a preview of what's
|
||||
|
@ -9,8 +8,7 @@ Cowboy is compatible with all the technology cited in this
|
|||
chapter except of course HTTP/2.0 which has no implementation
|
||||
in the wild at the time of writing.
|
||||
|
||||
The prehistoric Web
|
||||
-------------------
|
||||
:: The prehistoric Web
|
||||
|
||||
HTTP was initially created to serve HTML pages and only
|
||||
had the GET method for retrieving them. This initial
|
||||
|
@ -31,8 +29,7 @@ this.
|
|||
Most improvements done in recent years focused on reducing
|
||||
this load time and reducing the latency of the requests.
|
||||
|
||||
HTTP/1.1
|
||||
--------
|
||||
:: HTTP/1.1
|
||||
|
||||
HTTP/1.1 quickly followed and added a keep-alive mechanism
|
||||
to allow using the same connection for many requests, as
|
||||
|
@ -50,8 +47,7 @@ clients to perform what is called as pipelining: sending many
|
|||
requests in a row, and then processing the responses which will
|
||||
be received in the same order as the requests.
|
||||
|
||||
REST
|
||||
----
|
||||
:: REST
|
||||
|
||||
The design of HTTP/1.1 was influenced by the REST architectural
|
||||
style. REST, or REpresentational State Transfer, is a style of
|
||||
|
@ -76,8 +72,7 @@ to implement RESTful systems.
|
|||
REST is most often used when designing web application APIs
|
||||
which are generally meant to be used by executable code directly.
|
||||
|
||||
XmlHttpRequest
|
||||
--------------
|
||||
:: XmlHttpRequest
|
||||
|
||||
Also know as AJAX, this technology allows Javascript code running
|
||||
on a web page to perform asynchronous requests to the server.
|
||||
|
@ -93,8 +88,7 @@ This is of course still requests initiated by the client,
|
|||
the server still had no way of pushing data to the client
|
||||
on its own, so new technology appeared to allow that.
|
||||
|
||||
Long-polling
|
||||
------------
|
||||
:: Long-polling
|
||||
|
||||
Polling was a technique used to overcome the fact that the server
|
||||
cannot push data directly to the client. Therefore the client had
|
||||
|
@ -122,8 +116,7 @@ You probably guessed by now that long-polling is a hack, and
|
|||
like most hacks it can suffer from unforeseen issues, in this
|
||||
case it doesn't always play well with proxies.
|
||||
|
||||
HTML5
|
||||
-----
|
||||
:: HTML5
|
||||
|
||||
HTML5 is, of course, the HTML version after HTML4. But HTML5
|
||||
emerged to solve a specific problem: dynamic web applications.
|
||||
|
@ -147,8 +140,7 @@ events from the server.
|
|||
The solution went on to become HTML5. At the time of writing
|
||||
it is being standardized.
|
||||
|
||||
EventSource
|
||||
-----------
|
||||
:: EventSource
|
||||
|
||||
EventSource, sometimes also called Server-Sent Events, is a
|
||||
technology allowing servers to push data to HTML5 applications.
|
||||
|
@ -167,8 +159,7 @@ UTF-8 encoded text data. Binary data and text data encoded
|
|||
differently are not allowed by the protocol. A heavier but
|
||||
more generic approach can be found in Websocket.
|
||||
|
||||
Websocket
|
||||
---------
|
||||
:: Websocket
|
||||
|
||||
Websocket is a protocol built on top of HTTP/1.1 that provides
|
||||
a two-ways communication channel between the client and the
|
||||
|
@ -188,8 +179,7 @@ A Websocket connection can be used to transfer any kind of data,
|
|||
small or big, text or binary. Because of this Websocket is
|
||||
sometimes used for communication between systems.
|
||||
|
||||
SPDY
|
||||
----
|
||||
:: SPDY
|
||||
|
||||
SPDY is an attempt to reduce page loading time by opening a
|
||||
single connection per server, keeping it open for subsequent
|
||||
|
@ -213,8 +203,7 @@ to a SPDY connection seamlessly if the protocol supports it.
|
|||
The protocol itself has a few shortcomings which are being
|
||||
fixed in HTTP/2.0.
|
||||
|
||||
HTTP/2.0
|
||||
--------
|
||||
:: HTTP/2.0
|
||||
|
||||
HTTP/2.0 is the long-awaited update to the HTTP/1.1 protocol.
|
||||
It is based on SPDY although a lot has been improved at the
|
|
@ -1,5 +1,4 @@
|
|||
Introduction to multipart
|
||||
=========================
|
||||
::: Introduction to multipart
|
||||
|
||||
Multipart originates from MIME, an Internet standard that
|
||||
extends the format of emails. Multipart messages are a
|
||||
|
@ -19,8 +18,7 @@ Multipart is of course not required for uploading
|
|||
files, it is only required when you want to do so
|
||||
through HTML forms.
|
||||
|
||||
Structure
|
||||
---------
|
||||
:: Structure
|
||||
|
||||
A multipart message is a list of parts. Parts may
|
||||
contain either a multipart message or a non-multipart
|
||||
|
@ -28,8 +26,7 @@ content-type. This allows parts to be arranged in a
|
|||
tree structure, although this is a rare case as far
|
||||
as the Web is concerned.
|
||||
|
||||
Form-data
|
||||
---------
|
||||
:: Form-data
|
||||
|
||||
In the normal case, when a form is submitted, the
|
||||
browser will use the `application/x-www-form-urlencoded`
|
|
@ -1,5 +1,4 @@
|
|||
Multipart requests
|
||||
==================
|
||||
::: Multipart requests
|
||||
|
||||
You can read and parse multipart messages using the
|
||||
Req object directly.
|
||||
|
@ -7,8 +6,7 @@ Req object directly.
|
|||
Cowboy defines two functions that allows you to get
|
||||
information about each part and read their contents.
|
||||
|
||||
Checking the content-type
|
||||
-------------------------
|
||||
:: Checking the content-type
|
||||
|
||||
While there is a variety of multipart messages, the
|
||||
most common on the Web is `multipart/form-data`. It's
|
||||
|
@ -23,8 +21,7 @@ has been sent by parsing the `content-type` header.
|
|||
= cowboy_req:parse_header(<<"content-type">>, Req).
|
||||
```
|
||||
|
||||
Reading a multipart message
|
||||
---------------------------
|
||||
:: Reading a multipart message
|
||||
|
||||
To read a message you have to iterate over all its
|
||||
parts. Then, for each part, you can inspect its headers
|
||||
|
@ -84,8 +81,7 @@ to 8MB. This can of course be overriden. Both functions
|
|||
can take a second argument, the same list of options that
|
||||
will be passed to `cowboy_req:body/2` function.
|
||||
|
||||
Skipping unwanted parts
|
||||
-----------------------
|
||||
:: Skipping unwanted parts
|
||||
|
||||
If you do not want to read a part's body, you can skip it.
|
||||
Skipping is easy. If you do not call the function to read
|
|
@ -1,12 +1,10 @@
|
|||
The Req object
|
||||
==============
|
||||
::: The Req object
|
||||
|
||||
The Req object is this variable that you will use to obtain
|
||||
information about a request, read the body of the request
|
||||
and send a response.
|
||||
|
||||
A special variable
|
||||
------------------
|
||||
:: A special variable
|
||||
|
||||
While we call it an "object", it is not an object in the
|
||||
OOP sense of the term. In fact it is completely opaque
|
||||
|
@ -33,8 +31,7 @@ It also caches the result of operations performed
|
|||
on the immutable state. That means that some calls
|
||||
will give a result much faster when called many times.
|
||||
|
||||
Overview of the cowboy_req interface
|
||||
------------------------------------
|
||||
:: Overview of the cowboy_req interface
|
||||
|
||||
The `cowboy_req` interface is divided in four groups
|
||||
of functions, each having a well defined return type
|
||||
|
@ -72,8 +69,7 @@ This chapter covers most of the first group, plus a few other
|
|||
functions. The next few chapters cover cookies handling, reading
|
||||
the request body and sending a response.
|
||||
|
||||
Request
|
||||
-------
|
||||
:: Request
|
||||
|
||||
When a client performs a request, it first sends a few required
|
||||
values. They are sent differently depending on the protocol
|
||||
|
@ -109,8 +105,7 @@ Do note however that clients claiming to implement one version
|
|||
of the protocol does not mean they implement it fully, or even
|
||||
properly.
|
||||
|
||||
Bindings
|
||||
--------
|
||||
:: Bindings
|
||||
|
||||
After routing the request, bindings are available. Bindings
|
||||
are these parts of the host or path that you chose to extract
|
||||
|
@ -153,8 +148,7 @@ or get `undefined` otherwise.
|
|||
{PathInfo, Req2} = cowboy_req:path_info(Req).
|
||||
```
|
||||
|
||||
Query string
|
||||
------------
|
||||
:: Query string
|
||||
|
||||
The query string can be obtained directly.
|
||||
|
||||
|
@ -181,8 +175,7 @@ Finally, you can obtain all query string values.
|
|||
{AllValues, Req2} = cowboy_req:qs_vals(Req).
|
||||
```
|
||||
|
||||
Request URL
|
||||
-----------
|
||||
:: Request URL
|
||||
|
||||
You can reconstruct the full URL of the resource.
|
||||
|
||||
|
@ -197,8 +190,7 @@ path and query string.
|
|||
{BaseURL, Req2} = cowboy_req:host_url(Req).
|
||||
```
|
||||
|
||||
Headers
|
||||
-------
|
||||
:: Headers
|
||||
|
||||
Cowboy allows you to obtain the header values as string,
|
||||
or parsed into a more meaningful representation.
|
||||
|
@ -258,8 +250,7 @@ manual. Also note that the result of parsing is cached, so
|
|||
calling this function multiple times for the same values will
|
||||
not have a significant performance impact.
|
||||
|
||||
Meta
|
||||
----
|
||||
:: Meta
|
||||
|
||||
Cowboy will sometimes associate some meta information with
|
||||
the request. Built-in meta values are listed in the manual
|
||||
|
@ -285,8 +276,7 @@ an `atom()`.
|
|||
Req2 = cowboy_req:set_meta(the_answer, 42, Req).
|
||||
```
|
||||
|
||||
Peer
|
||||
----
|
||||
:: Peer
|
||||
|
||||
You can obtain the peer address and port number. This is
|
||||
not necessarily the actual IP and port of the client, but
|
||||
|
@ -296,8 +286,7 @@ rather the one of the machine that connected to the server.
|
|||
{{IP, Port}, Req2} = cowboy_req:peer(Req).
|
||||
```
|
||||
|
||||
Reducing the memory footprint
|
||||
-----------------------------
|
||||
:: Reducing the memory footprint
|
||||
|
||||
When you are done reading information from the request object
|
||||
and know you are not going to access it anymore, for example
|
|
@ -1,5 +1,4 @@
|
|||
Reading the request body
|
||||
========================
|
||||
::: Reading the request body
|
||||
|
||||
The Req object also allows you to read the request body.
|
||||
|
||||
|
@ -17,8 +16,7 @@ parse in a single call for form urlencoded formats or
|
|||
multipart. All of these except multipart are covered in
|
||||
this chapter. Multipart is covered later on in the guide.
|
||||
|
||||
Check for request body
|
||||
----------------------
|
||||
:: Check for request body
|
||||
|
||||
You can check whether a body was sent with the request.
|
||||
|
||||
|
@ -33,8 +31,7 @@ Note that it is generally safe to assume that a body is
|
|||
sent for `POST`, `PUT` and `PATCH` requests, without
|
||||
having to explicitly check for it.
|
||||
|
||||
Request body length
|
||||
-------------------
|
||||
:: Request body length
|
||||
|
||||
You can obtain the body length if it was sent with the
|
||||
request.
|
||||
|
@ -49,8 +46,7 @@ there's a body but no length is given, this means that
|
|||
the chunked transfer-encoding was used. You can read
|
||||
chunked bodies by using the stream functions.
|
||||
|
||||
Reading the body
|
||||
----------------
|
||||
:: Reading the body
|
||||
|
||||
You can read the whole body directly in one call.
|
||||
|
||||
|
@ -78,8 +74,7 @@ If the body is larger than the limit, then Cowboy will return
|
|||
a `more` tuple instead, allowing you to stream it if you
|
||||
would like to.
|
||||
|
||||
Streaming the body
|
||||
------------------
|
||||
:: Streaming the body
|
||||
|
||||
You can stream the request body by chunks.
|
||||
|
||||
|
@ -102,8 +97,7 @@ body_to_console(Req) ->
|
|||
You can of course set the `length` option to configure the
|
||||
size of chunks.
|
||||
|
||||
Rate of data transmission
|
||||
-------------------------
|
||||
:: Rate of data transmission
|
||||
|
||||
You can control the rate of data transmission by setting
|
||||
options when calling body functions. This applies not only
|
||||
|
@ -116,8 +110,7 @@ to be received from the socket at once, in bytes.
|
|||
The `read_timeout` option defines the time Cowboy waits
|
||||
before that amount is received, in milliseconds.
|
||||
|
||||
Transfer and content decoding
|
||||
-----------------------------
|
||||
:: Transfer and content decoding
|
||||
|
||||
Cowboy will by default decode the chunked transfer-encoding
|
||||
if any. It will not decode any content-encoding by default.
|
||||
|
@ -136,8 +129,7 @@ The following example shows how to set both options.
|
|||
]).
|
||||
```
|
||||
|
||||
Reading a form urlencoded body
|
||||
------------------------------
|
||||
:: Reading a form urlencoded body
|
||||
|
||||
You can directly obtain a list of key/value pairs if the
|
||||
body was sent using the application/x-www-form-urlencoded
|
|
@ -1,12 +1,10 @@
|
|||
Designing a resource handler
|
||||
============================
|
||||
::: Designing a resource handler
|
||||
|
||||
This chapter aims to provide you with a list of questions
|
||||
you must answer in order to write a good resource handler.
|
||||
It is meant to be usable as a step by step guide.
|
||||
|
||||
The service
|
||||
-----------
|
||||
:: The service
|
||||
|
||||
Can the service become unavailable, and when it does, can
|
||||
we detect it? For example database connectivity problems
|
||||
|
@ -19,8 +17,7 @@ more than the standard OPTIONS, HEAD, GET, PUT, POST,
|
|||
PATCH and DELETE? Are we not using one of those at all?
|
||||
Implement the `known_methods` callback.
|
||||
|
||||
Type of resource handler
|
||||
------------------------
|
||||
:: Type of resource handler
|
||||
|
||||
Am I writing a handler for a collection of resources,
|
||||
or for a single resource?
|
||||
|
@ -29,8 +26,7 @@ The semantics for each of these are quite different.
|
|||
You should not mix collection and single resource in
|
||||
the same handler.
|
||||
|
||||
Collection handler
|
||||
------------------
|
||||
:: Collection handler
|
||||
|
||||
Skip this section if you are not doing a collection.
|
||||
|
||||
|
@ -74,8 +70,7 @@ operation is atomic. The PATCH operation may
|
|||
be used for such things as reordering; adding,
|
||||
modifying or deleting parts of the collection.
|
||||
|
||||
Single resource handler
|
||||
-----------------------
|
||||
:: Single resource handler
|
||||
|
||||
Skip this section if you are doing a collection.
|
||||
|
||||
|
@ -103,8 +98,7 @@ operation is atomic. The PATCH operation may
|
|||
be used for adding, removing or modifying specific
|
||||
values in the resource.
|
||||
|
||||
The resource
|
||||
------------
|
||||
:: The resource
|
||||
|
||||
Following the above discussion, implement the
|
||||
`allowed_methods` callback.
|
||||
|
@ -131,8 +125,7 @@ Is there any constraints on the length of the resource URI?
|
|||
For example the URI may be used as a key in storage and may
|
||||
have a limit in length. Implement `uri_too_long`.
|
||||
|
||||
Representations
|
||||
---------------
|
||||
:: Representations
|
||||
|
||||
What media types do I provide? If text based, what charsets
|
||||
are provided? What languages do I provide?
|
||||
|
@ -156,8 +149,7 @@ representation available? Send a list of available
|
|||
representations in the response body and implement
|
||||
the `multiple_choices` callback.
|
||||
|
||||
Redirections
|
||||
------------
|
||||
:: Redirections
|
||||
|
||||
Do I need to keep track of what resources were deleted?
|
||||
For example you may have a mechanism where moving a
|
||||
|
@ -169,8 +161,7 @@ it is explicitly temporary, for example due to maintenance,
|
|||
implement the `moved_temporarily` callback. Otherwise,
|
||||
implement the `moved_permanently` callback.
|
||||
|
||||
The request
|
||||
-----------
|
||||
:: The request
|
||||
|
||||
Do we need to perform extra checks to make sure the request
|
||||
is valid? Cowboy will do many checks when receiving the
|
||||
|
@ -185,23 +176,20 @@ to accept? Implement `valid_entity_length`.
|
|||
Finally, take a look at the sections corresponding to the
|
||||
methods you are implementing.
|
||||
|
||||
OPTIONS method
|
||||
--------------
|
||||
:: OPTIONS method
|
||||
|
||||
Cowboy by default will send back a list of allowed methods.
|
||||
Do I need to add more information to the response? Implement
|
||||
the `options` method.
|
||||
|
||||
GET and HEAD methods
|
||||
--------------------
|
||||
:: GET and HEAD methods
|
||||
|
||||
If you implement the methods GET and/or HEAD, you must
|
||||
implement one `ProvideResource` callback for each
|
||||
content-type returned by the `content_types_provided`
|
||||
callback.
|
||||
|
||||
PUT, POST and PATCH methods
|
||||
---------------------------
|
||||
:: PUT, POST and PATCH methods
|
||||
|
||||
If you implement the methods PUT, POST and/or PATCH,
|
||||
you must implement the `content_types_accepted` callback,
|
||||
|
@ -220,8 +208,7 @@ a resource? Do we want to make sure that two updates around
|
|||
the same time are not cancelling one another? Implement the
|
||||
`is_conflict` callback.
|
||||
|
||||
DELETE methods
|
||||
--------------
|
||||
:: DELETE methods
|
||||
|
||||
If you implement the method DELETE, you must implement
|
||||
the `delete_resource` callback.
|
|
@ -1,5 +1,4 @@
|
|||
Sending a response
|
||||
==================
|
||||
::: Sending a response
|
||||
|
||||
The Req object also allows you to send a response.
|
||||
|
||||
|
@ -10,8 +9,7 @@ with its body streamed by chunks of arbitrary size.
|
|||
You can also set headers or the response body in advance
|
||||
and Cowboy will use them when you finally do reply.
|
||||
|
||||
Reply
|
||||
-----
|
||||
:: Reply
|
||||
|
||||
You can send a reply with no particular headers or body.
|
||||
Cowboy will make sure to send the mandatory headers with
|
||||
|
@ -66,8 +64,7 @@ Here is the same example but sending HTML this time.
|
|||
|
||||
Note that the reply is sent immediately.
|
||||
|
||||
Chunked reply
|
||||
-------------
|
||||
:: Chunked reply
|
||||
|
||||
You can also stream the response body. First, you need to
|
||||
initiate the reply by sending the response status code.
|
||||
|
@ -98,8 +95,7 @@ ok = cowboy_req:chunk("<body><p>Hats off!</p></body></html>", Req2).
|
|||
Note that the reply and each chunk following it are sent
|
||||
immediately.
|
||||
|
||||
Preset response headers
|
||||
-----------------------
|
||||
:: Preset response headers
|
||||
|
||||
You can define response headers in advance. They will be
|
||||
merged into the headers given in the reply call. Headers
|
||||
|
@ -129,8 +125,7 @@ needed. If you do, it will not be sent.
|
|||
Req2 = cowboy_req:delete_resp_header(<<"allow">>, Req).
|
||||
```
|
||||
|
||||
Preset response body
|
||||
--------------------
|
||||
:: Preset response body
|
||||
|
||||
You can set the response body in advance. Note that this
|
||||
body will be ignored if you then choose to send a chunked
|
||||
|
@ -180,8 +175,7 @@ end,
|
|||
Req2 = cowboy_req:set_resp_body_fun(F, Req).
|
||||
```
|
||||
|
||||
Sending files
|
||||
-------------
|
||||
:: Sending files
|
||||
|
||||
You can send files directly from disk without having to
|
||||
read them. Cowboy will use the `sendfile` syscall when
|
Before Width: | Height: | Size: 109 KiB After Width: | Height: | Size: 109 KiB |
Before Width: | Height: | Size: 76 KiB After Width: | Height: | Size: 76 KiB |
Before Width: | Height: | Size: 76 KiB After Width: | Height: | Size: 76 KiB |
Before Width: | Height: | Size: 52 KiB After Width: | Height: | Size: 52 KiB |
Before Width: | Height: | Size: 119 KiB After Width: | Height: | Size: 119 KiB |
Before Width: | Height: | Size: 80 KiB After Width: | Height: | Size: 80 KiB |
|
@ -1,5 +1,4 @@
|
|||
REST flowcharts
|
||||
===============
|
||||
::: REST flowcharts
|
||||
|
||||
This chapter will explain the REST handler state machine through
|
||||
a number of different diagrams.
|
||||
|
@ -18,12 +17,11 @@ indicate a response. Other squares may be either a callback or a
|
|||
question answered by Cowboy itself. Green arrows tend to indicate
|
||||
the default behavior if the callback is undefined.
|
||||
|
||||
Start
|
||||
-----
|
||||
:: Start
|
||||
|
||||
All requests start from here.
|
||||
|
||||

|
||||
^"REST starting flowchart^!rest_start.png
|
||||
|
||||
A series of callbacks are called in succession to perform
|
||||
a general checkup of the service, the request line and
|
||||
|
@ -50,12 +48,11 @@ This diagram is immediately followed by either the
|
|||
"OPTIONS method" diagram when the request method is
|
||||
OPTIONS, or the "Content negotiation" diagram otherwise.
|
||||
|
||||
OPTIONS method
|
||||
--------------
|
||||
:: OPTIONS method
|
||||
|
||||
This diagram only applies to OPTIONS requests.
|
||||
|
||||

|
||||
^"REST OPTIONS method flowchart^!rest_options.png
|
||||
|
||||
The `options` callback may be used to add information
|
||||
about the resource, such as media types or languages
|
||||
|
@ -67,14 +64,13 @@ If the `options` callback is not defined, Cowboy will
|
|||
send a response containing the list of allowed methods
|
||||
by default.
|
||||
|
||||
Content negotiation
|
||||
-------------------
|
||||
:: Content negotiation
|
||||
|
||||
This diagram applies to all request methods other than
|
||||
OPTIONS. It is executed right after the "Start" diagram
|
||||
is completed.
|
||||
|
||||

|
||||
^"REST content negotiation flowchart^!rest_conneg.png
|
||||
|
||||
The purpose of these steps is to determine an appropriate
|
||||
representation to be sent back to the client.
|
||||
|
@ -109,15 +105,14 @@ the "PUT, POST and PATCH methods" diagram,
|
|||
or the "DELETE method" diagram, depending on the
|
||||
method.
|
||||
|
||||
GET and HEAD methods
|
||||
--------------------
|
||||
:: GET and HEAD methods
|
||||
|
||||
This diagram only applies to GET and HEAD requests.
|
||||
|
||||
For a description of the `cond` step, please see
|
||||
the "Conditional requests" diagram.
|
||||
|
||||

|
||||
^"REST GET/HEAD methods flowchart^!rest_get_head.png
|
||||
|
||||
When the resource exists, and the conditional steps
|
||||
succeed, the resource can be retrieved.
|
||||
|
@ -139,15 +134,14 @@ The `moved_permanently` and `moved_temporarily` callbacks
|
|||
must return the new location of the resource if it was in
|
||||
fact moved.
|
||||
|
||||
PUT, POST and PATCH methods
|
||||
---------------------------
|
||||
:: PUT, POST and PATCH methods
|
||||
|
||||
This diagram only applies to PUT, POST and PATCH requests.
|
||||
|
||||
For a description of the `cond` step, please see
|
||||
the "Conditional requests" diagram.
|
||||
|
||||

|
||||
^"REST PUT/POST/PATCH methods flowchart^!rest_put_post_patch.png
|
||||
|
||||
When the resource exists, first the conditional steps
|
||||
are executed. When that succeeds, and the method is PUT,
|
||||
|
@ -194,15 +188,14 @@ on whether a resource has been created, rather than
|
|||
modified, and on the availability of a location header
|
||||
or a body in the response.
|
||||
|
||||
DELETE method
|
||||
-------------
|
||||
:: DELETE method
|
||||
|
||||
This diagram only applies to DELETE requests.
|
||||
|
||||
For a description of the `cond` step, please see
|
||||
the "Conditional requests" diagram.
|
||||
|
||||

|
||||
^"REST DELETE method flowchart^!rest_delete.png
|
||||
|
||||
When the resource exists, and the conditional steps
|
||||
succeed, the resource can be deleted.
|
||||
|
@ -234,14 +227,13 @@ The `moved_permanently` and `moved_temporarily` callbacks
|
|||
must return the new location of the resource if it was in
|
||||
fact moved.
|
||||
|
||||
Conditional requests
|
||||
--------------------
|
||||
:: Conditional requests
|
||||
|
||||
This diagram applies to all request methods other than
|
||||
OPTIONS. It is executed right after the `resource_exists`
|
||||
callback, when the resource exists.
|
||||
|
||||

|
||||
^"REST conditional requests flowchart^!rest_cond.png
|
||||
|
||||
A request becomes conditional when it includes either of
|
||||
the if-match header; the if-unmodified-since header; the
|
Before Width: | Height: | Size: 98 KiB After Width: | Height: | Size: 98 KiB |
Before Width: | Height: | Size: 70 KiB After Width: | Height: | Size: 70 KiB |
|
@ -1,5 +1,4 @@
|
|||
REST handlers
|
||||
=============
|
||||
::: REST handlers
|
||||
|
||||
REST is implemented in Cowboy as a protocol upgrade. Once upgraded,
|
||||
the request is handled as a state machine with many optional callbacks
|
||||
|
@ -7,8 +6,7 @@ describing the resource and modifying the machine's behavior.
|
|||
|
||||
The REST handler is the recommended way to handle requests.
|
||||
|
||||
Initialization
|
||||
--------------
|
||||
:: Initialization
|
||||
|
||||
First, the `init/3` callback is called. This callback is common
|
||||
to all handlers. To use REST for the current request, this function
|
||||
|
@ -23,8 +21,7 @@ Cowboy will then switch to the REST protocol and start executing
|
|||
the state machine, starting from `rest_init/2` if it's defined,
|
||||
and ending with `rest_terminate/2` also if defined.
|
||||
|
||||
Methods
|
||||
-------
|
||||
:: Methods
|
||||
|
||||
The REST component has code for handling the following HTTP methods:
|
||||
HEAD, GET, POST, PATCH, PUT, DELETE and OPTIONS.
|
||||
|
@ -32,8 +29,7 @@ HEAD, GET, POST, PATCH, PUT, DELETE and OPTIONS.
|
|||
Other methods can be accepted, however they have no specific callback
|
||||
defined for them at this time.
|
||||
|
||||
Callbacks
|
||||
---------
|
||||
:: Callbacks
|
||||
|
||||
All callbacks are optional. Some may become mandatory depending
|
||||
on what other defined callbacks return. The various flowcharts
|
||||
|
@ -63,39 +59,39 @@ All callbacks can also return `{halt, Req, State}` to stop execution
|
|||
of the request, at which point `rest_terminate/2` will be called.
|
||||
|
||||
In the following table, "skip" means the callback is entirely skipped
|
||||
if it is undefined, moving directly to the next step. Similarly, an
|
||||
empty column means there is no default value for this callback.
|
||||
if it is undefined, moving directly to the next step. Similarly,
|
||||
"none" means there is no default value for this callback.
|
||||
|
||||
| Callback name | Default value |
|
||||
| ---------------------- | ------------------------- |
|
||||
| allowed_methods | `[<<"GET">>, <<"HEAD">>, <<"OPTIONS">>]` |
|
||||
| allow_missing_post | `true` |
|
||||
| charsets_provided | skip |
|
||||
| content_types_accepted | |
|
||||
| content_types_provided | `[{{<<"text">>, <<"html">>, '*'}, to_html}] ` |
|
||||
| delete_completed | `true` |
|
||||
| delete_resource | `false` |
|
||||
| expires | `undefined` |
|
||||
| forbidden | `false` |
|
||||
| generate_etag | `undefined` |
|
||||
| is_authorized | `true` |
|
||||
| is_conflict | `false` |
|
||||
| known_content_type | `true` |
|
||||
| known_methods | `[<<"GET">>, <<"HEAD">>, <<"POST">>, <<"PUT">>, <<"PATCH">>, <<"DELETE">>, <<"OPTIONS">>]` |
|
||||
| languages_provided | skip |
|
||||
| last_modified | `undefined` |
|
||||
| malformed_request | `false` |
|
||||
| moved_permanently | `false` |
|
||||
| moved_temporarily | `false` |
|
||||
| multiple_choices | `false` |
|
||||
| options | `ok` |
|
||||
| previously_existed | `false` |
|
||||
| resource_exists | `true` |
|
||||
| service_available | `true` |
|
||||
| uri_too_long | `false` |
|
||||
| valid_content_headers | `true` |
|
||||
| valid_entity_length | `true` |
|
||||
| variances | `[]` |
|
||||
|| Callback name Default value
|
||||
|
|
||||
| allowed_methods `[<<"GET">>, <<"HEAD">>, <<"OPTIONS">>]`
|
||||
| allow_missing_post `true`
|
||||
| charsets_provided skip
|
||||
| content_types_accepted none
|
||||
| content_types_provided `[{{<<"text">>, <<"html">>, '*'}, to_html}] `
|
||||
| delete_completed `true`
|
||||
| delete_resource `false`
|
||||
| expires `undefined`
|
||||
| forbidden `false`
|
||||
| generate_etag `undefined`
|
||||
| is_authorized `true`
|
||||
| is_conflict `false`
|
||||
| known_content_type `true`
|
||||
| known_methods `[<<"GET">>, <<"HEAD">>, <<"POST">>, <<"PUT">>, <<"PATCH">>, <<"DELETE">>, <<"OPTIONS">>]`
|
||||
| languages_provided skip
|
||||
| last_modified `undefined`
|
||||
| malformed_request `false`
|
||||
| moved_permanently `false`
|
||||
| moved_temporarily `false`
|
||||
| multiple_choices `false`
|
||||
| options `ok`
|
||||
| previously_existed `false`
|
||||
| resource_exists `true`
|
||||
| service_available `true`
|
||||
| uri_too_long `false`
|
||||
| valid_content_headers `true`
|
||||
| valid_entity_length `true`
|
||||
| variances `[]`
|
||||
|
||||
As you can see, Cowboy tries to move on with the request whenever
|
||||
possible by using well thought out default values.
|
||||
|
@ -108,34 +104,32 @@ each function. For example, `from_html` and `to_html` indicate
|
|||
in the first case that we're accepting a resource given as HTML,
|
||||
and in the second case that we send one as HTML.
|
||||
|
||||
Meta data
|
||||
---------
|
||||
:: Meta data
|
||||
|
||||
Cowboy will set informative meta values at various points of the
|
||||
execution. You can retrieve them using `cowboy_req:meta/{2,3}`.
|
||||
The values are defined in the following table.
|
||||
|
||||
| Meta key | Details |
|
||||
| -----------| ---------------------------------------------------- |
|
||||
| media_type | The content-type negotiated for the response entity. |
|
||||
| language | The language negotiated for the response entity. |
|
||||
| charset | The charset negotiated for the response entity. |
|
||||
|| Meta key Details
|
||||
|
|
||||
| media_type The content-type negotiated for the response entity.
|
||||
| language The language negotiated for the response entity.
|
||||
| charset The charset negotiated for the response entity.
|
||||
|
||||
They can be used to send a proper body with the response to a
|
||||
request that used a method other than HEAD or GET.
|
||||
|
||||
Response headers
|
||||
----------------
|
||||
:: Response headers
|
||||
|
||||
Cowboy will set response headers automatically over the execution
|
||||
of the REST code. They are listed in the following table.
|
||||
|
||||
| Header name | Details |
|
||||
| ---------------- | -------------------------------------------------- |
|
||||
| content-language | Language used in the response body |
|
||||
| content-type | Media type and charset of the response body |
|
||||
| etag | Etag of the resource |
|
||||
| expires | Expiration date of the resource |
|
||||
| last-modified | Last modification date for the resource |
|
||||
| location | Relative or absolute URI to the requested resource |
|
||||
| vary | List of headers that may change the representation of the resource |
|
||||
|| Header name Details
|
||||
|
|
||||
| content-language Language used in the response body
|
||||
| content-type Media type and charset of the response body
|
||||
| etag Etag of the resource
|
||||
| expires Expiration date of the resource
|
||||
| last-modified Last modification date for the resource
|
||||
| location Relative or absolute URI to the requested resource
|
||||
| vary List of headers that may change the representation of the resource
|
Before Width: | Height: | Size: 8.3 KiB After Width: | Height: | Size: 8.3 KiB |
Before Width: | Height: | Size: 16 KiB After Width: | Height: | Size: 16 KiB |
|
@ -1,5 +1,4 @@
|
|||
REST principles
|
||||
===============
|
||||
::: REST principles
|
||||
|
||||
This chapter will attempt to define the concepts behind REST
|
||||
and explain what makes a service RESTful.
|
||||
|
@ -11,12 +10,11 @@ and POST methods. That's highly misguided at best.
|
|||
We will first attempt to define REST and will look at what
|
||||
it means in the context of HTTP and the Web.
|
||||
For a more in-depth explanation of REST, you can read
|
||||
[Roy T. Fielding's dissertation](http://www.ics.uci.edu/~fielding/pubs/dissertation/top.htm)
|
||||
^"Roy T. Fielding's dissertation^http://www.ics.uci.edu/~fielding/pubs/dissertation/top.htm
|
||||
as it does a great job explaining where it comes from and
|
||||
what it achieves.
|
||||
|
||||
REST architecture
|
||||
-----------------
|
||||
:: REST architecture
|
||||
|
||||
REST is a *client-server* architecture. The client and the server
|
||||
both have a different set of concerns. The server stores and/or
|
||||
|
@ -56,8 +54,7 @@ to extend client functionality. This is optional however because
|
|||
the client may not be able to download or run this code, and so
|
||||
a REST component cannot rely on it being executed.
|
||||
|
||||
Resources and resource identifiers
|
||||
----------------------------------
|
||||
:: Resources and resource identifiers
|
||||
|
||||
A resource is an abstract concept. In a REST system, any information
|
||||
that can be named may be a resource. This includes documents, images,
|
||||
|
@ -82,8 +79,7 @@ resources map to a set of one element, for example "user Joe".
|
|||
Collection of resources map to a set of 0 to N elements,
|
||||
for example "all users".
|
||||
|
||||
Resource representations
|
||||
------------------------
|
||||
:: Resource representations
|
||||
|
||||
The representation of a resource is a sequence of bytes associated
|
||||
with metadata.
|
||||
|
@ -115,8 +111,7 @@ type. Some media types are intended for direct rendering to the
|
|||
user, while others are intended for automated processing. The
|
||||
media type is a key component of the REST architecture.
|
||||
|
||||
Self-descriptive messages
|
||||
-------------------------
|
||||
:: Self-descriptive messages
|
||||
|
||||
Messages must be self-descriptive. That means that the data
|
||||
format of a representation must always come with its media
|
||||
|
@ -137,8 +132,7 @@ This means that you can create your own media types, like
|
|||
specifications for it and that both endpoints agree about
|
||||
it then the constraint is respected.
|
||||
|
||||
Hypermedia as the engine of application state
|
||||
---------------------------------------------
|
||||
:: Hypermedia as the engine of application state
|
||||
|
||||
The last constraint is generally where services that claim
|
||||
to be RESTful fail. Interactions with a server must be
|
Before Width: | Height: | Size: 214 KiB After Width: | Height: | Size: 214 KiB |
Before Width: | Height: | Size: 134 KiB After Width: | Height: | Size: 134 KiB |
Before Width: | Height: | Size: 115 KiB After Width: | Height: | Size: 115 KiB |
Before Width: | Height: | Size: 65 KiB After Width: | Height: | Size: 65 KiB |
|
@ -1,5 +1,4 @@
|
|||
Routing
|
||||
=======
|
||||
::: Routing
|
||||
|
||||
Cowboy does nothing by default.
|
||||
|
||||
|
@ -15,8 +14,7 @@ and then try to find a matching path.
|
|||
|
||||
Routes need to be compiled before they can be used by Cowboy.
|
||||
|
||||
Structure
|
||||
---------
|
||||
:: Structure
|
||||
|
||||
The general structure for the routes is defined as follow.
|
||||
|
||||
|
@ -51,8 +49,7 @@ Path2 = {PathMatch, Constraints, Handler, Opts}.
|
|||
Continue reading to learn more about the match syntax and the optional
|
||||
constraints.
|
||||
|
||||
Match syntax
|
||||
------------
|
||||
:: Match syntax
|
||||
|
||||
The match syntax is used to associate host names and paths with their
|
||||
respective handlers.
|
||||
|
@ -189,8 +186,7 @@ wildcard path, generally used alongside the `OPTIONS` method.
|
|||
HostMatch = "*".
|
||||
```
|
||||
|
||||
Constraints
|
||||
-----------
|
||||
:: Constraints
|
||||
|
||||
After the matching has completed, the resulting bindings can be tested
|
||||
against a set of constraints. Constraints are only tested when the
|
||||
|
@ -216,8 +212,7 @@ The value thus returned can be of any type.
|
|||
|
||||
Note that constraint functions SHOULD be pure and MUST NOT crash.
|
||||
|
||||
Compilation
|
||||
-----------
|
||||
:: Compilation
|
||||
|
||||
The structure defined in this chapter needs to be compiled before it is
|
||||
passed to Cowboy. This allows Cowboy to efficiently lookup the correct
|
||||
|
@ -240,8 +235,7 @@ cowboy:start_http(my_http_listener, 100,
|
|||
Note that this function will return `{error, badarg}` if the structure
|
||||
given is incorrect.
|
||||
|
||||
Live update
|
||||
-----------
|
||||
:: Live update
|
||||
|
||||
You can use the `cowboy:set_env/3` function for updating the dispatch
|
||||
list used by routing. This will apply to all new connections accepted
|
|
@ -1,5 +1,4 @@
|
|||
Static handler
|
||||
==============
|
||||
::: Static handler
|
||||
|
||||
The static handler is a built-in REST handler for serving files.
|
||||
It is available as a convenience and provides a quick solution
|
||||
|
@ -20,8 +19,7 @@ client-side caching.
|
|||
To use the static file handler, simply add routes for it
|
||||
with the appropriate options.
|
||||
|
||||
Serve one file
|
||||
--------------
|
||||
:: Serve one file
|
||||
|
||||
You can use the static handler to serve one specific file
|
||||
from an application's private directory. This is particularly
|
||||
|
@ -44,8 +42,7 @@ path to the file relative to the current directory.
|
|||
{"/", cowboy_static, {file, "/var/www/index.html"}}
|
||||
```
|
||||
|
||||
Serve all files from a directory
|
||||
--------------------------------
|
||||
:: Serve all files from a directory
|
||||
|
||||
You can also use the static handler to serve all files that
|
||||
can be found in the configured directory. The handler will
|
||||
|
@ -72,8 +69,7 @@ set it relative to the current directory.
|
|||
{"/assets/[...]", cowboy_static, {dir, "/var/www/assets"}}
|
||||
```
|
||||
|
||||
Customize the mimetype detection
|
||||
--------------------------------
|
||||
:: Customize the mimetype detection
|
||||
|
||||
By default, Cowboy will attempt to recognize the mimetype
|
||||
of your static files by looking at the extension.
|
||||
|
@ -141,8 +137,7 @@ and `priv_file` options as it avoids needless computation.
|
|||
[{mimetypes, {<<"text">>, <<"html">>, []}}]}}
|
||||
```
|
||||
|
||||
Generate an etag
|
||||
----------------
|
||||
:: Generate an etag
|
||||
|
||||
By default, the static handler will generate an etag header
|
||||
value based on the size and modified time. This solution
|
|
@ -1,5 +1,4 @@
|
|||
Protocol upgrades
|
||||
=================
|
||||
::: Protocol upgrades
|
||||
|
||||
Cowboy features many different handlers, each for different purposes.
|
||||
All handlers have a common entry point: the `init/3` function.
|
|
@ -1,5 +1,4 @@
|
|||
Handling Websocket connections
|
||||
==============================
|
||||
::: Handling Websocket connections
|
||||
|
||||
A special handler is required for handling Websocket connections.
|
||||
Websocket handlers allow you to initialize the connection,
|
||||
|
@ -10,8 +9,7 @@ Websocket handlers essentially act as a bridge between the client
|
|||
and the Erlang system. They will typically do little more than
|
||||
socket communication and decoding/encoding of frames.
|
||||
|
||||
Initialization
|
||||
--------------
|
||||
:: Initialization
|
||||
|
||||
First, the `init/3` callback is called. This callback is common
|
||||
to all handlers. To establish a Websocket connection, this function
|
||||
|
@ -105,8 +103,7 @@ websocket_info(post_init, Req, State) ->
|
|||
{ok, Req, State}.
|
||||
```
|
||||
|
||||
Handling frames from the client
|
||||
-------------------------------
|
||||
:: Handling frames from the client
|
||||
|
||||
Cowboy will call `websocket_handle/3` whenever a text, binary,
|
||||
ping or pong frame arrives from the client. Note that in the
|
||||
|
@ -126,8 +123,7 @@ websocket_handle(_Frame, Req, State) ->
|
|||
{ok, Req, State}.
|
||||
```
|
||||
|
||||
Handling Erlang messages
|
||||
------------------------
|
||||
:: Handling Erlang messages
|
||||
|
||||
Cowboy will call `websocket_info/3` whenever an Erlang message
|
||||
arrives.
|
||||
|
@ -145,8 +141,7 @@ websocket_info(_Info, Req, State) ->
|
|||
{ok, Req, State}.
|
||||
```
|
||||
|
||||
Sending frames to the socket
|
||||
----------------------------
|
||||
:: Sending frames to the socket
|
||||
|
||||
Cowboy allows sending either a single frame or a list of
|
||||
frames to the socket. Any frame can be sent: text, binary, ping,
|
||||
|
@ -176,8 +171,7 @@ be received will not be processed. Also note that when replying
|
|||
a list of frames that includes close, any frame found after the
|
||||
close frame will not be sent.
|
||||
|
||||
Ping and timeout
|
||||
----------------
|
||||
:: Ping and timeout
|
||||
|
||||
The biggest performance improvement you can do when dealing
|
||||
with a huge number of Websocket connections is to reduce the
|
||||
|
@ -208,8 +202,7 @@ websocket_init(_Type, Req, _Opts) ->
|
|||
This value cannot be changed once it is set. It defaults to
|
||||
`infinity`.
|
||||
|
||||
Hibernate
|
||||
---------
|
||||
:: Hibernate
|
||||
|
||||
Most tuples returned from handler callbacks can include an
|
||||
extra value `hibernate`. After doing any necessary operations
|
||||
|
@ -221,10 +214,9 @@ handle much traffic. It is a good idea to hibernate all
|
|||
connections by default and investigate only when you start
|
||||
noticing increased CPU usage.
|
||||
|
||||
Supporting older browsers
|
||||
-------------------------
|
||||
:: Supporting older browsers
|
||||
|
||||
Unfortunately Websocket is a relatively recent technology,
|
||||
which means that not all browsers support it. A library like
|
||||
[Bullet](https://github.com/extend/bullet) can be used to
|
||||
^"Bullet^https://github.com/extend/bullet^ can be used to
|
||||
emulate Websocket connections on older browsers.
|
|
@ -1,11 +1,9 @@
|
|||
The Websocket protocol
|
||||
======================
|
||||
::: The Websocket protocol
|
||||
|
||||
This chapter explains what Websocket is and why it is
|
||||
a vital component of soft realtime Web applications.
|
||||
|
||||
Description
|
||||
-----------
|
||||
:: Description
|
||||
|
||||
Websocket is an extension to HTTP that emulates plain TCP
|
||||
connections between the client, typically a Web browser,
|
||||
|
@ -24,8 +22,7 @@ and all drafts that were previously implemented by browsers,
|
|||
excluding the initial flawed draft sometimes known as
|
||||
"version 0".
|
||||
|
||||
Implementation
|
||||
--------------
|
||||
:: Implementation
|
||||
|
||||
Cowboy implements Websocket as a protocol upgrade. Once the
|
||||
upgrade is performed from the `init/3` callback, Cowboy
|
101
doc/src/manual/cowboy.ezdoc
Normal file
|
@ -0,0 +1,101 @@
|
|||
::: cowboy
|
||||
|
||||
The `cowboy` module provides convenience functions for
|
||||
manipulating Ranch listeners.
|
||||
|
||||
:: Types
|
||||
|
||||
: http_headers() = [{binary(), iodata()}]
|
||||
|
||||
HTTP headers as a list of key/values.
|
||||
|
||||
: http_status() = non_neg_integer() | binary()
|
||||
|
||||
HTTP status.
|
||||
|
||||
A binary status can be used to set a custom message.
|
||||
|
||||
: http_version() = 'HTTP/1.1' | 'HTTP/1.0'
|
||||
|
||||
HTTP version.
|
||||
|
||||
: onrequest_fun() = fun((cowboy_req:req()) -> cowboy_req:req())
|
||||
|
||||
Fun called immediately after receiving a request.
|
||||
|
||||
It can perform any operation on the Req object, including
|
||||
reading the request body or replying. If a reply is sent,
|
||||
the processing of the request ends here, before any middleware
|
||||
is executed.
|
||||
|
||||
: onresponse_fun() = fun((http_status(), http_headers(),
|
||||
iodata(), cowboy_req:req()) -> cowboy_req:req())
|
||||
|
||||
Fun called immediately before sending the response.
|
||||
|
||||
It can perform any operation on the Req object, including
|
||||
reading the request body or replying. If a reply is sent, it
|
||||
overrides the reply initially sent. The callback will not be
|
||||
called again for the new reply.
|
||||
|
||||
:: Exports
|
||||
|
||||
: start_http(Ref, NbAcceptors, TransOpts, ProtoOpts) -> {ok, pid()}
|
||||
|
||||
Types:
|
||||
|
||||
* Ref = ranch:ref()
|
||||
* NbAcceptors = non_neg_integer()
|
||||
* TransOpts = ranch_tcp:opts()
|
||||
* ProtoOpts = cowboy_protocol:opts()
|
||||
|
||||
Start listening for HTTP connections. Returns the pid for this
|
||||
listener's supervisor.
|
||||
|
||||
: start_https(Ref, NbAcceptors, TransOpts, ProtoOpts) -> {ok, pid()}
|
||||
|
||||
Types:
|
||||
|
||||
* Ref = ranch:ref()
|
||||
* NbAcceptors = non_neg_integer()
|
||||
* TransOpts = ranch_ssl:opts()
|
||||
* ProtoOpts = cowboy_protocol:opts()
|
||||
|
||||
Start listening for HTTPS connections. Returns the pid for this
|
||||
listener's supervisor.
|
||||
|
||||
: start_spdy(Ref, NbAcceptors, TransOpts, ProtoOpts) -> {ok, pid()}
|
||||
|
||||
Types:
|
||||
|
||||
* Ref = ranch:ref()
|
||||
* NbAcceptors = non_neg_integer()
|
||||
* TransOpts = ranch_ssl:opts()
|
||||
* ProtoOpts = cowboy_spdy:opts()
|
||||
|
||||
Start listening for SPDY connections. Returns the pid for this
|
||||
listener's supervisor.
|
||||
|
||||
: stop_listener(Ref) -> ok | {error, not_found}
|
||||
|
||||
Types:
|
||||
|
||||
* Ref = ranch:ref()
|
||||
|
||||
Stop a previously started listener.
|
||||
|
||||
: set_env(Ref, Name, Value) -> ok
|
||||
|
||||
Types:
|
||||
|
||||
* Ref = ranch:ref()
|
||||
* Name = atom()
|
||||
* Value = any()
|
||||
|
||||
Set or update an environment value for an already running listener.
|
||||
This will take effect on all subsequent connections.
|
||||
|
||||
:: See also
|
||||
|
||||
The ^"Ranch guide^http://ninenines.eu/docs/en/ranch/HEAD/guide
|
||||
provides detailed information about how listeners work.
|
|
@ -1,10 +1,8 @@
|
|||
The Cowboy Application
|
||||
======================
|
||||
::: The Cowboy Application
|
||||
|
||||
Small, fast, modular HTTP server.
|
||||
|
||||
Dependencies
|
||||
------------
|
||||
:: Dependencies
|
||||
|
||||
The `cowboy` application uses the Erlang applications `ranch`
|
||||
for listening and accepting TCP connections, `crypto` for
|
||||
|
@ -19,8 +17,7 @@ The `cowboy` application also uses the Erlang applications
|
|||
`asn1`, `public_key` and `ssl` when listening for HTTPS connections.
|
||||
These are started automatically if they weren't before.
|
||||
|
||||
Environment
|
||||
-----------
|
||||
:: Environment
|
||||
|
||||
The `cowboy` application does not define any application
|
||||
environment configuration parameters.
|
|
@ -1,25 +1,24 @@
|
|||
cowboy_handler
|
||||
==============
|
||||
::: cowboy_handler
|
||||
|
||||
The `cowboy_handler` middleware executes the handler passed
|
||||
through the environment values `handler` and `handler_opts`,
|
||||
and add the result of this execution to the environment as
|
||||
and adds the result of this execution to the environment as
|
||||
the value `result`, indicating that the request has been
|
||||
handled and received a response.
|
||||
|
||||
Environment input:
|
||||
|
||||
* handler = module()
|
||||
* handler_opts = any()
|
||||
|
||||
Environment output:
|
||||
|
||||
* result = ok
|
||||
|
||||
Types
|
||||
-----
|
||||
:: Types
|
||||
|
||||
None.
|
||||
|
||||
Exports
|
||||
-------
|
||||
:: Exports
|
||||
|
||||
None.
|
57
doc/src/manual/cowboy_http_handler.ezdoc
Normal file
|
@ -0,0 +1,57 @@
|
|||
::: cowboy_http_handler
|
||||
|
||||
The `cowboy_http_handler` behaviour defines the interface used
|
||||
by plain HTTP handlers.
|
||||
|
||||
Unless noted otherwise, the callbacks will be executed sequentially.
|
||||
|
||||
:: Types
|
||||
|
||||
None.
|
||||
|
||||
:: Callbacks
|
||||
|
||||
: init({TransportName, ProtocolName}, Req, Opts)
|
||||
-> {ok, Req, State} | {shutdown, Req, State}
|
||||
|
||||
Types:
|
||||
|
||||
* TransportName = tcp | ssl | atom()
|
||||
* ProtocolName = http | atom()
|
||||
* Req = cowboy_req:req()
|
||||
* Opts = any()
|
||||
* State = any()
|
||||
|
||||
Initialize the state for this request.
|
||||
|
||||
The `shutdown` return value can be used to skip the `handle/2`
|
||||
call entirely.
|
||||
|
||||
: handle(Req, State) -> {ok, Req, State}
|
||||
|
||||
Types:
|
||||
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
|
||||
Handle the request.
|
||||
|
||||
This callback is where the request is handled and a response
|
||||
should be sent. If a response is not sent, Cowboy will send
|
||||
a `204 No Content` response automatically.
|
||||
|
||||
: terminate(Reason, Req, State) -> ok
|
||||
|
||||
Types:
|
||||
|
||||
* Reason = {normal, shutdown} | {error, atom()}
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
|
||||
Perform any necessary cleanup of the state.
|
||||
|
||||
This callback should release any resource currently in use,
|
||||
clear any active timer and reset the process to its original
|
||||
state, as it might be reused for future requests sent on the
|
||||
same connection. Typical plain HTTP handlers rarely need to
|
||||
use it.
|
91
doc/src/manual/cowboy_loop_handler.ezdoc
Normal file
|
@ -0,0 +1,91 @@
|
|||
::: cowboy_loop_handler
|
||||
|
||||
The `cowboy_loop_handler` behaviour defines the interface used
|
||||
by HTTP handlers that do not send a response directly, instead
|
||||
requiring a receive loop to process Erlang messages.
|
||||
|
||||
This interface is best fit for long-polling types of requests.
|
||||
|
||||
The `init/3` callback will always be called, followed by zero
|
||||
or more calls to `info/3`. The `terminate/3` callback will
|
||||
always be called last.
|
||||
|
||||
:: Types
|
||||
|
||||
None.
|
||||
|
||||
:: Callbacks
|
||||
|
||||
: init({TransportName, ProtocolName}, Req, Opts)
|
||||
-> {loop, Req, State}
|
||||
| {loop, Req, State, hibernate}
|
||||
| {loop, Req, State, Timeout}
|
||||
| {loop, Req, State, Timeout, hibernate}
|
||||
| {shutdown, Req, State}
|
||||
|
||||
Types:
|
||||
|
||||
* TransportName = tcp | ssl | atom()
|
||||
* ProtocolName = http | atom()
|
||||
* Req = cowboy_req:req()
|
||||
* Opts = any()
|
||||
* State = any()
|
||||
* Timeout = timeout()
|
||||
|
||||
Initialize the state for this request.
|
||||
|
||||
This callback will typically be used to register this process
|
||||
to an event manager or a message queue in order to receive
|
||||
the messages the handler wants to process.
|
||||
|
||||
The receive loop will run for a duration of up to `Timeout`
|
||||
milliseconds after it last received data from the socket,
|
||||
at which point it will stop and send a `204 No Content` reply.
|
||||
By default this value is set to `infinity`. It is recommended
|
||||
to either set this value or ensure by any other mechanism
|
||||
that the handler will be closed after a certain period of
|
||||
inactivity.
|
||||
|
||||
The `hibernate` option will hibernate the process until it
|
||||
starts receiving messages.
|
||||
|
||||
The `shutdown` return value can be used to skip the receive
|
||||
loop entirely.
|
||||
|
||||
: info(Info, Req, State) -> {ok, Req, State} | {loop, Req, State}
|
||||
| {loop, Req, State, hibernate}
|
||||
|
||||
Types:
|
||||
|
||||
* Info = any()
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
|
||||
Handle the Erlang message received.
|
||||
|
||||
This function will be called every time an Erlang message
|
||||
has been received. The message can be any Erlang term.
|
||||
|
||||
The `ok` return value can be used to stop the receive loop,
|
||||
typically because a response has been sent.
|
||||
|
||||
The `hibernate` option will hibernate the process until
|
||||
it receives another message.
|
||||
|
||||
: terminate(Reason, Req, State) -> ok
|
||||
|
||||
Types:
|
||||
|
||||
* Reason = {normal, shutdown} | {normal, timeout} | {error, closed} | {error, overflow} | {error, atom()}
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
|
||||
Perform any necessary cleanup of the state.
|
||||
|
||||
This callback will typically unregister from any event manager
|
||||
or message queue it registered to in `init/3`.
|
||||
|
||||
This callback should release any resource currently in use,
|
||||
clear any active timer and reset the process to its original
|
||||
state, as it might be reused for future requests sent on the
|
||||
same connection.
|
54
doc/src/manual/cowboy_middleware.ezdoc
Normal file
|
@ -0,0 +1,54 @@
|
|||
::: cowboy_middleware
|
||||
|
||||
The `cowboy_middleware` behaviour defines the interface used
|
||||
by Cowboy middleware modules.
|
||||
|
||||
Middlewares process the request sequentially in the order they
|
||||
are configured.
|
||||
|
||||
:: Types
|
||||
|
||||
: env() = [{atom(), any()}]
|
||||
|
||||
The environment variable.
|
||||
|
||||
One is created for every request. It is passed to each
|
||||
middleware module executed and subsequently returned,
|
||||
optionally with its contents modified.
|
||||
|
||||
:: Callbacks
|
||||
|
||||
: execute(Req, Env)
|
||||
-> {ok, Req, Env}
|
||||
| {suspend, Module, Function, Args}
|
||||
| {halt, Req}
|
||||
| {error, StatusCode, Req}
|
||||
|
||||
Types:
|
||||
|
||||
* Req = cowboy_req:req()
|
||||
* Env = env()
|
||||
* Module = module()
|
||||
* Function = atom()
|
||||
* Args = [any()]
|
||||
* StatusCode = cowboy:http_status()
|
||||
|
||||
Execute the middleware.
|
||||
|
||||
The `ok` return value indicates that everything went well
|
||||
and that Cowboy should continue processing the request. A
|
||||
response may or may not have been sent.
|
||||
|
||||
The `suspend` return value will hibernate the process until
|
||||
an Erlang message is received. Note that when resuming, any
|
||||
previous stacktrace information will be gone.
|
||||
|
||||
The `halt` return value stops Cowboy from doing any further
|
||||
processing of the request, even if there are middlewares
|
||||
that haven't been executed yet. The connection may be left
|
||||
open to receive more requests from the client.
|
||||
|
||||
The `error` return value sends an error response identified
|
||||
by the `StatusCode` and then proceeds to terminate the
|
||||
connection. Middlewares that haven't been executed yet
|
||||
will not be called.
|
84
doc/src/manual/cowboy_protocol.ezdoc
Normal file
|
@ -0,0 +1,84 @@
|
|||
::: cowboy_protocol
|
||||
|
||||
The `cowboy_protocol` module implements HTTP/1.1 and HTTP/1.0
|
||||
as a Ranch protocol.
|
||||
|
||||
:: Types
|
||||
|
||||
: opts() = [{compress, boolean()}
|
||||
| {env, cowboy_middleware:env()}
|
||||
| {max_empty_lines, non_neg_integer()}
|
||||
| {max_header_name_length, non_neg_integer()}
|
||||
| {max_header_value_length, non_neg_integer()}
|
||||
| {max_headers, non_neg_integer()}
|
||||
| {max_keepalive, non_neg_integer()}
|
||||
| {max_request_line_length, non_neg_integer()}
|
||||
| {middlewares, [module()]}
|
||||
| {onrequest, cowboy:onrequest_fun()}
|
||||
| {onresponse, cowboy:onresponse_fun()}
|
||||
| {timeout, timeout()}]
|
||||
|
||||
Configuration for the HTTP protocol handler.
|
||||
|
||||
This configuration is passed to Cowboy when starting listeners
|
||||
using `cowboy:start_http/4` or `cowboy:start_https/4` functions.
|
||||
|
||||
It can be updated without restarting listeners using the
|
||||
Ranch functions `ranch:get_protocol_options/1` and
|
||||
`ranch:set_protocol_options/2`.
|
||||
|
||||
:: Option descriptions
|
||||
|
||||
The default value is given next to the option name.
|
||||
|
||||
: compress (false)
|
||||
|
||||
When enabled, Cowboy will attempt to compress the response body.
|
||||
|
||||
: env ([{listener, Ref}])
|
||||
|
||||
Initial middleware environment.
|
||||
|
||||
: max_empty_lines (5)
|
||||
|
||||
Maximum number of empty lines before a request.
|
||||
|
||||
: max_header_name_length (64)
|
||||
|
||||
Maximum length of header names.
|
||||
|
||||
: max_header_value_length (4096)
|
||||
|
||||
Maximum length of header values.
|
||||
|
||||
: max_headers (100)
|
||||
|
||||
Maximum number of headers allowed per request.
|
||||
|
||||
: max_keepalive (100)
|
||||
|
||||
Maximum number of requests allowed per connection.
|
||||
|
||||
: max_request_line_length (4096)
|
||||
|
||||
Maximum length of the request line.
|
||||
|
||||
: middlewares ([cowboy_router, cowboy_handler])
|
||||
|
||||
List of middlewares to execute for every requests.
|
||||
|
||||
: onrequest (undefined)
|
||||
|
||||
Fun called every time a request is received.
|
||||
|
||||
: onresponse (undefined)
|
||||
|
||||
Fun called every time a response is sent.
|
||||
|
||||
: timeout (5000)
|
||||
|
||||
Time in ms with no requests before Cowboy closes the connection.
|
||||
|
||||
:: Exports
|
||||
|
||||
None.
|
704
doc/src/manual/cowboy_req.ezdoc
Normal file
|
@ -0,0 +1,704 @@
|
|||
::: cowboy_req
|
||||
|
||||
The `cowboy_req` module provides functions to access, manipulate
|
||||
and respond to requests.
|
||||
|
||||
The functions in this module follow patterns for their return types,
|
||||
based on the kind of function.
|
||||
|
||||
* access: `{Value, Req}`
|
||||
* action: `{Result, Req} | {Result, Value, Req} | {error, atom()}`
|
||||
* modification: `Req`
|
||||
* question: `boolean()`
|
||||
|
||||
The only exception is the `chunk/2` function which may return `ok`.
|
||||
|
||||
Whenever `Req` is returned, you must use this returned value and
|
||||
ignore any previous you may have had. This value contains various
|
||||
state informations which are necessary for Cowboy to do some lazy
|
||||
evaluation or cache results where appropriate.
|
||||
|
||||
All functions which perform an action should only be called once.
|
||||
This includes reading the request body or replying. Cowboy will
|
||||
generally throw an error on the second call.
|
||||
|
||||
It is highly discouraged to pass the Req object to another process.
|
||||
Doing so and calling `cowboy_req` functions from it leads to
|
||||
undefined behavior.
|
||||
|
||||
:: Types
|
||||
|
||||
: body_opts() = [{continue, boolean()}
|
||||
| {length, non_neg_integer()}
|
||||
| {read_length, non_neg_integer()}
|
||||
| {read_timeout, timeout()}
|
||||
| {transfer_decode, transfer_decode_fun(), any()}
|
||||
| {content_decode, content_decode_fun()}]
|
||||
|
||||
Request body reading options.
|
||||
|
||||
: cookie_opts() = [{max_age, non_neg_integer()}
|
||||
| {domain, binary()} | {path, binary()}
|
||||
| {secure, boolean()} | {http_only, boolean()}]
|
||||
|
||||
Cookie options.
|
||||
|
||||
: req() - opaque to the user
|
||||
|
||||
The Req object.
|
||||
|
||||
All functions in this module receive a `Req` as argument,
|
||||
and most of them return a new object labelled `Req2` in
|
||||
the function descriptions below.
|
||||
|
||||
:: Request related exports
|
||||
|
||||
: binding(Name, Req) -> binding(Name, Req, undefined)
|
||||
: binding(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = atom()
|
||||
* Default = any()
|
||||
* Value = any() | Default
|
||||
|
||||
Return the value for the given binding.
|
||||
|
||||
By default the value is a binary, however constraints may change
|
||||
the type of this value (for example automatically converting
|
||||
numbers to integer).
|
||||
|
||||
: bindings(Req) -> {[{Name, Value}], Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = atom()
|
||||
* Value = any()
|
||||
|
||||
Return all bindings.
|
||||
|
||||
By default the value is a binary, however constraints may change
|
||||
the type of this value (for example automatically converting
|
||||
numbers to integer).
|
||||
|
||||
: cookie(Name, Req) -> cookie(Name, Req, undefined)
|
||||
: cookie(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
* Default = any()
|
||||
* Value = binary() | Default
|
||||
|
||||
Return the value for the given cookie.
|
||||
|
||||
Cookie names are case sensitive.
|
||||
|
||||
: cookies(Req) -> {[{Name, Value}], Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
* Value = binary()
|
||||
|
||||
Return all cookies.
|
||||
|
||||
: header(Name, Req) -> header(Name, Req, undefined)
|
||||
: header(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
* Default = any()
|
||||
* Value = binary() | Default
|
||||
|
||||
Return the value for the given header.
|
||||
|
||||
While header names are case insensitive, this function expects
|
||||
the name to be a lowercase binary.
|
||||
|
||||
: headers(Req) -> {Headers, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Headers = cowboy:http_headers()
|
||||
|
||||
Return all headers.
|
||||
|
||||
: host(Req) -> {Host, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Host = binary()
|
||||
|
||||
Return the requested host.
|
||||
|
||||
: host_info(Req) -> {HostInfo, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* HostInfo = cowboy_router:tokens() | undefined
|
||||
|
||||
Return the extra tokens from matching against `...` during routing.
|
||||
|
||||
: host_url(Req) -> {HostURL, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* HostURL = binary() | undefined
|
||||
|
||||
Return the requested URL excluding the path component.
|
||||
|
||||
This function will always return `undefined` until the
|
||||
`cowboy_router` middleware has been executed. This includes
|
||||
the `onrequest` hook.
|
||||
|
||||
: meta(Name, Req) -> meta(Name, Req, undefined)
|
||||
: meta(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = atom()
|
||||
* Default = any()
|
||||
* Value = any()
|
||||
|
||||
Return metadata about the request.
|
||||
|
||||
: method(Req) -> {Method, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Method = binary()
|
||||
|
||||
Return the method.
|
||||
|
||||
Methods are case sensitive. Standard methods are always uppercase.
|
||||
|
||||
: parse_header(Name, Req) ->
|
||||
: parse_header(Name, Req, Default) -> {ok, ParsedValue, Req2}
|
||||
| {undefined, Value, Req2} | {error, badarg}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
* Default = any()
|
||||
* ParsedValue - see below
|
||||
* Value = any()
|
||||
|
||||
Parse the given header.
|
||||
|
||||
While header names are case insensitive, this function expects
|
||||
the name to be a lowercase binary.
|
||||
|
||||
The `parse_header/2` function will call `parser_header/3` with a
|
||||
different default value depending on the header being parsed. The
|
||||
following table summarizes the default values used.
|
||||
|
||||
|| Header name Default value
|
||||
|
|
||||
| transfer-encoding `[<<"identity">>]`
|
||||
| Any other header `undefined`
|
||||
|
||||
The parsed value differs depending on the header being parsed. The
|
||||
following table summarizes the different types returned.
|
||||
|
||||
|| Header name Type
|
||||
|
|
||||
| accept `[{{Type, SubType, Params}, Quality, AcceptExt}]`
|
||||
| accept-charset `[{Charset, Quality}]`
|
||||
| accept-encoding `[{Encoding, Quality}]`
|
||||
| accept-language `[{LanguageTag, Quality}]`
|
||||
| authorization `{AuthType, Credentials}`
|
||||
| content-length `non_neg_integer()`
|
||||
| content-type `{Type, SubType, ContentTypeParams}`
|
||||
| cookie `[{binary(), binary()}]`
|
||||
| expect `[Expect | {Expect, ExpectValue, Params}]`
|
||||
| if-match `'*' | [{weak | strong, OpaqueTag}]`
|
||||
| if-modified-since `calendar:datetime()`
|
||||
| if-none-match `'*' | [{weak | strong, OpaqueTag}]`
|
||||
| if-unmodified-since `calendar:datetime()`
|
||||
| range `{Unit, [Range]}`
|
||||
| sec-websocket-protocol `[binary()]`
|
||||
| transfer-encoding `[binary()]`
|
||||
| upgrade `[binary()]`
|
||||
| x-forwarded-for `[binary()]`
|
||||
|
||||
Types for the above table:
|
||||
|
||||
* Type = SubType = Charset = Encoding = LanguageTag = binary()
|
||||
* AuthType = Expect = OpaqueTag = Unit = binary()
|
||||
* Params = ContentTypeParams = [{binary(), binary()}]
|
||||
* Quality = 0..1000
|
||||
* AcceptExt = [{binary(), binary()} | binary()]
|
||||
* Credentials - see below
|
||||
* Range = {non_neg_integer(), non_neg_integer() | infinity} | neg_integer()
|
||||
|
||||
The cookie names and values, the values of the sec-websocket-protocol
|
||||
and x-forwarded-for headers, the values in `AcceptExt` and `Params`,
|
||||
the authorization `Credentials`, the `ExpectValue` and `OpaqueTag`
|
||||
are case sensitive. All values in `ContentTypeParams` are case sensitive
|
||||
except the value of the charset parameter, which is case insensitive.
|
||||
All other values are case insensitive and will be returned as lowercase.
|
||||
|
||||
The headers accept, accept-encoding and cookie headers can return
|
||||
an empty list. Others will return `{error, badarg}` if the header
|
||||
value is empty.
|
||||
|
||||
The authorization header parsing code currently only supports basic
|
||||
HTTP authentication. The `Credentials` type is thus `{Username, Password}`
|
||||
with `Username` and `Password` being `binary()`.
|
||||
|
||||
The range header value `Range` can take three forms:
|
||||
|
||||
* `{From, To}`: from `From` to `To` units
|
||||
* `{From, infinity}`: everything after `From` units
|
||||
* `-Final`: the final `Final` units
|
||||
|
||||
An `undefined` tuple will be returned if Cowboy doesn't know how
|
||||
to parse the requested header.
|
||||
|
||||
: path(Req) -> {Path, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Path = binary()
|
||||
|
||||
Return the requested path.
|
||||
|
||||
: path_info(Req) -> {PathInfo, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* PathInfo = cowboy_router:tokens() | undefined
|
||||
|
||||
Return the extra tokens from matching against `...` during routing.
|
||||
|
||||
: peer(Req) -> {Peer, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Peer = {inet:ip_address(), inet:port_number()}
|
||||
|
||||
Return the client's IP address and port number.
|
||||
|
||||
: port(Req) -> {Port, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Port = inet:port_number()
|
||||
|
||||
Return the request's port.
|
||||
|
||||
The port returned by this function is obtained by parsing
|
||||
the host header. It may be different than the actual port
|
||||
the client used to connect to the Cowboy server.
|
||||
|
||||
: qs(Req) -> {QueryString, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* QueryString = binary()
|
||||
|
||||
Return the request's query string.
|
||||
|
||||
: qs_val(Name, Req) -> qs_val(Name, Req, undefined)
|
||||
: qs_val(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
* Default = any()
|
||||
* Value = binary() | true
|
||||
|
||||
Return a value from the request's query string.
|
||||
|
||||
The value `true` will be returned when the name was found
|
||||
in the query string without an associated value.
|
||||
|
||||
: qs_vals(Req) -> {[{Name, Value}], Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
* Value = binary() | true
|
||||
|
||||
Return the request's query string as a list of tuples.
|
||||
|
||||
The value `true` will be returned when a name was found
|
||||
in the query string without an associated value.
|
||||
|
||||
: set_meta(Name, Value, Req) -> Req2
|
||||
|
||||
Types:
|
||||
|
||||
* Name = atom()
|
||||
* Value = any()
|
||||
|
||||
Set metadata about the request.
|
||||
|
||||
An existing value will be overwritten.
|
||||
|
||||
: url(Req) -> {URL, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* URL = binary() | undefined
|
||||
|
||||
Return the requested URL.
|
||||
|
||||
This function will always return `undefined` until the
|
||||
`cowboy_router` middleware has been executed. This includes
|
||||
the `onrequest` hook.
|
||||
|
||||
: version(Req) -> {Version, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Version = cowboy:http_version()
|
||||
|
||||
Return the HTTP version used for this request.
|
||||
|
||||
:: Request body related exports
|
||||
|
||||
: body(Req) -> body(Req, [])
|
||||
: body(Req, Opts) -> {ok, Data, Req2} | {more, Data, Req2} | {error, Reason}
|
||||
|
||||
Types:
|
||||
|
||||
* Opts = [body_opt()]
|
||||
* Data = binary()
|
||||
* Reason = atom()
|
||||
|
||||
Read the request body.
|
||||
|
||||
This function will read a chunk of the request body. If there is
|
||||
more data to be read after this function call, then a `more` tuple
|
||||
is returned. Otherwise an `ok` tuple is returned.
|
||||
|
||||
Cowboy will automatically send a `100 Continue` reply if
|
||||
required. If this behavior is not desirable, it can be disabled
|
||||
by setting the `continue` option to `false`.
|
||||
|
||||
Cowboy will by default attempt to read up to 8MB of the body,
|
||||
but in chunks of 1MB. It will use a timeout of 15s per chunk.
|
||||
All these values can be changed using the `length`, `read_length`
|
||||
and `read_timeout` options respectively. Note that the size
|
||||
of the data may not be the same as requested as the decoding
|
||||
functions may grow or shrink it, and Cowboy makes not attempt
|
||||
at returning an exact amount.
|
||||
|
||||
Cowboy will properly handle chunked transfer-encoding by
|
||||
default. If any other transfer-encoding or content-encoding
|
||||
has been used for the request, custom decoding functions
|
||||
can be used. The `content_decode` and `transfer_decode`
|
||||
options allow setting the decode functions manually.
|
||||
|
||||
After the body has been streamed fully, Cowboy will remove
|
||||
the transfer-encoding header from the Req object, and add
|
||||
the content-length header if it wasn't already there.
|
||||
|
||||
This function can only be called once. Cowboy will not cache
|
||||
the result of this call.
|
||||
|
||||
: body_length(Req) -> {Length, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Length = non_neg_integer() | undefined
|
||||
|
||||
Return the length of the request body.
|
||||
|
||||
The length will only be returned if the request does not
|
||||
use any transfer-encoding and if the content-length header
|
||||
is present.
|
||||
|
||||
: body_qs(Req) -> body_qs(Req,
|
||||
[{length, 64000}, {read_length, 64000}, {read_timeout, 5000}])
|
||||
: body_qs(Req, Opts) -> {ok, [{Name, Value}], Req2}
|
||||
| {badlength, Req2} | {error, Reason}
|
||||
|
||||
Types:
|
||||
|
||||
* Opts = [body_opt()]
|
||||
* Name = binary()
|
||||
* Value = binary() | true
|
||||
* Reason = chunked | badlength | atom()
|
||||
|
||||
Return the request body as a list of tuples.
|
||||
|
||||
This function will parse the body assuming the content-type
|
||||
application/x-www-form-urlencoded, commonly used for the
|
||||
query string.
|
||||
|
||||
This function calls `body/2` for reading the body, with the
|
||||
same options it received. By default it will attempt to read
|
||||
a body of 64KB in one chunk, with a timeout of 5s. If the
|
||||
body is larger then a `badlength` tuple is returned.
|
||||
|
||||
This function can only be called once. Cowboy will not cache
|
||||
the result of this call.
|
||||
|
||||
: has_body(Req) -> boolean()
|
||||
|
||||
Return whether the request has a body.
|
||||
|
||||
: part(Req) -> part(Req,
|
||||
[{length, 64000}, {read_length, 64000}, {read_timeout, 5000}])
|
||||
: part(Req, Opts) -> {ok, Headers, Req2} | {done, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Opts = [body_opt()]
|
||||
* Headers = cow_multipart:headers()
|
||||
|
||||
Read the headers for the next part of the multipart message.
|
||||
|
||||
Cowboy will skip any data remaining until the beginning of
|
||||
the next part. This includes the preamble to the multipart
|
||||
message but also the body of a previous part if it hasn't
|
||||
been read. Both are skipped automatically when calling this
|
||||
function.
|
||||
|
||||
The headers returned are MIME headers, NOT HTTP headers.
|
||||
They can be parsed using the functions from the `cow_multipart`
|
||||
module. In addition, the `cow_multipart:form_data/1` function
|
||||
can be used to quickly figure out `multipart/form-data` messages.
|
||||
It takes the list of headers and returns whether this part is
|
||||
a simple form field or a file being uploaded.
|
||||
|
||||
Note that once a part has been read, or skipped, it cannot
|
||||
be read again.
|
||||
|
||||
This function calls `body/2` for reading the body, with the
|
||||
same options it received. By default it will only read chunks
|
||||
of 64KB with a timeout of 5s. This is tailored for reading
|
||||
part headers, not for skipping the previous part's body.
|
||||
You might want to consider skipping large parts manually.
|
||||
|
||||
: part_body(Req) -> part_body(Req, [])
|
||||
: part_body(Req, Opts) -> {ok, Data, Req2} | {more, Data, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* Opts = [body_opt()]
|
||||
* Data = binary()
|
||||
|
||||
Read the body of the current part of the multipart message.
|
||||
|
||||
This function calls `body/2` for reading the body, with the
|
||||
same options it received. It uses the same defaults.
|
||||
|
||||
If there are more data to be read from the socket for this
|
||||
part, the function will return what it could read inside a
|
||||
`more` tuple. Otherwise, it will return an `ok` tuple.
|
||||
|
||||
Calling this function again after receiving a `more` tuple
|
||||
will return another chunk of body. The last chunk will be
|
||||
returned inside an `ok` tuple.
|
||||
|
||||
Note that once the body has been read, fully or partially,
|
||||
it cannot be read again.
|
||||
|
||||
:: Response related exports
|
||||
|
||||
: chunk(Data, Req) -> ok | {error, Reason}
|
||||
|
||||
Types:
|
||||
|
||||
* Data = iodata()
|
||||
* Reason = atom()
|
||||
|
||||
Send a chunk of data.
|
||||
|
||||
This function should be called as many times as needed
|
||||
to send data chunks after calling `chunked_reply/{2,3}`.
|
||||
|
||||
When the method is HEAD, no data will actually be sent.
|
||||
|
||||
If the request uses HTTP/1.0, the data is sent directly
|
||||
without wrapping it in an HTTP/1.1 chunk, providing
|
||||
compatibility with older clients.
|
||||
|
||||
: chunked_reply(StatusCode, Req) -> chunked_reply(StatusCode, [], Req)
|
||||
: chunked_reply(StatusCode, Headers, Req) -> {ok, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* StatusCode = cowboy:http_status()
|
||||
* Headers = cowboy:http_headers()
|
||||
|
||||
Send a response using chunked transfer-encoding.
|
||||
|
||||
This function effectively sends the response status line
|
||||
and headers to the client.
|
||||
|
||||
This function will not send any body set previously. After
|
||||
this call the handler must use the `chunk/2` function
|
||||
repeatedly to send the body in as many chunks as needed.
|
||||
|
||||
If the request uses HTTP/1.0, the data is sent directly
|
||||
without wrapping it in an HTTP/1.1 chunk, providing
|
||||
compatibility with older clients.
|
||||
|
||||
This function can only be called once, with the exception
|
||||
of overriding the response in the `onresponse` hook.
|
||||
|
||||
: continue(Req) -> ok | {error, Reason}
|
||||
|
||||
Types:
|
||||
|
||||
* Reason = atom()
|
||||
|
||||
Send a 100 Continue intermediate reply.
|
||||
|
||||
This reply is required before the client starts sending the
|
||||
body when the request contains the `expect` header with the
|
||||
`100-continue` value.
|
||||
|
||||
Cowboy will send this automatically when required. However
|
||||
you may want to do it manually by disabling this behavior
|
||||
with the `continue` body option and then calling this
|
||||
function.
|
||||
|
||||
: delete_resp_header(Name, Req) -> Req2
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
|
||||
Delete the given response header.
|
||||
|
||||
While header names are case insensitive, this function expects
|
||||
the name to be a lowercase binary.
|
||||
|
||||
: has_resp_body(Req) -> boolean()
|
||||
|
||||
Return whether a response body has been set.
|
||||
|
||||
This function will return false if a response body has
|
||||
been set with a length of 0.
|
||||
|
||||
: has_resp_header(Name, Req) -> boolean()
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
|
||||
Return whether the given response header has been set.
|
||||
|
||||
While header names are case insensitive, this function expects
|
||||
the name to be a lowercase binary.
|
||||
|
||||
: reply(StatusCode, Req) -> reply(StatusCode, [], Req)
|
||||
: reply(StatusCode, Headers, Req) - see below
|
||||
: reply(StatusCode, Headers, Body, Req) -> {ok, Req2}
|
||||
|
||||
Types:
|
||||
|
||||
* StatusCode = cowboy:http_status()
|
||||
* Headers = cowboy:http_headers()
|
||||
* Body = iodata()
|
||||
|
||||
Send a response.
|
||||
|
||||
This function effectively sends the response status line,
|
||||
headers and body to the client, in a single send function
|
||||
call.
|
||||
|
||||
The `reply/2` and `reply/3` functions will send the body
|
||||
set previously, if any. The `reply/4` function overrides
|
||||
any body set previously and sends `Body` instead.
|
||||
|
||||
If a body function was set, and `reply/2` or `reply/3` was
|
||||
used, it will be called before returning.
|
||||
|
||||
No more data can be sent to the client after this function
|
||||
returns.
|
||||
|
||||
This function can only be called once, with the exception
|
||||
of overriding the response in the `onresponse` hook.
|
||||
|
||||
: set_resp_body(Body, Req) -> Req2
|
||||
|
||||
Types:
|
||||
|
||||
* Body = iodata()
|
||||
|
||||
Set a response body.
|
||||
|
||||
This body will not be sent if `chunked_reply/{2,3}` or
|
||||
`reply/4` is used, as they override it.
|
||||
|
||||
: set_resp_body_fun(Fun, Req) -> Req2
|
||||
: set_resp_body_fun(Length, Fun, Req) -> Req2
|
||||
|
||||
Types:
|
||||
|
||||
* Fun = fun((Socket, Transport) -> ok)
|
||||
* Socket = inet:socket()
|
||||
* Transport = module()
|
||||
* Length = non_neg_integer()
|
||||
|
||||
Set a fun for sending the response body.
|
||||
|
||||
If a `Length` is provided, it will be sent in the
|
||||
content-length header in the response. It is recommended
|
||||
to set the length if it can be known in advance. Otherwise,
|
||||
the transfer-encoding header will be set to identity.
|
||||
|
||||
This function will only be called if the response is sent
|
||||
using the `reply/2` or `reply/3` function.
|
||||
|
||||
The fun will receive the Ranch `Socket` and `Transport` as
|
||||
arguments. Only send and sendfile operations are supported.
|
||||
|
||||
: set_resp_body_fun(chunked, Fun, Req) -> Req2
|
||||
|
||||
Types:
|
||||
|
||||
* Fun = fun((ChunkFun) -> ok)
|
||||
* ChunkFun = fun((iodata()) -> ok | {error, atom()})
|
||||
|
||||
Set a fun for sending the response body using chunked transfer-encoding.
|
||||
|
||||
This function will only be called if the response is sent
|
||||
using the `reply/2` or `reply/3` function.
|
||||
|
||||
The fun will receive another fun as argument. This fun is to
|
||||
be used to send chunks in a similar way to the `chunk/2` function,
|
||||
except the fun only takes one argument, the data to be sent in
|
||||
the chunk.
|
||||
|
||||
: set_resp_cookie(Name, Value, Opts, Req) -> Req2
|
||||
|
||||
Types:
|
||||
|
||||
* Name = iodata()
|
||||
* Value = iodata()
|
||||
* Opts = cookie_opts()
|
||||
|
||||
Set a cookie in the response.
|
||||
|
||||
Cookie names are case sensitive.
|
||||
|
||||
: set_resp_header(Name, Value, Req) -> Req2
|
||||
|
||||
Types:
|
||||
|
||||
* Name = binary()
|
||||
* Value = iodata()
|
||||
|
||||
Set a response header.
|
||||
|
||||
You should use `set_resp_cookie/4` instead of this function
|
||||
to set cookies.
|
||||
|
||||
:: Misc. exports
|
||||
|
||||
: compact(Req) -> Req2
|
||||
|
||||
Remove any non-essential data from the Req object.
|
||||
|
||||
Long-lived connections usually only need to manipulate the
|
||||
Req object at initialization. Compacting allows saving up
|
||||
memory by discarding extraneous information.
|
561
doc/src/manual/cowboy_rest.ezdoc
Normal file
|
@ -0,0 +1,561 @@
|
|||
::: cowboy_rest
|
||||
|
||||
The `cowboy_rest` module implements REST semantics on top of
|
||||
the HTTP protocol.
|
||||
|
||||
This module cannot be described as a behaviour due to most of
|
||||
the callbacks it defines being optional. It has the same
|
||||
semantics as a behaviour otherwise.
|
||||
|
||||
The only mandatory callback is `init/3`, needed to perform
|
||||
the protocol upgrade.
|
||||
|
||||
:: Types
|
||||
|
||||
None.
|
||||
|
||||
:: Meta values
|
||||
|
||||
: charset
|
||||
|
||||
Type: binary()
|
||||
|
||||
Negotiated charset.
|
||||
|
||||
This value may not be defined if no charset was negotiated.
|
||||
|
||||
: language
|
||||
|
||||
Type: binary()
|
||||
|
||||
Negotiated language.
|
||||
|
||||
This value may not be defined if no language was negotiated.
|
||||
|
||||
: media_type
|
||||
|
||||
Type: {binary(), binary(), '*' | [{binary(), binary()}]}
|
||||
|
||||
Negotiated media-type.
|
||||
|
||||
The media-type is the content-type, excluding the charset.
|
||||
|
||||
This value is always defined after the call to
|
||||
`content_types_provided/2`.
|
||||
|
||||
:: Callbacks
|
||||
|
||||
: init({TransportName, ProtocolName}, Req, Opts)
|
||||
-> {upgrade, protocol, cowboy_rest}
|
||||
| {upgrade, protocol, cowboy_rest, Req, Opts}
|
||||
|
||||
Types:
|
||||
|
||||
* TransportName = tcp | ssl | atom()
|
||||
* ProtocolName = http | atom()
|
||||
* Req = cowboy_req:req()
|
||||
* Opts = any()
|
||||
|
||||
Upgrade the protocol to `cowboy_rest`.
|
||||
|
||||
This is the only mandatory callback.
|
||||
|
||||
: rest_init(Req, Opts) -> {ok, Req, State}
|
||||
|
||||
Types:
|
||||
|
||||
* Req = cowboy_req:req()
|
||||
* Opts = any()
|
||||
* State = any()
|
||||
|
||||
Initialize the state for this request.
|
||||
|
||||
: rest_terminate(Req, State) -> ok
|
||||
|
||||
Types:
|
||||
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
|
||||
Perform any necessary cleanup of the state.
|
||||
|
||||
This callback should release any resource currently in use,
|
||||
clear any active timer and reset the process to its original
|
||||
state, as it might be reused for future requests sent on the
|
||||
same connection.
|
||||
|
||||
: Callback(Req, State) -> {Value, Req, State} | {halt, Req, State}
|
||||
|
||||
Types:
|
||||
|
||||
* Callback - one of the REST callbacks described below
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
* Value - see the REST callbacks description below
|
||||
|
||||
Please see the REST callbacks description below for details
|
||||
on the `Value` type, the default value if the callback is
|
||||
not defined, and more general information on when the
|
||||
callback is called and what its intended use is.
|
||||
|
||||
The `halt` tuple can be returned to stop REST processing.
|
||||
It is up to the resource code to send a reply before that,
|
||||
otherwise a `204 No Content` will be sent.
|
||||
|
||||
:: REST callbacks description
|
||||
|
||||
: allowed_methods
|
||||
|
||||
* Methods: all
|
||||
* Value type: [binary()]
|
||||
* Default value: [<<"GET">>, <<"HEAD">>, <<"OPTIONS">>]
|
||||
|
||||
Return the list of allowed methods.
|
||||
|
||||
Methods are case sensitive. Standard methods are always uppercase.
|
||||
|
||||
: allow_missing_post
|
||||
|
||||
* Methods: POST
|
||||
* Value type: boolean()
|
||||
* Default value: true
|
||||
|
||||
Return whether POST is allowed when the resource doesn't exist.
|
||||
|
||||
Returning `true` here means that a new resource will be
|
||||
created. The URL to the created resource should also be
|
||||
returned from the `AcceptResource` callback.
|
||||
|
||||
: charsets_provided
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Value type: [binary()]
|
||||
* Skip to the next step if undefined
|
||||
|
||||
Return the list of charsets the resource provides.
|
||||
|
||||
The list must be ordered in order of preference.
|
||||
|
||||
If the accept-charset header was not sent, the first charset
|
||||
in the list will be selected. Otherwise Cowboy will select
|
||||
the most appropriate charset from the list.
|
||||
|
||||
The chosen charset will be set in the `Req` object as the meta
|
||||
value `charset`.
|
||||
|
||||
While charsets are case insensitive, this callback is expected
|
||||
to return them as lowercase binary.
|
||||
|
||||
: content_types_accepted
|
||||
|
||||
* Methods: POST, PUT, PATCH
|
||||
* No default
|
||||
|
||||
Types:
|
||||
|
||||
* Value = [{binary() | {Type, SubType, Params}, AcceptResource}]
|
||||
* Type = SubType = binary()
|
||||
* Params = '*' | [{binary(), binary()}]
|
||||
* AcceptResource = atom()
|
||||
|
||||
Return the list of content-types the resource accepts.
|
||||
|
||||
The list must be ordered in order of preference.
|
||||
|
||||
Each content-type can be given either as a binary string or as
|
||||
a tuple containing the type, subtype and parameters.
|
||||
|
||||
Cowboy will select the most appropriate content-type from the list.
|
||||
If any parameter is acceptable, then the tuple form should be used
|
||||
with parameters set to `'*'`. If the parameters value is set to `[]`
|
||||
only content-type values with no parameters will be accepted. All
|
||||
parameter values are treated in a case sensitive manner except the
|
||||
`charset` parameter, if present, which is case insensitive.
|
||||
|
||||
This function will be called for POST, PUT and PATCH requests.
|
||||
It is entirely possible to define different callbacks for different
|
||||
methods if the handling of the request differs. Simply verify
|
||||
what the method is with `cowboy_req:method/1` and return a
|
||||
different list for each methods.
|
||||
|
||||
The `AcceptResource` value is the name of the callback that will
|
||||
be called if the content-type matches. It is defined as follow.
|
||||
|
||||
* Value type: true | {true, URL} | false
|
||||
* No default
|
||||
|
||||
Process the request body.
|
||||
|
||||
This function should create or update the resource with the
|
||||
information contained in the request body. This information
|
||||
may be full or partial depending on the request method.
|
||||
|
||||
If the request body was processed successfully, `true` or
|
||||
`{true, URL}` may be returned. If an URL is provided, the
|
||||
response will redirect the client to the location of the
|
||||
resource.
|
||||
|
||||
If a response body must be sent, the appropriate media-type, charset
|
||||
and language can be retrieved using the `cowboy_req:meta/{2,3}`
|
||||
functions. The respective keys are `media_type`, `charset`
|
||||
and `language`. The body can be set using `cowboy_req:set_resp_body/2`.
|
||||
|
||||
: content_types_provided
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Default value: [{{<<"text">>, <<"html">>, '*'}, to_html}]
|
||||
|
||||
Types:
|
||||
|
||||
* Value = [{binary() | {Type, SubType, Params}, ProvideResource}]
|
||||
* Type = SubType = binary()
|
||||
* Params = '*' | [{binary(), binary()}]
|
||||
* ProvideResource = atom()
|
||||
|
||||
Return the list of content-types the resource provides.
|
||||
|
||||
The list must be ordered in order of preference.
|
||||
|
||||
Each content-type can be given either as a binary string or as
|
||||
a tuple containing the type, subtype and parameters.
|
||||
|
||||
Cowboy will select the most appropriate content-type from the list.
|
||||
If any parameter is acceptable, then the tuple form should be used
|
||||
with parameters set to `'*'`. If the parameters value is set to `[]`
|
||||
only content-type values with no parameters will be accepted. All
|
||||
parameter values are treated in a case sensitive manner except the
|
||||
`charset` parameter, if present, which is case insensitive.
|
||||
|
||||
The `ProvideResource` value is the name of the callback that will
|
||||
be called if the content-type matches. It will only be called when
|
||||
a representation of the resource needs to be returned. It is defined
|
||||
as follow.
|
||||
|
||||
* Methods: GET, HEAD
|
||||
* Value type: iodata() | {stream, Fun} | {stream, Len, Fun} | {chunked, ChunkedFun}
|
||||
* No default
|
||||
|
||||
Return the response body.
|
||||
|
||||
The response body may be provided directly or through a fun.
|
||||
If a fun tuple is returned, the appropriate `set_resp_body_fun`
|
||||
function will be called. Please refer to the documentation for
|
||||
these functions for more information about the types.
|
||||
|
||||
The call to this callback happens a good time after the call to
|
||||
`content_types_provided/2`, when it is time to start rendering
|
||||
the response body.
|
||||
|
||||
: delete_completed
|
||||
|
||||
* Methods: DELETE
|
||||
* Value type: boolean()
|
||||
* Default value: true
|
||||
|
||||
Return whether the delete action has been completed.
|
||||
|
||||
This function should return `false` if there is no guarantee
|
||||
that the resource gets deleted immediately from the system,
|
||||
including from any internal cache.
|
||||
|
||||
When this function returns `false`, a `202 Accepted`
|
||||
response will be sent instead of a `200 OK` or `204 No Content`.
|
||||
|
||||
: delete_resource
|
||||
|
||||
* Methods: DELETE
|
||||
* Value type: boolean()
|
||||
* Default value: false
|
||||
|
||||
Delete the resource.
|
||||
|
||||
The value returned indicates if the action was successful,
|
||||
regardless of whether the resource is immediately deleted
|
||||
from the system.
|
||||
|
||||
: expires
|
||||
|
||||
* Methods: GET, HEAD
|
||||
* Value type: calendar:datetime() | binary() | undefined
|
||||
* Default value: undefined
|
||||
|
||||
Return the date of expiration of the resource.
|
||||
|
||||
This date will be sent as the value of the expires header.
|
||||
|
||||
: forbidden
|
||||
|
||||
* Methods: all
|
||||
* Value type: boolean()
|
||||
* Default value: false
|
||||
|
||||
Return whether access to the resource is forbidden.
|
||||
|
||||
A `403 Forbidden` response will be sent if this
|
||||
function returns `true`. This status code means that
|
||||
access is forbidden regardless of authentication,
|
||||
and that the request shouldn't be repeated.
|
||||
|
||||
: generate_etag
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Value type: binary() | {weak | strong, binary()}
|
||||
* Default value: undefined
|
||||
|
||||
Return the entity tag of the resource.
|
||||
|
||||
This value will be sent as the value of the etag header.
|
||||
|
||||
If a binary is returned, then the value will be parsed
|
||||
to the tuple form automatically. The value must be in
|
||||
the same format as the etag header, including quotes.
|
||||
|
||||
: is_authorized
|
||||
|
||||
* Methods: all
|
||||
* Value type: true | {false, AuthHeader}
|
||||
* Default value: true
|
||||
|
||||
Return whether the user is authorized to perform the action.
|
||||
|
||||
This function should be used to perform any necessary
|
||||
authentication of the user before attempting to perform
|
||||
any action on the resource.
|
||||
|
||||
If the authentication fails, the value returned will be sent
|
||||
as the value for the www-authenticate header in the
|
||||
`401 Unauthorized` response.
|
||||
|
||||
: is_conflict
|
||||
|
||||
* Methods: PUT
|
||||
* Value type: boolean()
|
||||
* Default value: false
|
||||
|
||||
Return whether the put action results in a conflict.
|
||||
|
||||
A `409 Conflict` response will be sent if this function
|
||||
returns `true`.
|
||||
|
||||
: known_content_type
|
||||
|
||||
* Methods: all
|
||||
* Value type: boolean()
|
||||
* Default value: true
|
||||
|
||||
Return whether the content-type is known.
|
||||
|
||||
This function determines if the server understands the
|
||||
content-type, regardless of its use by the resource.
|
||||
|
||||
: known_methods
|
||||
|
||||
* Methods: all
|
||||
* Value type: [binary()]
|
||||
* Default value: [<<"GET">>, <<"HEAD">>, <<"POST">>, <<"PUT">>, <<"PATCH">>, <<"DELETE">>, <<"OPTIONS">>]
|
||||
|
||||
Return the list of known methods.
|
||||
|
||||
The full list of methods known by the server should be
|
||||
returned, regardless of their use in the resource.
|
||||
|
||||
The default value lists the methods Cowboy knows and
|
||||
implement in `cowboy_rest`.
|
||||
|
||||
Methods are case sensitive. Standard methods are always uppercase.
|
||||
|
||||
: languages_provided
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Value type: [binary()]
|
||||
* Skip to the next step if undefined
|
||||
|
||||
Return the list of languages the resource provides.
|
||||
|
||||
The list must be ordered in order of preference.
|
||||
|
||||
If the accept-language header was not sent, the first language
|
||||
in the list will be selected. Otherwise Cowboy will select
|
||||
the most appropriate language from the list.
|
||||
|
||||
The chosen language will be set in the `Req` object as the meta
|
||||
value `language`.
|
||||
|
||||
While languages are case insensitive, this callback is expected
|
||||
to return them as lowercase binary.
|
||||
|
||||
: last_modified
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Value type: calendar:datetime()
|
||||
* Default value: undefined
|
||||
|
||||
Return the date of last modification of the resource.
|
||||
|
||||
This date will be used to test against the if-modified-since
|
||||
and if-unmodified-since headers, and sent as the last-modified
|
||||
header in the response of GET and HEAD requests.
|
||||
|
||||
: malformed_request
|
||||
|
||||
* Methods: all
|
||||
* Value type: boolean()
|
||||
* Default value: false
|
||||
|
||||
Return whether the request is malformed.
|
||||
|
||||
Cowboy has already performed all the necessary checks
|
||||
by the time this function is called, so few resources
|
||||
are expected to implement it.
|
||||
|
||||
The check is to be done on the request itself, not on
|
||||
the request body, which is processed later.
|
||||
|
||||
: moved_permanently
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Value type: {true, URL} | false
|
||||
* Default value: false
|
||||
|
||||
Return whether the resource was permanently moved.
|
||||
|
||||
If it was, its new URL is also returned and sent in the
|
||||
location header in the response.
|
||||
|
||||
: moved_temporarily
|
||||
|
||||
* Methods: GET, HEAD, POST, PATCH, DELETE
|
||||
* Value type: {true, URL} | false
|
||||
* Default value: false
|
||||
|
||||
Return whether the resource was temporarily moved.
|
||||
|
||||
If it was, its new URL is also returned and sent in the
|
||||
location header in the response.
|
||||
|
||||
: multiple_choices
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Value type: boolean()
|
||||
* Default value: false
|
||||
|
||||
Return whether there are multiple representations of the resource.
|
||||
|
||||
This function should be used to inform the client if there
|
||||
are different representations of the resource, for example
|
||||
different content-type. If this function returns `true`,
|
||||
the response body should include information about these
|
||||
different representations using `cowboy_req:set_resp_body/2`.
|
||||
The content-type of the response should be the one previously
|
||||
negociated and that can be obtained by calling
|
||||
`cowboy_req:meta(media_type, Req)`.
|
||||
|
||||
: options
|
||||
|
||||
* Methods: OPTIONS
|
||||
* Value type: ok
|
||||
* Default value: ok
|
||||
|
||||
Handle a request for information.
|
||||
|
||||
The response should inform the client the communication
|
||||
options available for this resource.
|
||||
|
||||
By default, Cowboy will send a `200 OK` response with the
|
||||
allow header set.
|
||||
|
||||
: previously_existed
|
||||
|
||||
* Methods: GET, HEAD, POST, PATCH, DELETE
|
||||
* Value type: boolean()
|
||||
* Default value: false
|
||||
|
||||
Return whether the resource existed previously.
|
||||
|
||||
: resource_exists
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Value type: boolean()
|
||||
* Default value: true
|
||||
|
||||
Return whether the resource exists.
|
||||
|
||||
If it exists, conditional headers will be tested before
|
||||
attempting to perform the action. Otherwise, Cowboy will
|
||||
check if the resource previously existed first.
|
||||
|
||||
: service_available
|
||||
|
||||
* Methods: all
|
||||
* Value type: boolean()
|
||||
* Default value: true
|
||||
|
||||
Return whether the service is available.
|
||||
|
||||
This function can be used to test that all relevant backend
|
||||
systems are up and able to handle requests.
|
||||
|
||||
A `503 Service Unavailable` response will be sent if this
|
||||
function returns `false`.
|
||||
|
||||
: uri_too_long
|
||||
|
||||
* Methods: all
|
||||
* Value type: boolean()
|
||||
* Default value: false
|
||||
|
||||
Return whether the requested URI is too long.
|
||||
|
||||
Cowboy has already performed all the necessary checks
|
||||
by the time this function is called, so few resources
|
||||
are expected to implement it.
|
||||
|
||||
A `414 Request-URI Too Long` response will be sent if this
|
||||
function returns `true`.
|
||||
|
||||
: valid_content_headers
|
||||
|
||||
* Methods: all
|
||||
* Value type: boolean()
|
||||
* Default value: true
|
||||
|
||||
Return whether the content-* headers are valid.
|
||||
|
||||
This also applies to the transfer-encoding header. This
|
||||
function must return `false` for any unknown content-*
|
||||
headers, or if the headers can't be understood. The
|
||||
function `cowboy_req:parse_header/2` can be used to
|
||||
quickly check the headers can be parsed.
|
||||
|
||||
A `501 Not Implemented` response will be sent if this
|
||||
function returns `false`.
|
||||
|
||||
: valid_entity_length
|
||||
|
||||
* Methods: all
|
||||
* Value type: boolean()
|
||||
* Default value: true
|
||||
|
||||
Return whether the request body length is within acceptable boundaries.
|
||||
|
||||
A `413 Request Entity Too Large` response will be sent if this
|
||||
function returns `false`.
|
||||
|
||||
: variances
|
||||
|
||||
* Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
* Value type: [binary()]
|
||||
* Default value: []
|
||||
|
||||
Return the list of headers that affect the representation of the resource.
|
||||
|
||||
These request headers return the same resource but with different
|
||||
parameters, like another language or a different content-type.
|
||||
|
||||
Cowboy will automatically add the accept, accept-language and
|
||||
accept-charset headers to the list if the respective functions
|
||||
were defined in the resource.
|
||||
|
||||
This operation is performed right before the `resource_exists/2`
|
||||
callback. All responses past that point will contain the vary
|
||||
header which holds this list.
|
70
doc/src/manual/cowboy_router.ezdoc
Normal file
|
@ -0,0 +1,70 @@
|
|||
::: cowboy_router
|
||||
|
||||
The `cowboy_router` middleware maps the requested host and
|
||||
path to the handler to be used for processing the request.
|
||||
It uses the dispatch rules compiled from the routes given
|
||||
to the `compile/1` function for this purpose. It adds the
|
||||
handler name and options to the environment as the values
|
||||
`handler` and `handler_opts` respectively.
|
||||
|
||||
Environment input:
|
||||
|
||||
* dispatch = dispatch_rules()
|
||||
|
||||
Environment output:
|
||||
|
||||
* handler = module()
|
||||
* handler_opts = any()
|
||||
|
||||
:: Types
|
||||
|
||||
: bindings() = [{atom(), binary()}]
|
||||
|
||||
List of bindings found during routing.
|
||||
|
||||
: constraints() = [IntConstraint | FunConstraint]
|
||||
|
||||
Types:
|
||||
|
||||
* IntConstraint = {atom(), int}
|
||||
* FunConstraint = {atom(), function, Fun}
|
||||
* Fun = fun((binary()) -> true | {true, any()} | false)
|
||||
|
||||
List of constraints to apply to the bindings.
|
||||
|
||||
The int constraint will convert the binding to an integer.
|
||||
The fun constraint allows writing custom code for checking
|
||||
the bindings. Returning a new value from that fun allows
|
||||
replacing the current binding with a new value.
|
||||
|
||||
: dispatch_rules() - opaque to the user
|
||||
|
||||
Rules for dispatching request used by Cowboy.
|
||||
|
||||
: routes() = [{Host, Paths} | {Host, constraints(), Paths}]
|
||||
|
||||
Types:
|
||||
|
||||
* Host = Path = '_' | iodata()
|
||||
* Paths = [{Path, Handler, Opts} | {Path, constraints(), Handler, Opts}]
|
||||
* Handler = module()
|
||||
* Opts = any()
|
||||
|
||||
Human readable list of routes mapping hosts and paths to handlers.
|
||||
|
||||
The syntax for routes is defined in the user guide.
|
||||
|
||||
: tokens() = [binary()]
|
||||
|
||||
List of host_info and path_info tokens found during routing.
|
||||
|
||||
:: Exports
|
||||
|
||||
: compile(Routes) -> Dispatch
|
||||
|
||||
Types:
|
||||
|
||||
* Routes = routes()
|
||||
* Dispatch = dispatch_rules()
|
||||
|
||||
Compile the routes for use by Cowboy.
|
43
doc/src/manual/cowboy_spdy.ezdoc
Normal file
|
@ -0,0 +1,43 @@
|
|||
::: cowboy_spdy
|
||||
|
||||
The `cowboy_spdy` module implements SPDY/3 as a Ranch protocol.
|
||||
|
||||
:: Types
|
||||
|
||||
: opts() = [{env, cowboy_middleware:env()}
|
||||
| {middlewares, [module()]}
|
||||
| {onrequest, cowboy:onrequest_fun()}
|
||||
| {onresponse, cowboy:onresponse_fun()}]
|
||||
|
||||
Configuration for the SPDY protocol handler.
|
||||
|
||||
This configuration is passed to Cowboy when starting listeners
|
||||
using the `cowboy:start_spdy/4` function.
|
||||
|
||||
It can be updated without restarting listeners using the
|
||||
Ranch functions `ranch:get_protocol_options/1` and
|
||||
`ranch:set_protocol_options/2`.
|
||||
|
||||
:: Option descriptions
|
||||
|
||||
The default value is given next to the option name.
|
||||
|
||||
: env ([{listener, Ref}])
|
||||
|
||||
Initial middleware environment.
|
||||
|
||||
: middlewares ([cowboy_router, cowboy_handler])
|
||||
|
||||
List of middlewares to execute for every requests.
|
||||
|
||||
: onrequest (undefined)
|
||||
|
||||
Fun called every time a request is received.
|
||||
|
||||
: onresponse (undefined)
|
||||
|
||||
Fun called every time a response is sent.
|
||||
|
||||
:: Exports
|
||||
|
||||
None.
|
32
doc/src/manual/cowboy_static.ezdoc
Normal file
|
@ -0,0 +1,32 @@
|
|||
::: cowboy_static
|
||||
|
||||
The `cowboy_static` module implements file serving capabilities
|
||||
by using the REST semantics provided by `cowboy_rest`.
|
||||
|
||||
:: Types
|
||||
|
||||
: opts() = {priv_file, atom(), string() | binary()}
|
||||
| {priv_file, atom(), string() | binary(), extra()}
|
||||
| {file, string() | binary()}
|
||||
| {file, string() | binary(), extra()}
|
||||
| {priv_dir, atom(), string() | binary()}
|
||||
| {priv_dir, atom(), string() | binary(), extra()}
|
||||
| {dir, atom(), string() | binary()}
|
||||
| {dir, atom(), string() | binary(), extra()}
|
||||
|
||||
Configuration for the static handler.
|
||||
|
||||
The handler can be configured for sending either one file or
|
||||
a directory (including its subdirectories).
|
||||
|
||||
Extra options allow you to define how the etag should be calculated
|
||||
and how the mimetype of files should be detected. They are defined
|
||||
as follow, but do note that these types are not exported, only the
|
||||
`opts/0` type is public.
|
||||
|
||||
: extra() = [extra_etag() | extra_mimetypes()]
|
||||
|
||||
: extra_etag() = {etag, module(), function()} | {etag, false}
|
||||
|
||||
: extra_mimetypes() = {mimetypes, module(), function()}
|
||||
| {mimetypes, binary() | {binary(), binary(), [{binary(), binary()}]}}
|
32
doc/src/manual/cowboy_sub_protocol.ezdoc
Normal file
|
@ -0,0 +1,32 @@
|
|||
::: cowboy_sub_protocol
|
||||
|
||||
The `cowboy_sub_protocol` behaviour defines the interface used
|
||||
by modules that implement a protocol on top of HTTP.
|
||||
|
||||
:: Types
|
||||
|
||||
None.
|
||||
|
||||
:: Callbacks
|
||||
|
||||
: upgrade(Req, Env, Handler, Opts)
|
||||
-> {ok, Req, Env}
|
||||
| {suspend, Module, Function, Args}
|
||||
| {halt, Req}
|
||||
| {error, StatusCode, Req}
|
||||
|
||||
Types:
|
||||
|
||||
* Req = cowboy_req:req()
|
||||
* Env = env()
|
||||
* Handler = module()
|
||||
* Opts = any()
|
||||
* Module = module()
|
||||
* Function = atom()
|
||||
* Args = [any()]
|
||||
* StatusCode = cowboy:http_status()
|
||||
|
||||
Upgrade the protocol.
|
||||
|
||||
Please refer to the `cowboy_middleware` manual for a
|
||||
description of the return values.
|
36
doc/src/manual/cowboy_websocket.ezdoc
Normal file
|
@ -0,0 +1,36 @@
|
|||
::: cowboy_websocket
|
||||
|
||||
The `cowboy_websocket` module implements the Websocket protocol.
|
||||
|
||||
The callbacks for websocket handlers are defined in the manual
|
||||
for the `cowboy_websocket_handler` behaviour.
|
||||
|
||||
:: Types
|
||||
|
||||
: close_code() = 1000..4999
|
||||
|
||||
Reason for closing the connection.
|
||||
|
||||
: frame() = close | ping | pong
|
||||
| {text | binary | close | ping | pong, iodata()}
|
||||
| {close, close_code(), iodata()}
|
||||
|
||||
Frames that can be sent to the client.
|
||||
|
||||
:: Meta values
|
||||
|
||||
: websocket_compress
|
||||
|
||||
Type: true | false
|
||||
|
||||
Whether a websocket compression extension in in use.
|
||||
|
||||
: websocket_version
|
||||
|
||||
Type: 7 | 8 | 13
|
||||
|
||||
The version of the Websocket protocol being used.
|
||||
|
||||
:: Exports
|
||||
|
||||
None.
|
133
doc/src/manual/cowboy_websocket_handler.ezdoc
Normal file
|
@ -0,0 +1,133 @@
|
|||
::: cowboy_websocket_handler
|
||||
|
||||
The `cowboy_websocket_handler` behaviour defines the interface used
|
||||
by Websocket handlers.
|
||||
|
||||
The `init/3` and `websocket_init/3` callbacks will always be called,
|
||||
followed by zero or more calls to `websocket_handle/3` and
|
||||
`websocket_info/3`. The `websocket_terminate/3` will always
|
||||
be called last.
|
||||
|
||||
:: Types
|
||||
|
||||
None.
|
||||
|
||||
:: Callbacks
|
||||
|
||||
: init({TransportName, ProtocolName}, Req, Opts)
|
||||
-> {upgrade, protocol, cowboy_websocket}
|
||||
| {upgrade, protocol, cowboy_websocket, Req, Opts}
|
||||
|
||||
Types:
|
||||
|
||||
* TransportName = tcp | ssl | atom()
|
||||
* ProtocolName = http | atom()
|
||||
* Req = cowboy_req:req()
|
||||
* Opts = any()
|
||||
|
||||
Upgrade the protocol to `cowboy_websocket`.
|
||||
|
||||
: websocket_init(TransportName, Req, Opts)
|
||||
-> {ok, Req, State}
|
||||
| {ok, Req, State, hibernate}
|
||||
| {ok, Req, State, Timeout}
|
||||
| {ok, Req, State, Timeout, hibernate}
|
||||
| {shutdown, Req}
|
||||
|
||||
Types:
|
||||
|
||||
* TransportName = tcp | ssl | atom()
|
||||
* Req = cowboy_req:req()
|
||||
* Opts = any()
|
||||
* State = any()
|
||||
* Timeout = timeout()
|
||||
|
||||
Initialize the state for this session.
|
||||
|
||||
This function is called before the upgrade to Websocket occurs.
|
||||
It can be used to negotiate Websocket protocol extensions
|
||||
with the client. It will typically be used to register this process
|
||||
to an event manager or a message queue in order to receive
|
||||
the messages the handler wants to process.
|
||||
|
||||
The connection will stay up for a duration of up to `Timeout`
|
||||
milliseconds after it last received data from the socket,
|
||||
at which point it will stop and close the connection.
|
||||
By default this value is set to `infinity`. It is recommended
|
||||
to either set this value or ensure by any other mechanism
|
||||
that the handler will be closed after a certain period of
|
||||
inactivity.
|
||||
|
||||
The `hibernate` option will hibernate the process until it
|
||||
starts receiving either data from the Websocket connection
|
||||
or Erlang messages.
|
||||
|
||||
The `shutdown` return value can be used to close the connection
|
||||
before upgrading to Websocket.
|
||||
|
||||
: websocket_handle(InFrame, Req, State)
|
||||
-> {ok, Req, State}
|
||||
| {ok, Req, State, hibernate}
|
||||
| {reply, OutFrame | [OutFrame], Req, State}
|
||||
| {reply, OutFrame | [OutFrame], Req, State, hibernate}
|
||||
| {shutdown, Req, State}
|
||||
|
||||
Types:
|
||||
|
||||
* InFrame = {text | binary | ping | pong, binary()}
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
* OutFrame = cowboy_websocket:frame()
|
||||
|
||||
Handle the data received from the Websocket connection.
|
||||
|
||||
This function will be called every time data is received
|
||||
from the Websocket connection.
|
||||
|
||||
The `shutdown` return value can be used to close the
|
||||
connection. A close reply will also result in the connection
|
||||
being closed.
|
||||
|
||||
The `hibernate` option will hibernate the process until
|
||||
it receives new data from the Websocket connection or an
|
||||
Erlang message.
|
||||
|
||||
: websocket_info(Info, Req, State)
|
||||
-> {ok, Req, State}
|
||||
| {ok, Req, State, hibernate}
|
||||
| {reply, OutFrame | [OutFrame], Req, State}
|
||||
| {reply, OutFrame | [OutFrame], Req, State, hibernate}
|
||||
| {shutdown, Req, State}
|
||||
|
||||
Types:
|
||||
|
||||
* Info = any()
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
* OutFrame = cowboy_websocket:frame()
|
||||
|
||||
Handle the Erlang message received.
|
||||
|
||||
This function will be called every time an Erlang message
|
||||
has been received. The message can be any Erlang term.
|
||||
|
||||
The `shutdown` return value can be used to close the
|
||||
connection. A close reply will also result in the connection
|
||||
being closed.
|
||||
|
||||
The `hibernate` option will hibernate the process until
|
||||
it receives another message or new data from the Websocket
|
||||
connection.
|
||||
|
||||
: websocket_terminate(Reason, Req, State) -> ok
|
||||
|
||||
Types:
|
||||
|
||||
* Reason = {normal, shutdown | timeout} | {remote, closed} | {remote, cowboy_websocket:close_code(), binary()} | {error, badencoding | badframe | closed | atom()}
|
||||
* Req = cowboy_req:req()
|
||||
* State = any()
|
||||
|
||||
Perform any necessary cleanup of the state.
|
||||
|
||||
The connection will be closed and the process stopped right
|
||||
after this call.
|
|
@ -1,74 +1,61 @@
|
|||
HTTP status codes
|
||||
=================
|
||||
::: HTTP status codes
|
||||
|
||||
This chapter aims to list all HTTP status codes that Cowboy
|
||||
may return, with details on the reasons why. The list given
|
||||
here only includes the replies that Cowboy sends, not user
|
||||
replies.
|
||||
|
||||
100 Continue
|
||||
------------
|
||||
: 100 Continue
|
||||
|
||||
When the client sends an `expect: 100-continue` header,
|
||||
Cowboy automatically sends a this status code before
|
||||
trying to read the request body. This behavior can be
|
||||
disabled using the appropriate body option.
|
||||
|
||||
101 Switching Protocols
|
||||
-----------------------
|
||||
: 101 Switching Protocols
|
||||
|
||||
This is the status code sent when switching to the
|
||||
Websocket protocol.
|
||||
|
||||
200 OK
|
||||
------
|
||||
: 200 OK
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
201 Created
|
||||
-----------
|
||||
: 201 Created
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
202 Accepted
|
||||
------------
|
||||
: 202 Accepted
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
204 No Content
|
||||
--------------
|
||||
: 204 No Content
|
||||
|
||||
This status code is sent when the processing of a request
|
||||
ends without any reply having been sent. It may also be
|
||||
sent by `cowboy_rest` under normal conditions.
|
||||
|
||||
300 Multiple Choices
|
||||
--------------------
|
||||
: 300 Multiple Choices
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
301 Moved Permanently
|
||||
---------------------
|
||||
: 301 Moved Permanently
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
303 See Other
|
||||
-------------
|
||||
: 303 See Other
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
304 Not Modified
|
||||
----------------
|
||||
: 304 Not Modified
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
307 Temporary Redirect
|
||||
----------------------
|
||||
: 307 Temporary Redirect
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
400 Bad Request
|
||||
---------------
|
||||
: 400 Bad Request
|
||||
|
||||
Cowboy will send this status code for any of the
|
||||
following reasons:
|
||||
|
@ -86,94 +73,78 @@ following reasons:
|
|||
* REST under normal conditions.
|
||||
* A Websocket upgrade failed.
|
||||
|
||||
401 Unauthorized
|
||||
----------------
|
||||
: 401 Unauthorized
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
403 Forbidden
|
||||
-------------
|
||||
: 403 Forbidden
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
404 Not Found
|
||||
-------------
|
||||
: 404 Not Found
|
||||
|
||||
This status code is sent when the router successfully
|
||||
resolved the host but didn't find a matching path for
|
||||
the request. It may also be sent by `cowboy_rest` under
|
||||
normal conditions.
|
||||
|
||||
405 Method Not Allowed
|
||||
----------------------
|
||||
: 405 Method Not Allowed
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
406 Not Acceptable
|
||||
------------------
|
||||
: 406 Not Acceptable
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
408 Request Timeout
|
||||
-------------------
|
||||
: 408 Request Timeout
|
||||
|
||||
Cowboy will send this status code to the client if the
|
||||
client started to send a request, indicated by the
|
||||
request-line being received fully, but failed to send
|
||||
all headers in a reasonable time.
|
||||
|
||||
409 Conflict
|
||||
------------
|
||||
: 409 Conflict
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
410 Gone
|
||||
--------
|
||||
: 410 Gone
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
412 Precondition Failed
|
||||
-----------------------
|
||||
: 412 Precondition Failed
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
413 Request Entity Too Large
|
||||
----------------------------
|
||||
: 413 Request Entity Too Large
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
414 Request-URI Too Long
|
||||
------------------------
|
||||
: 414 Request-URI Too Long
|
||||
|
||||
Cowboy will send this status code to the client if the
|
||||
request-line is too long. It may also be sent by
|
||||
`cowboy_rest` under normal conditions.
|
||||
|
||||
415 Unsupported Media Type
|
||||
--------------------------
|
||||
: 415 Unsupported Media Type
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
500 Internal Server Error
|
||||
-------------------------
|
||||
: 500 Internal Server Error
|
||||
|
||||
This status code is sent when a crash occurs in HTTP, loop
|
||||
or REST handlers, or when an invalid return value is
|
||||
returned. It may also be sent by `cowboy_rest` under
|
||||
normal conditions.
|
||||
|
||||
501 Not Implemented
|
||||
-------------------
|
||||
: 501 Not Implemented
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
503 Service Unavailable
|
||||
-----------------------
|
||||
: 503 Service Unavailable
|
||||
|
||||
This status code is sent by `cowboy_rest`.
|
||||
|
||||
505 HTTP Version Not Supported
|
||||
------------------------------
|
||||
: 505 HTTP Version Not Supported
|
||||
|
||||
Cowboy only supports the versions 1.0 and 1.1 of HTTP.
|
||||
In all other cases this status code is sent back to the
|
20
doc/src/manual/index.ezdoc
Normal file
|
@ -0,0 +1,20 @@
|
|||
::: Cowboy Function Reference
|
||||
|
||||
The function reference documents the public interface of Cowboy.
|
||||
|
||||
* ^"The Cowboy Application^cowboy_app
|
||||
* ^cowboy
|
||||
* ^cowboy_handler
|
||||
* ^cowboy_http_handler
|
||||
* ^cowboy_loop_handler
|
||||
* ^cowboy_middleware
|
||||
* ^cowboy_protocol
|
||||
* ^cowboy_req
|
||||
* ^cowboy_rest
|
||||
* ^cowboy_router
|
||||
* ^cowboy_spdy
|
||||
* ^cowboy_static
|
||||
* ^cowboy_sub_protocol
|
||||
* ^cowboy_websocket
|
||||
* ^cowboy_websocket_handler
|
||||
* ^"HTTP status codes^http_status_codes
|
11
erlang.mk
vendored
|
@ -199,17 +199,6 @@ clean-deps:
|
|||
fi ; \
|
||||
done
|
||||
|
||||
# Documentation.
|
||||
|
||||
EDOC_OPTS ?=
|
||||
|
||||
docs: clean-docs
|
||||
$(gen_verbose) erl -noshell \
|
||||
-eval 'edoc:application($(PROJECT), ".", [$(EDOC_OPTS)]), init:stop().'
|
||||
|
||||
clean-docs:
|
||||
$(gen_verbose) rm -f doc/*.css doc/*.html doc/*.png doc/edoc-info
|
||||
|
||||
# Tests.
|
||||
|
||||
$(foreach dep,$(TEST_DEPS),$(eval $(call dep_target,$(dep))))
|
||||
|
|
68
guide/toc.md
|
@ -1,68 +0,0 @@
|
|||
Cowboy User Guide
|
||||
=================
|
||||
|
||||
The Cowboy User Guide explores the modern Web and how to make
|
||||
best use of Cowboy for writing powerful web applications.
|
||||
|
||||
Introducing Cowboy
|
||||
------------------
|
||||
|
||||
* [Introduction](introduction.md)
|
||||
* [The modern Web](modern_web.md)
|
||||
* [Erlang and the Web](erlang_web.md)
|
||||
* [Erlang for beginners](erlang_beginners.md)
|
||||
* [Getting started](getting_started.md)
|
||||
|
||||
HTTP
|
||||
----
|
||||
|
||||
* [The life of a request](http_req_life.md)
|
||||
* [Routing](routing.md)
|
||||
* [Handling plain HTTP requests](http_handlers.md)
|
||||
* [The Req object](req.md)
|
||||
* [Reading the request body](req_body.md)
|
||||
* [Sending a response](resp.md)
|
||||
* [Using cookies](cookies.md)
|
||||
|
||||
Multipart
|
||||
---------
|
||||
|
||||
* [Introduction to multipart](multipart_intro.md)
|
||||
* [Multipart requests](multipart_req.md)
|
||||
|
||||
Static files
|
||||
------------
|
||||
|
||||
* [Static handler](static_handlers.md)
|
||||
|
||||
REST
|
||||
----
|
||||
|
||||
* [REST principles](rest_principles.md)
|
||||
* [Handling REST requests](rest_handlers.md)
|
||||
* [REST flowcharts](rest_flowcharts.md)
|
||||
* [Designing a resource handler](resource_design.md)
|
||||
|
||||
Websocket
|
||||
---------
|
||||
|
||||
* [The Websocket protocol](ws_protocol.md)
|
||||
* [Handling Websocket connections](ws_handlers.md)
|
||||
|
||||
Server push
|
||||
-----------
|
||||
|
||||
* [Loop handlers](loop_handlers.md)
|
||||
|
||||
Pluggable interface
|
||||
-------------------
|
||||
|
||||
* [Middlewares](middlewares.md)
|
||||
* [Protocol upgrades](upgrade_protocol.md)
|
||||
* [Hooks](hooks.md)
|
||||
|
||||
Internals
|
||||
---------
|
||||
|
||||
* [Architecture](architecture.md)
|
||||
* [Dealing with broken clients](broken_clients.md)
|
100
manual/cowboy.md
|
@ -1,100 +0,0 @@
|
|||
cowboy
|
||||
======
|
||||
|
||||
The `cowboy` module provides convenience functions for
|
||||
manipulating Ranch listeners.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
### http_headers() = [{binary(), iodata()}]
|
||||
|
||||
> HTTP headers as a list of key/values.
|
||||
|
||||
### http_status() = non_neg_integer() | binary()
|
||||
|
||||
> HTTP status.
|
||||
>
|
||||
> A binary status can be used to set a custom message.
|
||||
|
||||
### http_version() = 'HTTP/1.1' | 'HTTP/1.0'
|
||||
|
||||
> HTTP version.
|
||||
|
||||
### onrequest_fun() = fun((cowboy_req:req()) -> cowboy_req:req())
|
||||
|
||||
> Fun called immediately after receiving a request.
|
||||
>
|
||||
> It can perform any operation on the `Req` object, including
|
||||
> reading the request body or replying. If a reply is sent,
|
||||
> the processing of the request ends here, before any middleware
|
||||
> is executed.
|
||||
|
||||
### onresponse_fun() = fun((http_status(), http_headers(),
|
||||
iodata(), cowboy_req:req()) -> cowboy_req:req())
|
||||
|
||||
> Fun called immediately before sending the response.
|
||||
>
|
||||
> It can perform any operation on the `Req` object, including
|
||||
> reading the request body or replying. If a reply is sent, it
|
||||
> overrides the reply initially sent. The callback will not be
|
||||
> called again for the new reply.
|
||||
|
||||
Exports
|
||||
-------
|
||||
|
||||
### start_http(Ref, NbAcceptors, TransOpts, ProtoOpts) -> {ok, pid()}
|
||||
|
||||
> Types:
|
||||
> * Ref = ranch:ref()
|
||||
> * NbAcceptors = non_neg_integer()
|
||||
> * TransOpts = ranch_tcp:opts()
|
||||
> * ProtoOpts = cowboy_protocol:opts()
|
||||
>
|
||||
> Start listening for HTTP connections. Returns the pid for this
|
||||
> listener's supervisor.
|
||||
|
||||
### start_https(Ref, NbAcceptors, TransOpts, ProtoOpts) -> {ok, pid()}
|
||||
|
||||
> Types:
|
||||
> * Ref = ranch:ref()
|
||||
> * NbAcceptors = non_neg_integer()
|
||||
> * TransOpts = ranch_ssl:opts()
|
||||
> * ProtoOpts = cowboy_protocol:opts()
|
||||
>
|
||||
> Start listening for HTTPS connections. Returns the pid for this
|
||||
> listener's supervisor.
|
||||
|
||||
### start_spdy(Ref, NbAcceptors, TransOpts, ProtoOpts) -> {ok, pid()}
|
||||
|
||||
> Types:
|
||||
> * Ref = ranch:ref()
|
||||
> * NbAcceptors = non_neg_integer()
|
||||
> * TransOpts = ranch_ssl:opts()
|
||||
> * ProtoOpts = cowboy_spdy:opts()
|
||||
>
|
||||
> Start listening for SPDY connections. Returns the pid for this
|
||||
> listener's supervisor.
|
||||
|
||||
### stop_listener(Ref) -> ok | {error, not_found}
|
||||
|
||||
> Types:
|
||||
> * Ref = ranch:ref()
|
||||
>
|
||||
> Stop a previously started listener.
|
||||
|
||||
### set_env(Ref, Name, Value) -> ok
|
||||
|
||||
> Types:
|
||||
> * Ref = ranch:ref()
|
||||
> * Name = atom()
|
||||
> * Value = any()
|
||||
>
|
||||
> Set or update an environment value for an already running listener.
|
||||
> This will take effect on all subsequent connections.
|
||||
|
||||
See also
|
||||
--------
|
||||
|
||||
The [Ranch guide](http://ninenines.eu/docs/en/ranch/HEAD/guide)
|
||||
provides detailed information about how listeners work.
|
|
@ -1,57 +0,0 @@
|
|||
cowboy_http_handler
|
||||
===================
|
||||
|
||||
The `cowboy_http_handler` behaviour defines the interface used
|
||||
by plain HTTP handlers.
|
||||
|
||||
Unless noted otherwise, the callbacks will be executed sequentially.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
None.
|
||||
|
||||
Callbacks
|
||||
---------
|
||||
|
||||
### init({TransportName, ProtocolName}, Req, Opts)
|
||||
-> {ok, Req, State} | {shutdown, Req, State}
|
||||
|
||||
> Types:
|
||||
> * TransportName = tcp | ssl | atom()
|
||||
> * ProtocolName = http | atom()
|
||||
> * Req = cowboy_req:req()
|
||||
> * Opts = any()
|
||||
> * State = any()
|
||||
>
|
||||
> Initialize the state for this request.
|
||||
>
|
||||
> The `shutdown` return value can be used to skip the `handle/2`
|
||||
> call entirely.
|
||||
|
||||
### handle(Req, State) -> {ok, Req, State}
|
||||
|
||||
> Types:
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
>
|
||||
> Handle the request.
|
||||
>
|
||||
> This callback is where the request is handled and a response
|
||||
> should be sent. If a response is not sent, Cowboy will send
|
||||
> a `204 No Content` response automatically.
|
||||
|
||||
### terminate(Reason, Req, State) -> ok
|
||||
|
||||
> Types:
|
||||
> * Reason = {normal, shutdown} | {error, atom()}
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
>
|
||||
> Perform any necessary cleanup of the state.
|
||||
>
|
||||
> This callback should release any resource currently in use,
|
||||
> clear any active timer and reset the process to its original
|
||||
> state, as it might be reused for future requests sent on the
|
||||
> same connection. Typical plain HTTP handlers rarely need to
|
||||
> use it.
|
|
@ -1,91 +0,0 @@
|
|||
cowboy_loop_handler
|
||||
===================
|
||||
|
||||
The `cowboy_loop_handler` behaviour defines the interface used
|
||||
by HTTP handlers that do not send a response directly, instead
|
||||
requiring a receive loop to process Erlang messages.
|
||||
|
||||
This interface is best fit for long-polling types of requests.
|
||||
|
||||
The `init/3` callback will always be called, followed by zero
|
||||
or more calls to `info/3`. The `terminate/3` will always be
|
||||
called last.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
None.
|
||||
|
||||
Callbacks
|
||||
---------
|
||||
|
||||
### init({TransportName, ProtocolName}, Req, Opts)
|
||||
-> {loop, Req, State}
|
||||
| {loop, Req, State, hibernate}
|
||||
| {loop, Req, State, Timeout}
|
||||
| {loop, Req, State, Timeout, hibernate}
|
||||
| {shutdown, Req, State}
|
||||
|
||||
> Types:
|
||||
> * TransportName = tcp | ssl | atom()
|
||||
> * ProtocolName = http | atom()
|
||||
> * Req = cowboy_req:req()
|
||||
> * Opts = any()
|
||||
> * State = any()
|
||||
> * Timeout = timeout()
|
||||
>
|
||||
> Initialize the state for this request.
|
||||
>
|
||||
> This callback will typically be used to register this process
|
||||
> to an event manager or a message queue in order to receive
|
||||
> the messages the handler wants to process.
|
||||
>
|
||||
> The receive loop will run for a duration of up to `Timeout`
|
||||
> milliseconds after it last received data from the socket,
|
||||
> at which point it will stop and send a `204 No Content` reply.
|
||||
> By default this value is set to `infinity`. It is recommended
|
||||
> to either set this value or ensure by any other mechanism
|
||||
> that the handler will be closed after a certain period of
|
||||
> inactivity.
|
||||
>
|
||||
> The `hibernate` option will hibernate the process until it
|
||||
> starts receiving messages.
|
||||
>
|
||||
> The `shutdown` return value can be used to skip the receive
|
||||
> loop entirely.
|
||||
|
||||
### info(Info, Req, State) -> {ok, Req, State} | {loop, Req, State}
|
||||
| {loop, Req, State, hibernate}
|
||||
|
||||
> Types:
|
||||
> * Info = any()
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
>
|
||||
> Handle the Erlang message received.
|
||||
>
|
||||
> This function will be called every time an Erlang message
|
||||
> has been received. The message can be any Erlang term.
|
||||
>
|
||||
> The `ok` return value can be used to stop the receive loop,
|
||||
> typically because a response has been sent.
|
||||
>
|
||||
> The `hibernate` option will hibernate the process until
|
||||
> it receives another message.
|
||||
|
||||
### terminate(Reason, Req, State) -> ok
|
||||
|
||||
> Types:
|
||||
> * Reason = {normal, shutdown} | {normal, timeout} | {error, closed} | {error, overflow} | {error, atom()}
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
>
|
||||
> Perform any necessary cleanup of the state.
|
||||
>
|
||||
> This callback will typically unregister from any event manager
|
||||
> or message queue it registered to in `init/3`.
|
||||
>
|
||||
> This callback should release any resource currently in use,
|
||||
> clear any active timer and reset the process to its original
|
||||
> state, as it might be reused for future requests sent on the
|
||||
> same connection.
|
|
@ -1,56 +0,0 @@
|
|||
cowboy_middleware
|
||||
=================
|
||||
|
||||
The `cowboy_middleware` behaviour defines the interface used
|
||||
by Cowboy middleware modules.
|
||||
|
||||
Middlewares process the request sequentially in the order they
|
||||
are configured.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
### env() = [{atom(), any()}]
|
||||
|
||||
> The environment variable.
|
||||
>
|
||||
> One is created for every request. It is passed to each
|
||||
> middleware module executed and subsequently returned,
|
||||
> optionally with its contents modified.
|
||||
|
||||
Callbacks
|
||||
---------
|
||||
|
||||
### execute(Req, Env)
|
||||
-> {ok, Req, Env}
|
||||
| {suspend, Module, Function, Args}
|
||||
| {halt, Req}
|
||||
| {error, StatusCode, Req}
|
||||
|
||||
> Types:
|
||||
> * Req = cowboy_req:req()
|
||||
> * Env = env()
|
||||
> * Module = module()
|
||||
> * Function = atom()
|
||||
> * Args = [any()]
|
||||
> * StatusCode = cowboy:http_status()
|
||||
>
|
||||
> Execute the middleware.
|
||||
>
|
||||
> The `ok` return value indicates that everything went well
|
||||
> and that Cowboy should continue processing the request. A
|
||||
> response may or may not have been sent.
|
||||
>
|
||||
> The `suspend` return value will hibernate the process until
|
||||
> an Erlang message is received. Note that when resuming, any
|
||||
> previous stacktrace information will be gone.
|
||||
>
|
||||
> The `halt` return value stops Cowboy from doing any further
|
||||
> processing of the request, even if there are middlewares
|
||||
> that haven't been executed yet. The connection may be left
|
||||
> open to receive more requests from the client.
|
||||
>
|
||||
> The `error` return value sends an error response identified
|
||||
> by the `StatusCode` and then proceeds to terminate the
|
||||
> connection. Middlewares that haven't been executed yet
|
||||
> will not be called.
|
|
@ -1,65 +0,0 @@
|
|||
cowboy_protocol
|
||||
===============
|
||||
|
||||
The `cowboy_protocol` module implements HTTP/1.1 and HTTP/1.0
|
||||
as a Ranch protocol.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
### opts() = [{compress, boolean()}
|
||||
| {env, cowboy_middleware:env()}
|
||||
| {max_empty_lines, non_neg_integer()}
|
||||
| {max_header_name_length, non_neg_integer()}
|
||||
| {max_header_value_length, non_neg_integer()}
|
||||
| {max_headers, non_neg_integer()}
|
||||
| {max_keepalive, non_neg_integer()}
|
||||
| {max_request_line_length, non_neg_integer()}
|
||||
| {middlewares, [module()]}
|
||||
| {onrequest, cowboy:onrequest_fun()}
|
||||
| {onresponse, cowboy:onresponse_fun()}
|
||||
| {timeout, timeout()}]
|
||||
|
||||
> Configuration for the HTTP protocol handler.
|
||||
>
|
||||
> This configuration is passed to Cowboy when starting listeners
|
||||
> using `cowboy:start_http/4` or `cowboy:start_https/4` functions.
|
||||
>
|
||||
> It can be updated without restarting listeners using the
|
||||
> Ranch functions `ranch:get_protocol_options/1` and
|
||||
> `ranch:set_protocol_options/2`.
|
||||
|
||||
Option descriptions
|
||||
-------------------
|
||||
|
||||
The default value is given next to the option name.
|
||||
|
||||
- compress (false)
|
||||
- When enabled, Cowboy will attempt to compress the response body.
|
||||
- env ([{listener, Ref}])
|
||||
- Initial middleware environment.
|
||||
- max_empty_lines (5)
|
||||
- Maximum number of empty lines before a request.
|
||||
- max_header_name_length (64)
|
||||
- Maximum length of header names.
|
||||
- max_header_value_length (4096)
|
||||
- Maximum length of header values.
|
||||
- max_headers (100)
|
||||
- Maximum number of headers allowed per request.
|
||||
- max_keepalive (100)
|
||||
- Maximum number of requests allowed per connection.
|
||||
- max_request_line_length (4096)
|
||||
- Maximum length of the request line.
|
||||
- middlewares ([cowboy_router, cowboy_handler])
|
||||
- List of middlewares to execute for every requests.
|
||||
- onrequest (undefined)
|
||||
- Fun called every time a request is received.
|
||||
- onresponse (undefined)
|
||||
- Fun called every time a response is sent.
|
||||
- timeout (5000)
|
||||
- Time in ms with no requests before Cowboy closes the connection.
|
||||
|
||||
Exports
|
||||
-------
|
||||
|
||||
None.
|
|
@ -1,670 +0,0 @@
|
|||
cowboy_req
|
||||
==========
|
||||
|
||||
The `cowboy_req` module provides functions to access, manipulate
|
||||
and respond to requests.
|
||||
|
||||
The functions in this module follow patterns for their return types,
|
||||
based on the kind of function.
|
||||
|
||||
* access: `{Value, Req}`
|
||||
* action: `{Result, Req} | {Result, Value, Req} | {error, atom()}`
|
||||
* modification: `Req`
|
||||
* question: `boolean()`
|
||||
|
||||
The only exception is the `chunk/2` function which may return `ok`.
|
||||
|
||||
Whenever `Req` is returned, you must use this returned value and
|
||||
ignore any previous you may have had. This value contains various
|
||||
state informations which are necessary for Cowboy to do some lazy
|
||||
evaluation or cache results where appropriate.
|
||||
|
||||
All functions which perform an action should only be called once.
|
||||
This includes reading the request body or replying. Cowboy will
|
||||
generally throw an error on the second call.
|
||||
|
||||
It is highly discouraged to pass the Req object to another process.
|
||||
Doing so and calling `cowboy_req` functions from it leads to
|
||||
undefined behavior.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
### body_opts() = [{continue, boolean()}
|
||||
| {length, non_neg_integer()}
|
||||
| {read_length, non_neg_integer()}
|
||||
| {read_timeout, timeout()}
|
||||
| {transfer_decode, transfer_decode_fun(), any()}
|
||||
| {content_decode, content_decode_fun()}]
|
||||
|
||||
> Request body reading options.
|
||||
|
||||
### cookie_opts() = [{max_age, non_neg_integer()}
|
||||
| {domain, binary()} | {path, binary()}
|
||||
| {secure, boolean()} | {http_only, boolean()}]
|
||||
|
||||
> Cookie options.
|
||||
|
||||
### req() - opaque to the user
|
||||
|
||||
> The `Req` object.
|
||||
>
|
||||
> All functions in this module receive a `Req` as argument,
|
||||
> and most of them return a new object labelled `Req2` in
|
||||
> the function descriptions below.
|
||||
|
||||
Request related exports
|
||||
-----------------------
|
||||
|
||||
### binding(Name, Req) -> binding(Name, Req, undefined)
|
||||
### binding(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
> Types:
|
||||
> * Name = atom()
|
||||
> * Default = any()
|
||||
> * Value = any() | Default
|
||||
>
|
||||
> Return the value for the given binding.
|
||||
>
|
||||
> By default the value is a binary, however constraints may change
|
||||
> the type of this value (for example automatically converting
|
||||
> numbers to integer).
|
||||
|
||||
### bindings(Req) -> {[{Name, Value}], Req2}
|
||||
|
||||
> Types:
|
||||
> * Name = atom()
|
||||
> * Value = any()
|
||||
>
|
||||
> Return all bindings.
|
||||
>
|
||||
> By default the value is a binary, however constraints may change
|
||||
> the type of this value (for example automatically converting
|
||||
> numbers to integer).
|
||||
|
||||
### cookie(Name, Req) -> cookie(Name, Req, undefined)
|
||||
### cookie(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
> * Default = any()
|
||||
> * Value = binary() | Default
|
||||
>
|
||||
> Return the value for the given cookie.
|
||||
>
|
||||
> Cookie names are case sensitive.
|
||||
|
||||
### cookies(Req) -> {[{Name, Value}], Req2}
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
> * Value = binary()
|
||||
>
|
||||
> Return all cookies.
|
||||
|
||||
### header(Name, Req) -> header(Name, Req, undefined)
|
||||
### header(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
> * Default = any()
|
||||
> * Value = binary() | Default
|
||||
>
|
||||
> Return the value for the given header.
|
||||
>
|
||||
> While header names are case insensitive, this function expects
|
||||
> the name to be a lowercase binary.
|
||||
|
||||
### headers(Req) -> {Headers, Req2}
|
||||
|
||||
> Types:
|
||||
> * Headers = cowboy:http_headers()
|
||||
>
|
||||
> Return all headers.
|
||||
|
||||
### host(Req) -> {Host, Req2}
|
||||
|
||||
> Types:
|
||||
> * Host = binary()
|
||||
>
|
||||
> Return the requested host.
|
||||
|
||||
### host_info(Req) -> {HostInfo, Req2}
|
||||
|
||||
> Types:
|
||||
> * HostInfo = cowboy_router:tokens() | undefined
|
||||
>
|
||||
> Return the extra tokens from matching against `...` during routing.
|
||||
|
||||
### host_url(Req) -> {HostURL, Req2}
|
||||
|
||||
> Types:
|
||||
> * HostURL = binary() | undefined
|
||||
>
|
||||
> Return the requested URL excluding the path component.
|
||||
>
|
||||
> This function will always return `undefined` until the
|
||||
> `cowboy_router` middleware has been executed. This includes
|
||||
> the `onrequest` hook.
|
||||
|
||||
### meta(Name, Req) -> meta(Name, Req, undefined)
|
||||
### meta(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
> Types:
|
||||
> * Name = atom()
|
||||
> * Default = any()
|
||||
> * Value = any()
|
||||
>
|
||||
> Return metadata about the request.
|
||||
|
||||
### method(Req) -> {Method, Req2}
|
||||
|
||||
> Types:
|
||||
> * Method = binary()
|
||||
>
|
||||
> Return the method.
|
||||
>
|
||||
> Methods are case sensitive. Standard methods are always uppercase.
|
||||
|
||||
### parse_header(Name, Req) ->
|
||||
### parse_header(Name, Req, Default) -> {ok, ParsedValue, Req2}
|
||||
| {undefined, Value, Req2} | {error, badarg}
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
> * Default = any()
|
||||
> * ParsedValue - see below
|
||||
> * Value = any()
|
||||
>
|
||||
> Parse the given header.
|
||||
>
|
||||
> While header names are case insensitive, this function expects
|
||||
> the name to be a lowercase binary.
|
||||
>
|
||||
> The `parse_header/2` function will call `parser_header/3` with a
|
||||
> different default value depending on the header being parsed. The
|
||||
> following table summarizes the default values used.
|
||||
>
|
||||
> | Header name | Default value |
|
||||
> | ----------------- | ------------------ |
|
||||
> | transfer-encoding | `[<<"identity">>]` |
|
||||
> | Any other header | `undefined` |
|
||||
>
|
||||
> The parsed value differs depending on the header being parsed. The
|
||||
> following table summarizes the different types returned.
|
||||
>
|
||||
> | Header name | Type |
|
||||
> | ---------------------- | ------------------------------------------------- |
|
||||
> | accept | `[{{Type, SubType, Params}, Quality, AcceptExt}]` |
|
||||
> | accept-charset | `[{Charset, Quality}]` |
|
||||
> | accept-encoding | `[{Encoding, Quality}]` |
|
||||
> | accept-language | `[{LanguageTag, Quality}]` |
|
||||
> | authorization | `{AuthType, Credentials}` |
|
||||
> | content-length | `non_neg_integer()` |
|
||||
> | content-type | `{Type, SubType, ContentTypeParams}` |
|
||||
> | cookie | `[{binary(), binary()}]` |
|
||||
> | expect | `[Expect | {Expect, ExpectValue, Params}]` |
|
||||
> | if-match | `'*' | [{weak | strong, OpaqueTag}]` |
|
||||
> | if-modified-since | `calendar:datetime()` |
|
||||
> | if-none-match | `'*' | [{weak | strong, OpaqueTag}]` |
|
||||
> | if-unmodified-since | `calendar:datetime()` |
|
||||
> | range | `{Unit, [Range]}` |
|
||||
> | sec-websocket-protocol | `[binary()]` |
|
||||
> | transfer-encoding | `[binary()]` |
|
||||
> | upgrade | `[binary()]` |
|
||||
> | x-forwarded-for | `[binary()]` |
|
||||
>
|
||||
> Types for the above table:
|
||||
> * Type = SubType = Charset = Encoding = LanguageTag = binary()
|
||||
> * AuthType = Expect = OpaqueTag = Unit = binary()
|
||||
> * Params = ContentTypeParams = [{binary(), binary()}]
|
||||
> * Quality = 0..1000
|
||||
> * AcceptExt = [{binary(), binary()} | binary()]
|
||||
> * Credentials - see below
|
||||
> * Range = {non_neg_integer(), non_neg_integer() | infinity} | neg_integer()
|
||||
>
|
||||
> The cookie names and values, the values of the sec-websocket-protocol
|
||||
> and x-forwarded-for headers, the values in `AcceptExt` and `Params`,
|
||||
> the authorization `Credentials`, the `ExpectValue` and `OpaqueTag`
|
||||
> are case sensitive. All values in `ContentTypeParams` are case sensitive
|
||||
> except the value of the charset parameter, which is case insensitive.
|
||||
> All other values are case insensitive and will be returned as lowercase.
|
||||
>
|
||||
> The headers accept, accept-encoding and cookie headers can return
|
||||
> an empty list. Others will return `{error, badarg}` if the header
|
||||
> value is empty.
|
||||
>
|
||||
> The authorization header parsing code currently only supports basic
|
||||
> HTTP authentication. The `Credentials` type is thus `{Username, Password}`
|
||||
> with `Username` and `Password` being `binary()`.
|
||||
>
|
||||
> The range header value `Range` can take three forms:
|
||||
> * `{From, To}`: from `From` to `To` units
|
||||
> * `{From, infinity}`: everything after `From` units
|
||||
> * `-Final`: the final `Final` units
|
||||
>
|
||||
> An `undefined` tuple will be returned if Cowboy doesn't know how
|
||||
> to parse the requested header.
|
||||
|
||||
### path(Req) -> {Path, Req2}
|
||||
|
||||
> Types:
|
||||
> * Path = binary()
|
||||
>
|
||||
> Return the requested path.
|
||||
|
||||
### path_info(Req) -> {PathInfo, Req2}
|
||||
|
||||
> Types:
|
||||
> * PathInfo = cowboy_router:tokens() | undefined
|
||||
>
|
||||
> Return the extra tokens from matching against `...` during routing.
|
||||
|
||||
### peer(Req) -> {Peer, Req2}
|
||||
|
||||
> Types:
|
||||
> * Peer = {inet:ip_address(), inet:port_number()}
|
||||
>
|
||||
> Return the client's IP address and port number.
|
||||
|
||||
### port(Req) -> {Port, Req2}
|
||||
|
||||
> Types:
|
||||
> * Port = inet:port_number()
|
||||
>
|
||||
> Return the request's port.
|
||||
>
|
||||
> The port returned by this function is obtained by parsing
|
||||
> the host header. It may be different than the actual port
|
||||
> the client used to connect to the Cowboy server.
|
||||
|
||||
### qs(Req) -> {QueryString, Req2}
|
||||
|
||||
> Types:
|
||||
> * QueryString = binary()
|
||||
>
|
||||
> Return the request's query string.
|
||||
|
||||
### qs_val(Name, Req) -> qs_val(Name, Req, undefined)
|
||||
### qs_val(Name, Req, Default) -> {Value, Req2}
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
> * Default = any()
|
||||
> * Value = binary() | true
|
||||
>
|
||||
> Return a value from the request's query string.
|
||||
>
|
||||
> The value `true` will be returned when the name was found
|
||||
> in the query string without an associated value.
|
||||
|
||||
### qs_vals(Req) -> {[{Name, Value}], Req2}
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
> * Value = binary() | true
|
||||
>
|
||||
> Return the request's query string as a list of tuples.
|
||||
>
|
||||
> The value `true` will be returned when a name was found
|
||||
> in the query string without an associated value.
|
||||
|
||||
### set_meta(Name, Value, Req) -> Req2
|
||||
|
||||
> Types:
|
||||
> * Name = atom()
|
||||
> * Value = any()
|
||||
>
|
||||
> Set metadata about the request.
|
||||
>
|
||||
> An existing value will be overwritten.
|
||||
|
||||
### url(Req) -> {URL, Req2}
|
||||
|
||||
> Types:
|
||||
> * URL = binary() | undefined
|
||||
>
|
||||
> Return the requested URL.
|
||||
>
|
||||
> This function will always return `undefined` until the
|
||||
> `cowboy_router` middleware has been executed. This includes
|
||||
> the `onrequest` hook.
|
||||
|
||||
### version(Req) -> {Version, Req2}
|
||||
|
||||
> Types:
|
||||
> * Version = cowboy:http_version()
|
||||
>
|
||||
> Return the HTTP version used for this request.
|
||||
|
||||
Request body related exports
|
||||
----------------------------
|
||||
|
||||
### body(Req) -> body(Req, [])
|
||||
### body(Req, Opts) -> {ok, Data, Req2} | {more, Data, Req2} | {error, Reason}
|
||||
|
||||
> Types:
|
||||
> * Opts = [body_opt()]
|
||||
> * Data = binary()
|
||||
> * Reason = atom()
|
||||
>
|
||||
> Read the request body.
|
||||
>
|
||||
> This function will read a chunk of the request body. If there is
|
||||
> more data to be read after this function call, then a `more` tuple
|
||||
> is returned. Otherwise an `ok` tuple is returned.
|
||||
>
|
||||
> Cowboy will automatically send a `100 Continue` reply if
|
||||
> required. If this behavior is not desirable, it can be disabled
|
||||
> by setting the `continue` option to `false`.
|
||||
>
|
||||
> Cowboy will by default attempt to read up to 8MB of the body,
|
||||
> but in chunks of 1MB. It will use a timeout of 15s per chunk.
|
||||
> All these values can be changed using the `length`, `read_length`
|
||||
> and `read_timeout` options respectively. Note that the size
|
||||
> of the data may not be the same as requested as the decoding
|
||||
> functions may grow or shrink it, and Cowboy makes not attempt
|
||||
> at returning an exact amount.
|
||||
>
|
||||
> Cowboy will properly handle chunked transfer-encoding by
|
||||
> default. If any other transfer-encoding or content-encoding
|
||||
> has been used for the request, custom decoding functions
|
||||
> can be used. The `content_decode` and `transfer_decode`
|
||||
> options allow setting the decode functions manually.
|
||||
>
|
||||
> After the body has been streamed fully, Cowboy will remove
|
||||
> the transfer-encoding header from the `Req` object, and add
|
||||
> the content-length header if it wasn't already there.
|
||||
>
|
||||
> This function can only be called once. Cowboy will not cache
|
||||
> the result of this call.
|
||||
|
||||
### body_length(Req) -> {Length, Req2}
|
||||
|
||||
> Types:
|
||||
> * Length = non_neg_integer() | undefined
|
||||
>
|
||||
> Return the length of the request body.
|
||||
>
|
||||
> The length will only be returned if the request does not
|
||||
> use any transfer-encoding and if the content-length header
|
||||
> is present.
|
||||
|
||||
### body_qs(Req) -> body_qs(Req,
|
||||
[{length, 64000}, {read_length, 64000}, {read_timeout, 5000}])
|
||||
### body_qs(Req, Opts) -> {ok, [{Name, Value}], Req2}
|
||||
| {badlength, Req2} | {error, Reason}
|
||||
|
||||
> Types:
|
||||
> * Opts = [body_opt()]
|
||||
> * Name = binary()
|
||||
> * Value = binary() | true
|
||||
> * Reason = chunked | badlength | atom()
|
||||
>
|
||||
> Return the request body as a list of tuples.
|
||||
>
|
||||
> This function will parse the body assuming the content-type
|
||||
> application/x-www-form-urlencoded, commonly used for the
|
||||
> query string.
|
||||
>
|
||||
> This function calls `body/2` for reading the body, with the
|
||||
> same options it received. By default it will attempt to read
|
||||
> a body of 64KB in one chunk, with a timeout of 5s. If the
|
||||
> body is larger then a `badlength` tuple is returned.
|
||||
>
|
||||
> This function can only be called once. Cowboy will not cache
|
||||
> the result of this call.
|
||||
|
||||
### has_body(Req) -> boolean()
|
||||
|
||||
> Return whether the request has a body.
|
||||
|
||||
### part(Req) -> part(Req,
|
||||
[{length, 64000}, {read_length, 64000}, {read_timeout, 5000}])
|
||||
### part(Req, Opts) -> {ok, Headers, Req2} | {done, Req2}
|
||||
|
||||
> Types:
|
||||
> * Opts = [body_opt()]
|
||||
> * Headers = cow_multipart:headers()
|
||||
>
|
||||
> Read the headers for the next part of the multipart message.
|
||||
>
|
||||
> Cowboy will skip any data remaining until the beginning of
|
||||
> the next part. This includes the preamble to the multipart
|
||||
> message but also the body of a previous part if it hasn't
|
||||
> been read. Both are skipped automatically when calling this
|
||||
> function.
|
||||
>
|
||||
> The headers returned are MIME headers, NOT HTTP headers.
|
||||
> They can be parsed using the functions from the `cow_multipart`
|
||||
> module. In addition, the `cow_multipart:form_data/1` function
|
||||
> can be used to quickly figure out `multipart/form-data` messages.
|
||||
> It takes the list of headers and returns whether this part is
|
||||
> a simple form field or a file being uploaded.
|
||||
>
|
||||
> Note that once a part has been read, or skipped, it cannot
|
||||
> be read again.
|
||||
>
|
||||
> This function calls `body/2` for reading the body, with the
|
||||
> same options it received. By default it will only read chunks
|
||||
> of 64KB with a timeout of 5s. This is tailored for reading
|
||||
> part headers, not for skipping the previous part's body.
|
||||
> You might want to consider skipping large parts manually.
|
||||
|
||||
### part_body(Req) -> part_body(Req, [])
|
||||
### part_body(Req, Opts) -> {ok, Data, Req2} | {more, Data, Req2}
|
||||
|
||||
> Types:
|
||||
> * Opts = [body_opt()]
|
||||
> * Data = binary()
|
||||
>
|
||||
> Read the body of the current part of the multipart message.
|
||||
>
|
||||
> This function calls `body/2` for reading the body, with the
|
||||
> same options it received. It uses the same defaults.
|
||||
>
|
||||
> If there are more data to be read from the socket for this
|
||||
> part, the function will return what it could read inside a
|
||||
> `more` tuple. Otherwise, it will return an `ok` tuple.
|
||||
>
|
||||
> Calling this function again after receiving a `more` tuple
|
||||
> will return another chunk of body. The last chunk will be
|
||||
> returned inside an `ok` tuple.
|
||||
>
|
||||
> Note that once the body has been read, fully or partially,
|
||||
> it cannot be read again.
|
||||
|
||||
Response related exports
|
||||
------------------------
|
||||
|
||||
### chunk(Data, Req) -> ok | {error, Reason}
|
||||
|
||||
> Types:
|
||||
> * Data = iodata()
|
||||
> * Reason = atom()
|
||||
>
|
||||
> Send a chunk of data.
|
||||
>
|
||||
> This function should be called as many times as needed
|
||||
> to send data chunks after calling `chunked_reply/{2,3}`.
|
||||
>
|
||||
> When the method is HEAD, no data will actually be sent.
|
||||
>
|
||||
> If the request uses HTTP/1.0, the data is sent directly
|
||||
> without wrapping it in an HTTP/1.1 chunk, providing
|
||||
> compatibility with older clients.
|
||||
|
||||
### chunked_reply(StatusCode, Req) -> chunked_reply(StatusCode, [], Req)
|
||||
### chunked_reply(StatusCode, Headers, Req) -> {ok, Req2}
|
||||
|
||||
> Types:
|
||||
> * StatusCode = cowboy:http_status()
|
||||
> * Headers = cowboy:http_headers()
|
||||
>
|
||||
> Send a response using chunked transfer-encoding.
|
||||
>
|
||||
> This function effectively sends the response status line
|
||||
> and headers to the client.
|
||||
>
|
||||
> This function will not send any body set previously. After
|
||||
> this call the handler must use the `chunk/2` function
|
||||
> repeatedly to send the body in as many chunks as needed.
|
||||
>
|
||||
> If the request uses HTTP/1.0, the data is sent directly
|
||||
> without wrapping it in an HTTP/1.1 chunk, providing
|
||||
> compatibility with older clients.
|
||||
>
|
||||
> This function can only be called once, with the exception
|
||||
> of overriding the response in the `onresponse` hook.
|
||||
|
||||
### continue(Req) -> ok | {error, Reason}
|
||||
|
||||
> Types:
|
||||
> * Reason = atom()
|
||||
>
|
||||
> Send a 100 Continue intermediate reply.
|
||||
>
|
||||
> This reply is required before the client starts sending the
|
||||
> body when the request contains the `expect` header with the
|
||||
> `100-continue` value.
|
||||
>
|
||||
> Cowboy will send this automatically when required. However
|
||||
> you may want to do it manually by disabling this behavior
|
||||
> with the `continue` body option and then calling this
|
||||
> function.
|
||||
|
||||
### delete_resp_header(Name, Req) -> Req2
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
>
|
||||
> Delete the given response header.
|
||||
>
|
||||
> While header names are case insensitive, this function expects
|
||||
> the name to be a lowercase binary.
|
||||
|
||||
### has_resp_body(Req) -> boolean()
|
||||
|
||||
> Return whether a response body has been set.
|
||||
>
|
||||
> This function will return false if a response body has
|
||||
> been set with a length of 0.
|
||||
|
||||
### has_resp_header(Name, Req) -> boolean()
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
>
|
||||
> Return whether the given response header has been set.
|
||||
>
|
||||
> While header names are case insensitive, this function expects
|
||||
> the name to be a lowercase binary.
|
||||
|
||||
### reply(StatusCode, Req) -> reply(StatusCode, [], Req)
|
||||
### reply(StatusCode, Headers, Req) - see below
|
||||
### reply(StatusCode, Headers, Body, Req) -> {ok, Req2}
|
||||
|
||||
> Types:
|
||||
> * StatusCode = cowboy:http_status()
|
||||
> * Headers = cowboy:http_headers()
|
||||
> * Body = iodata()
|
||||
>
|
||||
> Send a response.
|
||||
>
|
||||
> This function effectively sends the response status line,
|
||||
> headers and body to the client, in a single send function
|
||||
> call.
|
||||
>
|
||||
> The `reply/2` and `reply/3` functions will send the body
|
||||
> set previously, if any. The `reply/4` function overrides
|
||||
> any body set previously and sends `Body` instead.
|
||||
>
|
||||
> If a body function was set, and `reply/2` or `reply/3` was
|
||||
> used, it will be called before returning.
|
||||
>
|
||||
> No more data can be sent to the client after this function
|
||||
> returns.
|
||||
>
|
||||
> This function can only be called once, with the exception
|
||||
> of overriding the response in the `onresponse` hook.
|
||||
|
||||
### set_resp_body(Body, Req) -> Req2
|
||||
|
||||
> Types:
|
||||
> * Body = iodata()
|
||||
>
|
||||
> Set a response body.
|
||||
>
|
||||
> This body will not be sent if `chunked_reply/{2,3}` or
|
||||
> `reply/4` is used, as they override it.
|
||||
|
||||
### set_resp_body_fun(Fun, Req) -> Req2
|
||||
### set_resp_body_fun(Length, Fun, Req) -> Req2
|
||||
|
||||
> Types:
|
||||
> * Fun = fun((Socket, Transport) -> ok)
|
||||
> * Socket = inet:socket()
|
||||
> * Transport = module()
|
||||
> * Length = non_neg_integer()
|
||||
>
|
||||
> Set a fun for sending the response body.
|
||||
>
|
||||
> If a `Length` is provided, it will be sent in the
|
||||
> content-length header in the response. It is recommended
|
||||
> to set the length if it can be known in advance. Otherwise,
|
||||
> the transfer-encoding header will be set to identity.
|
||||
>
|
||||
> This function will only be called if the response is sent
|
||||
> using the `reply/2` or `reply/3` function.
|
||||
>
|
||||
> The fun will receive the Ranch `Socket` and `Transport` as
|
||||
> arguments. Only send and sendfile operations are supported.
|
||||
|
||||
### set_resp_body_fun(chunked, Fun, Req) -> Req2
|
||||
|
||||
> Types:
|
||||
> * Fun = fun((ChunkFun) -> ok)
|
||||
> * ChunkFun = fun((iodata()) -> ok | {error, atom()})
|
||||
>
|
||||
> Set a fun for sending the response body using chunked transfer-encoding.
|
||||
>
|
||||
> This function will only be called if the response is sent
|
||||
> using the `reply/2` or `reply/3` function.
|
||||
>
|
||||
> The fun will receive another fun as argument. This fun is to
|
||||
> be used to send chunks in a similar way to the `chunk/2` function,
|
||||
> except the fun only takes one argument, the data to be sent in
|
||||
> the chunk.
|
||||
|
||||
### set_resp_cookie(Name, Value, Opts, Req) -> Req2
|
||||
|
||||
> Types:
|
||||
> * Name = iodata()
|
||||
> * Value = iodata()
|
||||
> * Opts = cookie_opts()
|
||||
>
|
||||
> Set a cookie in the response.
|
||||
>
|
||||
> Cookie names are case sensitive.
|
||||
|
||||
### set_resp_header(Name, Value, Req) -> Req2
|
||||
|
||||
> Types:
|
||||
> * Name = binary()
|
||||
> * Value = iodata()
|
||||
>
|
||||
> Set a response header.
|
||||
>
|
||||
> You should use `set_resp_cookie/4` instead of this function
|
||||
> to set cookies.
|
||||
|
||||
Misc. exports
|
||||
-------------
|
||||
|
||||
### compact(Req) -> Req2
|
||||
|
||||
> Remove any non-essential data from the `Req` object.
|
||||
>
|
||||
> Long-lived connections usually only need to manipulate the
|
||||
> `Req` object at initialization. Compacting allows saving up
|
||||
> memory by discarding extraneous information.
|
|
@ -1,560 +0,0 @@
|
|||
cowboy_rest
|
||||
===========
|
||||
|
||||
The `cowboy_rest` module implements REST semantics on top of
|
||||
the HTTP protocol.
|
||||
|
||||
This module cannot be described as a behaviour due to most of
|
||||
the callbacks it defines being optional. It has the same
|
||||
semantics as a behaviour otherwise.
|
||||
|
||||
The only mandatory callback is `init/3`, needed to perform
|
||||
the protocol upgrade.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
None.
|
||||
|
||||
Meta values
|
||||
-----------
|
||||
|
||||
### charset
|
||||
|
||||
> Type: binary()
|
||||
>
|
||||
> Negotiated charset.
|
||||
>
|
||||
> This value may not be defined if no charset was negotiated.
|
||||
|
||||
### language
|
||||
|
||||
> Type: binary()
|
||||
>
|
||||
> Negotiated language.
|
||||
>
|
||||
> This value may not be defined if no language was negotiated.
|
||||
|
||||
### media_type
|
||||
|
||||
> Type: {binary(), binary(), '*' | [{binary(), binary()}]}
|
||||
>
|
||||
> Negotiated media-type.
|
||||
>
|
||||
> The media-type is the content-type, excluding the charset.
|
||||
>
|
||||
> This value is always defined after the call to
|
||||
> `content_types_provided/2`.
|
||||
|
||||
Callbacks
|
||||
---------
|
||||
|
||||
### init({TransportName, ProtocolName}, Req, Opts)
|
||||
-> {upgrade, protocol, cowboy_rest}
|
||||
| {upgrade, protocol, cowboy_rest, Req, Opts}
|
||||
|
||||
> Types:
|
||||
> * TransportName = tcp | ssl | atom()
|
||||
> * ProtocolName = http | atom()
|
||||
> * Req = cowboy_req:req()
|
||||
> * Opts = any()
|
||||
>
|
||||
> Upgrade the protocol to `cowboy_rest`.
|
||||
>
|
||||
> This is the only mandatory callback.
|
||||
|
||||
### rest_init(Req, Opts) -> {ok, Req, State}
|
||||
|
||||
> Types:
|
||||
> * Req = cowboy_req:req()
|
||||
> * Opts = any()
|
||||
> * State = any()
|
||||
>
|
||||
> Initialize the state for this request.
|
||||
|
||||
### rest_terminate(Req, State) -> ok
|
||||
|
||||
> Types:
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
>
|
||||
> Perform any necessary cleanup of the state.
|
||||
>
|
||||
> This callback should release any resource currently in use,
|
||||
> clear any active timer and reset the process to its original
|
||||
> state, as it might be reused for future requests sent on the
|
||||
> same connection.
|
||||
|
||||
### Callback(Req, State) -> {Value, Req, State} | {halt, Req, State}
|
||||
|
||||
> Types:
|
||||
> * Callback - one of the REST callbacks described below
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
> * Value - see the REST callbacks description below
|
||||
>
|
||||
> Please see the REST callbacks description below for details
|
||||
> on the `Value` type, the default value if the callback is
|
||||
> not defined, and more general information on when the
|
||||
> callback is called and what its intended use is.
|
||||
>
|
||||
> The `halt` tuple can be returned to stop REST processing.
|
||||
> It is up to the resource code to send a reply before that,
|
||||
> otherwise a `204 No Content` will be sent.
|
||||
|
||||
REST callbacks description
|
||||
--------------------------
|
||||
|
||||
### allowed_methods
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: [binary()]
|
||||
> * Default value: [<<"GET">>, <<"HEAD">>, <<"OPTIONS">>]
|
||||
>
|
||||
> Return the list of allowed methods.
|
||||
>
|
||||
> Methods are case sensitive. Standard methods are always uppercase.
|
||||
|
||||
### allow_missing_post
|
||||
|
||||
> * Methods: POST
|
||||
> * Value type: boolean()
|
||||
> * Default value: true
|
||||
>
|
||||
> Return whether POST is allowed when the resource doesn't exist.
|
||||
>
|
||||
> Returning `true` here means that a new resource will be
|
||||
> created. The URL to the created resource should also be
|
||||
> returned from the `AcceptResource` callback.
|
||||
|
||||
### charsets_provided
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Value type: [binary()]
|
||||
> * Skip to the next step if undefined
|
||||
>
|
||||
> Return the list of charsets the resource provides.
|
||||
>
|
||||
> The list must be ordered in order of preference.
|
||||
>
|
||||
> If the accept-charset header was not sent, the first charset
|
||||
> in the list will be selected. Otherwise Cowboy will select
|
||||
> the most appropriate charset from the list.
|
||||
>
|
||||
> The chosen charset will be set in the `Req` object as the meta
|
||||
> value `charset`.
|
||||
>
|
||||
> While charsets are case insensitive, this callback is expected
|
||||
> to return them as lowercase binary.
|
||||
|
||||
### content_types_accepted
|
||||
|
||||
> * Methods: POST, PUT, PATCH
|
||||
> * No default
|
||||
>
|
||||
> Types:
|
||||
> * Value = [{binary() | {Type, SubType, Params}, AcceptResource}]
|
||||
> * Type = SubType = binary()
|
||||
> * Params = '*' | [{binary(), binary()}]
|
||||
> * AcceptResource = atom()
|
||||
>
|
||||
> Return the list of content-types the resource accepts.
|
||||
>
|
||||
> The list must be ordered in order of preference.
|
||||
>
|
||||
> Each content-type can be given either as a binary string or as
|
||||
> a tuple containing the type, subtype and parameters.
|
||||
>
|
||||
> Cowboy will select the most appropriate content-type from the list.
|
||||
> If any parameter is acceptable, then the tuple form should be used
|
||||
> with parameters set to `'*'`. If the parameters value is set to `[]`
|
||||
> only content-type values with no parameters will be accepted. All
|
||||
> parameter values are treated in a case sensitive manner except the
|
||||
> `charset` parameter, if present, which is case insensitive.
|
||||
>
|
||||
> This function will be called for POST, PUT and PATCH requests.
|
||||
> It is entirely possible to define different callbacks for different
|
||||
> methods if the handling of the request differs. Simply verify
|
||||
> what the method is with `cowboy_req:method/1` and return a
|
||||
> different list for each methods.
|
||||
>
|
||||
> The `AcceptResource` value is the name of the callback that will
|
||||
> be called if the content-type matches. It is defined as follow.
|
||||
>
|
||||
> * Value type: true | {true, URL} | false
|
||||
> * No default
|
||||
>
|
||||
> Process the request body.
|
||||
>
|
||||
> This function should create or update the resource with the
|
||||
> information contained in the request body. This information
|
||||
> may be full or partial depending on the request method.
|
||||
>
|
||||
> If the request body was processed successfully, `true` or
|
||||
> `{true, URL}` may be returned. If an URL is provided, the
|
||||
> response will redirect the client to the location of the
|
||||
> resource.
|
||||
>
|
||||
> If a response body must be sent, the appropriate media-type, charset
|
||||
> and language can be retrieved using the `cowboy_req:meta/{2,3}`
|
||||
> functions. The respective keys are `media_type`, `charset`
|
||||
> and `language`. The body can be set using `cowboy_req:set_resp_body/2`.
|
||||
|
||||
### content_types_provided
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Default value: [{{<<"text">>, <<"html">>, '*'}, to_html}]
|
||||
>
|
||||
> Types:
|
||||
> * Value = [{binary() | {Type, SubType, Params}, ProvideResource}]
|
||||
> * Type = SubType = binary()
|
||||
> * Params = '*' | [{binary(), binary()}]
|
||||
> * ProvideResource = atom()
|
||||
>
|
||||
> Return the list of content-types the resource provides.
|
||||
>
|
||||
> The list must be ordered in order of preference.
|
||||
>
|
||||
> Each content-type can be given either as a binary string or as
|
||||
> a tuple containing the type, subtype and parameters.
|
||||
>
|
||||
> Cowboy will select the most appropriate content-type from the list.
|
||||
> If any parameter is acceptable, then the tuple form should be used
|
||||
> with parameters set to `'*'`. If the parameters value is set to `[]`
|
||||
> only content-type values with no parameters will be accepted. All
|
||||
> parameter values are treated in a case sensitive manner except the
|
||||
> `charset` parameter, if present, which is case insensitive.
|
||||
>
|
||||
> The `ProvideResource` value is the name of the callback that will
|
||||
> be called if the content-type matches. It will only be called when
|
||||
> a representation of the resource needs to be returned. It is defined
|
||||
> as follow.
|
||||
>
|
||||
> * Methods: GET, HEAD
|
||||
> * Value type: iodata() | {stream, Fun} | {stream, Len, Fun} | {chunked, ChunkedFun}
|
||||
> * No default
|
||||
>
|
||||
> Return the response body.
|
||||
>
|
||||
> The response body may be provided directly or through a fun.
|
||||
> If a fun tuple is returned, the appropriate `set_resp_body_fun`
|
||||
> function will be called. Please refer to the documentation for
|
||||
> these functions for more information about the types.
|
||||
>
|
||||
> The call to this callback happens a good time after the call to
|
||||
> `content_types_provided/2`, when it is time to start rendering
|
||||
> the response body.
|
||||
|
||||
### delete_completed
|
||||
|
||||
> * Methods: DELETE
|
||||
> * Value type: boolean()
|
||||
> * Default value: true
|
||||
>
|
||||
> Return whether the delete action has been completed.
|
||||
>
|
||||
> This function should return `false` if there is no guarantee
|
||||
> that the resource gets deleted immediately from the system,
|
||||
> including from any internal cache.
|
||||
>
|
||||
> When this function returns `false`, a `202 Accepted`
|
||||
> response will be sent instead of a `200 OK` or `204 No Content`.
|
||||
|
||||
### delete_resource
|
||||
|
||||
> * Methods: DELETE
|
||||
> * Value type: boolean()
|
||||
> * Default value: false
|
||||
>
|
||||
> Delete the resource.
|
||||
>
|
||||
> The value returned indicates if the action was successful,
|
||||
> regardless of whether the resource is immediately deleted
|
||||
> from the system.
|
||||
|
||||
### expires
|
||||
|
||||
> * Methods: GET, HEAD
|
||||
> * Value type: calendar:datetime() | binary() | undefined
|
||||
> * Default value: undefined
|
||||
>
|
||||
> Return the date of expiration of the resource.
|
||||
>
|
||||
> This date will be sent as the value of the expires header.
|
||||
|
||||
### forbidden
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: boolean()
|
||||
> * Default value: false
|
||||
>
|
||||
> Return whether access to the resource is forbidden.
|
||||
>
|
||||
> A `403 Forbidden` response will be sent if this
|
||||
> function returns `true`. This status code means that
|
||||
> access is forbidden regardless of authentication,
|
||||
> and that the request shouldn't be repeated.
|
||||
|
||||
### generate_etag
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Value type: binary() | {weak | strong, binary()}
|
||||
> * Default value: undefined
|
||||
>
|
||||
> Return the entity tag of the resource.
|
||||
>
|
||||
> This value will be sent as the value of the etag header.
|
||||
>
|
||||
> If a binary is returned, then the value will be parsed
|
||||
> to the tuple form automatically. The value must be in
|
||||
> the same format as the etag header, including quotes.
|
||||
|
||||
### is_authorized
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: true | {false, AuthHeader}
|
||||
> * Default value: true
|
||||
>
|
||||
> Return whether the user is authorized to perform the action.
|
||||
>
|
||||
> This function should be used to perform any necessary
|
||||
> authentication of the user before attempting to perform
|
||||
> any action on the resource.
|
||||
>
|
||||
> If the authentication fails, the value returned will be sent
|
||||
> as the value for the www-authenticate header in the
|
||||
> `401 Unauthorized` response.
|
||||
|
||||
### is_conflict
|
||||
|
||||
> * Methods: PUT
|
||||
> * Value type: boolean()
|
||||
> * Default value: false
|
||||
>
|
||||
> Return whether the put action results in a conflict.
|
||||
>
|
||||
> A `409 Conflict` response will be sent if this function
|
||||
> returns `true`.
|
||||
|
||||
### known_content_type
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: boolean()
|
||||
> * Default value: true
|
||||
>
|
||||
> Return whether the content-type is known.
|
||||
>
|
||||
> This function determines if the server understands the
|
||||
> content-type, regardless of its use by the resource.
|
||||
|
||||
### known_methods
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: [binary()]
|
||||
> * Default value: [<<"GET">>, <<"HEAD">>, <<"POST">>, <<"PUT">>, <<"PATCH">>, <<"DELETE">>, <<"OPTIONS">>]
|
||||
>
|
||||
> Return the list of known methods.
|
||||
>
|
||||
> The full list of methods known by the server should be
|
||||
> returned, regardless of their use in the resource.
|
||||
>
|
||||
> The default value lists the methods Cowboy knows and
|
||||
> implement in `cowboy_rest`.
|
||||
>
|
||||
> Methods are case sensitive. Standard methods are always uppercase.
|
||||
|
||||
### languages_provided
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Value type: [binary()]
|
||||
> * Skip to the next step if undefined
|
||||
>
|
||||
> Return the list of languages the resource provides.
|
||||
>
|
||||
> The list must be ordered in order of preference.
|
||||
>
|
||||
> If the accept-language header was not sent, the first language
|
||||
> in the list will be selected. Otherwise Cowboy will select
|
||||
> the most appropriate language from the list.
|
||||
>
|
||||
> The chosen language will be set in the `Req` object as the meta
|
||||
> value `language`.
|
||||
>
|
||||
> While languages are case insensitive, this callback is expected
|
||||
> to return them as lowercase binary.
|
||||
|
||||
### last_modified
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Value type: calendar:datetime()
|
||||
> * Default value: undefined
|
||||
>
|
||||
> Return the date of last modification of the resource.
|
||||
>
|
||||
> This date will be used to test against the if-modified-since
|
||||
> and if-unmodified-since headers, and sent as the last-modified
|
||||
> header in the response of GET and HEAD requests.
|
||||
|
||||
### malformed_request
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: boolean()
|
||||
> * Default value: false
|
||||
>
|
||||
> Return whether the request is malformed.
|
||||
>
|
||||
> Cowboy has already performed all the necessary checks
|
||||
> by the time this function is called, so few resources
|
||||
> are expected to implement it.
|
||||
>
|
||||
> The check is to be done on the request itself, not on
|
||||
> the request body, which is processed later.
|
||||
|
||||
### moved_permanently
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Value type: {true, URL} | false
|
||||
> * Default value: false
|
||||
>
|
||||
> Return whether the resource was permanently moved.
|
||||
>
|
||||
> If it was, its new URL is also returned and sent in the
|
||||
> location header in the response.
|
||||
|
||||
### moved_temporarily
|
||||
|
||||
> * Methods: GET, HEAD, POST, PATCH, DELETE
|
||||
> * Value type: {true, URL} | false
|
||||
> * Default value: false
|
||||
>
|
||||
> Return whether the resource was temporarily moved.
|
||||
>
|
||||
> If it was, its new URL is also returned and sent in the
|
||||
> location header in the response.
|
||||
|
||||
### multiple_choices
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Value type: boolean()
|
||||
> * Default value: false
|
||||
>
|
||||
> Return whether there are multiple representations of the resource.
|
||||
>
|
||||
> This function should be used to inform the client if there
|
||||
> are different representations of the resource, for example
|
||||
> different content-type. If this function returns `true`,
|
||||
> the response body should include information about these
|
||||
> different representations using `cowboy_req:set_resp_body/2`.
|
||||
> The content-type of the response should be the one previously
|
||||
> negociated and that can be obtained by calling
|
||||
> `cowboy_req:meta(media_type, Req)`.
|
||||
|
||||
### options
|
||||
|
||||
> * Methods: OPTIONS
|
||||
> * Value type: ok
|
||||
> * Default value: ok
|
||||
>
|
||||
> Handle a request for information.
|
||||
>
|
||||
> The response should inform the client the communication
|
||||
> options available for this resource.
|
||||
>
|
||||
> By default, Cowboy will send a `200 OK` response with the
|
||||
> allow header set.
|
||||
|
||||
### previously_existed
|
||||
|
||||
> * Methods: GET, HEAD, POST, PATCH, DELETE
|
||||
> * Value type: boolean()
|
||||
> * Default value: false
|
||||
>
|
||||
> Return whether the resource existed previously.
|
||||
|
||||
### resource_exists
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Value type: boolean()
|
||||
> * Default value: true
|
||||
>
|
||||
> Return whether the resource exists.
|
||||
>
|
||||
> If it exists, conditional headers will be tested before
|
||||
> attempting to perform the action. Otherwise, Cowboy will
|
||||
> check if the resource previously existed first.
|
||||
|
||||
### service_available
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: boolean()
|
||||
> * Default value: true
|
||||
>
|
||||
> Return whether the service is available.
|
||||
>
|
||||
> This function can be used to test that all relevant backend
|
||||
> systems are up and able to handle requests.
|
||||
>
|
||||
> A `503 Service Unavailable` response will be sent if this
|
||||
> function returns `false`.
|
||||
|
||||
### uri_too_long
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: boolean()
|
||||
> * Default value: false
|
||||
>
|
||||
> Return whether the requested URI is too long.
|
||||
>
|
||||
> Cowboy has already performed all the necessary checks
|
||||
> by the time this function is called, so few resources
|
||||
> are expected to implement it.
|
||||
>
|
||||
> A `414 Request-URI Too Long` response will be sent if this
|
||||
> function returns `true`.
|
||||
|
||||
### valid_content_headers
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: boolean()
|
||||
> * Default value: true
|
||||
>
|
||||
> Return whether the content-* headers are valid.
|
||||
>
|
||||
> This also applies to the transfer-encoding header. This
|
||||
> function must return `false` for any unknown content-*
|
||||
> headers, or if the headers can't be understood. The
|
||||
> function `cowboy_req:parse_header/2` can be used to
|
||||
> quickly check the headers can be parsed.
|
||||
>
|
||||
> A `501 Not Implemented` response will be sent if this
|
||||
> function returns `false`.
|
||||
|
||||
### valid_entity_length
|
||||
|
||||
> * Methods: all
|
||||
> * Value type: boolean()
|
||||
> * Default value: true
|
||||
>
|
||||
> Return whether the request body length is within acceptable boundaries.
|
||||
>
|
||||
> A `413 Request Entity Too Large` response will be sent if this
|
||||
> function returns `false`.
|
||||
|
||||
### variances
|
||||
|
||||
> * Methods: GET, HEAD, POST, PUT, PATCH, DELETE
|
||||
> * Value type: [binary()]
|
||||
> * Default value: []
|
||||
>
|
||||
> Return the list of headers that affect the representation of the resource.
|
||||
>
|
||||
> These request headers return the same resource but with different
|
||||
> parameters, like another language or a different content-type.
|
||||
>
|
||||
> Cowboy will automatically add the accept, accept-language and
|
||||
> accept-charset headers to the list if the respective functions
|
||||
> were defined in the resource.
|
||||
>
|
||||
> This operation is performed right before the `resource_exists/2`
|
||||
> callback. All responses past that point will contain the vary
|
||||
> header which holds this list.
|
|
@ -1,68 +0,0 @@
|
|||
cowboy_router
|
||||
=============
|
||||
|
||||
The `cowboy_router` middleware maps the requested host and
|
||||
path to the handler to be used for processing the request.
|
||||
It uses the dispatch rules compiled from the routes given
|
||||
to the `compile/1` function for this purpose. It adds the
|
||||
handler name and options to the environment as the values
|
||||
`handler` and `handler_opts` respectively.
|
||||
|
||||
Environment input:
|
||||
* dispatch = dispatch_rules()
|
||||
|
||||
Environment output:
|
||||
* handler = module()
|
||||
* handler_opts = any()
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
### bindings() = [{atom(), binary()}]
|
||||
|
||||
> List of bindings found during routing.
|
||||
|
||||
### constraints() = [IntConstraint | FunConstraint]
|
||||
|
||||
> Types:
|
||||
> * IntConstraint = {atom(), int}
|
||||
> * FunConstraint = {atom(), function, Fun}
|
||||
> * Fun = fun((binary()) -> true | {true, any()} | false)
|
||||
>
|
||||
> List of constraints to apply to the bindings.
|
||||
>
|
||||
> The int constraint will convert the binding to an integer.
|
||||
> The fun constraint allows writing custom code for checking
|
||||
> the bindings. Returning a new value from that fun allows
|
||||
> replacing the current binding with a new value.
|
||||
|
||||
### dispatch_rules() - opaque to the user
|
||||
|
||||
> Rules for dispatching request used by Cowboy.
|
||||
|
||||
### routes() = [{Host, Paths} | {Host, constraints(), Paths}]
|
||||
|
||||
> Types:
|
||||
> * Host = Path = '_' | iodata()
|
||||
> * Paths = [{Path, Handler, Opts} | {Path, constraints(), Handler, Opts}]
|
||||
> * Handler = module()
|
||||
> * Opts = any()
|
||||
>
|
||||
> Human readable list of routes mapping hosts and paths to handlers.
|
||||
>
|
||||
> The syntax for routes is defined in the user guide.
|
||||
|
||||
### tokens() = [binary()]
|
||||
|
||||
> List of host_info and path_info tokens found during routing.
|
||||
|
||||
Exports
|
||||
-------
|
||||
|
||||
### compile(Routes) -> Dispatch
|
||||
|
||||
> Types:
|
||||
> * Routes = routes()
|
||||
> * Dispatch = dispatch_rules()
|
||||
>
|
||||
> Compile the routes for use by Cowboy.
|
|
@ -1,40 +0,0 @@
|
|||
cowboy_spdy
|
||||
===========
|
||||
|
||||
The `cowboy_spdy` module implements SPDY/3 as a Ranch protocol.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
### opts() = [{env, cowboy_middleware:env()}
|
||||
| {middlewares, [module()]}
|
||||
| {onrequest, cowboy:onrequest_fun()}
|
||||
| {onresponse, cowboy:onresponse_fun()}]
|
||||
|
||||
> Configuration for the SPDY protocol handler.
|
||||
>
|
||||
> This configuration is passed to Cowboy when starting listeners
|
||||
> using the `cowboy:start_spdy/4` function.
|
||||
>
|
||||
> It can be updated without restarting listeners using the
|
||||
> Ranch functions `ranch:get_protocol_options/1` and
|
||||
> `ranch:set_protocol_options/2`.
|
||||
|
||||
Option descriptions
|
||||
-------------------
|
||||
|
||||
The default value is given next to the option name.
|
||||
|
||||
- env ([{listener, Ref}])
|
||||
- Initial middleware environment.
|
||||
- middlewares ([cowboy_router, cowboy_handler])
|
||||
- List of middlewares to execute for every requests.
|
||||
- onrequest (undefined)
|
||||
- Fun called every time a request is received.
|
||||
- onresponse (undefined)
|
||||
- Fun called every time a response is sent.
|
||||
|
||||
Exports
|
||||
-------
|
||||
|
||||
None.
|
|
@ -1,34 +0,0 @@
|
|||
cowboy_static
|
||||
=============
|
||||
|
||||
The `cowboy_static` module implements file serving capabilities
|
||||
by using the REST semantics provided by `cowboy_rest`.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
### opts() = {priv_file, atom(), string() | binary()}
|
||||
| {priv_file, atom(), string() | binary(), extra()}
|
||||
| {file, string() | binary()}
|
||||
| {file, string() | binary(), extra()}
|
||||
| {priv_dir, atom(), string() | binary()}
|
||||
| {priv_dir, atom(), string() | binary(), extra()}
|
||||
| {dir, atom(), string() | binary()}
|
||||
| {dir, atom(), string() | binary(), extra()}
|
||||
|
||||
> Configuration for the static handler.
|
||||
>
|
||||
> The handler can be configured for sending either one file or
|
||||
> a directory (including its subdirectories).
|
||||
>
|
||||
> Extra options allow you to define how the etag should be calculated
|
||||
> and how the mimetype of files should be detected. They are defined
|
||||
> as follow, but do note that these types are not exported, only the
|
||||
> `opts/0` type is public.
|
||||
|
||||
### extra() = [extra_etag() | extra_mimetypes()]
|
||||
|
||||
### extra_etag() = {etag, module(), function()} | {etag, false}
|
||||
|
||||
### extra_mimetypes() = {mimetypes, module(), function()}
|
||||
| {mimetypes, binary() | {binary(), binary(), [{binary(), binary()}]}}
|
|
@ -1,34 +0,0 @@
|
|||
cowboy_sub_protocol
|
||||
===================
|
||||
|
||||
The `cowboy_sub_protocol` behaviour defines the interface used
|
||||
by modules that implement a protocol on top of HTTP.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
None.
|
||||
|
||||
Callbacks
|
||||
---------
|
||||
|
||||
### upgrade(Req, Env, Handler, Opts)
|
||||
-> {ok, Req, Env}
|
||||
| {suspend, Module, Function, Args}
|
||||
| {halt, Req}
|
||||
| {error, StatusCode, Req}
|
||||
|
||||
> Types:
|
||||
> * Req = cowboy_req:req()
|
||||
> * Env = env()
|
||||
> * Handler = module()
|
||||
> * Opts = any()
|
||||
> * Module = module()
|
||||
> * Function = atom()
|
||||
> * Args = [any()]
|
||||
> * StatusCode = cowboy:http_status()
|
||||
>
|
||||
> Upgrade the protocol.
|
||||
>
|
||||
> Please refer to the `cowboy_middleware` manual for a
|
||||
> description of the return values.
|
|
@ -1,40 +0,0 @@
|
|||
cowboy_websocket
|
||||
================
|
||||
|
||||
The `cowboy_websocket` module implements the Websocket protocol.
|
||||
|
||||
The callbacks for websocket handlers are defined in the manual
|
||||
for the `cowboy_websocket_handler` behaviour.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
### close_code() = 1000..4999
|
||||
|
||||
> Reason for closing the connection.
|
||||
|
||||
### frame() = close | ping | pong
|
||||
| {text | binary | close | ping | pong, iodata()}
|
||||
| {close, close_code(), iodata()}
|
||||
|
||||
> Frames that can be sent to the client.
|
||||
|
||||
Meta values
|
||||
-----------
|
||||
|
||||
### websocket_compress
|
||||
|
||||
> Type: true | false
|
||||
>
|
||||
> Whether a websocket compression extension in in use.
|
||||
|
||||
### websocket_version
|
||||
|
||||
> Type: 7 | 8 | 13
|
||||
>
|
||||
> The version of the Websocket protocol being used.
|
||||
|
||||
Exports
|
||||
-------
|
||||
|
||||
None.
|
|
@ -1,131 +0,0 @@
|
|||
cowboy_websocket_handler
|
||||
========================
|
||||
|
||||
The `cowboy_websocket_handler` behaviour defines the interface used
|
||||
by Websocket handlers.
|
||||
|
||||
The `init/3` and `websocket_init/3` callbacks will always be called,
|
||||
followed by zero or more calls to `websocket_handle/3` and
|
||||
`websocket_info/3`. The `websocket_terminate/3` will always
|
||||
be called last.
|
||||
|
||||
Types
|
||||
-----
|
||||
|
||||
None.
|
||||
|
||||
Callbacks
|
||||
---------
|
||||
|
||||
### init({TransportName, ProtocolName}, Req, Opts)
|
||||
-> {upgrade, protocol, cowboy_websocket}
|
||||
| {upgrade, protocol, cowboy_websocket, Req, Opts}
|
||||
|
||||
> Types:
|
||||
> * TransportName = tcp | ssl | atom()
|
||||
> * ProtocolName = http | atom()
|
||||
> * Req = cowboy_req:req()
|
||||
> * Opts = any()
|
||||
>
|
||||
> Upgrade the protocol to `cowboy_websocket`.
|
||||
|
||||
### websocket_init(TransportName, Req, Opts)
|
||||
-> {ok, Req, State}
|
||||
| {ok, Req, State, hibernate}
|
||||
| {ok, Req, State, Timeout}
|
||||
| {ok, Req, State, Timeout, hibernate}
|
||||
| {shutdown, Req}
|
||||
|
||||
> Types:
|
||||
> * TransportName = tcp | ssl | atom()
|
||||
> * Req = cowboy_req:req()
|
||||
> * Opts = any()
|
||||
> * State = any()
|
||||
> * Timeout = timeout()
|
||||
>
|
||||
> Initialize the state for this session.
|
||||
>
|
||||
> This function is called before the upgrade to Websocket occurs.
|
||||
> It can be used to negotiate Websocket protocol extensions
|
||||
> with the client. It will typically be used to register this process
|
||||
> to an event manager or a message queue in order to receive
|
||||
> the messages the handler wants to process.
|
||||
>
|
||||
> The connection will stay up for a duration of up to `Timeout`
|
||||
> milliseconds after it last received data from the socket,
|
||||
> at which point it will stop and close the connection.
|
||||
> By default this value is set to `infinity`. It is recommended
|
||||
> to either set this value or ensure by any other mechanism
|
||||
> that the handler will be closed after a certain period of
|
||||
> inactivity.
|
||||
>
|
||||
> The `hibernate` option will hibernate the process until it
|
||||
> starts receiving either data from the Websocket connection
|
||||
> or Erlang messages.
|
||||
>
|
||||
> The `shutdown` return value can be used to close the connection
|
||||
> before upgrading to Websocket.
|
||||
|
||||
### websocket_handle(InFrame, Req, State)
|
||||
-> {ok, Req, State}
|
||||
| {ok, Req, State, hibernate}
|
||||
| {reply, OutFrame | [OutFrame], Req, State}
|
||||
| {reply, OutFrame | [OutFrame], Req, State, hibernate}
|
||||
| {shutdown, Req, State}
|
||||
|
||||
> Types:
|
||||
> * InFrame = {text | binary | ping | pong, binary()}
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
> * OutFrame = cowboy_websocket:frame()
|
||||
>
|
||||
> Handle the data received from the Websocket connection.
|
||||
>
|
||||
> This function will be called every time data is received
|
||||
> from the Websocket connection.
|
||||
>
|
||||
> The `shutdown` return value can be used to close the
|
||||
> connection. A close reply will also result in the connection
|
||||
> being closed.
|
||||
>
|
||||
> The `hibernate` option will hibernate the process until
|
||||
> it receives new data from the Websocket connection or an
|
||||
> Erlang message.
|
||||
|
||||
### websocket_info(Info, Req, State)
|
||||
-> {ok, Req, State}
|
||||
| {ok, Req, State, hibernate}
|
||||
| {reply, OutFrame | [OutFrame], Req, State}
|
||||
| {reply, OutFrame | [OutFrame], Req, State, hibernate}
|
||||
| {shutdown, Req, State}
|
||||
|
||||
> Types:
|
||||
> * Info = any()
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
> * OutFrame = cowboy_websocket:frame()
|
||||
>
|
||||
> Handle the Erlang message received.
|
||||
>
|
||||
> This function will be called every time an Erlang message
|
||||
> has been received. The message can be any Erlang term.
|
||||
>
|
||||
> The `shutdown` return value can be used to close the
|
||||
> connection. A close reply will also result in the connection
|
||||
> being closed.
|
||||
>
|
||||
> The `hibernate` option will hibernate the process until
|
||||
> it receives another message or new data from the Websocket
|
||||
> connection.
|
||||
|
||||
### websocket_terminate(Reason, Req, State) -> ok
|
||||
|
||||
> Types:
|
||||
> * Reason = {normal, shutdown | timeout} | {remote, closed} | {remote, cowboy_websocket:close_code(), binary()} | {error, badencoding | badframe | closed | atom()}
|
||||
> * Req = cowboy_req:req()
|
||||
> * State = any()
|
||||
>
|
||||
> Perform any necessary cleanup of the state.
|
||||
>
|
||||
> The connection will be closed and the process stopped right
|
||||
> after this call.
|
|
@ -1,21 +0,0 @@
|
|||
Cowboy Function Reference
|
||||
=========================
|
||||
|
||||
The function reference documents the public interface of Cowboy.
|
||||
|
||||
* [The Cowboy Application](cowboy_app.md)
|
||||
* [cowboy](cowboy.md)
|
||||
* [cowboy_handler](cowboy_handler.md)
|
||||
* [cowboy_http_handler](cowboy_http_handler.md)
|
||||
* [cowboy_loop_handler](cowboy_loop_handler.md)
|
||||
* [cowboy_middleware](cowboy_middleware.md)
|
||||
* [cowboy_protocol](cowboy_protocol.md)
|
||||
* [cowboy_req](cowboy_req.md)
|
||||
* [cowboy_rest](cowboy_rest.md)
|
||||
* [cowboy_router](cowboy_router.md)
|
||||
* [cowboy_spdy](cowboy_spdy.md)
|
||||
* [cowboy_static](cowboy_static.md)
|
||||
* [cowboy_sub_protocol](cowboy_sub_protocol.md)
|
||||
* [cowboy_websocket](cowboy_websocket.md)
|
||||
* [cowboy_websocket_handler](cowboy_websocket_handler.md)
|
||||
* [HTTP status codes](http_status_codes.md)
|