Files
securelens-backend/app/services/scanner/transport.py
2026-04-07 18:13:43 +05:30

77 lines
2.9 KiB
Python

import httpx
from app.schemas.scan import Issue
from app.services.scanner.base import BaseScanner
MIN_HSTS_MAX_AGE = 15768000 # 6 months in seconds
class TransportScanner(BaseScanner):
async def scan(self, url: str, response: httpx.Response) -> list[Issue]:
issues: list[Issue] = []
headers = response.headers
if not url.startswith("https"):
issues.append(Issue(
issue="Website is not using HTTPS",
severity="Critical",
layer="Transport Layer",
fix="Install SSL certificate and redirect HTTP to HTTPS",
))
return issues
hsts = headers.get("Strict-Transport-Security", "")
if not hsts:
issues.append(Issue(
issue="Missing HSTS header",
severity="Warning",
layer="Transport Layer",
fix="Add header: Strict-Transport-Security: max-age=31536000; includeSubDomains; preload",
))
else:
hsts_lower = hsts.lower()
max_age = 0
for directive in hsts_lower.split(";"):
directive = directive.strip()
if directive.startswith("max-age="):
try:
max_age = int(directive.split("=", 1)[1])
except ValueError:
pass
if max_age < MIN_HSTS_MAX_AGE:
issues.append(Issue(
issue=f"HSTS max-age is too short ({max_age}s, minimum recommended: {MIN_HSTS_MAX_AGE}s)",
severity="Warning",
layer="Transport Layer",
fix="Set HSTS max-age to at least 15768000 (6 months), ideally 31536000 (1 year)",
))
if "includesubdomains" not in hsts_lower:
issues.append(Issue(
issue="HSTS header missing includeSubDomains directive",
severity="Info",
layer="Transport Layer",
fix="Add includeSubDomains to HSTS header to protect all subdomains",
))
if "preload" not in hsts_lower:
issues.append(Issue(
issue="HSTS header missing preload directive",
severity="Info",
layer="Transport Layer",
fix="Add preload to HSTS header and submit to hstspreload.org for browser preload list",
))
csp = headers.get("Content-Security-Policy", "")
if url.startswith("https") and "upgrade-insecure-requests" not in csp.lower():
issues.append(Issue(
issue="CSP does not include upgrade-insecure-requests directive",
severity="Info",
layer="Transport Layer",
fix="Add 'upgrade-insecure-requests' to Content-Security-Policy to auto-upgrade HTTP resources",
))
return issues