Email Injection in Flask with Bearer Tokens
Email Injection in Flask with Bearer Tokens — how this specific combination creates or exposes the vulnerability
Email Injection is a technique where attackers inject additional email addresses or control email headers to send messages to unintended recipients. In Flask applications that handle user-supplied data used in email workflows (e.g., "cc", "bcc", or display names), improper validation or concatenation can permit injection even when authentication is enforced via Bearer Tokens. Bearer Tokens protect endpoint access by requiring a token in the Authorization header, but they do not inherently validate or sanitize data used in email composition. This creates a mismatch: authentication confirms who is making the request, while input handling determines whether the data is safe to use in downstream email protocols such as SMTP or libraries like Flask-Mail.
Consider a Flask route that accepts a JSON payload with an email field and uses a Bearer Token for authentication. If the application directly embeds the user input into email headers without validation, an attacker can supply a payload like malicious@example.com, attacker@evil.com or inject newline characters (%0a, %0d) to control additional recipients. Common vulnerable patterns include using Python string concatenation or formatting to build headers, for example:
message = f"To: {user_email}\nFrom: noreply@example.com\nSubject: Welcome\n\nHello"
If user_email contains newline sequences or extra headers, the resulting message can be altered. OWASP API Top 10's 'Input Validation' and the broader category of 'Email Injection' highlight this risk. Real-world CVEs affecting similar stacks include CVE-2021-34501 (related to header injection in print systems), which illustrates how unchecked inputs can manipulate message routing. Because Bearer Tokens do not restrict data content, scanners running 12 security checks in parallel—including Input Validation and Data Exposure—will flag such endpoints when user-controlled data reaches email generation without sanitization, potentially exposing PII or enabling spam campaigns through your application's infrastructure.
In a middleBrick scan, this scenario would appear under the Input Validation and Data Exposure findings, with remediation guidance emphasizing strict allowlists for email formats and avoiding direct header interpolation. The scanner cross-references OpenAPI specifications against runtime behavior to detect mismatches between documented expectations and actual handling, ensuring that even authenticated endpoints are evaluated for content-level risks.
Bearer Tokens-Specific Remediation in Flask — concrete code fixes
Remediation focuses on validating and sanitizing any user-controlled data used in email composition, regardless of Bearer Token presence. Use strict allowlists for email addresses and explicitly define headers instead of building them through string interpolation. Below are concrete code examples for Flask that demonstrate secure handling when Bearer Tokens are used for authentication.
First, ensure your authentication middleware verifies the Bearer Token before processing the request, but do not rely on it for data safety. Then, validate email inputs using a dedicated library or regex that enforces a standard format. For headers, construct the message with a library that escapes or prohibits raw user input in header fields.
Example of vulnerable code:
from flask import Flask, request, jsonify
app = Flask(__name__)
@app.route('/notify', methods=['POST'])
def notify():
auth = request.headers.get('Authorization', '')
if not auth.startswith('Bearer '):
return jsonify({'error': 'Unauthorized'}), 401
token = auth.split(' ')[1]
# Token validation logic would go here
user_email = request.json.get('email', '')
# Vulnerable: direct use in header
message = f"To: {user_email}\nFrom: noreply@example.com\nSubject: Alert\n\nAlert triggered."
# sendmail(message) would be called here
return jsonify({'status': 'queued'})
Secure alternative using explicit header definitions and email validation:
import re
from flask import Flask, request, jsonify
from email.message import EmailMessage
app = Flask(__name__)
def is_valid_email(value):
pattern = r'^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$'
return re.match(pattern, value) is not None
@app.route('/notify', methods=['POST'])
def notify():
auth = request.headers.get('Authorization', '')
if not auth.startswith('Bearer '):
return jsonify({'error': 'Unauthorized'}), 401
token = auth.split(' ')[1]
# Token validation logic would go here
user_email = request.json.get('email', '')
if not is_valid_email(user_email):
return jsonify({'error': 'Invalid email format'}), 400
msg = EmailMessage()
msg['To'] = user_email
msg['From'] = 'noreply@example.com'
msg['Subject'] = 'Alert'
msg.set_content('Alert triggered.')
# sendmail(msg.as_string()) would be called here
return jsonify({'status': 'queued'})
This approach ensures that user input is never directly interpolated into headers or body in a way that allows injection. It aligns with the remediation guidance provided in middleBrick findings, which prioritize input validation and safe consumption patterns. The CLI tool (middlebrick scan <url>) can be used to verify that such endpoints are no longer flagged, and the Web Dashboard helps track improvements over time. For teams using CI/CD, the GitHub Action can enforce a minimum security score before deployment, while the MCP Server allows you to run scans directly from AI coding assistants during development.
Frequently Asked Questions
Does a Bearer Token alone prevent email injection in Flask APIs?
How can I test if my Flask endpoint is vulnerable to email injection while using Bearer Tokens?
middlebrick scan <your-api-url> or via the Web Dashboard. The scan will flag endpoints where user-controlled email data reaches message headers without validation, even when Bearer Token authentication is present.