30 KiB
API
Descripción general
La API de BunkerWeb es el plano de control utilizado para gestionar las instancias de BunkerWeb de forma programática: listar y gestionar instancias, recargar/detener, manejar baneos, plugins, trabajos, configuraciones y más. Expone una aplicación FastAPI documentada con autenticación fuerte, autorización y limitación de velocidad.
Abre la documentación interactiva en /docs (o <root_path>/docs si estableciste API_ROOT_PATH). El esquema OpenAPI está disponible en /openapi.json.
!!! warning "Seguridad" La API es un plano de control privilegiado. No la expongas en la Internet pública sin protecciones adicionales.
Como mínimo, restringe las IP de origen (`API_WHITELIST_IPS`), habilita la autenticación (`API_TOKEN` o usuarios de API + Biscuit), y considera ponerla detrás de BunkerWeb con una ruta difícil de adivinar y controles de acceso adicionales.
Requisitos previos
El servicio de la API requiere acceso a la base de datos de BunkerWeb (DATABASE_URI). Generalmente se despliega junto con el Programador y opcionalmente la Interfaz de Usuario Web. La configuración recomendada es ejecutar BunkerWeb al frente como un proxy inverso y aislar la API en una red interna.
Consulta el asistente de inicio rápido y la guía de arquitectura en la guía de inicio rápido.
Despliegue recomendado (Contenedores dedicados)
Para producción, despliega la API como su propio contenedor junto al plano de datos de BunkerWeb y el scheduler. Mantén la API unida a la red interna del plano de control y publícala únicamente a través de BunkerWeb como un proxy inverso. Esta disposición coincide con la referencia de integración de Docker y garantiza que el scheduler, BunkerWeb y la API compartan la misma configuración.
x-bw-env: &bw-env
# Usamos un ancla para evitar repetir la misma configuración en ambos servicios
API_WHITELIST_IP: "127.0.0.0/8 10.20.30.0/24" # Asegúrate de establecer el rango de IP correcto para que el scheduler pueda enviar la configuración a la instancia
DATABASE_URI: "mariadb+pymysql://bunkerweb:changeme@bw-db:3306/db" # Recuerda usar una contraseña más fuerte para la base de datos
services:
bunkerweb:
# Este es el nombre que se usará para identificar la instancia en el Scheduler
image: bunkerity/bunkerweb:1.6.6
ports:
- "80:8080/tcp"
- "443:8443/tcp"
- "443:8443/udp" # Para compatibilidad con QUIC / HTTP3
environment:
<<: *bw-env # Usamos el ancla para evitar repetir la misma configuración en todos los servicios
restart: "unless-stopped"
networks:
- bw-universe
- bw-services
bw-scheduler:
image: bunkerity/bunkerweb-scheduler:1.6.6
environment:
<<: *bw-env
BUNKERWEB_INSTANCES: "bunkerweb" # Asegúrate de establecer el nombre correcto de la instancia
SERVER_NAME: "api.example.com" # Cámbialo si es necesario
MULTISITE: "yes"
USE_REDIS: "yes"
REDIS_HOST: "redis"
api.example.com_USE_TEMPLATE: "bw-api"
api.example.com_GENERATE_SELF_SIGNED_SSL: "yes"
api.example.com_USE_REVERSE_PROXY: "yes"
api.example.com_REVERSE_PROXY_URL: "/"
api.example.com_REVERSE_PROXY_HOST: "http://bw-api:8888"
volumes:
- bw-storage:/data # Se utiliza para persistir la caché y otros datos como las copias de seguridad
restart: "unless-stopped"
networks:
- bw-universe
- bw-db
bw-api:
image: bunkerity/bunkerweb-api:1.6.6
environment:
<<: *bw-env
API_USERNAME: "admin"
API_PASSWORD: "Str0ng&P@ss!" # Recuerda usar una contraseña más fuerte para el usuario administrador
DEBUG: "1"
restart: "unless-stopped"
networks:
bw-universe:
aliases:
- bw-api
bw-db:
aliases:
- bw-api
bw-db:
image: mariadb:11
# Definimos el tamaño máximo de paquete permitido para evitar problemas con consultas grandes
command: --max-allowed-packet=67108864
environment:
MYSQL_RANDOM_ROOT_PASSWORD: "yes"
MYSQL_DATABASE: "db"
MYSQL_USER: "bunkerweb"
MYSQL_PASSWORD: "changeme" # Recuerda usar una contraseña más fuerte para la base de datos
volumes:
- bw-data:/var/lib/mysql
restart: "unless-stopped"
networks:
- bw-db
redis: # Servicio de Redis para la persistencia de informes/baneos/estadísticas
image: redis:7-alpine
command: >
redis-server
--maxmemory 256mb
--maxmemory-policy allkeys-lru
--save 60 1000
--appendonly yes
volumes:
- redis-data:/data
restart: "unless-stopped"
networks:
- bw-universe
volumes:
bw-data:
bw-storage:
redis-data:
networks:
bw-universe:
name: bw-universe
ipam:
driver: default
config:
- subnet: 10.20.30.0/24 # Asegúrate de establecer el rango de IP correcto para que el scheduler pueda enviar la configuración a la instancia
bw-services:
name: bw-services
bw-db:
name: bw-db
Esto aísla la API detrás de BunkerWeb, mantiene el tráfico en redes de confianza y te permite aplicar autenticación, listas blancas y límites de tasa tanto en el plano de control como en el nombre de host expuesto.
Puntos destacados
- Consciente de las instancias: transmite acciones operativas a las instancias descubiertas.
- Autenticación fuerte: Básica para administradores, anulación de administrador con Bearer, o ACL de Biscuit para permisos detallados.
- Lista blanca de IP y limitación de velocidad flexible por ruta.
- Señales estándar de salud/disponibilidad y comprobaciones de seguridad al inicio.
Plantillas de Compose
=== "Docker"
Haz un proxy inverso de la API bajo `/api` con BunkerWeb.
```yaml
x-bw-env: &bw-env
# Lista blanca compartida del plano de control de instancias para BunkerWeb/Scheduler
API_WHITELIST_IP: "127.0.0.0/8 10.20.30.0/24"
services:
bunkerweb:
image: bunkerity/bunkerweb:1.6.6
ports:
- "80:8080/tcp"
- "443:8443/tcp"
- "443:8443/udp" # QUIC
environment:
<<: *bw-env
restart: unless-stopped
networks:
- bw-universe
- bw-services
bw-scheduler:
image: bunkerity/bunkerweb-scheduler:1.6.6
environment:
<<: *bw-env
BUNKERWEB_INSTANCES: "bunkerweb" # Coincide con el nombre del servicio de la instancia
SERVER_NAME: "www.example.com"
MULTISITE: "yes"
DATABASE_URI: "mariadb+pymysql://bunkerweb:changeme@bw-db:3306/db"
DISABLE_DEFAULT_SERVER: "yes"
# Proxy inverso de la API en /api
www.example.com_USE_REVERSE_PROXY: "yes"
www.example.com_REVERSE_PROXY_URL: "/api"
www.example.com_REVERSE_PROXY_HOST: "http://bw-api:8888"
volumes:
- bw-storage:/data
restart: unless-stopped
networks:
- bw-universe
- bw-db
bw-api:
image: bunkerity/bunkerweb-api:1.6.6
environment:
DATABASE_URI: "mariadb+pymysql://bunkerweb:changeme@bw-db:3306/db" # Usa una contraseña fuerte
API_WHITELIST_IPS: "127.0.0.0/8 10.20.30.0/24" # Lista blanca de la API
API_TOKEN: "secret" # Token de anulación de administrador opcional
API_ROOT_PATH: "/api" # Coincide con la ruta del proxy inverso
restart: unless-stopped
networks:
- bw-universe
- bw-db
bw-db:
image: mariadb:11
# Evita problemas con consultas grandes
command: --max-allowed-packet=67108864
environment:
MYSQL_RANDOM_ROOT_PASSWORD: "yes"
MYSQL_DATABASE: "db"
MYSQL_USER: "bunkerweb"
MYSQL_PASSWORD: "changeme" # Usa una contraseña fuerte
volumes:
- bw-data:/var/lib/mysql
restart: unless-stopped
networks:
- bw-db
volumes:
bw-data:
bw-storage:
networks:
bw-universe:
name: bw-universe
ipam:
driver: default
config:
- subnet: 10.20.30.0/24
bw-services:
name: bw-services
bw-db:
name: bw-db
```
=== "Docker Autoconf"
Lo mismo que arriba pero aprovechando el servicio Autoconf para descubrir y configurar servicios automáticamente. La API se expone bajo `/api` usando etiquetas en el contenedor de la API.
```yaml
x-api-env: &api-env
AUTOCONF_MODE: "yes"
DATABASE_URI: "mariadb+pymysql://bunkerweb:changeme@bw-db:3306/db" # Usa una contraseña fuerte
services:
bunkerweb:
image: bunkerity/bunkerweb:1.6.6
ports:
- "80:8080/tcp"
- "443:8443/tcp"
- "443:8443/udp" # QUIC
environment:
AUTOCONF_MODE: "yes"
API_WHITELIST_IP: "127.0.0.0/8 10.20.30.0/24"
restart: unless-stopped
networks:
- bw-universe
- bw-services
bw-scheduler:
image: bunkerity/bunkerweb-scheduler:1.6.6
environment:
<<: *api-env
BUNKERWEB_INSTANCES: "" # Descubierto por Autoconf
SERVER_NAME: "" # Rellenado a través de etiquetas
MULTISITE: "yes" # Obligatorio con Autoconf
API_WHITELIST_IP: "127.0.0.0/8 10.20.30.0/24"
volumes:
- bw-storage:/data
restart: unless-stopped
networks:
- bw-universe
- bw-db
bw-autoconf:
image: bunkerity/bunkerweb-autoconf:1.6.6
depends_on:
- bunkerweb
- bw-docker
environment:
<<: *api-env
DOCKER_HOST: "tcp://bw-docker:2375"
restart: unless-stopped
networks:
- bw-universe
- bw-docker
- bw-db
bw-api:
image: bunkerity/bunkerweb-api:1.6.6
environment:
<<: *api-env
API_WHITELIST_IPS: "127.0.0.0/8 10.20.30.0/24"
API_TOKEN: "secret"
API_ROOT_PATH: "/api"
labels:
- "bunkerweb.SERVER_NAME=www.example.com"
- "bunkerweb.USE_REVERSE_PROXY=yes"
- "bunkerweb.REVERSE_PROXY_URL=/api"
- "bunkerweb.REVERSE_PROXY_HOST=http://bw-api:8888"
restart: unless-stopped
networks:
- bw-universe
- bw-db
bw-db:
image: mariadb:11
command: --max-allowed-packet=67108864
environment:
MYSQL_RANDOM_ROOT_PASSWORD: "yes"
MYSQL_DATABASE: "db"
MYSQL_USER: "bunkerweb"
MYSQL_PASSWORD: "changeme"
volumes:
- bw-data:/var/lib/mysql
restart: unless-stopped
networks:
- bw-db
bw-docker:
image: tecnativa/docker-socket-proxy:nightly
environment:
CONTAINERS: "1"
LOG_LEVEL: "warning"
volumes:
- /var/run/docker.sock:/var/run/docker.sock:ro
restart: unless-stopped
networks:
- bw-docker
volumes:
bw-data:
bw-storage:
networks:
bw-universe:
name: bw-universe
ipam:
driver: default
config:
- subnet: 10.20.30.0/24
bw-services:
name: bw-services
bw-db:
name: bw-db
bw-docker:
name: bw-docker
```
!!! warning "Ruta del proxy inverso" Mantén la ruta de la API difícil de adivinar y combínala con la lista blanca de la API y la autenticación.
Si ya expones otra aplicación en el mismo nombre de servidor con una plantilla (p. ej., `USE_TEMPLATE`), prefiere un nombre de host separado para la API para evitar conflictos.
Todo en Uno
Si utilizas la imagen Todo en Uno, la API se puede habilitar estableciendo SERVICE_API=yes:
docker run -d \
--name bunkerweb-aio \
-e SERVICE_API=yes \
-e API_WHITELIST_IPS="127.0.0.0/8" \
-p 80:8080/tcp -p 443:8443/tcp -p 443:8443/udp \
bunkerity/bunkerweb-all-in-one:1.6.6
Autenticación
Formas admitidas para autenticar solicitudes:
- Administrador Básico: Cuando las credenciales pertenecen a un usuario de API administrador, los puntos finales protegidos aceptan
Authorization: Basic <base64(nombredeusuario:contraseña)>. - Anulación de Administrador con Bearer: Si se configura
API_TOKEN,Authorization: Bearer <API_TOKEN>otorga acceso completo. - Token Biscuit (recomendado): Obtén un token desde
POST /authutilizando credenciales Básicas o un cuerpo JSON/formulario que contengausernameypassword. Utiliza el token devuelto comoAuthorization: Bearer <token>en llamadas posteriores.
Ejemplo: obtener un Biscuit, listar instancias y luego recargar todas las instancias.
# 1) Obtener un token Biscuit con credenciales de administrador
TOKEN=$(curl -s -X POST -u admin:changeme http://api.example.com/auth | jq -r .token)
# 2) Listar instancias
curl -H "Authorization: Bearer $TOKEN" http://api.example.com/instances
# 3) Recargar la configuración en todas las instancias (sin prueba)
curl -X POST -H "Authorization: Bearer $TOKEN" \
"http://api.example.com/instances/reload?test=no"
Hechos y comprobaciones de Biscuit
Los tokens incorporan hechos como user(<username>), client_ip(<ip>), domain(<host>), y un rol general role("api_user", ["read", "write"]) derivado de los permisos de la base de datos. Los administradores incluyen admin(true) mientras que los no administradores llevan hechos detallados como api_perm(<resource_type>, <resource_id|*>, <permission>).
La autorización mapea la ruta/método a los permisos requeridos; admin(true) siempre pasa. Cuando los hechos detallados están ausentes, la guarda recurre al rol general: GET/HEAD/OPTIONS requieren read; los verbos de escritura requieren write.
Las claves se almacenan en /var/lib/bunkerweb/.api_biscuit_private_key y /var/lib/bunkerweb/.api_biscuit_public_key. También puedes proporcionar BISCUIT_PUBLIC_KEY/BISCUIT_PRIVATE_KEY a través de variables de entorno; si no se establecen ni archivos ni variables de entorno, la API genera un par de claves al inicio y lo persiste de forma segura.
Permisos (ACL)
Esta API soporta dos capas de autorización:
- Rol general: Los tokens llevan
role("api_user", ["read"[, "write"]])para los puntos finales sin un mapeo detallado. Lectura se mapea a GET/HEAD/OPTIONS; escritura se mapea a POST/PUT/PATCH/DELETE. - ACL detallada: Los tokens incorporan
api_perm(<resource_type>, <resource_id|*>, <permission>)y las rutas declaran lo que requieren.admin(true)omite todas las comprobaciones.
Tipos de recursos admitidos: instances, global_config, services, configs, plugins, cache, bans, jobs.
Nombres de permisos por tipo de recurso:
- instances:
instances_read,instances_update,instances_delete,instances_create,instances_execute - global_config:
global_config_read,global_config_update - services:
service_read,service_create,service_update,service_delete,service_convert,service_export - configs:
configs_read,config_read,config_create,config_update,config_delete - plugins:
plugin_read,plugin_create,plugin_delete - cache:
cache_read,cache_delete - bans:
ban_read,ban_update,ban_delete,ban_created - jobs:
job_read,job_run
ID de recursos: Para comprobaciones detalladas, el segundo segmento de la ruta se trata como resource_id cuando tiene sentido. Ejemplos: /services/{service} -> {service}; /configs/{service}/... -> {service}. Usa "*" (u omite) para otorgar globalmente para un tipo de recurso.
Configuración de usuario y ACL:
- Usuario administrador: Establece
API_USERNAMEyAPI_PASSWORDpara crear el primer administrador al inicio. Para rotar las credenciales más tarde, estableceOVERRIDE_API_CREDS=yes(o asegúrate de que el administrador fue creado con el métodomanual). Solo existe un administrador; los intentos adicionales recurren a la creación de no administradores. - Usuarios no administradores y concesiones: Proporciona
API_ACL_BOOTSTRAP_FILEapuntando a un archivo JSON, o monta/var/lib/bunkerweb/api_acl_bootstrap.json. La API lo lee al inicio para crear/actualizar usuarios y permisos. - Archivo de caché de ACL: Se escribe un resumen de solo lectura en
/var/lib/bunkerweb/api_acl.jsonal inicio para introspección; la autorización evalúa las concesiones respaldadas por la base de datos incorporadas en el token Biscuit.
Ejemplos de JSON de arranque (se admiten ambas formas):
{
"users": {
"ci": {
"admin": false,
"password": "Str0ng&P@ss!",
"permissions": {
"services": {
"*": { "service_read": true },
"app-frontend": { "service_update": true, "service_delete": false }
},
"configs": {
"app-frontend": { "config_read": true, "config_update": true }
}
}
},
"ops": {
"admin": false,
"password_hash": "$2b$13$...bcrypt-hash...",
"permissions": {
"instances": { "*": { "instances_execute": true } },
"jobs": { "*": { "job_run": true } }
}
}
}
}
O en formato de lista:
{
"users": [
{
"username": "ci",
"password": "Str0ng&P@ss!",
"permissions": [
{ "resource_type": "services", "resource_id": "*", "permission": "service_read" },
{ "resource_type": "services", "resource_id": "app-frontend", "permission": "service_update" }
]
}
]
}
Notas:
- Las contraseñas pueden ser texto plano (
password) o bcrypt (password_hash/password_bcrypt). Las contraseñas de texto plano débiles son rechazadas en compilaciones que no son de depuración; si faltan, se genera una aleatoria y se registra una advertencia. resource_id: "*"(o nulo/vacío) otorga globalmente sobre ese tipo de recurso.- Las contraseñas de los usuarios existentes pueden actualizarse y se pueden aplicar concesiones adicionales a través del arranque.
Referencia de características
La API está organizada por enrutadores centrados en recursos. Utiliza las secciones a continuación como un mapa de capacidades; el esquema interactivo en /docs documenta los modelos de solicitud/respuesta en detalle.
Núcleo y autenticación
GET /ping,GET /health: sondas de actividad ligeras para el propio servicio de la API.POST /auth: intercambia credenciales Básicas (o el token de anulación de administrador) por un Biscuit. Acepta JSON, formulario o cabecerasAuthorization. Los administradores también pueden continuar usando HTTP Basic directamente en rutas protegidas cuando lo deseen.
Plano de control de instancias
GET /instances: lista las instancias registradas, incluyendo marcas de tiempo de creación/última vez visto, método de registro y metadatos.POST /instances: registra una nueva instancia gestionada por la API (nombre de host, puerto opcional, nombre de servidor, nombre amigable, método).GET /instances/{hostname}/PATCH /instances/{hostname}/DELETE /instances/{hostname}: inspecciona, actualiza campos mutables o elimina instancias gestionadas por la API.DELETE /instances: eliminación masiva; omite las instancias que no son de la API y las informa enskipped.GET /instances/pingyGET /instances/{hostname}/ping: comprobaciones de salud en todas o en instancias individuales.POST /instances/reload?test=yes|no,POST /instances/{hostname}/reload: activa la recarga de la configuración (el modo de prueba realiza una validación de ejecución en seco).POST /instances/stop,POST /instances/{hostname}/stop: retransmite comandos de detención a las instancias.
Configuración global
GET /global_config: obtiene configuraciones no predeterminadas (usafull=truepara la configuración completa,methods=truepara incluir la procedencia).PATCH /global_config: actualiza o inserta configuraciones globales propiedad de la API (method="api"); los errores de validación señalan claves desconocidas o de solo lectura.
Ciclo de vida del servicio
GET /services: enumera los servicios con metadatos, incluido el estado de borrador y las marcas de tiempo.GET /services/{service}: recupera las superposiciones no predeterminadas (full=false) o la instantánea completa de la configuración (full=true) para un servicio.POST /services: crea servicios, opcionalmente como borrador, y siembra variables con prefijo ({service}_{KEY}). Actualiza la listaSERVER_NAMEatómicamente.PATCH /services/{service}: renombra servicios, cambia los indicadores de borrador y actualiza las variables con prefijo. Ignora las ediciones directas aSERVER_NAMEdentro devariablespor seguridad.DELETE /services/{service}: elimina un servicio y sus claves de configuración derivadas.POST /services/{service}/convert?convert_to=online|draft: cambia rápidamente el estado borrador/en línea sin alterar otras variables.
Fragmentos de configuración personalizados
GET /configs: lista fragmentos de configuración personalizados (HTTP/servidor/stream/ModSecurity/ganchos CRS) para un servicio (service=globalpor defecto).with_data=trueincrusta contenido UTF-8 cuando es imprimible.POST /configsyPOST /configs/upload: crea nuevos fragmentos a partir de cargas útiles JSON o archivos subidos. Los tipos aceptados incluyenhttp,server_http,default_server_http,modsec,modsec_crs,stream,server_stream, y ganchos de plugins CRS. Los nombres deben coincidir con^[\w_-]{1,255}$.GET /configs/{service}/{type}/{name}: recupera un fragmento con contenido opcional (with_data=true).PATCH /configs/{service}/{type}/{name}yPATCH .../upload: actualiza o mueve fragmentos gestionados por la API; las entradas gestionadas por plantilla o archivo permanecen de solo lectura.DELETE /configsyDELETE /configs/{service}/{type}/{name}: elimina fragmentos gestionados por la API conservando los gestionados por plantilla, devolviendo una listaskippedpara las entradas ignoradas.
Orquestación de baneos
GET /bans: agrega los baneos activos informados por todas las instancias.POST /bansoPOST /bans/ban: aplica uno o varios baneos. Las cargas útiles pueden ser objetos JSON, matrices o JSON en formato de cadena.servicees opcional; cuando se omite, el baneo es global.POST /bans/unbanoDELETE /bans: elimina baneos globalmente o por servicio utilizando las mismas cargas útiles flexibles.
Gestión de plugins
GET /plugins?type=all|external|ui|pro: lista plugins con metadatos;with_data=trueincluye los bytes empaquetados cuando están disponibles.POST /plugins/upload: instala plugins de UI desde archivos.zip,.tar.gzo.tar.xz. Los archivos pueden agrupar múltiples plugins siempre que cada uno contenga unplugin.json.DELETE /plugins/{id}: elimina un plugin de UI por ID (^[\w.-]{4,64}$).
Caché y ejecución de trabajos
GET /cache: lista los artefactos en caché producidos por los trabajos del programador, filtrados por servicio, ID de plugin o nombre de trabajo.with_data=trueincluye contenido de archivo imprimible.GET /cache/{service}/{plugin}/{job}/{file}: obtiene un archivo de caché específico (download=truetransmite un archivo adjunto).DELETE /cacheoDELETE /cache/{service}/{plugin}/{job}/{file}: elimina archivos de caché y notifica al programador sobre los plugins afectados.GET /jobs: inspecciona trabajos conocidos, sus metadatos de programación y resúmenes de caché.POST /jobs/run: solicita la ejecución de un trabajo marcando el(los) plugin(s) asociado(s) como cambiado(s).
Notas operativas
- Los puntos finales de escritura persisten en la base de datos compartida; las instancias recogen los cambios a través de la sincronización del programador o después de un
/instances/reload. - Los errores se normalizan a
{ "status": "error", "message": "..." }con los códigos de estado HTTP apropiados (422 validación, 404 no encontrado, 403 ACL, 5xx fallos de origen).
Limitación de velocidad
La limitación de velocidad por cliente es manejada por SlowAPI. Habilítala/deshabilítala y configura los límites a través de variables de entorno o /etc/bunkerweb/api.yml.
API_RATE_LIMIT_ENABLED(predeterminado:yes)- Límite predeterminado:
API_RATE_LIMIT_TIMESporAPI_RATE_LIMIT_SECONDS(p. ej.,100por60) API_RATE_LIMIT_RULES: JSON/CSV en línea, o una ruta a un archivo YAML/JSON con reglas por ruta- Backend de almacenamiento: en memoria o Redis/Valkey cuando
USE_REDIS=yesy se proporcionan las variablesREDIS_*(compatible con Sentinel) - Cabeceras:
API_RATE_LIMIT_HEADERS_ENABLED(predeterminado:yes)
POST /auth siempre aplica su propio límite de API_RATE_LIMIT_AUTH_TIMES por API_RATE_LIMIT_AUTH_SECONDS (predeterminado 10 por 60). Establece cualquiera de estos valores en 0 o agrega una regla personalizada para /auth para anularlo o desactivarlo. Esta regla integrada pasa por el mismo backend de SlowAPI (memoria o Redis/Valkey), por lo que el límite se aplica de forma coherente en todas las réplicas.
Ejemplo de YAML (montado en /etc/bunkerweb/api.yml):
API_RATE_LIMIT_ENABLED: yes
API_RATE_LIMIT_DEFAULTS: ["200/minute"]
API_RATE_LIMIT_RULES:
- path: "/auth"
methods: "POST"
times: 10
seconds: 60
- path: "/instances*"
methods: "GET|POST"
times: 100
seconds: 60```
## Configuración
Puedes configurar la API a través de variables de entorno, secretos de Docker y los archivos opcionales `/etc/bunkerweb/api.yml` o `/etc/bunkerweb/api.env`. Configuraciones clave:
- Documentación y esquema: `API_DOCS_URL`, `API_REDOC_URL`, `API_OPENAPI_URL`, `API_ROOT_PATH`.
- Autenticación básica: `API_TOKEN` (Bearer de anulación de administrador), `API_USERNAME`/`API_PASSWORD` (crear/actualizar administrador), `OVERRIDE_API_CREDS`.
- ACL y usuarios: `API_ACL_BOOTSTRAP_FILE` (ruta JSON).
- Política de Biscuit: `API_BISCUIT_TTL_SECONDS` (0/desactivado deshabilita el TTL), `CHECK_PRIVATE_IP` (vincula el token a la IP del cliente a menos que sea privada).
- Lista blanca de IP: `API_WHITELIST_ENABLED`, `API_WHITELIST_IPS`.
- Limitación de velocidad (núcleo): `API_RATE_LIMIT_ENABLED`, `API_RATE_LIMIT_TIMES`, `API_RATE_LIMIT_SECONDS`, `API_RATE_LIMIT_HEADERS_ENABLED`.
- Limitación de velocidad (avanzado): `API_RATE_LIMIT_AUTH_TIMES`, `API_RATE_LIMIT_AUTH_SECONDS`, `API_RATE_LIMIT_RULES`, `API_RATE_LIMIT_DEFAULTS`, `API_RATE_LIMIT_APPLICATION_LIMITS`, `API_RATE_LIMIT_STRATEGY`, `API_RATE_LIMIT_KEY`, `API_RATE_LIMIT_EXEMPT_IPS`, `API_RATE_LIMIT_STORAGE_OPTIONS`.
- Almacenamiento de limitación de velocidad: en memoria o Redis/Valkey cuando `USE_REDIS=yes` y se establecen configuraciones de Redis como `REDIS_HOST`, `REDIS_PORT`, `REDIS_PASSWORD`, `REDIS_DATABASE`, `REDIS_SSL`, o variables de Sentinel. Consulta la tabla de configuraciones de Redis en `docs/features.md`.
- Red/TLS: `API_LISTEN_ADDR`, `API_LISTEN_PORT`, `API_FORWARDED_ALLOW_IPS`, `API_SSL_ENABLED`, `API_SSL_CERTFILE`, `API_SSL_KEYFILE`, `API_SSL_CA_CERTS`.
### Cómo se carga la configuración
Precedencia de mayor a menor:
- Variables de entorno (p. ej., `environment:` del contenedor o variables de shell exportadas)
- Archivos de secretos en `/run/secrets` (secretos de Docker/K8s; los nombres de archivo coinciden con los nombres de las variables)
- Archivo YAML en `/etc/bunkerweb/api.yml`
- Archivo de entorno en `/etc/bunkerweb/api.env` (líneas clave=valor)
- Valores predeterminados incorporados
Notas:
- YAML admite la inserción de archivos de secretos con `<file:relative/path>`; la ruta se resuelve contra `/run/secrets`.
- Establece las URL de la documentación en `off`/`disabled`/`none` para deshabilitar los puntos finales (p. ej., `API_DOCS_URL=off`).
- Si `API_SSL_ENABLED=yes`, también debes establecer `API_SSL_CERTFILE` y `API_SSL_KEYFILE`.
- Si Redis está habilitado (`USE_REDIS=yes`), proporciona los detalles de Redis; consulta la sección de Redis en `docs/features.md`.
### Autenticación y usuarios
- Arranque de administrador: establece `API_USERNAME` y `API_PASSWORD` para crear el primer administrador. Para volver a aplicar más tarde, establece `OVERRIDE_API_CREDS=yes`.
- No administradores y permisos: proporciona `API_ACL_BOOTSTRAP_FILE` con una ruta JSON (o monta en `/var/lib/bunkerweb/api_acl_bootstrap.json`). El archivo puede listar usuarios y concesiones detalladas.
- Claves de Biscuit: establece `BISCUIT_PUBLIC_KEY`/`BISCUIT_PRIVATE_KEY` o monta archivos en `/var/lib/bunkerweb/.api_biscuit_public_key` y `/var/lib/bunkerweb/.api_biscuit_private_key`. Si no se proporciona ninguno, la API genera y persiste un par de claves al inicio.
### TLS y redes
- Dirección/puerto de enlace: `API_LISTEN_ADDR` (predeterminado `0.0.0.0`), `API_LISTEN_PORT` (predeterminado `8888`).
- Proxies inversos: establece `API_FORWARDED_ALLOW_IPS` en las IP del proxy para que Gunicorn confíe en las cabeceras `X-Forwarded-*`.
- Terminación de TLS en la API: `API_SSL_ENABLED=yes` más `API_SSL_CERTFILE` y `API_SSL_KEYFILE`; opcional `API_SSL_CA_CERTS`
### Recetas rápidas de limitación de velocidad
- Deshabilitar globalmente: `API_RATE_LIMIT_ENABLED=no`
- Establecer un límite global simple: `API_RATE_LIMIT_TIMES=100`, `API_RATE_LIMIT_SECONDS=60`
- Reglas por ruta: establece `API_RATE_LIMIT_RULES` en una ruta de archivo JSON/YAML o YAML en línea en `/etc/bunkerweb/api.yml`.
!!! warning "Seguridad de inicio"
La API se cierra si no hay una ruta de autenticación configurada (sin claves Biscuit, sin usuario administrador y sin `API_TOKEN`). Asegúrate de que al menos un método esté configurado antes de iniciar.
Seguridad de inicio: La API se cierra si no hay una ruta de autenticación disponible (sin claves Biscuit, sin usuario de API administrador y sin `API_TOKEN`). Asegúrate de que al menos una esté configurada.
!!! info "Ruta raíz y proxies"
Si despliegas la API detrás de BunkerWeb en una subruta, establece `API_ROOT_PATH` en esa ruta para que `/docs` y las rutas relativas funcionen correctamente cuando se usan con un proxy.
## Operaciones
- Salud: `GET /health` devuelve `{"status":"ok"}` cuando el servicio está activo.
- Servicio de Linux: se empaqueta una unidad `systemd` llamada `bunkerweb-api.service`. Personaliza a través de `/etc/bunkerweb/api.env` y gestiona con `systemctl`.
- Seguridad de inicio: la API falla rápidamente cuando no hay una ruta de autenticación disponible (sin claves Biscuit, sin usuario administrador, sin `API_TOKEN`). Los errores se escriben en `/var/tmp/bunkerweb/api.error`.