Skip to main content

10 posts tagged with "release"

View All Tags

Snakeway v0.13.1

Highlights

HTTP/2 to HTTP/1.1 protocol translation

Snakeway no longer requires TLS-enabled upstreams when serving HTTP/2 clients. Previously, HTTP/2 downstream connections were only supported for gRPC routes with TLS backends.

Now, HTTP/2 clients can connect to any TLS ingress bind and the proxy translates requests to HTTP/1.1 for plaintext upstream services automatically.

This means you can enable enable_http2 = true on an ingress bind and point it at standard HTTP/1.1 backends without any additional configuration. The proxy handles the protocol difference transparently.

Three protocol paths are now supported:

Client protocolUpstreamBehavior
HTTP/2 + TLSTLSEnd-to-end HTTP/2 (gRPC, h2-to-h2)
HTTP/2 + TLSPlaintextHTTP/2 to HTTP/1.1 translation (new)
HTTP/1.1EitherHTTP/1.1 pass-through (unchanged)

Response device pipeline for HTTP/2

Response devices (logging, header manipulation) now run on all HTTP/2 responses, not just HTTP/1.1 responses. Previously, the response device pipeline was skipped for HTTP/2 connections. This was incorrect for the h2-to-h1 path where the response is a normal HTTP response that should be processed by devices.

Upgrade Notes

No configuration changes are required.

Existing enable_http2 = true ingresses will continue to work as before for gRPC and TLS upstreams. The new h2-to-h1 translation activates automatically when an HTTP/2 client connects to an ingress that routes to plaintext upstreams.

Snakeway v0.13.0

Highlights

Graceful shutdown controls

Snakeway now gives you explicit control over how the proxy shuts down. When the process receives SIGTERM (or systemctl stop), active connections get a configurable window to finish before being dropped:

server {
shutdown {
drain_seconds = 10 # default: 10
force_timeout_seconds = 30
}
}

Previously, a shutdown with long-lived connections (WebSocket, gRPC streams) could hang indefinitely. The new defaults give connections 10 seconds to complete, and force_timeout_seconds provides a hard ceiling when set.

Organized server configuration (breaking)

Several server settings have been reorganized into logical groups. This makes the config file easier to read and reduces clutter at the top level of the server block.

Before (v0.12.0):

server {
version = 1
threads = 8
work_stealing = true
upgrade_sock = "/var/run/snakeway_upgrade.sock"
}

After (v0.13.0):

server {
version = 1
threads = 8

upgrade {
sock = "/var/run/snakeway_upgrade.sock"
}

performance {
work_stealing = true
}
}

The following fields moved into sub-blocks:

  • work_stealing moved into performance {}
  • upgrade_sock and upgrade_max_retries moved into upgrade {} (renamed to sock and max_retries)

All sub-blocks are optional. When omitted, the defaults apply.

New performance tuning options

Two new settings in the performance {} block let you tune connection handling:

performance {
upstream_connection_pool_size = 256 # default: 128
parallel_accepts_per_listener = 4 # default: 1
}

upstream_connection_pool_size controls how many idle connections are kept warm to upstream servers per worker thread. Increase this for high-traffic deployments with many backends.

parallel_accepts_per_listener controls how many accept tasks run per listener. Higher values reduce contention under bursty connection rates. Most deployments do not need to change this.

Upstream source address binding

A new upstream_source_addresses block lets you pin outbound upstream connections to specific local IP addresses:

server {
upstream_source_addresses {
ipv4 = ["10.0.1.5", "10.0.1.6"]
ipv6 = ["fd00::1"]
}
}

This is useful when your server has multiple network interfaces and you need upstream traffic to exit through a specific one, or when upstream servers use IP-based access control. When multiple addresses are specified, Snakeway round-robins across them.

Default config directory

The default config directory is now /etc/snakeway on all platforms. Previously, the --config flag was required unless SNAKEWAY_CONFIG was set. This aligns with the systemd unit and Docker image, both of which already used /etc/snakeway.

Improved systemd service

