It is a simple firewall for a flask application. You can use it in you flask application.
First going into FFw, we first learn what is a firewall. A firewall is a network security system, either hardware or software, that monitors and controls incoming and outgoing network traffic, acting as a digital barrier between a trusted internal network and untrusted external networks like the internet, blocking or allowing data packets based on predefined security rules to prevent unauthorized access and malicious activity. It functions like a security guard, checking data (packets) against rules to decide if they can pass, protecting networks from hackers, viruses, and other threats. for more details about firewall ⤴
- Inspects traffic: Firewalls examine data packets traveling between networks.
- Applies rules: They compare packet information (like source/destination IP, port, protocol) against a set of security rules.
- Blocks or allows: Based on the rules, they permit safe traffic and block harmful or unauthorized traffic.
- Hardware Firewalls: Physical devices, often built into home routers, protecting entire networks.
- Software Firewalls: Programs installed on individual devices (like Windows Defender), protecting that specific host.
- Next-Generation Firewalls (NGFW): Advanced firewalls with features like deep packet inspection, intrusion prevention, and application control.
- Web Application Firewalls (WAFs): Protect specific web applications from web-based attacks like SQL injection.
To install the firewall there are two ways of doing it. method one is by downloading it from github by using git.
# for all os
$ git clone https://github.com/veeracoder508/flask-firewall.gitmethod two is by using uv or pip
# for windows
>>> pip install flask-firewall # using pip
>>> uv add flask-firewall # using uv
# for linux/mac
$ pip3 install flask-firewall
$ uv add flask-firewallAfter installation we need to create a flask app.
from flask import Flask
app = Flask(__name__)
@app.route('/')
def index():
return "veera"
if __name__ == "__main__":
app.run(host="0.0.0.0")in this simple flask app we can import our flask-firewall module and initilize our firewall for the flask app.
from flask import Flask
from flask_firewall import Firewall, Rule
app = Flask(__name__)
fw = Firewall(app)
fw.engine.rules = [
Rule(action=fw.ALLOW, proto=fw.TCP, dport=80, src_cidr=fw.ANY, dst_cidr=fw.ANY, desc="Permits HTTP"),
Rule(action=fw.DROP, proto=fw.TCP, dport=443, src_cidr=fw.ANY, dst_cidr=fw.ANY, desc="Permits HTTPS"),
Rule(action=fw.DROP, proto=fw.TCP, dport=23, src_cidr=fw.ANY, dst_cidr="10.0.0.0/24", desc="Blocks Telnet to a subnet"),
Rule(action=fw.ALLOW, proto=fw.TCP, dport=22, src_cidr="192.168.1.10", dst_cidr=fw.ANY, desc="Only allows SSH from one specific IP"),
]
@app.route('/')
@fw.firewall(port=5000)
def index():
return "veera"
if __name__ == "__main__":
app.run(host=5000)in the above program we see that first we see that we are importing the flask_firewall module that we installed. secondly we are initialising the firewall by using fw = Firewall(app), we give a parameter flask_instance of type Flask whick is the flask application we are initialising the firewall for. Next we are setting up the rules for the firewall in fw.engine.rules which contain all the rules for the firewall. We use the Rule() object for a instance for a single rule.
Rule(action=fw.DROP, proto=fw.TCP, dport=23, src_cidr=fw.ANY, dst_cidr="10.0.0.0/24", desc="Blocks Telnet to a subnet")In the Rule() object there are 6 attributes
action: what should do if the packet and the rule matches(ALLOW/DROP)proto: The portocol of the packet for the rule can be 'ANY'dport: the destination port for the rulesrc_cidr: the source cidr for the rule can be 'ANY'dst_cidr: the destination cidr for the rule can be 'ANY'desc: the description for the rule for readability
After youn run the application, a log file will nbe created <name of flask app>_firewall.log. In the log file you can see all the requests and how it is processed by the firewall.
If no matching allow rule.
2026-01-11 10:52:46,996 [WARNING] ACL DROP: [TCP] 192.168.29.83:62075 -> 127.0.0.1:5000 - No matching allow rule.
2026-01-11 10:52:46,997 [ERROR] Firewall Processing Error: 403 Forbidden: Access denied by Firewall.
In the following logs we see that the conection is denied by the firewall, and the server sends a 403 code.
If matching allow rule.
2026-01-11 11:07:39,364 [INFO] ACL ALLOW: [TCP] 127.0.0.1:62286 -> 127.0.0.1:5000
In this log the firewall allows the conection.
You can create a monitor to monitor the logs and the rules and automate stuff. you can do it by tweaking the last code to have a monitor.
from flask import Flask
from flask_firewall import Firewall, Rule
from flask_firewall.monitor import SentinelMonitor
app = Flask(__name__)
fw = Firewall(app)
fw.engine.rules = [
Rule(action=fw.ALLOW, proto=fw.TCP, dport=80, src_cidr=fw.ANY, dst_cidr=fw.ANY, desc="Permits HTTP"),
Rule(action=fw.DROP, proto=fw.TCP, dport=443, src_cidr=fw.ANY, dst_cidr=fw.ANY, desc="Permits HTTPS"),
Rule(action=fw.DROP, proto=fw.TCP, dport=23, src_cidr=fw.ANY, dst_cidr="10.0.0.0/24", desc="Blocks Telnet to a subnet"),
Rule(action=fw.ALLOW, proto=fw.TCP, dport=22, src_cidr="192.168.1.10", dst_cidr=fw.ANY, desc="Only allows SSH from one specific IP"),
]
monitor = SentinelMonitor(fw)
@app.route('/')
@fw.firewall(port=5000)
def index():
return "veera"
if __name__ == "__main__":
create_monitor(monitor)
app.run(host=5000)Important
the instance for the SentinelMonitor must be monitor for the monitor to work properly.
after running the application with the updated code, it should create a flie <name of flask app>_monitor.py in the same folder as the flask app.
# FlaskFirewall Monitor (FFWM)
from {name of flask app} import monitor
monitor.mainloop()You can run the file to open the monitor
there is a web monitor also
from flask_firewall.firewall import Firewall, Rule
from flask import Flask
app = Flask(__name__)
fw = Firewall(app)
fw.engine.rules = [
Rule(action=fw.DROP, proto=fw.TCP, dport=80, src_cidr=fw.ANY, dst_cidr=fw.ANY, desc="Permits HTTP"),
Rule(action=fw.DROP, proto=fw.TCP, dport=443, src_cidr=fw.ANY, dst_cidr=fw.ANY, desc="Permits HTTPS"),
Rule(action=fw.DROP, proto=fw.TCP, dport=23, src_cidr=fw.ANY, dst_cidr="10.0.0.0/24", desc="Blocks Telnet to a subnet"),
Rule(action=fw.ALLOW, proto=fw.TCP, dport=22, src_cidr="192.168.1.10", dst_cidr=fw.ANY, desc="Only allows SSH from one specific IP"),
# allow the application port so local requests to / are permitted
Rule(action=fw.ALLOW, proto=fw.TCP, dport=5000, src_cidr=fw.ANY, dst_cidr=fw.ANY, desc="Allow HTTP to Flask app on 5000"),
]
@app.route('/')
@fw.firewall(port=5000)
def index():
return "VEERA"
if __name__ == "__main__":
from flask_firewall.web_monitor import create_monitor # Changed from flask_firewall.web_monitor
import time
print("--- Starting Sentinel SOC Monitor on http://127.0.0.1:8000 ---")
monitor_app, monitor_thread = create_monitor(fw, host='127.0.0.1', port=8000, run_server=True)
# Give the monitor a second to warm up
time.sleep(1)
print("--- Starting Main Protected Application on http://127.0.0.1:5000 ---")
# debug=False is recommended when using threading/monitors to avoid double-execution
app.run(host="0.0.0.0", port=5000, debug=False)the following code creates a seperate thread for the web monitor so it does not intreact with the main server. you can go to http://localhost:8000
licence: MIT