Sitemap
Aytxc

Aytxc

Deploying ModSecurity WAF with OWASP Core Rule Set (CRS) on Ubuntu Server

8 min readJul 12, 2026

--

Introduction

Web applications are frequent targets of cyberattacks such as SQL Injection (SQLi), Cross-Site Scripting (XSS), and Remote Code Execution (RCE). A Web Application Firewall (WAF) helps mitigate these threats by inspecting incoming HTTP requests and blocking malicious traffic before it reaches the web application.

In this project, ModSecurity was deployed on an Ubuntu Server and integrated with the OWASP Core Rule Set (CRS) to create a layered defense for a web application hosted on Apache. The lab demonstrates the installation, configuration, and validation of the WAF by simulating common web attacks.

Lab Environment

The lab was conducted on an Apple Silicon (M2) host machine using VMware Fusion as the virtualization platform. An Ubuntu Server 26.04 LTS (ARM64) virtual machine was deployed to serve as the target server. Apache2 was used as the web server, while ModSecurity was configured as the Web Application Firewall (WAF) and integrated with the OWASP Core Rule Set (CRS) to detect and block common web attacks. Google Chrome was used to access and test the web application from the host machine.

Step 1: Preparing the Ubuntu Server

An Ubuntu Server 26.04 LTS (ARM64) virtual machine was created in VMware Fusion to serve as the lab environment. Once the installation was complete, the operating system was updated to ensure that all packages were up to date.

The following commands were executed to update the system:

sudo apt update
sudo apt upgrade -y

After the update process, the server information was verified to confirm the operating system version, kernel, and system architecture.

hostnamectl
lsb_release -a

The output confirmed that the virtual machine was running Ubuntu Server 26.04 LTS (ARM64) on VMware Fusion.

Step 2: Installing Apache Web Server

Apache2 was selected as the web server for this lab because it integrates seamlessly with ModSecurity and is one of the most widely used web servers in production environments.

First, Apache2 was installed using the APT package manager:

sudo apt install apache2 -y

After the installation, the Apache service was enabled to start automatically during system boot and then started manually.

sudo systemctl enable apache2
sudo systemctl start apache2

To verify that Apache was running correctly, the service status was checked:

sudo systemctl status apache2
Press enter or click to view image in full size

A successful installation displays the service status as active (running).

Next, the server’s IP address was identified:

hostname -I

Finally, the Apache default page was accessed from the host machine by navigating to:

http://<server-ip>

If the installation was successful, the default Apache2 Ubuntu Default Page was displayed in the browser, confirming that the web server was operational.

Press enter or click to view image in full size

Step 3: Creating a Test Web Page

After confirming that Apache was running successfully, the default Apache landing page was replaced with a custom HTML page. This page served as the test application that would later be protected by ModSecurity and the OWASP Core Rule Set (CRS). Creating a simple web page also provided an easy way to verify that the web server was functioning correctly before deploying the Web Application Firewall.

sudo rm /var/www/html/index.html
sudo nano /var/www/html/index.html
Press enter or click to view image in full size
Press enter or click to view image in full size

Step 4: Installing ModSecurity

With the Apache web server successfully deployed, the next step was to install ModSecurity, an open-source Web Application Firewall (WAF). ModSecurity acts as a security layer between incoming HTTP requests and the web application, inspecting traffic and applying predefined security rules to identify and block malicious requests.

The ModSecurity module was installed using the APT package manager:

sudo apt install libapache2-mod-security2 -y

After the installation, the loaded Apache modules were checked to verify that the ModSecurity module had been successfully enabled.

apache2ctl -M | grep security

A successful installation returns:

security2_module (shared)
Press enter or click to view image in full size

Step 5: Enabling ModSecurity

After installing ModSecurity, the next step was to enable its security engine. By default, ModSecurity operates in DetectionOnly mode, which logs suspicious requests but does not block them. To transform the WAF into an active protection mechanism, the rule engine was configured to block malicious traffic.

First, the recommended configuration file was copied to the default ModSecurity configuration directory.

sudo cp /etc/modsecurity/modsecurity.conf-recommended /etc/modsecurity/modsecurity.conf

Next, the modsecurity.conf file was opened and the following directive was modified:

SecRuleEngine DetectionOnly

was changed to:

SecRuleEngine On

The Apache service was then restarted to apply the configuration changes.

sudo systemctl restart apache2

Finally, the configuration was verified to ensure that the ModSecurity rule engine was running in blocking mode.

grep SecRuleEngine /etc/modsecurity/modsecurity.conf

The output confirmed that the rule engine was successfully enabled.

Press enter or click to view image in full size

Step 6: Installing and Configuring the OWASP Core Rule Set (CRS)

The ModSecurity engine requires a set of security rules to detect malicious requests. For this purpose, the OWASP Core Rule Set (CRS) was used. The CRS is a community-maintained collection of rules designed to protect web applications against common attacks such as SQL Injection (SQLi), Cross-Site Scripting (XSS), Remote Code Execution (RCE), Local File Inclusion (LFI), and many other threats.

