Skip to content
/ vicarian Public

Vicarian is a TLS-first reverse proxy with built-in ACME support.

License

Notifications You must be signed in to change notification settings

tarka/vicarian

Repository files navigation

Vicarian

Vicarian is a TLS-first reverse proxy server with built-in ACME support. It is currently targeted at self-hosting and SOHO installations; in particular it supports provisioning TLS certificates behind-the-firewall via ACME DNS-01 and the zone-update library.

Vicarian aims to have sensible defaults without additional configuration.

Project Status

Crates.io GitHub CI License

This software should be consider pre-alpha; the feature-set is MVP and is still in active development. It should not be considered production-ready and no warranty is expressed or implied. It is very-much a work-in-progress and virtually every part of it subject to change without notice.

Only Linux is currently supported (x86_64 and Arm64). Testing for other platforms is welcome.

Features

Current features

  • TLS-first: Port-80/HTTP can be enabled, but will always redirect to the configured TLS server. The exception to this is when the HTTP-01 ACME is enabled; Vicarian will serve any challenge responses directly.
  • Native ACME Support: Vicarian has first-class support for ACME/LetsEncrypt, including DNS-01. LetEncrypt certificate profiles are supported; tlsserver is the default.
  • Multiple DNS Providers: Multiple DNS providers are supported for DNS-01 via the zone-update sibling-project. See that project for a list of supported providers. (Contributions of provider support are very welcome.)
  • Dynamic Certificate Loading: Where TLS certificates are maintained externally Vicarian will dynamically reload certificates when they are updated.
  • Simple backend routing: Traffic can be routed to multiple backend services based on URL paths.
  • Basic path rewriting: This may work with some simple apps that don't support contexts natively, but is likely to fail with more complex apps that have hardcoded paths.
  • Virtual hosts: Hosting of multiple domains and domain aliases is supported, along with certificate generation for host aliases.
  • Separated secrets: ACME DNS requires DNS-provider secrets to be configured. These can be placed in a separate secure file using systemd EnvironmentFile and corn environment injection (see vicarian-dns01.corn for an example).
  • Wildcards: Wildcard ACME certificate generation.

To-dos

  • Access & error logs

  • Happy Eyeballs support

  • Static file support. Pingora itself doesn't support static-files. There are 3rd-party crates that support this but they appear unmaintained at the moment and will need to be evaluated. If you wish to serve a static website one workaround is to use static-web-server to create a static backend:

    static-web-server \
        --host 127.0.0.1 --port 8080 \
        --security-headers true \
        --log-level info \
        --root .
    

    This is how vicarian.org and haltcondition.net are served currently.

  • Docker images.

Possible Future Features

The following may be implemented at some point depending on interest and resources.

  • TLS-ALPN-01 ACME support.
  • Other ACME providers (e.g. ZeroSSL)
  • Prometheus stats.
  • HTTP3/Quic support.
  • h2c backend support (avoids a lot of proxy security corner-cases, but there's not much support in backend server software).
  • Basic 12-factor-style configuration. This should be relatively easy due to corn's support for environment injection; however there is a known issue limiting this currently.

Probably-not features

Vicarian is very opinionated and tries to do the sensible thing by default. Ideally if a particular header or setting was usually required by, say, nginx then it should be the default. e.g. X-Forwarded-For and HSTS are always set. Consequently there are no plans to add a large number of features and settings.

Other notable non-features:

  • Load-balancing, round-robin, complex rewrite rules, etc.
  • Advanced connection tuning

Installation

Release Binaries

Tarballs are available on the Github release page. These contain binaries, documentation, example configuration files, and an example systemd configuration:

├── bin
│   └── vicarian
├── CONFIGURATION.md
├── etc
│   ├── systemd
│   │   └── system
│   │       └── vicarian.service
│   └── vicarian
│       ├── examples
│       │   ├── vicarian-dns01.corn
│       │   ├── vicarian-http01.corn
│       │   └── vicarian-tls-files.corn
│       ├── secrets
│       └── vicarian.corn
├── LICENSE
└── README.md

Install from crates.io

cargo install vicarian

The binary will be available at ~/.crates/bin/vicarian. cargo-binstall is also supported.

Running

Systemd Service

An example systemd service in provided in systemd/vicarian.service. The systemd service sets the CAP_NET_BIND_SERVICE flag which allows binding to ports 80/443 without root.

Configuration

Vicarian currently uses the corn configuration language. The default configuration file is located at /etc/vicarian/vicarian.corn, but can be changed with the --config flag.

Basic Configuration Structure

The full configuration structure is documented in CONFIGURATION.md, and additional examples are available in the examples directory, but a basic working configuration with HTTP-based Let's Encrypt TLS would look like:

{
    listen = {
        addrs = [
            "[::]"  // Default; this covers IPv4 & IPv6
        ]
        insecure_port = 80 // Disabled by default, this will redirect to HTTPS
        tls_port = 443 // Default
    }

    vhosts = [
        {
            hostname = "example.com"

            tls = {
                acme = {
                    contact = "admin@example.com"
                    challenge.type = "http-01"
                }
            }

            backends = [
                {
                    context = "/"
                    url = "http://localhost:8080"
                }
                {
                    context = "/app2"
                    url = "https://localhost:8443"
                    trust = true
                }
            ]
        }
    ]
}

Contributing

Contributions, bug reports, fixes, etc. are welcome.

Additionally, a useful contributions would be to add additional DNS provider APIs to the zone-update project.

Code of Conduct

The project follows the Rust Code of Conduct; this can be found online.

Tech stack

As well as the usual dependencies Vicarian also uses:

AI Contribution Policy

This project will not accept runtime code generated by AI. Generation of draft documentation and test code is acceptable, but should be reviewed by the submitter before raising a PR.

Security Notes

  • Vicarian binds to ports 80 and 443 by default, requiring appropriate permissions
  • The systemd service uses CAP_NET_BIND_SERVICE to bind to privileged ports without full root privileges
  • Private keys are stored in PEM format and should be properly secured
  • When using ACME with DNS-01 challenges, ensure DNS provider API credentials are stored securely

License

This project is licensed under the Apache License 2.0 - see the LICENSE file for details.

About

Vicarian is a TLS-first reverse proxy with built-in ACME support.

Resources

License

Code of conduct

Stars

Watchers

Forks

Packages

No packages published

Languages