Tenant Isolation
This commit is contained in:
@@ -77,7 +77,15 @@ LUA RESTY CORE SCRIPTS = /usr/nginx_lua
|
|||||||
Confines each site's **static** file serving to its own `root` directory. A symlink, `..`,
|
Confines each site's **static** file serving to its own `root` directory. A symlink, `..`,
|
||||||
magic-link or cross-tenant path that escapes the site tree (e.g. a symlink to `/etc/passwd`)
|
magic-link or cross-tenant path that escapes the site tree (e.g. a symlink to `/etc/passwd`)
|
||||||
is refused with **403**, kernel-enforced via `openat2(RESOLVE_BENEATH)`.
|
is refused with **403**, kernel-enforced via `openat2(RESOLVE_BENEATH)`.
|
||||||
**On by default — no vhost config needed.** In-tree symlinks still work.
|
**On by default, no vhost config needed.** In-tree symlinks still work.
|
||||||
|
|
||||||
|
**Where the config lives (nothing to add on a fresh install)**
|
||||||
|
- `tenant_isolation` is compiled **default-on**, so it applies to every site with no directive.
|
||||||
|
- The `disable_symlinks if_not_owner from=$document_root;` backstop ships in the `http { }`
|
||||||
|
block of `/nginx/nginx.conf`, so **every** vhost inherits it. Do not add it per-site.
|
||||||
|
- Your site configs live in `/nginx/live/*` and inherit both layers automatically.
|
||||||
|
- Upgrading an old install that kept its own `/nginx/nginx.conf`? Add that one
|
||||||
|
`disable_symlinks` line to its `http { }` block once (or re-run `postfix` to refresh the config).
|
||||||
|
|
||||||
**Covered**
|
**Covered**
|
||||||
- Static files served by nginx (the normal file path).
|
- Static files served by nginx (the normal file path).
|
||||||
@@ -85,13 +93,13 @@ is refused with **403**, kernel-enforced via `openat2(RESOLVE_BENEATH)`.
|
|||||||
covers `gzip_static`, `autoindex`, `dav`, `mp4`/`flv`.
|
covers `gzip_static`, `autoindex`, `dav`, `mp4`/`flv`.
|
||||||
|
|
||||||
**Not covered**
|
**Not covered**
|
||||||
- Dynamic content (PHP-FPM / NGINX Unit) — isolated separately per tenant (user / cgroup / namespace).
|
- Dynamic content (PHP-FPM / NGINX Unit) is isolated separately per tenant (user / cgroup / namespace).
|
||||||
- Not fully race-free: a narrow probe→open timing window remains (closing it fully would
|
- Not fully race-free: a narrow probe->open timing window remains (closing it fully would
|
||||||
break `open_file_cache`), so it's *mitigated* by the `disable_symlinks` backstop, not eliminated.
|
break `open_file_cache`), so it is *mitigated* by the `disable_symlinks` backstop, not eliminated.
|
||||||
|
|
||||||
**Optional per-vhost tuning**
|
**Optional per-vhost tuning**
|
||||||
- `tenant_isolation off;` — turn it off for a `server`/`location`.
|
- `tenant_isolation off;` turns it off for a `server`/`location`.
|
||||||
- `tenant_isolation_root /home/<user>;` — widen the confinement root to the tenant home
|
- `tenant_isolation_root /home/<user>;` widens the confinement root to the tenant home
|
||||||
(allows above-docroot in-tree symlinks, e.g. Laravel's `storage`).
|
(allows above-docroot in-tree symlinks, e.g. Laravel's `storage`).
|
||||||
|
|
||||||
## How to install lua scripts
|
## How to install lua scripts
|
||||||
@@ -108,7 +116,7 @@ nginx -s reload
|
|||||||
|
|
||||||
| Area | Twiy | Vanilla nginx | Why |
|
| Area | Twiy | Vanilla nginx | Why |
|
||||||
|---|---|---|---|
|
|---|---|---|---|
|
||||||
| TLS handshake throughput | **+5–15%** | baseline | AWS-LC's tuned AES/ChaCha asm vs OpenSSL |
|
| TLS handshake throughput | **+5-15%** | baseline | AWS-LC's tuned AES/ChaCha asm vs OpenSSL |
|
||||||
| WAF, Lua, HTTP/3 | included | not included | needs custom build |
|
| WAF, Lua, HTTP/3 | included | not included | needs custom build |
|
||||||
|
|
||||||
# Support options.
|
# Support options.
|
||||||
|
|||||||
Reference in New Issue
Block a user