# Virtual machine or bare metal Type of document: How-to guide Product: F5 WAF for NGINX --- This page describes how to install F5 WAF for NGINX in a virtual machine or bare metal environment. ## Before you begin To complete this guide, you will need the following prerequisites: - A [supported operating system](/waf/fundamentals/technical-specifications.md#supported-operating-systems). - Ensure you have an active F5 WAF for NGINX subscription (purchased or trial) and have downloaded the associated [SSL certificate, private key, and JWT license](#download-your-subscription-credentials) file from the MyF5 Customer Portal. Depending on your deployment type, you may have additional requirements: You should read the [IP intelligence](/waf/policies/ip-intelligence.md) topics for additional set-up configuration if you want to use them immediately. **Note:** Security mechanisms like SELinux or AppArmor may potentially block necessary file access for the NGINX process and any component containers. For more information, view the [Configure SELinux](/waf/configure/selinux.md) topic. ## Default security policy and logging profile F5 WAF for NGINX uses built-in default security policy and logging profile after installation. To use custom policies or logging profiles, update your NGINX configuration file accordingly. ## Download your subscription credentials To use NGINX Plus, you will need to download the JWT license file associated with your F5 WAF for NGINX WAF subscription from the [MyF5](https://my.f5.com/manage/s/) Customer Portal: 1. Log in to [MyF5](https://my.f5.com/manage/s/). 1. Go to **My Products & Plans > Subscriptions** to see your active subscriptions. 1. Find your NGINX subscription, and select the **Subscription ID** for details. 1. Download the **SSL Certificate**, **Private Key** and **JSON Web Token** files from the subscription page. **Note:** Starting from [NGINX Plus Release 33](nginx/releases.md#r33), a JWT file is required for each NGINX Plus instance. For more information, see [About Subscription Licenses](/solutions/about-subscription-licenses.md). ## Platform-specific instructions Navigate to your chosen operating system, which are alphabetically ordered. ### Alpine Linux Add the F5 WAF for NGINX signing key: ```shell sudo wget -O /etc/apk/keys/app-protect-security-updates.rsa.pub https://cs.nginx.com/static/keys/app-protect-security-updates.rsa.pub ``` Add the F5 WAF for NGINX repository: ```shell printf "https://pkgs.nginx.com/app-protect/alpine/v`egrep -o '^[0-9]+\.[0-9]+' /etc/alpine-release`/main\n" | sudo tee -a /etc/apk/repositories printf "https://pkgs.nginx.com/app-protect-security-updates/alpine/v`egrep -o '^[0-9]+\.[0-9]+' /etc/alpine-release`/main\n" | sudo tee -a /etc/apk/repositories ``` Update the repositories, then install the F5 WAF for NGINX package and its dependencies: ```shell sudo apk update sudo apk add openssl ca-certificates app-protect ``` #### Installing a specific version of F5 WAF for NGINX If you need to install a specific version of F5 WAF for NGINX, you can use `apk info` to list available versions, then append it to the package name: ```shell sudo apk info app-protect sudo apk add openssl ca-certificates app-protect= ``` ### Amazon Linux Add the F5 WAF for NGINX repository: ```shell sudo wget -P /etc/yum.repos.d https://cs.nginx.com/static/files/app-protect-amazonlinux2023.repo ``` Add F5 WAF for NGINX dependencies: ```shell sudo wget -P /etc/yum.repos.d https://cs.nginx.com/static/files/dependencies.amazonlinux2023.repo ``` Install the F5 WAF for NGINX package and its dependencies: ```shell sudo dnf install app-protect ``` #### Installing a specific version of F5 WAF for NGINX If you need to install a specific version of F5 WAF for NGINX, you can use `--showduplicates list` to list available versions, then append it to the package name: ```shell sudo dnf --showduplicates list app-protect sudo dnf install app-protect-= ``` ### Debian Add the F5 WAF for NGINX signing key: ```shell wget -qO - https://cs.nginx.com/static/keys/app-protect-security-updates.key | gpg --dearmor | \ sudo tee /usr/share/keyrings/app-protect-security-updates.gpg > /dev/null ``` Add the F5 WAF for NGINX repositories: ```shell printf "deb [signed-by=/usr/share/keyrings/nginx-archive-keyring.gpg] \ https://pkgs.nginx.com/app-protect/debian `lsb_release -cs` nginx-plus\n" | \ sudo tee /etc/apt/sources.list.d/nginx-app-protect.list printf "deb [signed-by=/usr/share/keyrings/app-protect-security-updates.gpg] \ https://pkgs.nginx.com/app-protect-security-updates/debian `lsb_release -cs` nginx-plus\n" | \ sudo tee /etc/apt/sources.list.d/app-protect-security-updates.list ``` Update the repositories, then install the F5 WAF for NGINX package and its dependencies: ```shell sudo apt-get update sudo apt-get install app-protect ``` #### Installing a specific version of F5 WAF for NGINX If you need to install a specific version of F5 WAF for NGINX, you can use `apt-cache` to list available versions, then append it to the package name: ```shell sudo apt-get update sudo apt-cache policy app-protect sudo apt-get install app-protect= ``` When installing a specific version of F5 WAF for NGINX, you will also need to manually install its package dependencies. You can use the following script to get the dependent packages: ```shell findDeps () { local pkgs=$(apt show $1 2>/dev/null | grep Depends: | grep -oE "(nginx-plus-module|app-protect)-[a-z]+ *\(= *[0-9\+\.-]+~`lsb_release -cs`\)" | tr -d ' ()'); for p in ${pkgs[@]}; do echo $p; findDeps $p; done; } findDeps app-protect= ``` ### Oracle Linux / RHEL / Rocky Linux 8 **Note:** The steps are identical for these platforms due to their similar architecture. Add the F5 WAF for NGINX repository: ```shell sudo wget -P /etc/yum.repos.d https://cs.nginx.com/static/files/app-protect-8.repo ``` Add F5 WAF for NGINX dependencies: ```shell sudo wget -P /etc/yum.repos.d https://cs.nginx.com/static/files/dependencies.repo ``` Enable F5 WAF for NGINX dependencies: ```shell sudo dnf config-manager --set-enabled crb ``` Enable the _ol8_codeready_builder_ repository: ```shell sudo dnf config-manager --set-enabled ol8_codeready_builder ``` Install the F5 WAF for NGINX package and its dependencies: ```shell sudo dnf install app-protect ``` #### Installing a specific version of F5 WAF for NGINX If you need to install a specific version of F5 WAF for NGINX, you can use `--showduplicates list` to list available versions, then append it to the package name: ```shell sudo dnf --showduplicates list app-protect sudo dnf install app-protect-= ``` ### RHEL / Rocky Linux 9 Add the F5 WAF for NGINX repository: ```shell sudo wget -P /etc/yum.repos.d https://cs.nginx.com/static/files/app-protect-9.repo ``` Add F5 WAF for NGINX dependencies: ```shell sudo wget -P /etc/yum.repos.d https://cs.nginx.com/static/files/dependencies.repo ``` Enable F5 WAF for NGINX dependencies: ```shell sudo dnf config-manager --set-enabled crb ``` Install the F5 WAF for NGINX package and its dependencies: ```shell sudo dnf install app-protect ``` ### RHEL 10 Add the F5 WAF for NGINX repository: ```shell sudo wget -P /etc/yum.repos.d https://cs.nginx.com/static/files/app-protect-10.repo ``` Add F5 WAF for NGINX dependencies: ```shell sudo wget -P /etc/yum.repos.d https://cs.nginx.com/static/files/dependencies.repo ``` Install the F5 WAF for NGINX package and its dependencies: ```shell sudo dnf install app-protect ``` #### Installing a specific version of F5 WAF for NGINX If you need to install a specific version of F5 WAF for NGINX, you can use `--showduplicates list` to list available versions, then append it to the package name: ```shell sudo dnf --showduplicates list app-protect sudo dnf install app-protect-= ``` ### Ubuntu Add the F5 WAF for NGINX signing key: ```shell wget -qO - https://cs.nginx.com/static/keys/app-protect-security-updates.key | \ gpg --dearmor | sudo tee /usr/share/keyrings/app-protect-security-updates.gpg > /dev/null ``` Add the F5 WAF for NGINX repositories: ```shell printf "deb [signed-by=/usr/share/keyrings/nginx-archive-keyring.gpg] \ https://pkgs.nginx.com/app-protect/ubuntu `lsb_release -cs` nginx-plus\n" | \ sudo tee /etc/apt/sources.list.d/nginx-app-protect.list printf "deb [signed-by=/usr/share/keyrings/app-protect-security-updates.gpg] \ https://pkgs.nginx.com/app-protect-security-updates/ubuntu `lsb_release -cs` nginx-plus\n" | \ sudo tee /etc/apt/sources.list.d/app-protect-security-updates.list ``` Update the repositories, then install the F5 WAF for NGINX package and its dependencies: ```shell sudo apt-get update sudo apt-get install app-protect ``` #### Installing a specific version of F5 WAF for NGINX If you need to install a specific version of F5 WAF for NGINX, you can use `apt-cache` to list available versions, then append it to the package name: ```shell sudo apt-get update sudo apt-cache policy app-protect sudo apt-get install app-protect= ``` When installing a specific version of F5 WAF for NGINX, you will also need to manually install its package dependencies. You can use the following script to get the dependent packages: ```shell findDeps () { local pkgs=$(apt show $1 2>/dev/null | grep Depends: | grep -oE "(nginx-plus-module|app-protect)-[a-z]+ *\(= *[0-9\+\.-]+~`lsb_release -cs`\)" | tr -d ' ()'); for p in ${pkgs[@]}; do echo $p; findDeps $p; done; } findDeps app-protect= ``` ## Install NGINX Plus license If you have not already copied your NGINX Plus JWT license file to the `/etc/nginx/` directory (for example, if NGINX Plus was installed automatically as a dependency), do so now: ```shell sudo cp .jwt /etc/nginx/license.jwt ``` ## Update configuration files Once you have installed F5 WAF for NGINX, you must load it as a module in the main context of your NGINX configuration. ```nginx load_module modules/ngx_http_app_protect_module.so; ``` And finally, F5 WAF for NGINX can enabled on a _http_, _server_ or _location_ context: ```nginx app_protect_enable on; ``` **Note:** You should only enable F5 WAF for NGINX on _proxy_pass_ and _grpc_pass_ locations. Here are two examples of how these additions could look in configuration files: #### nginx.conf The default path for this file is `/etc/nginx/nginx.conf`. ```nginx {hl_lines=[5]} user nginx; worker_processes auto; # F5 WAF for NGINX load_module modules/ngx_http_app_protect_module.so; error_log /var/log/nginx/error.log notice; pid /var/run/nginx.pid; events { worker_connections 1024; } http { include /etc/nginx/mime.types; default_type application/octet-stream; log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$status $body_bytes_sent "$http_referer" ' '"$http_user_agent" "$http_x_forwarded_for"'; access_log /var/log/nginx/access.log main; sendfile on; #tcp_nopush on; keepalive_timeout 65; #gzip on; include /etc/nginx/conf.d/*.conf; } ``` #### default.conf The default path for this file is `/etc/nginx/conf.d/default.conf`. ```nginx {hl_lines=[9]} server { listen 80; server_name domain.com; location / { # F5 WAF for NGINX app_protect_enable on; client_max_body_size 0; default_type text/html; proxy_pass http://127.0.0.1:8080/; } } server { listen 8080; server_name localhost; location / { root /usr/share/nginx/html; index index.html index.htm; } # redirect server error pages to the static page /50x.html # error_page 500 502 503 504 /50x.html; location = /50x.html { root /usr/share/nginx/html; } } ``` Once you have updated your configuration files, reload NGINX with the following command: - `nginx -s reload` ## Post-installation checks The following steps check that F5 WAF for NGINX enforcement is operational. They should be ran in the environment with the WAF components. Check that the three processes for F5 WAF for NGINX are running using `ps aux`: - _bd-socket-plugin_ - _nginx: master process_ - _nginx: worker process_ ```shell USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND root 8 1.3 2.4 3486948 399092 ? Sl 09:11 0:02 /usr/share/ts/bin/bd-socket-plugin tmm_count 4 proc_cpuinfo_cpu_mhz 2000000 total_xml_memory 307200000 total_umu_max_size 3129344 sys_max_account_id 1024 no_static_config root 14 0.0 0.1 71060 26680 ? S 09:11 0:00 nginx: master process /usr/sbin/nginx -c /tmp/policy/test_nginx.conf -g daemon off; root 26 0.0 0.3 99236 52092 ? S 09:12 0:00 nginx: worker process root 28 0.0 0.0 11788 2920 pts/0 Ss 09:12 0:00 bash root 43 0.0 0.0 47460 3412 pts/0 R+ 09:14 0:00 ps aux ``` Verify there are no errors in the file `/var/log/nginx/error.log` and that the policy compiled successfully: ```none 2020/05/10 13:21:04 [notice] 402#402: APP_PROTECT { "event": "configuration_load_start", "configSetFile": "/opt/f5waf/config/config_set.json" } 2020/05/10 13:21:04 [notice] 402#402: APP_PROTECT policy 'app_protect_default_policy' from: /etc/app_protect/conf/NginxDefaultPolicy.json compiled successfully 2020/05/10 13:21:04 [notice] 402#402: APP_PROTECT { "event": "configuration_load_success", "software_version": "1.1.1", "attack_signatures_package":{"revision_datetime":"2019-07-16T12:21:31Z"},"completed_successfully":true} 2020/05/10 13:21:04 [notice] 402#402: using the "epoll" event method 2020/05/10 13:21:04 [notice] 402#402: nginx/1.17.6 (nginx-plus-r20) 2020/05/10 13:21:04 [notice] 402#402: built by gcc 4.8.5 20150623 (Red Hat 4.8.5-36) (GCC) 2020/05/10 13:21:04 [notice] 402#402: OS: Linux 3.10.0-957.27.2.el7.x86_64 2020/05/10 13:21:04 [notice] 402#402: getrlimit(RLIMIT_NOFILE): 1048576:1048576 2020/05/10 13:21:04 [notice] 406#406: start worker processes 2020/05/10 13:21:04 [notice] 406#406: start worker process 407 ``` Check that sending an attack signature in a request returns a response block page containing a support ID: ```shell Request: http://10.240.185.211/?a=