Middleware is a powerful concept in web applications that allows you to process requests and responses before they reach the main application logic. In Flask, middleware functions sit between the client request and the final response, enabling tasks like logging, authentication, request modifications, and more.
Flask applications generally uses middleware's in:
- Authentication & Authorization: Checking user authentication before processing a request.
- Logging & Monitoring: Capturing request details for debugging and analytics.
- Request Validation: Ensuring requests meet certain criteria before reaching the main app.
- Response Modification: Adding or modifying headers before sending a response.
- Rate Limiting & Security: Controlling request rates and preventing malicious activities.
Let's explore several ways to implement middleware in Flask applications.
Creating Custom Middleware in Flask
Flask provides hooks, which are special functions that allow you to execute code before or after processing a request. These hooks help in modifying requests, logging, authentication, and more. Two commonly used hooks for middleware are:
- before_request : Runs before the request is processed.
- after_request : Runs after the request is processed, modifying the response if needed.
A simple way to implement middleware in Flask is by using these hooks.
Python
from flask import Flask, request
app = Flask(__name__)
@app.before_request
def log_request():
print(f"Incoming request: {request.method} {request.url}")
@app.after_request
def log_response(response):
print(f"Outgoing response: {response.status_code}")
return response
@app.route('/')
def home():
return "Hello, Flask!"
if __name__ == '__main__':
app.run(debug=True)
Explanation:
1. @app.before_request: Middleware that handels incoming requests ()
- log_request(): Runs before each request.
- Prints the HTTP method and request URL.
2. @app.after_request: Middleware that handles outgoing responses ()
- log_response(response)- Runs after each request.
- Logs the response status code.
- Returns response to complete the request cycle.
Output:
Middleware OutputNotice that every time we refresh the Flask app, the terminal displays "Outgoing response: 200" because of the middleware. This demonstrates how middleware can handle tasks before reaching the main logic.
Middleware for Authentication and Authorization
Authentication middleware ensures that only authorized users can access specific routes. This is useful for securing APIs and web applications. Let's create a simple flask app and implement middleware for authentication and authorization in it.
Python
from flask import Flask, request, jsonify
app = Flask(__name__)
API_KEY = "my_secret_api_key"
@app.before_request
def check_authentication():
token = request.headers.get("Authorization")
if token != f"Bearer {API_KEY}":
return jsonify({"error": "Unauthorized"}), 401
@app.route('/protected')
def protected():
return jsonify({"message": "Welcome to the protected route!"})
if __name__ == '__main__':
app.run(debug=True)
Explanation:
1. before_request Middleware:
- Extracts the Authorization token from request headers.
- If the token is missing or incorrect, returns 401 Unauthorized.
2. /protected - route that can only be accessed if a valid token is provided.
Output:
We can test the application using Postman API, below is snapshot of response when a GET request is made to the /protected route with providing the header.
Response without authentication tokenNotice that when the GET request is made to the route with the authentication token, we get a 200 OK status response. Below is the snapshot.
Response with authentication tokenThird-Party Middleware in Flask
Instead of writing custom middleware for every feature, we can use Flask extensions or third-party libraries for advanced middleware functionalities. Some commonly used middleware libraries include:
- Flask-CORS – Handles Cross-Origin Resource Sharing (CORS).
- Flask-Limiter – Implements rate limiting to prevent abuse.
- Flask-Talisman – Adds security headers for better protection.
Let's create a flask app using CORS.
What is CORS
CORS (Cross-Origin Resource Sharing) is a security feature implemented by web browsers that restricts how resources on a web page can be requested from another domain.
For example, if your frontend (React, Vue, or plain JavaScript) is running on http://localhost:3000 and your Flask backend is running on http://127.0.0.1:5000, the browser will block requests from the frontend to the backend due to CORS policy. CORS middleware allows controlled access to your Flask API from different origins.
To use any third party middleware in our application, we are required to install its module in our environment, use this command in terminal to install flask-cors
pip install flask-cors
After installing the flask-core module, create the file app.py an paste the code below.
Python
from flask import Flask, jsonify
from flask_cors import CORS
app = Flask(__name__)
# Allow requests only from specific frontend origins
CORS(app, origins=["http://localhost:3000", "https://myfrontend.com"])
@app.route('/public-data')
def public_data():
return jsonify({"message": "This data is accessible from allowed origins."})
@app.route('/private-data')
def private_data():
return jsonify({"message": "This endpoint also follows CORS rules."})
if __name__ == '__main__':
app.run(debug=True)
Explanation:
- CORS(app, origins=["http://localhost:3000"]) allows only http://localhost:3000 and https://myfrontend.com to make API requests.
- It enables CORS for all routes but only for allowed domains.
- If a request comes from an unlisted domain, the browser will block it.
Using Multiple Middleware Layers
In Flask, wecan apply multiple middleware functions to process requests before they reach the route handler. This is useful when we need to enforce multiple layers of checks, such as logging, authentication, validation, or security policies. By chaining middleware, we can ensure structured request handling without duplicating logic inside individual route functions.
Let's create a flask app that demonstrate using multiple middleware.
Python
from flask import Flask, request, jsonify
app = Flask(__name__)
API_KEY = "my_secret_api_key"
@app.before_request
def log_request():
""" Logs incoming request details. """
print(f"Incoming request: {request.method} {request.url}")
@app.before_request
def check_authentication():
""" Checks if the request has a valid authentication token. """
token = request.headers.get("Authorization")
if token != f"Bearer {API_KEY}":
return jsonify({"error": "Unauthorized"}), 401 # Block unauthorized requests
@app.after_request
def log_response(response):
""" Logs outgoing response details. """
print(f"Outgoing response: {response.status_code}")
return response # Must return the response object
@app.route('/secure-data')
def secure_data():
return jsonify({"message": "Access granted to secure data."})
if __name__ == '__main__':
app.run(debug=True)
Explanation:
- Logging Middleware (before_request):
- Logs the HTTP method and URL of every incoming request.
- Helps in debugging and monitoring request flow.
- Authentication Middleware (before_request):
- Extracts the Authorization token from the request headers.
- Blocks access (401 Unauthorized) if the token is missing or incorrect.
- Response Logging Middleware (after_request):
- Logs the response status code before sending it to the client.
- Ensures tracking of both incoming and outgoing traffic.
Output:
Allowed Request (Valid Token)
Status OKBlocked Request (No Token)
Status - Unauthorized Without TokenBlocked Request (Invalid Token)
Request logs
Similar Reads
Python Tutorial - Learn Python Programming Language Python is one of the most popular programming languages. Itâs simple to use, packed with features and supported by a wide range of libraries and frameworks. Its clean syntax makes it beginner-friendly. It'sA high-level language, used in web development, data science, automation, AI and more.Known fo
10 min read
Python Interview Questions and Answers Python is the most used language in top companies such as Intel, IBM, NASA, Pixar, Netflix, Facebook, JP Morgan Chase, Spotify and many more because of its simplicity and powerful libraries. To crack their Online Assessment and Interview Rounds as a Python developer, we need to master important Pyth
15+ min read
Python OOPs Concepts Object Oriented Programming is a fundamental concept in Python, empowering developers to build modular, maintainable, and scalable applications. By understanding the core OOP principles (classes, objects, inheritance, encapsulation, polymorphism, and abstraction), programmers can leverage the full p
11 min read
Python Projects - Beginner to Advanced Python is one of the most popular programming languages due to its simplicity, versatility, and supportive community. Whether youâre a beginner eager to learn the basics or an experienced programmer looking to challenge your skills, there are countless Python projects to help you grow.Hereâs a list
10 min read
Python Exercise with Practice Questions and Solutions Python Exercise for Beginner: Practice makes perfect in everything, and this is especially true when learning Python. If you're a beginner, regularly practicing Python exercises will build your confidence and sharpen your skills. To help you improve, try these Python exercises with solutions to test
9 min read
Python Programs Practice with Python program examples is always a good choice to scale up your logical understanding and programming skills and this article will provide you with the best sets of Python code examples.The below Python section contains a wide collection of Python programming examples. These Python co
11 min read
Python Introduction Python was created by Guido van Rossum in 1991 and further developed by the Python Software Foundation. It was designed with focus on code readability and its syntax allows us to express concepts in fewer lines of code.Key Features of PythonPythonâs simple and readable syntax makes it beginner-frien
3 min read
Python Data Types Python Data types are the classification or categorization of data items. It represents the kind of value that tells what operations can be performed on a particular data. Since everything is an object in Python programming, Python data types are classes and variables are instances (objects) of thes
9 min read
Input and Output in Python Understanding input and output operations is fundamental to Python programming. With the print() function, we can display output in various formats, while the input() function enables interaction with users by gathering input during program execution. Taking input in PythonPython input() function is
8 min read
Enumerate() in Python enumerate() function adds a counter to each item in a list or other iterable. It turns the iterable into something we can loop through, where each item comes with its number (starting from 0 by default). We can also turn it into a list of (number, item) pairs using list().Let's look at a simple exam
3 min read