FlaskPaste Threat Model
Security architecture, attack surfaces, and mitigations for FlaskPaste.
System Architecture
Trust Boundaries
Attack Surface Analysis
Entry Points
| Entry Point |
Protocol |
Auth |
Rate Limited |
Description |
| POST / |
HTTPS |
Optional |
Yes |
Create paste |
| GET /{id} |
HTTPS |
Optional |
Yes |
View paste metadata |
| GET /{id}/raw |
HTTPS |
Optional |
Yes |
View raw content |
| HEAD /{id} |
HTTPS |
None |
Yes |
Check existence |
| DELETE /{id} |
HTTPS |
Required |
Yes |
Delete paste |
| GET /challenge |
HTTPS |
None |
Yes |
Get PoW challenge |
| POST /pki/* |
HTTPS |
Required |
Yes |
PKI operations |
| GET /metrics |
HTTPS |
None |
No |
Prometheus metrics |
| GET /health |
HTTPS |
None |
No |
Health check |
Data Flows
Threat Actors
Anonymous Attacker
- Motivation: Abuse, DoS, content injection
- Capabilities: Automated tools, botnets
- Mitigations: PoW, rate limiting, anti-flood
Authenticated Attacker
- Motivation: Data exfiltration, privilege escalation
- Capabilities: Valid credentials, API access
- Mitigations: Ownership checks, audit logging
Malicious Operator
- Motivation: Credential theft, data access
- Capabilities: Proxy access, log access
- Mitigations: X-Proxy-Secret, no plaintext passwords
Sophisticated Attacker
- Motivation: Zero-day exploitation, APT
- Capabilities: Reverse engineering, timing attacks
- Mitigations: Constant-time operations, defense in depth
Threat Categories (STRIDE)
Spoofing
| Threat |
Vector |
Mitigation |
Status |
| Client identity spoofing |
Forge X-SSL-Client-SHA1 |
X-Proxy-Secret validation |
MITIGATED |
| IP address spoofing |
Forge X-Forwarded-For |
Proxy secret required |
MITIGATED |
| Paste ownership claim |
Guess owner cert SHA1 |
40-char hex, DB lookup |
MITIGATED |
Tampering
| Threat |
Vector |
Mitigation |
Status |
| Content modification |
MITM attack |
TLS 1.3 required |
MITIGATED |
| Paste content tampering |
Direct DB access |
File permissions, no shell access |
MITIGATED |
| PoW token replay |
Reuse solved challenge |
Token expiration (60s) |
MITIGATED |
Repudiation
| Threat |
Vector |
Mitigation |
Status |
| Deny paste creation |
No audit trail |
Audit logging with X-Request-ID |
MITIGATED |
| Deny deletion |
Claim not deleted |
Audit log with operator ID |
MITIGATED |
Information Disclosure
| Threat |
Vector |
Mitigation |
Status |
| Paste enumeration |
Sequential IDs |
Random hex IDs (64-bit entropy) |
MITIGATED |
| Password-protected content |
Brute force |
PBKDF2 600k iterations, rate limit |
MITIGATED |
| Timing oracle on passwords |
Response time variance |
Constant-time comparison |
MITIGATED |
| Burn-after-read race |
HEAD then GET |
HEAD triggers deletion |
MITIGATED |
| Metrics exposure |
/metrics endpoint |
Public by design (no PII) |
ACCEPTED |
Denial of Service
| Threat |
Vector |
Mitigation |
Status |
| Request flooding |
High volume requests |
Rate limiting (per-IP) |
MITIGATED |
| Content spam |
Large pastes |
Size limits (100KB anon, 10MB auth) |
MITIGATED |
| Memory exhaustion |
Unbounded dicts |
MAX_ENTRIES caps (10000) |
MITIGATED |
| CPU exhaustion |
Complex operations |
PoW offloads to client |
MITIGATED |
| Anti-flood bypass |
Distributed attack |
Dynamic PoW (16-28 bits) |
MITIGATED |
| Content hash bypass |
Unique content |
Dedup window + PoW |
MITIGATED |
Elevation of Privilege
| Threat |
Vector |
Mitigation |
Status |
| Delete others' pastes |
Guess owner ID |
Ownership verification |
MITIGATED |
| Bypass size limits |
Forge auth header |
X-Proxy-Secret required |
MITIGATED |
| PKI CA compromise |
Unauthorized cert issue |
Client cert required |
MITIGATED |
| SQL injection |
Malformed input |
Parameterized queries |
MITIGATED |
| SSTI |
Template injection |
No user content in templates |
MITIGATED |
| Command injection |
Shell escape |
No shell execution |
MITIGATED |
Security Controls Matrix
MIME Detection Security
Content is detected by UTF-8 validation (text vs binary):
| Header |
Value |
Protection |
| X-Content-Type-Options |
nosniff |
Prevents MIME sniffing |
| Content-Security-Policy |
default-src 'none' |
Blocks script execution |
| X-Frame-Options |
DENY |
Prevents framing |
Cryptographic Controls
| Purpose |
Algorithm |
Parameters |
| Password hashing |
PBKDF2-SHA256 |
600,000 iterations |
| Paste ID generation |
secrets.token_hex |
32 chars (128 bits) |
| PoW challenge |
SHA-256 |
Variable difficulty (16-28 bits) |
| HMAC verification |
hmac.compare_digest |
Constant-time |
| PKI certificates |
RSA-2048 / ECDSA P-256 |
SHA-256 signing |
Residual Risks
Accepted Risks
| Risk |
Justification |
Monitoring |
| Metrics exposed |
No PII, needed for monitoring |
Access logs |
| Anonymous paste creation |
Core functionality |
Rate limiting |
| Content storage |
User-provided, may be malicious |
MIME detection |
Known Limitations
| Limitation |
Impact |
Workaround |
| TAR detection |
ustar at offset 257 |
Falls back to text/plain |
| Java .class files |
0xCAFEBABE = Mach-O |
Falls back to Mach-O |
| Large file DoS |
Memory during upload |
Gunicorn body limit |
Audit Compliance
| Control |
Evidence |
Frequency |
| Input validation |
Unit tests |
Every commit (CI) |
| Rate limiting |
Integration tests |
Every commit (CI) |
| Security headers |
headers_audit.py |
Every commit (CI) |
| Injection prevention |
Fuzz tests |
Every commit (CI) |
| Timing attacks |
Timing tests |
Weekly |
| Penetration testing |
pentest_session.py |
Monthly |
Incident Response
Detection Points
/metrics - Request rates, error rates, PoW difficulty
- Audit logs - Unusual patterns, failed auth attempts
- Anti-flood - Difficulty increase indicates attack
Response Actions
| Trigger |
Automatic Response |
Manual Response |
| High request rate |
PoW difficulty increase |
Review logs, block IPs |
| Failed auth spike |
Rate limit enforcement |
Investigate, rotate certs |
| Large paste flood |
Size limit rejection |
Block IP range |
| Enumeration attempt |
400 responses |
Add to blocklist |
Version History
| Date |
Change |
| 2025-12-26 |
Initial threat model |