docs polishing and fix install.sh gpg --verify

This commit is contained in:
bunkerity 2021-08-11 15:13:44 +02:00
parent d9f7706969
commit e98da9b637
No known key found for this signature in database
GPG Key ID: 3D80806F12602A7C
10 changed files with 75 additions and 216 deletions

View File

@ -48,7 +48,7 @@ Fooling automated tools/scanners :
<img src="https://github.com/bunkerity/bunkerized-nginx/blob/dev/docs/img/demo.gif?raw=true" />
You can find a live demo at https://demo-nginx.bunkerity.com, feel free to do some security tests.
You can find a live demo at [https://demo-nginx.bunkerity.com](https://demo-nginx.bunkerity.com), feel free to do some security tests.
# Table of contents
<details>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 46 KiB

After

Width:  |  Height:  |  Size: 51 KiB

View File

@ -24,7 +24,7 @@ To use bunkerized-nginx as a Docker container you have to pass specific environm
To demonstrate the use of the Docker image, we will create a simple "Hello World" static file that will be served by bunkerized-nginx.
**One important thing to know is that the container runs as an unprivileged user with UID and GID 101. The reason behind this behavior is the security : in case a vulnerability is exploited the attacker won't have full privileges. But there is also a downside because bunkerized-nginx (heavily) make use of volumes, you will need to adjust the rights on the host.**
**One important thing to know is that the container runs as an unprivileged user with UID and GID 101. The reason behind this behavior is the security : in case a vulnerability is exploited the attacker won't have full privileges inside the container. But there is also a downside because bunkerized-nginx (heavily) make use of volumes, you will need to adjust the rights on the host.**
First create the environment on the host :
```shell
@ -82,7 +82,7 @@ Important things to note :
Inspect the container logs until bunkerized-nginx is started then visit http(s)://www.example.com to confirm that everything is working as expected.
This example is really simple but, as you can see in the [list of environment variables](#TODO), you may get a lot of environment variables depending on your use case. To make things cleanier, you can write the environment variables to a file :
This example is really simple but, as you can see in the [list of environment variables](https://bunkerized-nginx.readthedocs.io/en/latest/environment_variables.html), you may get a lot of environment variables depending on your use case. To make things cleanier, you can write the environment variables to a file :
```shell
$ cat variables.env
SERVER_NAME=www.example.com
@ -116,23 +116,22 @@ The downside of using environment variables is that the container needs to be re
### Usage
First of all, you will need a network so autoconf and bunkerized-nginx can communicate and another one to allow communication between bunkerized-nginx and your web services :
First of all, you will need a network to allow communication between bunkerized-nginx and your web services :
```shell
$ docker network create bunkerized-net
$ docker network create services-net
```
We will also make use of a named volume to share the configuration :
We will also make use of a named volume to share the configuration between autoconf and bunkerized-nginx :
```shell
$ docker volume create bunkerized-vol
```
You can now create the bunkerized-nginx container, connect it to the web services network and start it :
You can now create the bunkerized-nginx container :
```shell
$ docker create \
--name mybunkerized \
-l bunkerized-nginx.AUTOCONF \
--network bunkerized-net \
--network services-net \
-p 80:8080 \
-p 443:8443 \
-v "${PWD}/www:/www:ro" \
@ -142,15 +141,12 @@ $ docker create \
-e SERVER_NAME= \
-e AUTO_LETS_ENCRYPT=yes \
bunkerity/bunkerized-nginx
$ docker network connect services-net mybunkerized
$ docker start mybunkerized
```
The autoconf one can now be started :
```shell
$ docker run \
--name myautoconf \
--network bunkerized-net \
--volumes-from mybunkerized:rw \
-v /var/run/docker.sock:/var/run/docker.sock:ro \
bunkerity/bunkerized-nginx-autoconf
@ -179,7 +175,6 @@ services:
labels:
- "bunkerized-nginx.AUTOCONF"
networks:
- bunkerized-net
- services-net
myautoconf:
@ -191,31 +186,26 @@ services:
- /var/run/docker.sock:/var/run/docker.sock:ro
depends_on:
- mybunkerized
networks:
- bunkerized-net
volumes:
autoconf:
networks:
bunkerized-net:
name: bunkerized-net
services-net:
name: services-net
```
Important things to note :
- autoconf needs to send reload orders to bunkerized-nginx, they need to be on the same network
- autoconf is generating config files and other artefacts for the bunkerized-nginx, they need to share the volumes
- autoconf must have access to the Docker socket in order to get events and access to labels
- autoconf is generating config files and other artefacts for the bunkerized-nginx, they need to share the same volumes
- autoconf must have access to the Docker socket in order to get events, access to labels and send SIGHUP signal (reload order) to bunkerized-nginx
- bunkerized-nginx must have the bunkerized-nginx.AUTOCONF label
- bunkerized-nginx must be started in [multisite mode](#) with the `MULTISITE=yes` environment variable
- bunkerized-nginx must be started in [multisite mode](https://bunkerized-nginx.readthedocs.io/en/latest/quickstart_guide.html#multisite) with the `MULTISITE=yes` environment variable
- When setting the `SERVER_NAME` environment variable to an empty value, bunkerized-nginx won't generate any web service configuration at startup
- The `AUTO_LETS_ENCRYPT=yes` will be applied to all subsequent web service configuration, unless overriden by the web service labels
Check the logs of both autoconf and bunkerized-nginx to see if everything is working as expected.
You can now create a new web service and add environment variables as labels with the **"bunkerized-nginx." prefix** so the autoconf service will "automagically" do the configuration for you :
You can now create a new web service and add environment variables as labels with the `bunkerized-nginx.` prefix to let the autoconf service "automagically" do the configuration for you :
```shell
$ docker run \
--name myservice \
@ -255,7 +245,7 @@ Please note that if you want to override the `AUTO_LETS_ENCRYPT=yes` previously
Look at the logs of both autoconf and bunkerized-nginx to check if the configuration has been generated and loaded by bunkerized-nginx. You should now be able to visit http(s)://www.example.com.
When your container is not needed anymore, you can delete it as usual. The autoconf should get the event and remove generate the configuration again.
When your container is not needed anymore, you can delete it as usual. The autoconf should get the event and generate the configuration again.
## Docker Swarm
@ -267,11 +257,9 @@ Using bunkerized-nginx in a Docker Swarm cluster requires a shared folder access
### Usage
**We will assume that a shared directory is mounted at the /shared location on both your managers and workers. Don't forget that bunkerized-nginx and autoconf are running as unprivileged users with UID and GID 101. You must set the rights and permissions of the subfolder in /shared accordingly.**
**We will assume that a shared directory is mounted at the /shared location on both your managers and workers. Keep in mind that bunkerized-nginx and autoconf are running as unprivileged users with UID and GID 101. You must set the rights and permissions of the subfolders in /shared accordingly.**
**We also recommend you to first read the [Docker](#TODO) section before.**
In this setup we will deploy bunkerized-nginx in global mode on all workers and autoconf as a single replica.
In this setup we will deploy bunkerized-nginx in global mode on all workers and autoconf as a single replica on a manager.
First of all, you will need to setup the shared folders :
```shell
@ -309,7 +297,7 @@ $ docker service create \
-e AUTO_LETS_ENCRYPT=yes \
bunkerity/bunkerized-nginx
$ docker service update \
--network-add services-net
--network-add services-net \
mybunkerized
```
@ -366,6 +354,7 @@ services:
placement:
constraints:
- "node.role==worker"
# mandatory label
labels:
- "bunkerized-nginx.AUTOCONF"
@ -401,7 +390,7 @@ networks:
Check the logs of both autoconf and bunkerized-nginx services to see if everything is working as expected.
You can now create a new service and add environment variables as labels with the **"bunkerized-nginx." prefix** so the autoconf service will "automagically" do the configuration for you :
You can now create a new service and add environment variables as labels with the `bunkerized-nginx.` prefix to let the autoconf service "automagically" do the configuration for you :
```shell
$ docker service create \
--name myservice \
@ -440,11 +429,11 @@ networks:
name: services-net
```
Please note that if you want to override the AUTO_LETS_ENCRYPT=yes previously defined in the bunkerized-nginx service, you simply need to add the bunkerized-nginx.AUTO_LETS_ENCRYPT=no label.
Please note that if you want to override the `AUTO_LETS_ENCRYPT=yes` previously defined in the bunkerized-nginx service, you simply need to add the `bunkerized-nginx.AUTO_LETS_ENCRYPT=no` label.
Look at the logs of both autoconf and bunkerized-nginx to check if the configuration has been generated and loaded by bunkerized-nginx. You should now be able to visit http(s)://www.example.com.
When your service is not needed anymore, you can delete it as usual. The autoconf should get the event and remove generate the configuration again.
When your service is not needed anymore, you can delete it as usual. The autoconf should get the event and generate the configuration again.
## Kubernetes
@ -458,9 +447,7 @@ Using bunkerized-nginx in a Kubernetes cluster requires a shared folder accessib
### Usage
**We will assume that a shared directory is mounted at the /shared location on your nodes. Don't forget that bunkerized-nginx and autoconf are running as unprivileged users with UID and GID 101. You must set the rights and permissions of the subfolder in /shared accordingly.**
**We also recommend you to first read the [Docker](#TODO) section before.**
**We will assume that a shared directory is mounted at the /shared location on your nodes. Keep in mind that bunkerized-nginx and autoconf are running as unprivileged users with UID and GID 101. You must set the rights and permissions of the subfolders in /shared accordingly.**
First of all, you will need to setup the shared folders :
```shell
@ -470,7 +457,7 @@ $ chown root:nginx www confs letsencrypt acme-challenge
$ chmod 770 www confs letsencrypt acme-challenge
```
The first step to do is to declare the RBAC authorization that will be used by the Ingress Controller to access the Kubernetes API. A ready-to-use declaration is available that you should audit before applying it :
The first step to do is to declare the RBAC authorization that will be used by the Ingress Controller to access the Kubernetes API. A ready-to-use declaration is available here :
```yaml
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
@ -714,7 +701,7 @@ spec:
Check the logs to see if the configuration has been generated and bunkerized-nginx reloaded. You should be able to visit http(s)://www.example.com.
Note that an alternative would be to add annotations directly to your services (a common use-case is for [PHP applications](#TODO) because the Ingress resource is only for reverse proxy) without editing the ingress resource :
Note that an alternative would be to add annotations directly to your services (a common use-case is for [PHP applications](https://bunkerized-nginx.readthedocs.io/en/latest/quickstart_guide.html#php-applications) because the Ingress resource is only for reverse proxy) without editing the Ingress resource :
```yaml
apiVersion: v1
kind: Service
@ -750,7 +737,7 @@ List of supported Linux distributions :
- CentOS 7
- Fedora 34
Unlike containers, Linux integration can be tedious because bunkerized-nginx has a bunch of dependencies that need to be installed before we can use it. Fortunately, we provide a helper script to make the process easier and automatic. Once installed, the configuration is really simple, all you have to do is to edit the /opt/bunkerized-nginx/variables.env configuration file and run the bunkerized-nginx command to apply it.
Unlike containers, Linux integration can be tedious because bunkerized-nginx has a bunch of dependencies that need to be installed before we can use it. Fortunately, we provide a helper script to make the process easier and automatic. Once installed, the configuration is really simple, all you have to do is to edit the `/opt/bunkerized-nginx/variables.env` configuration file and run the `bunkerized-nginx` command to apply it.
### Usage
@ -775,14 +762,14 @@ $ /tmp/bunkerized-nginx.sh
To demonstrate the configuration on Linux, we will create a simple “Hello World” static file that will be served by bunkerized-nginx.
Static files are stored inside the /opt/bunkerized-nginx/www folder and the unprivileged nginx user must have read access on it :
Static files are stored inside the `/opt/bunkerized-nginx/www` folder and the unprivileged nginx user must have read access on it :
```shell
$ echo "Hello bunkerized World !" > /opt/bunkerized-nginx/www/index.html
$ chown root:nginx /opt/bunkerized-nginx/www/index.html
$ chmod 740 /opt/bunkerized-nginx/www/index.html
```
Here is the example configuration file that needs to be written at /opt/bunkerized-nginx/variables.env :
Here is the example configuration file that needs to be written at `/opt/bunkerized-nginx/variables.env` :
```conf
HTTP_PORT=80
HTTPS_PORT=443

View File

@ -27,4 +27,4 @@ Fooling automated tools/scanners :
<img src="https://github.com/bunkerity/bunkerized-nginx/blob/dev/docs/img/demo.gif?raw=true" />
You can find a live demo at https://demo-nginx.bunkerity.com, feel free to do some security tests.
You can find a live demo at [https://demo-nginx.bunkerity.com](https://demo-nginx.bunkerity.com), feel free to do some security tests.

View File

@ -15,7 +15,7 @@ REVERSE_PROXY_URL=/
REVERSE_PROXY_HOST=http://my-service.example.local:8080
```
If you have multiple web services you configure multiple reverse proxy rules by appending a number to the environment variables names :
If you have multiple web services you can configure multiple reverse proxy rules by appending a number to the environment variables names :
```conf
SERVER_NAME=www.example.com
USE_REVERSE_PROXY=yes
@ -27,7 +27,7 @@ REVERSE_PROXY_HOST_2=http://app2.example.local:8080
### Docker
When using Docker, the recommended way is to create a network so bunkerized-nginx can communicate with the web service using its container name :
When using Docker, the recommended way is to create a network so bunkerized-nginx can communicate with the web service using the container name :
```shell
$ docker network create services-net
$ docker run -d \
@ -289,7 +289,7 @@ LOCAL_PHP_PATH=/opt/bunkerized-nginx/www
### Docker
When using Docker, the recommended way is to create a network so bunkerized-nginx can communicate with the PHP-FPM instance using its container name :
When using Docker, the recommended way is to create a network so bunkerized-nginx can communicate with the PHP-FPM instance using the container name :
```shell
$ docker network create services-net
$ docker run -d \
@ -429,7 +429,7 @@ networks:
### Kubernetes
You need to use environment variables as annotations prefixed with "bunkerized-nginx." inside the Service resource of your PHP-FPM instance :
You need to use environment variables as annotations prefixed with `bunkerized-nginx.` inside the Service resource of your PHP-FPM instance :
```yaml
apiVersion: apps/v1
@ -500,7 +500,7 @@ LOCAL_PHP_PATH=/opt/bunkerized-nginx/www
## Multisite
If you have multiple services to protect, the easiest way to do it is by enabling the "multisite" mode. When using multisite, bunkerized-nginx will create one server block per server defined in the SERVER_NAME environment variable. You can configure each servers independently by adding the server name as a prefix.
If you have multiple services to protect, the easiest way to do it is by enabling the "multisite" mode. When using multisite, bunkerized-nginx will create one server block per server defined in the `SERVER_NAME` environment variable. You can configure each servers independently by adding the server name as a prefix.
Here is an example :
```conf
@ -513,7 +513,7 @@ app2.example.com_REMOTE_PHP=app2.example.local
app2.example.com_REMOTE_PHP_PATH=/var/www/html
```
TODO : some words about special folders
When using the multisite mode, some [special folders](https://bunkerized-nginx.readthedocs.io/en/latest/special_folders.html) must have a specific structure with subfolders named the same as the servers defined in the `SERVER_NAME` environment variable. Let's take the **app2.example.com** as an example : if some static files need to be served by nginx, you need to place them under **www/app2.example.com**.
### Docker
@ -593,7 +593,7 @@ networks:
### Docker autoconf
**The multisite feature is implicitly activated when using the Docker autoconf integration.**
**The multisite feature must be activated when using the Docker autoconf integration.**
When the Docker autoconf stack is running, you simply need to start the containers hosting your web services and add the environment variables as labels :
```shell
@ -654,7 +654,7 @@ networks:
### Docker Swarm
**The multisite feature is implicitly activated when using the Docker Swarm integration.**
**The multisite feature must be activated when using the Docker Swarm integration.**
When the Docker Swarm stack is running, you simply need to start the Swarm service hosting your web services and add the environment variables as labels :
```shell
@ -721,7 +721,7 @@ networks:
### Kubernetes
**The multisite feature is implicitly activated when using the Kubernetes integration.**
**The multisite feature must be activated when using the Kubernetes integration.**
```yaml
apiVersion: apps/v1

View File

@ -6,7 +6,7 @@ bunkerized-nginx comes with a set of predefined security settings that you can (
Here is a list of miscellaneous environment variables related more or less to security :
- `MAX_CLIENT_SIZE=10m` : maximum size of client body
- `ALLOWED_METHODS=GET|POST|HEAD` : list of HTTP methos that clients are allowed to use
- `ALLOWED_METHODS=GET|POST|HEAD` : list of HTTP methods that clients are allowed to use
- `DISABLE_DEFAULT_SERVER=no` : enable/disable the default server (i.e. : should your server respond to unknown Host header ?)
- `SERVER_TOKENS=off` : enable/disable sending the version number of nginx
@ -26,11 +26,11 @@ Here is a list of environment variables and the corresponding default value rela
Using Let's Encrypt with the `AUTO_LETS_ENCRYPT=yes` environment variable is the easiest way to add HTTPS supports to your web services if they are connected to internet and you have public DNS A record(s).
You can also set the `EMAIL_LETS_ENCRYPT` environment variable if you want to receive notifications from Let's Encrypt (e.g. : expiration).
You can also set the `EMAIL_LETS_ENCRYPT` environment variable if you want to receive notifications from Let's Encrypt like expiration alerts.
### Custom certificate(s)
If you have security constraints (e.g : local network, custom PKI, ...) you can use custom certificates of your choice and tell bunkerized-nginx to use them with the following environment variables :
If you have security constraints (e.g., local network, custom PKI, ...) you can use custom certificates of your choice and tell bunkerized-nginx to use them with the following environment variables :
- `USE_CUSTOM_HTTPS=yes`
- `CUSTOM_HTTPS_CERT=/path/inside/container/to/cert.pem`
- `CUSTOM_HTTPS_KEY=/path/inside/container/to/key.pem`
@ -53,12 +53,23 @@ $ docker run -p 80:8080 \
Please note that if you have one or more intermediate certificate(s) in your chain of trust, you will need to provide the bundle to `CUSTOM_HTTPS_CERT` (more info [here](https://nginx.org/en/docs/http/configuring_https_servers.html#chains)).
You can reload the certificate(s) (e.g. : in case of a renewal) by sending the SIGHUP/HUP signal to the container bunkerized-nginx will catch the signal and send a reload order to nginx :
You can reload the certificate(s) (i.e., in case of a renewal) by sending a reload order to bunkerized-nginx.
Docker reload :
```shell
docker kill --signal=SIGHUP my-container
```
Swarm and Kubernetes reload (repeat for each node) :
```shell
$ curl http://node-local-ip:80/reload
```
Linux reload :
```shell
$ /usr/sbin/nginx -s reload
```
### Self-signed certificate
This method is not recommended in production but can be used to quickly deploy HTTPS for testing purposes. Just use the `GENERATE_SELF_SIGNED_SSL=yes` environment variable and bunkerized-nginx will generate a self-signed certificate for you :
@ -74,17 +85,17 @@ $ docker run -p 80:8080 \
Some important HTTP headers related to client security are sent with a default value. Sometimes it can break a web application or can be tuned to provide even more security. The complete list is available [here](https://bunkerized-nginx.readthedocs.io/en/latest/environment_variables.html#security-headers).
You can also remove headers (e.g. : too verbose ones) by using the `REMOVE_HEADERS` environment variable which takes a list of header name separated with space (default value = `Server X-Powered-By X-AspNet-Version X-AspNetMvc-Version`).
You can also remove headers (e.g., too verbose ones) by using the `REMOVE_HEADERS` environment variable which takes a list of header name separated with space (default value = `Server X-Powered-By X-AspNet-Version X-AspNetMvc-Version`).
## ModSecurity
ModSecurity is integrated and enabled by default alongside the OWASP Core Rule Set within bunkerized-nginx. To change this behaviour you can use the `USE_MODSECURITY=no` or `USE_MODSECURITY_CRS=no` environment variables.
We strongly recommend to keep both ModSecurity and the OWASP Core Rule Set enabled. The only downsides are the false positives that may occur. But they can be fixed easily and the CRS team maintains a list of exclusions for common application (e.g : wordpress, nextcloud, drupal, cpanel, ...).
We strongly recommend to keep both ModSecurity and the OWASP Core Rule Set enabled. The only downsides are the false positives that may occur. But they can be fixed easily and the CRS team maintains a list of exclusions for common application (e.g., wordpress, nextcloud, drupal, cpanel, ...).
Tuning the CRS with bunkerized-nginx is pretty simple : you can add configuration before (i.e. : exclusions) and after (i.e. : exceptions/tuning) the rules are loaded. You just need to mount your .conf files into the /modsec-crs-confs (before CRS is loaded) and /modsec-confs (after CRS is loaded).
Tuning the CRS with bunkerized-nginx is pretty simple : you can add configuration before and after the rules are loaded. You just need to mount your .conf files into the `/modsec-crs-confs` (before CRS is loaded) and `/modsec-confs` (after CRS is loaded) volumes. If you are using Linux integration the [special folders](https://bunkerized-nginx.readthedocs.io/en/dev/special_folders.html) are `/opt/bunkerized-nginx/modsec-confs` and `/opt/bunkerized-nginx/modsec-crs-confs`.
Here is an example to illustrate it :
Here is a Docker example to illustrate it :
```shell
$ cat /data/exclusions-crs/wordpress.conf
@ -122,7 +133,7 @@ That kind of security measure is implemented and enabled by default in bunkerize
## Antibot challenge
Attackers will certainly use automated tools to exploit/find some vulnerabilities on your web service. One countermeasure is to challenge the users to detect if it looks like a bot. It might be effective against script kiddies or "lazy" attackers.
Attackers will certainly use automated tools to exploit/find some vulnerabilities on your web services. One countermeasure is to challenge the users to detect if they look like a bot. It might be effective against script kiddies or "lazy" attackers.
You can use the `USE_ANTIBOT` environment variable to add that kind of checks whenever a new client is connecting. The available challenges are : `cookie`, `javascript`, `captcha` and `recaptcha`. More info [here](https://bunkerized-nginx.readthedocs.io/en/latest/environment_variables.html#antibot).
@ -132,15 +143,6 @@ You can use the `USE_ANTIBOT` environment variable to add that kind of checks wh
Automatic checks on external DNS BlackLists are enabled by default with the `USE_DNSBL=yes` environment variable. The list of DNSBL zones is also configurable, you just need to edit the `DNSBL_LIST` environment variable which contains the following value by default `bl.blocklist.de problems.dnsbl.sorbs.net sbl.spamhaus.org xbl.spamhaus.org`.
### CrowdSec
CrowdSec is not enabled by default because it's more than an external blacklists and needs some extra work to get it working. But bunkerized-nginx is fully working with CrowdSec, here are the related environment variables :
- `USE_CROWDSEC=no` : enable/disable CrowdSec checks before we authorize a client
- `CROWDSEC_HOST=` : full URL to your CrowdSec instance API
- `CROWDSEC_KEY=` : bouncer key given from **cscli bouncer add MyBouncer**
You will also need to share the logs generated by bunkerized-nginx with your CrowdSec instance. One approach is to send the logs to a syslog server which is writing the logs to the file system and then CrowdSec can easily read the logs. If you want to give it a try, you have a concrete example on how to use CrowdSec with bunkerized-nginx [here](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/crowdsec).
### User-Agents
Sometimes script kiddies or lazy attackers don't put a "legitimate" value inside the **User-Agent** HTTP header so we can block them. This is controlled with the `BLOCK_USER_AGENT=yes` environment variable. The blacklist is composed of two files from [here](https://raw.githubusercontent.com/mitchellkrogza/nginx-ultimate-bad-bot-blocker/master/_generator_lists/bad-user-agents.list) and [here](https://raw.githubusercontent.com/JayBizzle/Crawler-Detect/master/raw/Crawlers.txt).
@ -169,7 +171,7 @@ This list contains bad referrers domains known for spamming (downloaded from [he
### Requests
To limit bruteforce attacks we decided to use the [rate limiting feature in nginx](https://www.nginx.com/blog/rate-limiting-nginx/) so attackers will be limited to X request(s)/s for the same resource. That kind of protection might be useful against other attacks too (e.g. : blind SQL injection).
To limit bruteforce attacks we decided to use the [rate limiting feature in nginx](https://www.nginx.com/blog/rate-limiting-nginx/) so attackers will be limited to X request(s)/s for the same resource. That kind of protection might be useful against other attacks too (e.g., blind SQL injection).
Here is the list of related environment variables and their default value :
- `USE_LIMIT_REQ=yes` : enable/disable request limiting
@ -217,47 +219,16 @@ Here is the list of related environment variables and their default value :
- `USE_BLACKLIST_REVERSE=yes` : enable/disable blacklisting by reverse DNS
- `BLACKLIST_REVERSE_LIST=.shodan.io` : the list of reverse DNS suffixes to never trust
## Web UI
Mounting the docker socket in a container which is facing the network, like we do with the [web UI](https://bunkerized-nginx.readthedocs.io/en/latest/quickstart_guide.html#web-ui), is not a good security practice. In case of a vulnerability inside the application, attackers can freely use the Docker socket and the whole host can be compromised.
A possible workaround is to use the [tecnativa/docker-socket-proxy](https://github.com/Tecnativa/docker-socket-proxy) image which acts as a reverse proxy between the application and the Docker socket. It can allow/deny the requests made to the Docker API.
Before starting the web UI, you need to fire up the docker-socket-proxy (we also need a network because of inter-container communication) :
```shell
docker network create mynet
```
```shell
docker run --name mysocketproxy \
--network mynet \
-v /var/run/docker.sock:/var/run/docker.sock:ro \
-e POST=1 \
-e CONTAINERS=1 \
tecnativa/docker-socket-proxy
```
You can now start the web UI container and use the `DOCKER_HOST` environment variable to define the Docker API endpoint :
```shell
docker run --network mynet \
-v autoconf:/etc/nginx \
-e ABSOLUTE_URI=https://my.webapp.com/admin/ \
-e DOCKER_HOST=tcp://mysocketproxy:2375 \
bunkerity/bunkerized-nginx-ui
```
## Plugins
Some security features can be added through the plugins system (e.g. : ClamAV). You will find more info in the [plugins section](https://bunkerized-nginx.readthedocs.io/en/latest/plugins.html).
Some security features can be added through the plugins system (e.g., ClamAV, CrowdSec, ...). You will find more info in the [plugins section](https://bunkerized-nginx.readthedocs.io/en/latest/plugins.html).
## Container hardening
You will find a ready to use docker-compose.yml file focused on container hardening [here](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/hardened).
### Drop capabilities
By default, *bunkerized-nginx* runs as non-root user inside the container and should not use any of the default [capabilities](https://docs.docker.com/engine/security/#linux-kernel-capabilities) allowed by Docker. You can safely remove all capabilities to harden the container :
By default, bunkerized-nginx runs as non-root user inside the container and should not use any of the default [capabilities](https://docs.docker.com/engine/security/#linux-kernel-capabilities) allowed by Docker. You can safely remove all capabilities to harden the container :
```shell
docker run ... --drop-cap=all ... bunkerity/bunkerized-nginx

View File

@ -1,10 +1,10 @@
# Special folders
Please note that bunkerized-nginx run as an unprivileged user (UID/GID 101 when using the Docker image) and you should set the rights on the host accordingly to the files and folders on your host.
Please note that bunkerized-nginx runs as an unprivileged user (UID/GID 101 when using the Docker image) and you should set the rights on the host accordingly to the files and folders on your host.
## Multisite
When the special folder "support" the multisite mode, you can create subfolders named as the server names used in the configuration. When doing it only the subfolder files will be "used" by the corresponding web service.
When the special folder "supports" the multisite mode, you can create subfolders named as the server names used in the configuration. When doing it only the subfolder files will be "used" by the corresponding web service.
## Web files
@ -16,8 +16,8 @@ Multisite : `yes`
Read-only : `yes`
Examples :
- [TODO basic single](#TODO)
- [TODO advanced multi](#TODO)
- [Basic website with PHP](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/basic-website-with-php)
- [Multisite basic](https://github.com/bunkerity/bunkerized-nginx/blob/master/examples/multisite-basic)
## http configurations
@ -29,7 +29,7 @@ Multisite : `no`
Read-only : `yes`
Examples :
- [TODO](#TODO)
- [Load balancer](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/load-balancer)
## server configurations
@ -41,8 +41,8 @@ Multisite : `yes`
Read-only : `yes`
Examples :
- [TODO basic single](#TODO)
- [TODO advanced multi](#TODO)
- [Wordpress](https://github.com/bunkerity/bunkerized-nginx/blob/master/examples/wordpress)
- [Multisite custom confs](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/multisite-custom-confs)
## ModSecurity configurations
@ -54,8 +54,8 @@ Multisite : `yes`
Read-only : `yes`
Examples :
- [TODO basic single](#TODO)
- [TODO advanced multi](#TODO)
- [Wordpress](https://github.com/bunkerity/bunkerized-nginx/blob/master/examples/wordpress)
- [Multisite custom confs](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/multisite-custom-confs)
## CRS configurations
@ -67,8 +67,8 @@ Multisite : `yes`
Read-only : `yes`
Examples :
- [TODO basic single](#TODO)
- [TODO advanced multi](#TODO)
- [Wordpress](https://github.com/bunkerity/bunkerized-nginx/blob/master/examples/wordpress)
- [Multisite custom confs](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/multisite-custom-confs)
## Cache
@ -81,7 +81,7 @@ Read-only : `no`
## Plugins
This special folder is the placeholder for the plugins loaded by bunkerized-nginx. See the [plugin section](#TODO) for more information.
This special folder is the placeholder for the plugins loaded by bunkerized-nginx. See the [plugins section](https://bunkerized-nginx.readthedocs.io/en/latest/plugins.html) for more information.
Location (container) : `/plugins`
Location (Linux) : `/opt/bunkerized-nginx/plugins`

View File

@ -1,93 +0,0 @@
# Volumes list
Please note that bunkerized-nginx run as an unprivileged user inside the container (UID/GID = 101) and you should set the rights on the host accordingly (e.g. : chmod 101:101 ...) to the files and folders on your host.
## Web files
Mountpoint : `/www`
Description :
If `MULTISITE=no`, the web files are directly stored inside the `/www` folder. When `MULTISITE=yes`, you need to create subdirectories named as the servers defined in the `SERVER_NAME` environment variable.
Examples : [basic](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/basic-website-with-php) and [multisite](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/multisite-basic)
Read-only : yes
## Let's Encrypt
Mountpoint : `/etc/letsencrypt`
Description :
When `AUTO_LETS_ENCRYPT=yes`, certbot will save configurations, certificates and keys inside the `/etc/letsencrypt` folder. It's a common practise to save it so you can remount it in case of a container restart and certbot won't generate new certificate(s).
Examples : [here](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/basic-website-with-php)
Read-only : no
## Custom nginx configurations
### http context
Mountpoint : `/http-confs`
Description :
If you need to add custom configurations at http context, you can create **.conf** files and mount them to the `/http-confs` folder.
Examples : [load balancer](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/load-balancer)
Read-only : yes
### server context
Mountpoint : `/server-confs`
Description :
If `MULTISITE=no`, you can create **.conf** files and mount them to the `/server-confs` folder. When `MULTISITE=yes`, you need to create subdirectories named as the servers defined in the `SERVER_NAME` environment variable.
Examples : [nextcloud](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/nextcloud) and [multisite](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/multisite-custom-server-confs)
Read-only : yes
## ModSecurity
### Rules and before CRS
Mountpoint : `/modsec-confs`
Description :
Use this volume if you need to add custom ModSecurity rules and/or OWASP Core Rule Set configurations before the rules are loaded (e.g. : exclusions).
If `MULTISITE=no` you can create **.conf** files and mount them to the `/modsec-confs` folder. When `MULTISITE=yes`, you need to create subdirectories named as the servers defined in the `SERVER_NAME` environment variable. You can also apply global configuration to all servers by putting **.conf** files directly on the root folder.
Examples : [wordpress](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/wordpress) and [multisite](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/multisite-custom-server-confs)
Read-only : yes
### After CRS
Mountpoint : `/modsec-crs-confs`
Description :
Use this volume to tweak OWASP Core Rule Set (e.g. : tweak rules to avoid false positives). Your files are loaded after the rules.
If `MULTISITE=no` you can create **.conf** files and mount them to the `/modsec-crs-confs` folder. When `MULTISITE=yes`, you need to create subdirectories named as the servers defined in the `SERVER_NAME` environment variable. You can also apply global configuration to all servers by putting **.conf** files directly on the root folder.
Examples : [wordpress](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/wordpress) and [multisite](https://github.com/bunkerity/bunkerized-nginx/tree/master/examples/multisite-custom-server-confs)
Read-only : yes
## Cache
Mountpoint : `/cache`
Description :
Depending of the settings you use, bunkerized-nginx may download external content (e.g. : blacklists, GeoIP DB, ...). To avoid downloading it again in case of a container restart, you can save the data on the host.
Read-only : no
## Plugins
Mountpoint : `/plugins`
Description :
This volume is used to extend bunkerized-nginx with [additional plugins](https://bunkerized-nginx.readthedocs.io/en/latest/plugins.html). Please note that you will need to have a subdirectory for each plugin you want to enable.
Read-only : yes

View File

@ -12,12 +12,11 @@ The web UI has its own set of environment variables to configure it :
- `API_URI` : path of the bunkerized-nginx API (must match the corresponding `API_URI` of the bunkerized-nginx instance)
- `DOCKER_HOST` : Docker API endpoint address (default = `unix:///var/run/docker.sock`)
The deployment should be very easy because the web UI is web a service itself so we can use bunkerized-nginx as a reverse proxy in front of it.
Since the web UI is ia service itself, we can use bunkerized-nginx as a reverse proxy in front of it.
**
Using the web UI in a Docker environment (containers, autoconf or Swarm) exposes a security risk because you need to mount the Docker API socket into the web UI container. It's highly recommended to use a middleware like [tecnativa/docker-socket-proxy](https://github.com/Tecnativa/docker-socket-proxy) to reduce the risk as much as possible.
Extra security steps still needs to be done like : complex admin password, hard to guess public URI, network isolation from others services, HTTPS only, ...
**
**Using the web UI in a Docker environment exposes a security risk because you need to mount the Docker API socket into the web UI container. It's highly recommended to use a middleware like [tecnativa/docker-socket-proxy](https://github.com/Tecnativa/docker-socket-proxy) to reduce the risk as much as possible.**
**You need to apply the security best practices because the web UI contains code and that code might be vulnerable : complex admin password, hard to guess public URI, network isolation from others services, HTTPS only, ...**
### Docker

View File

@ -604,12 +604,7 @@ do_and_check_cmd wget -O "/tmp/bunkerized-nginx/nginx-${NGINX_VERSION}.tar.gz" "
do_and_check_cmd wget -O "/tmp/bunkerized-nginx/nginx-${NGINX_VERSION}.tar.gz.asc" "https://nginx.org/download/nginx-${NGINX_VERSION}.tar.gz.asc"
get_sign_source_keys > /tmp/bunkerized-nginx/nginx.key
do_and_check_cmd gpg --import /tmp/bunkerized-nginx/nginx.key
check=$(gpg --verify /tmp/bunkerized-nginx/nginx-${NGINX_VERSION}.tar.gz.asc /tmp/bunkerized-nginx/nginx-${NGINX_VERSION}.tar.gz 2>&1 | grep "^gpg: Good signature from ")
if [ "$check" = "" ] ; then
echo "[!] Wrong signature from nginx source !!!"
cleanup
exit 1
fi
do_and_check_cmd gpg --verify /tmp/bunkerized-nginx/nginx-${NGINX_VERSION}.tar.gz.asc /tmp/bunkerized-nginx/nginx-${NGINX_VERSION}.tar.gz
CHANGE_DIR="/tmp/bunkerized-nginx" do_and_check_cmd tar -xvzf nginx-${NGINX_VERSION}.tar.gz
# Compile dynamic modules