Search code examples
perlnginxpsgi

Is there a Perl PSGI/Plack server available that only speaks PSGI and not also HTTP?


A usual deployment have looked in past and present like the following to me:

+------------------+     +---------+ tcp +-------+ tcp
| PSGI Application |----o| Starman |---->| nginx |<----(internet)
+------------------+     +---------+     +-------+

In fact I do have two fully fledged web servers in between the internet and the actual web application.

Since nginx has uWSGI directly build in and uWSGI supports the PSGI protocol, which is a fork of WSGI, I would love to use a PSGI-broker (only PSGI no HTTP) instead of a full fledged web server (Starman).

Is there an PSGI-only-broker solution available?


Solution

  • The PSGI 'protocol' (like WSGI) is essentially a calling convention for a subroutine. A request comes into the application as a subroutine call with a hash as an argument. The application responds through the subroutine's return value: an arrayref containing HTTP status code, HTTP headers and body. There's more to it than that, but those are the essentials.

    What this means is that a process can only implement PSGI if the process contains a Perl interpreter. To achieve this, the process might be implemented in Perl or it might be implemented in a language like C that can load the libperl.so shared library. Similarly a process can only implement WSGI if it contains a Python interpreter.

    Your block diagram contains three parts, but in reality the PSGI application is inside the Starman process. So there are really only two parts (although both parts are multiprocess containers).

    You say that "nginx has uWSGI directly build in". This does not mean that a WGSI application runs inside the Nginx process. It means that the WSGI application runs in a separate uwsgi process and Nginx communicates with that process over a TCP socket using the uWSGI protocol. This is essentially the same model as Nginx with Starman behind it, but with the distinction that the socket connection to Starman will use the HTTP protocol:

    .----------------------.          .-----------.
    |       Starman        |          |   Nginx   |
    |                      |   HTTP   |           |   HTTP
    | .------------------. |<---------|           |<-------(internet)
    | | PSGI Application | |          |           |
    | '------------------' |          |           |
    '----------------------'          '-----------'
    

    The HTTP protocol does have higher overheads than the uWSGI protocol so you could get better performance by running an application server that speaks the WSGI socket protocol and can load libperl.so to implement the PSGI interface. uWSGI can do that:

    .----------------------.          .----------.
    |        uWSGI         |          |  Nginx   |
    |                      |   WSGI   |          |   HTTP
    | .------------------. |<---------|          |<-------(internet)
    | | PSGI Application | |          |          |
    | '------------------' |          |          |
    '----------------------'          '----------'