Architecture¶
omni_httpd serves HTTP connections by employing a fleet of background workers.
There's a master worker that handles starting HTTP workers and handling configuration change requests 1
There are multiple HTTP workers 2. Each HTTP worker is an instance of Postgres and can therefore handle incoming requests. This is done by running a matching route handler on the main thread, and handling network I/O of HTTP requests and responses on a secondary thread 3.
To enable scenarios where multiplexing is possible (such as HTTP/2), omni_httpd will attempt to re-send incoming HTTP/2 (or higher) requests to other workers if the current worker is busy handling a request.
Below is a diagram outlining general workflow.
sequenceDiagram
autonumber
actor B as Browser
box lightyellow Multiple instances
participant H as HTTP server thread
participant HW as HTTP worker
end
participant MW as Master worker
participant P as Postgres
actor O as Operator
P -->> MW: Start background worker
loop omni_httpd.http_workers GUC times
MW -->> HW: Start background worker
end
HW -->> H: Start
loop for every request
B ->> H: HTTP request
critical Dispatch
H ->> HW: Request
HW ->> HW: Run handler query
option HTTP worker busy (HTTP/2+)
H ->> H: proxy to another worker
option HTTP worker busy (HTTP/1)
H ->> H: Wait until not busy
end
HW ->> H: Response
H ->> B: Response
end
O ->> P: Update listeners and/or handlers
Want to know more?
Master worker opens the listening socket and shares it with HTTP workers over a UNIX socket (using
SCM_RIGHTS
). More work needs to be done to improve this. Please consider contributing!Actual HTTP functionality is enabled by awesome h2o web server. Particularly, its libh2o component.