Ace

HTTP web server and client, supports http1 and http2

Hex pm Build Status License

Get started

Hello, World!

defmodule MyApp do
  use Raxx.Server

  @impl Raxx.Server
  def handle_request(%{method: :GET, path: []}, %{greeting: greeting}) do
    response(:ok)
    |> set_header("content-type", "text/plain")
    |> set_body("#{greeting}, World!")
  end
end

Raxx

Ace implements the Raxx HTTP interface. This allows applications to be built with any components from the Raxx ecosystem.

Raxx has tooling for streaming, server-push, routing, api documentation and more. See documentation for details.

The correct version of raxx is included with ace, raxx does not need to be added as a dependency.

Start a service

application = {MyApp, %{greeting: "Hello"}}
options = [port: 8080, cleartext: true]

Ace.HTTP.Service.start_link(application, options)

TLS/SSL

If a service is started without the cleartext it will start using TLS. This requires a certificate and key.

application = {MyApp, %{greeting: "Hello"}}
options = [port: 8443, certfile: "path/to/certificate", keyfile: "path/to/key"]

Ace.HTTP.Service.start_link(application, options)

TLS is required to serve content via HTTP/2.

Supervising services

The normal way to run services is as part of a projects supervision tree. When starting a new project use the --sup flag.

mix new my_app --sup

Add the services to be supervised in the application file lib/my_app/application.ex.

defmodule MyApp.Application do
  # See https://hexdocs.pm/elixir/Application.html
  # for more information on OTP Applications
  @moduledoc false

  use Application

  def start(_type, _args) do
    import Supervisor.Spec, warn: false

    # List all child processes to be supervised
    children = [
       supervisor(Ace.HTTP.Service, [
         {MyApp, %{greeting: "Hello"}},
         [port: 8080, cleartext: true]
       ]),
    ]

    # See https://hexdocs.pm/elixir/Supervisor.html
    # for other strategies and supported options
    opts = [strategy: :one_for_one, name: MyApp.Supervisor]
    Supervisor.start_link(children, opts)
  end
end

Start project using iex -S mix and visit http://localhost:8080.

Features

  • [x] Consistent server and client interfaces
  • [x] Stream isolation; one process per stream
  • [x] Bidirectional streaming; send and receive streamed data
  • [x] Server push; to reduce latency
  • [x] Automatic flow control; at stream and connection level
  • [x] Secure data transport; TLS(SSL) support via ALPN
  • [x] Verified against h2spec (143/146)
  • [x] Simple request/response interactions; Raxx interface
  • [x] HTTP upgrade mechanisms
  • [ ] HTTP/1.1 pipelining

View progress on the roadmap.

Testing

Run h2spec against the example hello_http2 application.

  1. Start the example app.
  cd examples/hello_http2
  iex -S mix
  1. Run h2spec from docker
  sudo docker run --net="host" summerwind/h2spec --port 8443 -t -k -S