The packaged systemd unit gained several fixes discovered during production testing:

  • SNAKEWAY_LOG_DIR is now set, so logs are written to /var/log/snakeway/.
  • LogsDirectory=snakeway ensures the log directory exists with correct ownership.
  • TimeoutStopSec=30 prevents the stop command from hanging indefinitely if connections do not drain within the configured shutdown window.

Validation warnings no longer block startup

Configuration warnings (non-critical issues like unused TLS automation with no TLS listeners) no longer prevent the proxy from starting. Only errors block startup. Warnings are still printed to stderr so operators can address them at their convenience.

Documentation

  • The Server block reference documents all new settings: shutdown, performance, upstream_source_addresses, and the reorganized upgrade block.
  • New confval page documents the validation primitives crate.
  • The Configuration Internals page reflects the updated validation architecture.

Upgrade Notes

The work_stealing, upgrade_sock, and upgrade_max_retries fields have moved into sub-blocks. Update your snakeway.hcl before upgrading:

  • work_stealing = true becomes performance { work_stealing = true }
  • upgrade_sock = "..." becomes upgrade { sock = "..." }
  • upgrade_max_retries = 5 becomes upgrade { max_retries = 5 }

If you omit these blocks entirely, the defaults apply and no action is needed.

Snakeway v0.12.0

Highlights

Zero-drop hot reload of listeners

Snakeway can now reload listener-level configuration without dropping connections. Previously, changes to listener address, port, TLS termination, HTTP/2, connection filters, or worker thread count required a full restart with a brief interruption. These now apply through a zero-drop upgrade that preserves the TCP accept queue and lets in-flight requests drain to completion.

The reload loop picks the right path automatically. SIGHUP and POST /admin/reload continue to work for both runtime-swappable changes (routes, services, devices, TLS certs) and listener-level changes; operators do not need to choose between them.

A new snakeway upgrade command is available for manual control, but most operators will not need it. See the Hot Reload page for details, including the Linux-only caveat for the underlying file-descriptor transfer.

Admin API authentication (breaking)

The Admin API now requires bearer token authentication. Every admin request must present an Authorization: Bearer <token> header; requests without one (or with an unknown token) receive 401 Unauthorized.

Tokens are configured via a token file referenced from the bind_admin block:

bind_admin = {
interface = "127.0.0.1"
port = 8440
tls = {
mode = "manual"
cert = "/etc/snakeway/admin.crt"
key = "/etc/snakeway/admin.key"
}
auth = {
bearer = {
token_file = "/etc/snakeway/admin.tokens"
}
}
}

The token file holds one token per line, each at least 32 bytes. Multiple tokens are accepted concurrently to support rotation: append the new token, reload, migrate callers, remove the old token, reload again. There is no window where a caller must choose between the old and new token.

Authentication is the innermost of three layers and does not replace network-level restriction or TLS. The bind_admin listener still rejects wildcard interfaces and still requires manual TLS. See the Admin API guide for the full reference and rotation workflow.

Configurable config directory via environment variable

A new SNAKEWAY_CONFIG environment variable sets the config directory for all CLI commands. This removes the need to repeat --config /etc/snakeway on every invocation when working with a non-default config path.

export SNAKEWAY_CONFIG=/etc/snakeway

snakeway config check
snakeway config dump
snakeway route solve ...
snakeway run

An explicit --config flag always takes precedence. The packaged systemd unit and Docker image both set this variable to /etc/snakeway, so operators who SSH into a production host can run diagnostic commands without specifying the path.

Secret zeroize-on-drop

Bearer token digests and TLS private keys are now zeroed in memory when dropped, narrowing the window during which a process memory dump could expose long-lived secrets.

Everything else

CLI

  • New snakeway upgrade command for manually triggering a zero-drop upgrade. Like reload, it requires a configured pid_file. The automatic upgrade path triggered by reload is sufficient for most workflows.
  • New --test flag on snakeway run validates the configuration and exits with code 0 if valid or 1 if not. Useful for verifying a new binary or config before committing to an upgrade.

Server block

