An open API service indexing awesome lists of open source software.

https://github.com/zellerin/http2

HTTP/2 implementation in Common Lisp
https://github.com/zellerin/http2

common-lisp http2

Last synced: about 1 month ago
JSON representation

HTTP/2 implementation in Common Lisp

Awesome Lists containing this project

README

          

#+TITLE: HTTP/2 in Common Lisp

[[https://github.com/zellerin/http2/actions/workflows/test.yml/badge.svg]]

This is an implementation of HTTP/2 protocol as described in RFC9113 (and
RFC7540 before) and RFC7541 (HPACK). It provides both high-level interface as
well as ways to fine tune its behaviour for better performance or specific use
cases.

For quick start, quickload "http2" and run
#+begin_src lisp
(http2/client:retrieve-url "https://example.com")
#+end_src
to fetch a HTTP/2 resource, and
#+begin_src lisp
(http2/server:start 8443)

(define-exact-handler "/" (send-text-handler "Hello World"))
#+end_src
to start an empty TLS server and serve a "Hello world" page.

Check [[https://doc.zellerin.cz/http2/#HTTP2:@TUTORIALS%20MGL-PAX:SECTION][tutorials]] that show in more detail how to use the client or the server.

** Demo pages

Simple demo can be started by running
: sbcl --script scaffolding/run-server.lisp

It opens two web server, multi-threaded one https://localhost:8080 and a polling
one on https://localhost:8081. Both should be functionally equivalent with a
different backend. Both provide a ~/test~ page that tests some more tricky parts
of the backend in the browser.

** Status
In quicklisp. Documentation on [[https://doc.zellerin.cz/http2/][separate page]].

Implements both thread-per-client and poll-based single threaded server (that may be actually faster).

Tested primarily on sbcl, occasionally on ecl.

Almost all parts of the listed standards implemented, not necessary documented or declared stable

** Missing pieces
- No handling of priorities is implemented. This is more or less OK, as these are
only suggestions, and they are more or less dropped in RFC9113 anyway. But
nothing from RFC9218 is implemented neither (except for the setting).
- Push promises are not implemented in the client. This is OK, they are disabled
by default (settings)
- The MAX-HEADER-LIST-SIZE limit is not enforced, but it is declared as an
advisory setting anyway.
- Some checks on behaviour of the peer are not enforced
- The ping and setting frames are not automatically prioritized (they are
replied as soon as processed, but nothing prevent finishing long response
before that)

** Dependencies

The core library used trivial-gray-streams to implement streams over data frames.

Client and server - or at least some server versions - require usocket and
cl+ssl to talk over TLS, and bordeaux-threads for concurrency.

Client and server use puri to manipulate URLs.

Server also uses cffi directly to check and confirm alpn

Documentation is done with mgl-pax.

Additionally, fiasco is used for testing (and Javascript for browser-side testing).

** Speed & scaling
The code was not written with speed as primary concern. Measurements depend on
many tunable factor both on the client and the server (including platform).

Anyway, run or modify the [[file:scaffolding/speed-test.lisp][speed test code]] for your results.
: sbcl --script scaffolding/speed-test.lisp

** License
Licensed by MIT license.

Some comments are taken over from the RFCs above and copyrighted by RFC
contributors. I read the copyright licenses for RFC that this is allowed.

** Related software
There is an Akamai code on https://github.com/akamai/cl-http2-protocol that
supported bigger parts of the drafted HTTP/2 protocol in 2014; apparently hard
if not impossible to run now. It used NPN instead of ALPN.

# LocalWords: HPACK