Skip to content

Caddy plugin that gives native support for Python WSGI apps.

License

Notifications You must be signed in to change notification settings

vsajip/caddy-snake

 
 

Repository files navigation

Caddy Snake 🐍

Caddy plugin that gives native support for Python WSGI apps.

It embeds the Python interpreter inside Caddy and serves requests directly without going through a reverse proxy or creating a new process.

Docker image

There's a docker image available, it ships Python 3.12 and can be used as follows:

FROM ghcr.io/mliezun/caddy-snake:main

WORKDIR /app

# Copy your project into app
COPY . /app

# Caddy snake is already installed and has support for Python 3.12
CMD ["caddy", "run", "--config", "/app/Caddyfile"]

Build from source

Go 1.21 and Python 3.9 or later is required, with development files to embed the interpreter.

To install in Ubuntu do:

sudo apt-get update
sudo apt-get install -y python3-dev

To install in macOS do:

brew install python@3

Bundling with Caddy

Build this module using xcaddy:

CGO_ENABLED=1 xcaddy build --with github.com/mliezun/[email protected]

Build with Docker (or Podman)

There's a template file in the project: builder.Dockerfile. It supports build arguments to configure which Python or Go version is desired for the build.

FROM ubuntu:latest

ARG GO_VERSION=1.22.1
ARG PY_VERSION=3.12

RUN export DEBIAN_FRONTEND=noninteractive &&\
    apt-get update -yyqq &&\
    apt-get install -yyqq wget tar software-properties-common gcc pkgconf &&\
    add-apt-repository -y ppa:deadsnakes/ppa &&\
    apt-get update -yyqq &&\
    apt-get install -yyqq python${PY_VERSION}-dev &&\
    mv /usr/lib/x86_64-linux-gnu/pkgconfig/python-${PY_VERSION}-embed.pc /usr/lib/x86_64-linux-gnu/pkgconfig/python3-embed.pc &&\
    rm -rf /var/lib/apt/lists/* &&\
    wget https://dl.google.com/go/go${GO_VERSION}.linux-amd64.tar.gz && \
    tar -C /usr/local -xzf go*.linux-amd64.tar.gz && \
    rm go*.linux-amd64.tar.gz

ENV PATH=$PATH:/usr/local/go/bin

RUN go install github.com/caddyserver/xcaddy/cmd/xcaddy@latest &&\
    cd /usr/local/bin &&\
    CGO_ENABLED=1 /root/go/bin/xcaddy build --with github.com/mliezun/caddy-snake &&\
    rm -rf /build

CMD ["cp", "/usr/local/bin/caddy", "/output/caddy"]

You can copy the contents of the builder Dockerfile and execute the following commands to get your Caddy binary:

docker build -f builder.Dockerfile --build-arg PY_VERSION=3.9 -t caddy-snake .
docker run --rm -v $(pwd):/output caddy-snake

Example Caddyfile

{
    http_port 9080
    https_port 9443
    log {
        level error
    }
}
localhost:9080 {
    route {
        python "simple_app:main"
    }
}

The python rule is an HTTP handler that expects a wsgi app as an argument.

Examples

  • simple_app. WSGI App that returns the standard hello world message and a UUID.
  • simple_exception. WSGI App that always raises an exception.
  • example_flask. Flask application that also returns hello world message and a UUID.
  • example_fastapi. FastAPI application that also returns hello world message and a UUID.
  • Caddyfile. Caddy config that uses all of the example apps.

NOTE

It's also possible to provide virtual environments with the following syntax:

python {
    module_wsgi "simple_app:main"
    venv_path "./venv"
}

What it does behind the scenes is to append venv/lib/python3.x/site-packages to python sys.path.

Disclaimer: Currently, when you provide a venv it gets added to the global sys.path, which in consequence means all apps have access to those packages.

Dev resources

LICENSE

MIT License.

About

Caddy plugin that gives native support for Python WSGI apps.

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages

  • C 53.5%
  • Go 37.6%
  • Dockerfile 6.9%
  • Python 2.0%