Two new fields support the zero-drop upgrade path:

  • upgrade_sock (default /tmp/pingora_upgrade.sock): set a unique value when running multiple Snakeway instances on the same host.
  • upgrade_max_retries (default 5): retry budget for the cross-process handoff.

Packaging

  • The Docker image and systemd unit both set SNAKEWAY_CONFIG=/etc/snakeway.

Documentation

  • New Hot Reload page covering both reload paths and platform constraints.
  • The Admin API guide gained a full Authentication section.
  • The Server block reference documents the new upgrade_sock and upgrade_max_retries fields.
  • The CLI reference documents the new upgrade command, the run --test flag, and the SNAKEWAY_CONFIG environment variable.
  • Added an Ubuntu/Debian install note pointing to the .deb package on the releases page.
  • Roadmap milestones reorganized.

Upgrade Notes

If you have a bind_admin block in your config, add an auth.bearer.token_file entry and create the token file before upgrading. Existing configs without admin auth will fail validation on the new release. See the Admin API authentication guide for the token file format.

If you intend to use the zero-drop upgrade path, ensure pid_file is set in your server block, and set upgrade_sock to a host-unique path if you run multiple Snakeway instances on the same machine.

Snakeway v0.10.0

Highlights

Observability

  • OpenTelemetry support fleshed out
  • Request tracing with span context propagation
  • Async telemetry initialization

Configuration overhaul (snakeway-conf)

  • Deferred upstream DNS resolution to connection time instead of startup
  • ACME directories now require pre-provisioning (no auto-creation)
  • Reworked device config loading, validation, and lowering
  • Eliminated duplicate validation

WASM device API

  • on_stream_request_body hook added with BodyChunk/BodyResult types
  • wit-bindgen upgraded, WIT bindings updated

Everything else

Repository restructuring

  • Moved source code into a crates/ workspace layout: snakeway, snakeway-conf, snakeway-core, snakeway-wit, snakeway-tests
  • Moved integration tests from tests/integration/ to crates/snakeway-tests/
  • Adopted workspace-level package metadata in Cargo.toml

Core library buildout (snakeway-core)

  • All business logic extracted/moved into snakeway-core
  • New runtime state management, server module, and types
  • Device pipeline rework: device trait extracted, explicit re-exports, WASM device improvements
  • Identity device added
  • Device path scoping (devices can now be scoped to specific URL paths)
  • ServiceId optimized from String to Arc<str>
  • Hotpath profiling instrumentation added
  • CL.TE smuggling check moved to early_request_filter
  • Removed redundant header lowercasing (HTTP library already canonicalizes)

Testing and CI

  • Fleshed out integration test suite with HTTP replay tests (raw .http fixture files over TCP)
  • Refactored ConfigBuilder for integration tests
  • Added Criterion microbenchmarks in snakeway-core/benches/ with a public bench_api module
  • Added sccache to CI, test count badges, coverage badges
  • Multi-platform build/release workflow (x86_64 + aarch64 musl)
  • Nextest configuration added

Dependency upgrades

  • wasmtime/wasi 42 -> 43, wit-bindgen 0.50 -> 0.56
  • criterion 0.5 -> 0.8, rand 0.9 -> 0.10, sha2 0.10 -> 0.11
  • tokio 1.48 -> 1.52, reqwest -> 0.13, tokio-tungstenite -> 0.29

Packaging and distribution

  • Dockerfile added
  • .dockerignore added
  • Packaging/distribution infrastructure (Phase 6)

Documentation and tooling

  • CLAUDE.md and 8 skill files added
  • Docusaurus docs resynced, versioning enabled
  • Justfile significantly expanded (+343 lines), decomposed into modular recipes
  • LLM_DISCLOSURE.md added
  • Public API renamed (run_cli -> run)

Snakeway v0.9.0

Breaking Changes

TLS configuration now requires a mode

The tls block inside bind and bind_admin now requires an explicit mode field.

Before (v0.8.0):

bind = {
tls = {
cert = "/path/to/certs/server.pem"
key = "/path/to/certs/server.key"
}
}

After (v0.9.0):

bind = {
tls = {
mode = "manual"
cert = "/path/to/certs/server.pem"
key = "/path/to/certs/server.key"
}
}

