Clickjacking in Fastapi with Dynamodb
Clickjacking in Fastapi with Dynamodb — how this specific combination creates or exposes the vulnerability
Clickjacking is a client-side UI deception attack where an attacker tricks a user into clicking a hidden or disguised element inside a transparent or nested frame. In a Fastapi application that uses Dynamodb as the backend datastore, the risk arises when pages render dynamic content without enforcing frame-protection mechanisms and the UI reflects sensitive actions driven by Dynamodb-stored permissions or state. For example, an admin settings page served by Fastapi might retrieve user permissions from a Dynamodb table and render buttons or forms without anti-CSRF tokens or X-Frame-Options/Content-Security-Policy headers. An attacker can embed this page in an iframe on a malicious site, overlay invisible controls, and coerce the victim into performing unintended actions such as changing email, updating preferences, or escalating privileges, all while the application reads and writes Dynamodb based on the authenticated session.
The combination amplifies risk because Fastapi often serves server-generated HTML or client-side apps that call Dynamodb-backed APIs. If the API endpoints that mutate state (e.g., updating user email or role in Dynamodb) do not validate the Origin or Referer headers and do not require per-request anti-CSRF tokens, an attacker can craft a form on their page that submits to those endpoints. The victim’s browser sends credentials and session cookies automatically, and Fastapi processes the request against the user’s Dynamodb record, assuming it is legitimate. Because Dynamodb holds authorization data (like role flags or consent status), incorrect or missing validation of business logic in the API layer can allow an attacker to exploit trust relationships encoded in the database.
Additionally, if Fastapi serves unauthenticated or weakly authenticated endpoints that expose sensitive UI components based on Dynamodb attributes (for example, showing an admin panel when a flag is true), an attacker can enumerate or induce state changes via clickjacking. The scanner’s checks for Authentication, BOLA/IDOR, and Property Authorization are relevant here: misconfigured permissions stored in Dynamodb or missing ownership checks can allow one user to influence another’s UI context. Insecure Direct Object References in Dynamodb queries combined with missing frame-breaking headers enable an attacker to craft a convincing multi-step UI deception that appears to originate from the trusted domain.
Dynamodb-Specific Remediation in Fastapi — concrete code fixes
To mitigate clickjacking in a Fastapi application backed by Dynamodb, apply defense-in-depth: frame protection headers, anti-CSRF tokens for state-changing operations, strict content security policies, and secure handling of Dynamodb data that influences UI decisions. Below are concrete, working examples that integrate Dynamodb access patterns with Fastapi security controls.
1. Frame protection headers
Ensure every response includes headers that prevent embedding. For Fastapi, add middleware or a dependency that injects these headers.
from fastapi import Fastapi, Response
app = Fastapi()
@app.middleware("http")
async def add_frame_protection_headers(request, call_next):
response: Response = call_next(request)
response.headers["X-Frame-Options"] = "DENY"
response.headers["Content-Security-Policy"] = "frame-ancestors 'none'"
return response
2. Anti-CSRF tokens for Dynamodb-mutating endpoints
Use per-session or per-request CSRF tokens for any endpoint that writes to Dynamodb. Store the token server-side (e.g., in a session record in Dynamodb or a signed cookie) and require it on state-changing requests.
from fastapi import Fastapi, Cookie, Depends, HTTPException, status
import secrets
app = Fastapi()
# Example: store token in a signed cookie and validate against a Dynamodb attribute
async def get_csrf_token(session_id: str = Cookie(None)):
if not session_id:
raise HTTPException(status_code=status.HTTP_401_UNAUTHORIZED, detail="Session required")
# Fetch user session record from Dynamodb (pseudocode)
# user_session = dynamodb.get_item(Key={"session_id": session_id})
# return user_session.get("csrf_token")
return "stored-csrf-from-dynamodb"
@app.post("/api/update-email")
async def update_email(
email: str,
csrf_token: str,
session_id: str = Cookie(None),
csrf_token_dep: str = Depends(get_csrf_token),
):
if csrf_token != csrf_token_dep:
raise HTTPException(status_code=status.HTTP_403_FORBIDDEN, detail="Invalid CSRF token")
# Proceed to update Dynamodb record for the user
# dynamodb.update_item(Key={"user_id": user_id}, UpdateExpression="SET email = :val", ...)
return {"status": "email updated"}
3. Secure Dynamodb access patterns that influence UI
When querying Dynamodb to decide what UI to render, enforce ownership and least privilege. Avoid exposing sensitive actions based solely on a flag in Dynamodb without verifying the requesting user’s identity and permissions.
import boto3
from fastapi import Depends
# Use a thin wrapper to enforce ownership checks
def get_user_record(user_id: str, requesting_user_id: str):
client = boto3.client("dynamodb", region_name="us-east-1")
response = client.get_item(TableName="Users", Key={"user_id": {"S": user_id}})
item = response.get("Item")
if not item:
raise ValueError("User not found")
# Enforce ownership: ensure the requesting user is allowed to view/modify this record
if item.get("owner_id", {}).get("S") != requesting_user_id:
raise PermissionError("Not authorized")
return item
4. Content-Security-Policy frame rules
Add a strict CSP header to disallow framing. The following example disallows any frame ancestors and can be tailored for trusted embeds if necessary.
from fastapi.middleware.cors import CORSMiddleware
@app.add_middleware(
"cors",
allow_origins=["https://yourapp.com"],
allow_methods=["GET", "POST"],
allow_headers=["Authorization", "Content-Type"],
)
# Note: CSP is set in the earlier frame protection middleware
5. Continuous monitoring of permissions in Dynamodb
Use the dashboard or CLI to scan for BOLA/IDOR and Property Authorization findings. Ensure that any attribute controlling UI visibility or admin capabilities in Dynamodb is validated server-side on every request. Remediation guidance from scans should be followed to tighten ownership checks and remove overly permissive flags.