


Guard Backend Changes Against Attacks Through Uploads and User Input
Use this when an AI changes backend code that handles uploaded files, archives, or request data. It traces where outside data goes, checks it before use, applies the same fix to every similar code path, and finishes with a security checklist plus passing lint and tests.
To use this AI rule
## Before Changing Code, Trace Where Outside Data Goes and Find Similar Code Paths
Assume that uploaded files, archive contents, request parameters, manifests, metadata, and device identifiers may be attacker-controlled, even when the user is authenticated.
Before changing a sensitive code path:
1. Identify where untrusted data enters, how it is transformed, and every file, process, database, rendering, redirect, and network operation it can reach.
2. Search for sibling implementations that perform the same operation. Include alternate formats, API and web views, binary and source flows, and legacy call sites.
3. Reuse or extend centralized security helpers instead of scattering ad hoc checks across views and handlers.
4. Review prior vulnerability patterns when available, especially incomplete fixes that protected only one path.
5. Keep imports and local conventions consistent, then run the required lint and focused tests until they exit successfully.
A security fix is incomplete if an equivalent path can still reach the vulnerable operation.
## Check Request Data and Uploads at the Entry Point, and Require Login and Permissions
Validate raw input before it becomes a path, command argument, query value, redirect, rendered string, or outbound host.
- Use typed forms or schemas as the primary validation layer.
- Use finite-choice fields for parameters with a known set of valid values.
- Put field-specific rejection logic in the validation layer and return a standard error response when validation fails.
- Validate identifiers against their exact format before using them in paths or lookups.
- Check upload magic bytes, size limits, and extension allowlists; an extension alone is insufficient.
- Treat values from manifests and metadata as untrusted input.
Sensitive handlers must apply all applicable controls:
- authentication;
- role or permission authorization;
- explicit HTTP method restriction;
- CSRF protection for browser-originated state changes.
Do not disable template escaping or mark untrusted content as safe. When building output outside an auto-escaping template, encode the value for its destination context.
## Keep File Paths and ZIP/TAR Extraction Inside the Intended Folder
Use two layers for filesystem paths:
1. Reject dangerous raw forms such as traversal segments, absolute paths, encoded bypasses, and invalid characters.
2. After constructing the path, resolve it canonically and verify that it remains inside the intended root.
Before reading a filesystem object, reject symbolic links, named pipes, device files, and other unexpected types when the operation expects a regular file.
For TAR extraction:
- Prefer a runtime-provided, per-member, type-aware extraction filter that rejects traversal, absolute paths, device files, and links escaping the destination.
- Do not rely on a name-only or `abspath` check; it does not resolve symlinks.
- If a safe built-in filter is unavailable, reject symbolic and hard links, resolve the destination with `realpath`, and validate immediately before extracting each member.
- Avoid batch validation followed by batch extraction because filesystem state can change between the two phases.
For ZIP extraction:
- Validate every member name for traversal before extraction.
- Resolve the proposed destination and verify containment inside the extraction root.
- Extract only after that member passes both checks.
Every failed guard must stop the unsafe operation with `continue`, `return`, or `raise`. Logging a warning without blocking execution is not a security control.
## Make User Input Harmless for Each Use, Such as SQL or Shell Commands
- Pass subprocess arguments as a list. Never interpolate untrusted input into a shell command string.
- Use parameterized ORM or query-builder operations. Never construct SQL with string formatting.
- Escape user-controlled content before rendering it outside an auto-escaping context.
- Sanitize active formats such as SVG before display.
- Remove newlines and control characters from user-derived log fields to prevent log injection.
- Generate safe filenames before placing them in response headers.
- Allow only validated relative redirect destinations.
- Before outbound requests, resolve and validate the host, rejecting loopback, private, link-local, multicast, and other forbidden address ranges.
Apply context-specific validation rather than a single generic sanitizer. A value safe for a database filter may still be unsafe in a filename, shell command, HTML fragment, log entry, redirect, or URL.
## Finish with a Security Checklist and Show Proof for Each Item
For every change involving file I/O or user input, verify the applicable items:
- [ ] Raw input is validated before path construction.
- [ ] Constructed paths are canonically contained within the intended root.
- [ ] Unexpected links, pipes, and file types are rejected before reading.
- [ ] Archive members are validated individually before extraction.
- [ ] Shell arguments are passed without string interpolation.
- [ ] Rendered values are escaped and active content is sanitized.
- [ ] Outbound hosts and redirect destinations are constrained.
- [ ] User-derived log values are sanitized.
- [ ] Database access uses parameterized operations.
- [ ] Every rejection branch prevents the dangerous operation.
- [ ] Equivalent code paths receive the same fix.
- [ ] Focused tests cover accepted input, rejected input, and bypass attempts.
- [ ] Lint and relevant tests finish with exit code zero.
Report the evidence for each completed check and identify any path that could not be verified.
