65 lines
3.2 KiB
Markdown
65 lines
3.2 KiB
Markdown
# lolly
|
||
|
||
高性能 HTTP 服务器,类似 nginx 的纯 Go 实现。YAML 配置,单二进制,支持反向代理、负载均衡、SSL/TLS、HTTP/2、HTTP/3、Lua 脚本。
|
||
|
||
Module: `rua.plus/lolly` | Go 1.26+ | CGO disabled (static builds)
|
||
|
||
## Commands
|
||
|
||
```
|
||
make build # static build → bin/lolly
|
||
make test # unit tests only (./internal/...)
|
||
make test-integration # L2 integration tests (build tag: integration)
|
||
make test-e2e # L3 E2E tests (build tag: e2e, requires Docker)
|
||
make test-all # all three in parallel
|
||
make fmt # gofumpt (not go fmt)
|
||
make lint # golangci-lint (falls back to go vet)
|
||
make check # fmt → lint → test-all
|
||
```
|
||
|
||
Run a single test or package:
|
||
```
|
||
go test -v -run TestName ./internal/config/...
|
||
go test -v ./internal/server/...
|
||
```
|
||
|
||
Integration/E2E require build tags:
|
||
```
|
||
go test -v -tags=integration ./internal/integration/...
|
||
go test -v -tags=e2e ./internal/e2e/...
|
||
```
|
||
|
||
## Architecture
|
||
|
||
- `main.go` → `internal/app` — CLI entry; `app.Run()` owns lifecycle
|
||
- `internal/config` — YAML config structs; `config.go` is the root, split into `server_config.go`, `ssl_config.go`, `proxy_config.go`, etc.
|
||
- `internal/server` — HTTP server core: routing, middleware chain, vhosts, upgrade/reload, connection pool
|
||
- `internal/proxy` — reverse proxy + load balancing
|
||
- `internal/middleware/` — individual middleware packages (compression, bodylimit, security, rewrite, accesslog, errorintercept)
|
||
- `internal/handler` — static file handler and other request handlers
|
||
- `internal/lua` — embedded Lua scripting (gopher-lua)
|
||
- `internal/converter/nginx` — nginx config importer
|
||
- `internal/{http2,http3,stream,ssl,sslutil,cache,loadbalance,resolver,logging,variable,matcher}` — supporting packages
|
||
- `internal/e2e` — L3 E2E tests (testcontainers, build tag `e2e`)
|
||
- `internal/integration` — L2 integration tests (build tag `integration`)
|
||
|
||
## Key Conventions
|
||
|
||
- HTTP stack: **fasthttp** + **fasthttp/router** (NOT net/http). All handlers use `fasthttp.RequestHandler` signature.
|
||
- Logging: **zerolog** (zero-alloc JSON). No fmt.Printf or log.Printf in production code.
|
||
- Config: YAML with `yaml` struct tags, parsed by `gopkg.in/yaml.v3`.
|
||
- Version: injected at build time via `-ldflags -X` into `internal/version`.
|
||
- Signals: SIGTERM/SIGINT = fast stop, SIGQUIT = graceful stop. Graceful upgrade via `internal/server/upgrade.go`.
|
||
- Formatter: **gofumpt** (stricter than gofmt). `make fmt` runs it.
|
||
- Linter: **golangci-lint** with v2 config (`.golangci.yml`). Uses `default: all` with many disabled — don't add new linter warnings.
|
||
- Build: always `CGO_ENABLED=0`, static linked, `-trimpath`.
|
||
- Tests use **testify** assertions.
|
||
|
||
## Gotchas
|
||
|
||
- fasthttp uses `[]byte` strings, NOT `string`. Use `[]byte("literal")` or `fasthttp.AcquireRequest()` patterns. Don't mix net/http types.
|
||
- E2E tests need Docker running (testcontainers-go). If Docker is unavailable, run `make test-e2e-short` for testutil-only tests.
|
||
- Config file path defaults to `lolly.yaml` in CWD. Use `-c path` or `--config path`.
|
||
- `--generate-config` outputs a full config template; `-o file` writes to file.
|
||
- `--import nginx.conf` converts nginx config to lolly YAML.
|