25 releases
new 0.11.0 | May 11, 2025 |
---|---|
0.9.0 | Nov 2, 2024 |
0.6.2 | Jul 26, 2024 |
0.1.2 | Mar 29, 2024 |
#109 in HTTP server
1,288 downloads per month
1MB
21K
SLoC
pingap
Before the pingap version is stable, no pull requests will be accepted. If you have any questions, please create a new issue first.
Overview
Pingap is a high-performance reverse proxy built on pingora, offering a simpler and more efficient alternative to nginx. Sentry and OpenTelemetry are supported in full-featured release version.
中文说明 | Examples | Documentation
flowchart LR
internet("Internet") -- request --> pingap["Pingap"]
pingap -- proxy:pingap.io/api/* --> apiUpstream["10.1.1.1,10.1.1.2"]
pingap -- proxy:cdn.pingap.io --> cdnUpstream["10.1.2.1,10.1.2.2"]
pingap -- proxy:pingap.io --> upstream["10.1.3.1,10.1.3.2"]
Key Features
- Multi-Location Support: Configure multiple locations with host/path filtering and weighted routing
- Advanced Proxy Features:
- Path rewriting with regex support
- Transparent proxy
- HTTP/1.1 and HTTP/2 support (including h2c)
- gRPC-web reverse proxy
- Service Discovery: Static, DNS, and Docker label support
- Monitoring & Observability:
- 10+ Prometheus metrics (pull/push)
- OpenTelemetry with W3C context and Jaeger trace support
- Access logging with 30+ configurable attributes
- Configuration:
- TOML-based configuration
- File and etcd storage support
- Hot reload support (10-second activation)
- Web UI for easy management
- Security & Performance:
- Let's Encrypt integration
- Multi-domain TLS support with automatic certificate selection
- HTTP plugin system (caching, compression, auth, rate limiting)
- Detailed performance metrics
Quick Start
Pingap can be started with either a configuration directory or a single TOML file:
# Using a config directory
RUST_LOG=INFO pingap -c=/opt/pingap/conf -d --log=/opt/pingap/pingap.log
# Using a single TOML file
RUST_LOG=INFO pingap -c=/opt/pingap/pingap.toml -d --log=/opt/pingap/pingap.log
Key flags:
-c
: Path to config directory or TOML file-d
: Run in daemon/background mode--log
: Path to log file (logs are appended)RUST_LOG=INFO
: Set logging level (DEBUG, INFO, WARN, ERROR)
Graceful Restart
Performs a zero-downtime restart of Pingap by following these steps:
- Validates the new configuration
- Gracefully shuts down the existing process
- Starts a new process to handle incoming requests
# Graceful restart command
RUST_LOG=INFO pingap -c=/opt/pingap/conf -t \
&& pkill -SIGQUIT pingap \
&& RUST_LOG=INFO pingap -c=/opt/pingap/conf -d -u --log=/opt/pingap/pingap.log
Key flags:
-t
: Test/validate configuration before restart-u
: Upgrade mode (ensures smooth handover from old process)-d
: Run in daemon modeSIGQUIT
: Signal for graceful shutdown
Auto Restart
Automatically monitors configuration files and handles changes in two ways:
- Full Restart: When core configurations change, performs a graceful restart
- Hot Reload: When only upstream or location configurations change, updates take effect within ~10 seconds without restart
# Enable auto-restart and hot reload
RUST_LOG=INFO pingap -c=/opt/pingap/conf \
-a -d --autoreload --log=/opt/pingap/pingap.log
Key flags:
-a
: Enable auto-restart on configuration changes--autoreload
: Enable hot reload for upstream/location changes-d
: Run in daemon mode-c
: Path to configuration directory
Docker
Run Pingap in a Docker container with auto-reload and admin interface enabled:
docker run -it -d --restart=always \
-v $PWD/pingap:/opt/pingap \
-p 3018:3018 \
-e PINGAP_ADMIN_ADDR=0.0.0.0:3018 \
-e PINGAP_ADMIN_USER=pingap \
-e PINGAP_ADMIN_PASSWORD=123123 \
-e PINGAP_AUTORELOAD=true \
vicanso/pingap -c /opt/pingap/conf
Key options:
-it
: Interactive terminal (allows input/output)-d
: Run container in detached/background mode--restart=always
: Automatically restart container if it stops-v $PWD/pingap:/opt/pingap
: Mount local config directory into container-p 3018:3018
: Expose admin interface port
Note: Remember to change the default admin credentials (pingap:123123
) in production environments.
Dev
make dev
If you need a web admin, you should install nodejs and build web asssets.
# generate admin web asset
cd web
npm i
cd ..
make build-web
Config
[upstreams.charts]
addrs = ["127.0.0.1:5000"]
[locations.lo]
upstream = "charts"
path = "/"
[servers.test]
addr = "0.0.0.0:6188"
locations = ["lo"]
All toml configurations are as follows pingap.toml.
Proxy step
graph TD;
server["HTTP Server"];
locationA["Location A"];
locationB["Location B"];
locationPluginListA["Proxy Plugin List A"];
locationPluginListB["Proxy Plugin List B"];
upstreamA1["Upstream A1"];
upstreamA2["Upstream A2"];
upstreamB1["Upstream B1"];
upstreamB2["Upstream B2"];
locationResponsePluginListA["Response Plugin List A"];
locationResponsePluginListB["Response Plugin List B"];
start("New Request") --> server
server -- "host:HostA, Path:/api/*" --> locationA
server -- "Path:/rest/*"--> locationB
locationA -- "Exec Proxy Plugins" --> locationPluginListA
locationB -- "Exec Proxy Plugins" --> locationPluginListB
locationPluginListA -- "proxy pass: 10.0.0.1:8001" --> upstreamA1
locationPluginListA -- "proxy pass: 10.0.0.2:8001" --> upstreamA2
locationPluginListA -- "done" --> response
locationPluginListB -- "proxy pass: 10.0.0.1:8002" --> upstreamB1
locationPluginListB -- "proxy pass: 10.0.0.2:8002" --> upstreamB2
locationPluginListB -- "done" --> response
upstreamA1 -- "Exec Response Plugins" --> locationResponsePluginListA
upstreamA2 -- "Exec Response Plugins" --> locationResponsePluginListA
upstreamB1 -- "Exec Response Plugins" --> locationResponsePluginListB
upstreamB2 -- "Exec Response Plugins" --> locationResponsePluginListB
locationResponsePluginListA --> response
locationResponsePluginListB --> response
response["HTTP Response"] --> stop("Logging");
Performance
CPU: M4 Pro, Thread: 1
Ping no access log:
wrk 'http://127.0.0.1:6100/ping' --latency
Running 10s test @ http://127.0.0.1:6100/ping
2 threads and 10 connections
Thread Stats Avg Stdev Max +/- Stdev
Latency 59.87us 20.27us 1.00ms 81.00%
Req/Sec 82.12k 3.04k 85.77k 90.59%
Latency Distribution
50% 63.00us
75% 69.00us
90% 76.00us
99% 97.00us
1650275 requests in 10.10s, 215.61MB read
Requests/sec: 163396.17
Transfer/sec: 21.35MB
Rust version
Our current MSRV is 1.74
License
This project is Licensed under Apache License, Version 2.0.
Dependencies
~66–105MB
~2M SLoC