Before enabling the rule set, the CRS installation directory was verified to ensure that the required rule files were available.

ls /etc/modsecurity/crs

The presence of the CRS rule files confirmed that the rule set was successfully installed and ready to be integrated with ModSecurity.

Press enter or click to view image in full size

Step 6: Installing the OWASP Core Rule Set (CRS)

The default ModSecurity installation does not include the complete OWASP Core Rule Set (CRS). Therefore, the latest version of the CRS was downloaded from its official GitHub repository.

Get Aytxc’s stories in your inbox

Join Medium for free to get updates from this writer.

The rule files were copied to the ModSecurity configuration directory, and the default CRS configuration file was created from the provided example template.

sudo apt install git -y
cd /tmp
git clone https://github.com/coreruleset/coreruleset.git
sudo cp -r /tmp/coreruleset/rules /etc/modsecurity/sudo cp /tmp/coreruleset/crs-setup.conf.example \
/etc/modsecurity/crs/crs-setup.conf

After the installation, the rules directory was verified to ensure that the complete OWASP Core Rule Set had been successfully deployed.

Press enter or click to view image in full size

Step 7: Loading the OWASP Core Rule Set

After installing the OWASP Core Rule Set (CRS), the rule files were integrated with ModSecurity. This step ensures that Apache loads the CRS configuration and all security rules whenever the web server starts.

The CRS setup file and all rule files were included in the ModSecurity configuration using Apache’s configuration directives.

Finally, Apache was restarted to apply the changes, enabling ModSecurity to inspect incoming HTTP requests using the OWASP Core Rule Set.

Step 8: Testing the Web Application Firewall

After successfully deploying ModSecurity and integrating the OWASP Core Rule Set (CRS), the final step was to verify that the Web Application Firewall was functioning correctly.

Several common web attack payloads were sent to the web application to determine whether ModSecurity could detect and block malicious requests. If the WAF was configured correctly, the server responded with HTTP 403 Forbidden, indicating that the request had been denied before reaching the application.

To further validate the results, the ModSecurity audit log was monitored to confirm that the malicious requests were detected and logged.

Press enter or click to view image in full size
SQLi
Press enter or click to view image in full size
Press enter or click to view image in full size
XSS
Press enter or click to view image in full size

Step 8: Validating the WAF

To verify the deployment, several malicious payloads were sent to the web application. The WAF successfully intercepted the malicious HTTP requests before they reached the application. The server returned an HTTP 403 Forbidden response, indicating that the requests had been blocked.

The ModSecurity audit log further confirmed the successful detection. The log recorded the intercepted request, identified the matching OWASP CRS rule, and showed that the security engine was running in ENABLED mode.

Log verification:

sudo tail -f /var/log/apache2/modsec_audit.log

Example output:

Action: Intercepted (phase 2)
Producer: ModSecurity for Apache/2.9.12
OWASP_CRS/3.3.8
Engine-Mode: "ENABLED"
Press enter or click to view image in full size

Relevant log entries included:

  • Rule ID: 942100
  • Message: SQL Injection Attack Detected via libinjection
  • HTTP Response: 403 Forbidden
  • Action: Intercepted (Phase 2)
  • Engine Mode: ENABLED

These results confirmed that the WAF was successfully deployed and was capable of detecting and blocking SQL Injection attacks.

Conclusion

This project demonstrated the successful deployment of a Web Application Firewall using Apache, ModSecurity, and the OWASP Core Rule Set on Ubuntu Server.

The web server was configured, ModSecurity was enabled in blocking mode, and the OWASP CRS was integrated to provide protection against common web application attacks. Functional testing confirmed that malicious SQL Injection requests were detected, logged, and blocked before reaching the application.

The audit logs verified that the corresponding OWASP CRS rules were triggered successfully, demonstrating that the WAF was operating as intended and providing effective protection for the hosted web application.

Edit: Additional Configuration: HTTP POST Request Logging with ModSecurity

(Added after initial configuration to improve WAF monitoring capabilities)

Changing Login Form from GET to POST

The login form was initially using the default GET method, which exposed credentials in the URL:

login.php?username=admin&password=password123

To prevent sensitive data exposure, the form method was changed to POST:

<form action="login.php" method="POST">

After this change, credentials were sent inside the HTTP request body instead of the URL:

username=admin&password=password123

Enabling ModSecurity Request Body Logging

To allow ModSecurity to capture POST request data, the audit log configuration was updated.

Before:

SecAuditLogParts ABDEFHIJZ

After:

SecAuditLogParts ABCDEFHIJZ

The C section was enabled to log request bodies.

Verification

After restarting Apache:

sudo systemctl restart apache2

POST requests were tested and monitored using:

sudo tail -f /var/log/apache2/modsec_audit.log

The request body was successfully captured:

username=admin&password=password123

This confirmed that POST parameters were visible to ModSecurity and could be monitored for malicious activity.

Security Improvement:
This additional configuration reduced credential exposure through URLs and improved ModSecurity’s ability to inspect and detect threats inside HTTP request bodies.

--

--