# Configuration Reference This file maps the top-level configuration keys used by `upload-logger.json` (UploadShield) to their effect and defaults. Use absolute paths in production where possible. ## Top-level sections - `modules` (object): enable or disable features by name. Keys used in code: - `flood` (bool) — per-IP upload counting and flood alerts. Default: `true`. - `filename` (bool) — run `FilenameDetector`. Default: `true`. - `mime_sniff` (bool) — run `MimeDetector` & content sniffing. Default: `true`. - `hashing` (bool) — compute hashes for forensic records. Default: `true`. - `base64_detection` (bool) — detect JSON/base64 embedded payloads in raw bodies. Default: `true`. - `raw_peek` (bool) — allow guarded reads of `php://input`. Disabled by default (`false`) because it may consume request bodies. - `archive_inspect` (bool) — inspect archives moved to quarantine. Default: `true`. - `quarantine` (bool) — enable quarantine moves. Default: `true`. - `paths` (object): filesystem locations used by the script. Common keys: - `log_file` (string) — path to JSON log file. Default: `logs/uploads.log` (relative to script). Recommended: absolute path under a per-site `.security` folder. - `quarantine_dir` (string) — path to quarantine directory. Default: `quarantine`. - `state_dir` (string) — path to store flood counters/state. Default: `state`. - `allowlist_file` (string) — optional allowlist of URIs/content-types. Default: `allowlist.json`. - `limits` (object): thresholds controlling scanning and resource limits. - `max_size` (int) — bytes threshold for `big_upload` warning. Default: `52428800` (50 MB). - `raw_body_min` (int) — min bytes for raw body events. Default: `512000` (500 KB). - `sniff_max_bytes` (int) — bytes to read from a file head for content sniffing. Default: `8192` (8 KB). - `sniff_max_filesize` (int) — only sniff files up to this size. Default: `2097152` (2 MB). - `hash_max_filesize` (int) — max file size to compute hashes for. Default: `10485760` (10 MB). - `archive_max_inspect_size` (int) — skip inspecting archives larger than this. Default: `52428800` (50 MB). - `archive_max_entries` (int) — max entries to inspect inside an archive. Default: `200`. - `ops` (object): operator-facing options. - `quarantine_owner` / `quarantine_group` (string) — desired owner:group for quarantine. Default: `root`:`www-data`. - `quarantine_dir_perms` (string) — octal string for dir perms (recommended `0700`). Default: `0700`. - `block_suspicious` (bool) — when `true` the script returns 403 for suspicious uploads. Default: `false` (observe mode). - `log_rotate` (object) — hints for log rotation (size, keep, enabled) used in examples. - `trusted_proxy_ips` (array) — proxies allowed to signal buffered bodies or peek permission. - `allowlists` (object): reduce false positives for known safe flows. - `base64_uris` (array of strings) — substrings or PCRE (when wrapped with `#`) matching URIs to ignore for base64/raw detections. - `ctypes` (array of strings) — content-types treated as trusted for encoded payloads (e.g., `image/svg+xml`). ## Detector-specific keys - `detectors.content` (object) - `sniff_max_bytes` (int) — override `limits.sniff_max_bytes` for content detector. - `sniff_max_filesize` (int) — override `limits.sniff_max_filesize`. - `allow_xml_eval` (bool) — relax `eval()` detection for XML/SVG content when true. - `custom_patterns` (array) — array of PCRE patterns (as strings) applied to the file head. Invalid patterns are ignored. ## Example `upload-logger.json` ```json { "modules": { "flood": true, "filename": true, "mime_sniff": true, "hashing": true, "base64_detection": true, "raw_peek": false, "archive_inspect": true, "quarantine": true }, "paths": { "log_file": "/var/www/site/.security/logs/uploads.log", "quarantine_dir": "/var/www/site/quarantine", "state_dir": "/var/www/site/state", "allowlist_file": "/var/www/site/.security/allowlist.json" }, "limits": { "max_size": 52428800, "raw_body_min": 512000, "sniff_max_bytes": 8192, "sniff_max_filesize": 2097152 }, "ops": { "quarantine_owner": "root", "quarantine_group": "www-data", "quarantine_dir_perms": "0700", "block_suspicious": false }, "allowlists": { "base64_uris": ["/api/uploads/avatars"], "ctypes": ["image/svg+xml"] } } ``` ## Operational tips - Keep `block_suspicious` disabled while tuning; use `allowlists.base64_uris` and `ctypes` to reduce false positives. - Avoid enabling `raw_peek` unless your front end buffers request bodies or you accept the risk of consuming `php://input`. - Use absolute paths in `paths.*` when deploying under systemd/Ansible to avoid cwd surprises. - Ensure `quarantine_dir` is inaccessible from the web and set to owner `root` and mode `0700`; files inside should be `0600`. If you want, I can generate a per-site `upload-logger.json` filled with your preferred absolute paths and ownership values. --