Set mode = "manual" to preserve the existing behavior. The new "acme" mode enables automatic certificate issuance and renewal.

Routes now require a hosts field

Service routes and static file routes now require a hosts list. This enables virtual hosting — multiple domains can be served from a single Snakeway instance.

Before (v0.8.0):

routes = [
{ path = "/api" }
]

After (v0.9.0):

routes = [
{
hosts = ["example.com"]
path = "/api"
}
]

Use ["*"] to match all hostnames and preserve previous behavior when upgrading:

routes = [
{
hosts = ["*"]
path = "/api"
}
]

New Features

Automatic TLS Certificate Renewal (ACME)

Snakeway now supports automatic TLS certificate issuance and renewal via the ACME protocol (Let's Encrypt).

Configure tls_automation in snakeway.hcl:

server {
tls_automation = {
renew_within_days = 30
acme = {
directory_url = "https://acme-v02.api.letsencrypt.org/directory"
data_dir = "/var/lib/snakeway/acme"
contact_email = ["admin@example.com"]
}
cert_store = {
type = "filesystem"
cert_dir = "/var/lib/snakeway/acme/certs"
}
}
}

Then set mode = "acme" on any bind block you want managed automatically:

bind = {
tls = {
mode = "acme"
domains = ["example.com", "api.example.com"]
challenge = "http01"
}
}

Certificates are renewed automatically in the background. No restart or reload is required.

See the TLS Cert Management guide for full details.

Virtual Hosting (SNI / host-based routing)

Routes now accept a hosts list, allowing a single Snakeway instance to serve multiple domains. Incoming requests are matched against the Host header before path matching is applied.

See the Routes reference for full details.

Upstream TLS

Upstream connections can now be made over TLS. Configure this per endpoint:

endpoint = {
host = "backend.internal"
port = 8443
tls = {
sni = "backend.internal"
verify = true
// ca_file = "/path/to/ca.pem" // optional; falls back to server.ca_file
}
}

See the Upstream TLS reference for the full field reference.

route solve CLI Command

Debug routing decisions without starting the proxy. The command runs the same config loading, lowering, and routing logic used by the live proxy:

snakeway route solve http://example.com/api/v1/users --config /etc/snakeway

Supports --trace, --verbose, --format=json, and deterministic upstream selection via --lb-index / --lb-key.

See route solve for full documentation.

Snakeway v0.7.0

Highlights

1. New config init Templates

You can now generate a fully structured configuration directory using built-in templates:

snakeway config init ./my-proxy --template=httpbin

Available templates:

  • minimal -- Barebones starting point
  • httpbin -- Working reverse proxy example
  • dev -- Full-featured development setup

Generated structure:

my-proxy/ ├── device.d/ ├── ingress.d/ └── snakeway.hcl

This makes onboarding easier and removes guesswork when starting a new deployment.

2. Standardized config dump and config check

Both commands now support consistent output formats using --format:

snakeway config check /etc/snakeway --format=json
snakeway config dump /etc/snakeway --format=hcl --repr=runtime

Supported formats:

  • hcl
  • json
  • yaml

You can inspect either:

  • --repr=spec (your configuration files)
  • --repr=runtime (internal resolved state)

This improves automation, CI validation, and debugging workflows.

3. Directory Naming Cleanup (Breaking Change)

The include section has been standardized.

Old:

include {
devices = "devices.d/*.hcl"
ingress = "ingress.d/*.hcl"
}

New:

include {
devices = "device.d/*.hcl"
ingresses = "ingress.d/*.hcl"
}

Changes:

  • devices.d/device.d/
  • ingressingresses

If upgrading, update both your snakeway.hcl and directory names.

4. Identity Device Hardening

The Identity device now exposes two configurable limits:

identity_device = {
max_x_forwarded_for_length = 1024
max_user_agent_length = 2048
}

These were previously hard-coded. Both are range validated and applied during parsing, improving safety against oversized or malicious headers.

5. Logging Simplified and Clarified

Runtime logging is now controlled via environment variables:

  • RUST_LOG
  • SNAKEWAY_LOG_DIR
  • TOKIO_CONSOLE

Structured observability remains available via the structured_logging_device.

Everything Else

Config System Refactor

  • Clear separation between specification types and runtime types
  • Health check and circuit breaker moved to explicit Spec and Config types
  • Reduced internal unwrap/expect usage

CLI Namespace Cleanup

Internal CLI modules moved from cli::conf to cli::config.
User-facing commands remain unchanged.

HCL Serialization Improvements

Snakeway now uses an internal HCL serializer that:

  • Preserves identifier keys
  • Produces clean HCL output
  • Supports dumping runtime structures

Optional Field Serialization Cleanup

Many configuration fields now use:

#[serde(skip_serializing_if = "Option::is_none")]

This keeps generated configurations clean and avoids emitting default values unnecessarily.

WASM Feature Gate Cleanup

Header mutation APIs are now gated behind the wasm feature.
They are only available when WASM support is enabled.

Removal of rust-embed

Embedded config templates have been removed.
Templates are now generated programmatically at runtime, reducing binary size and improving clarity.

Validation Improvements

  • Identity header limits are now range validated
  • Validation error output improved
  • Fixture failures now clearly display violations

Documentation Updates

  • CLI docs updated for new flags and behavior
  • Logging docs clarified
  • Getting started guide updated for template-based initialization
  • Roadmap reorganized for clearer phase separation

Upgrade Notes

If upgrading:

In snakeway.hcl:

  1. Rename devices.d/device.d/
  2. Update the include block to use ingresses

In your Identity device config file:

  1. Consider explicitly setting:
    • max_x_forwarded_for_length
    • max_user_agent_length

Snakeway v0.6.0

Highlights

  • New built-in Network Policy device (L7 allow/deny by client identity)

    • Add a network_policy_device to enforce CIDR-based allow/deny decisions at the HTTP layer.
    • Includes forwarded-request handling controls (e.g., whether to allow forwarded requests and what to do when forwarded headers are invalid).
  • New built-in Request Rate Limiting device (L7)

    • Add a request_rate_limiting_device to cap request volume per client over a rolling time window.
  • Listener-level connection controls

    • Connection filtering (CIDR allow/deny + IP family controls + behavior when peer address is missing).
    • Connection rate limiting to cap new connections per client per window.
    • These are configured under your listener bind block, so you can enforce them before requests even reach routing/devices.
  • WASM tooling renamed and clarified

    • The CLI command previously surfaced as “plugin” tooling is now presented as WASM device tooling to match Snakeway’s “device” model.
  • Docs overhaul focused on “how to operate Snakeway”

    • Device configuration docs were reorganized under /configuration/devices/*.
    • New/updated guides for CLI usage, WASM device authoring, and runtime logging.

Everything Else

  • Config scaffolding and templates

    • The repo now includes config templates for common devices (identity, network policy, request filtering, request rate limiting, structured logging) and ingress examples.
    • snakeway config init uses embedded templates to generate a starter config directory (useful for first-run setup and repeatable environments).
  • Config dump improvements

    • snakeway config dump supports emitting both “spec” (as-written config) and “runtime” (lowered internal representation) to help debug what Snakeway actually loaded.
  • Routing and service spec ergonomics

    • Service route settings were refined (for example, websocket connection limits can be expressed as an optional field where applicable).
  • Dependency upgrades that matter to operators

    • Upgraded the underlying Pingora dependency line and related runtime components, which is groundwork for newer networking features and future performance work.
    • WASM toolchain dependencies were updated to newer versions, aligning with current WASI/WIT tooling.
  • Tests and fixtures refreshed

    • Expanded integration coverage for newly added devices and network-level controls to reduce regressions in “real proxy” scenarios.

If you are upgrading from v0.5.4:

  • Review any configs that previously relied on “plugin” CLI naming—use the WASM device command naming going forward.
  • If you want connection-level admission control, move those policies into the listener bind configuration (connection filter / connection rate limiting).
  • If you want request-level admission control, enable the new L7 devices (Network Policy / Request Rate Limiting) in devices.d/.