| name | brokk-security-scan |
| description | Use when asked to find security vulnerabilities, insecure code patterns, or security risks in a codebase - scans for OWASP Top 10 patterns, hardcoded secrets, and dependency vulnerabilities |
brokk-security-scan
Overview
Scan a codebase for security vulnerabilities using two passes: (1) universal ripgrep patterns covering OWASP Top 10 and common weaknesses, (2) language-specific security tools where available. Always report severity and file location.
Important: This is a static analysis skill. It finds likely vulnerabilities — confirm before acting. Dynamic or runtime vulnerabilities require runtime testing.
Prerequisites
rg --version 2>/dev/null || echo "rg MISSING — install before scanning"
Pass 1 — Universal Secret & Credential Detection
Run first — hardcoded secrets are always critical.
rg -in "(password|passwd|pwd|secret|api_key|apikey|auth_token|access_token)\s*[=:]\s*['\"][^'\"]{6,}" \
--glob "!*.{md,txt,example,sample,test,spec}"
rg -n "['\"][A-Za-z0-9+/]{40,}={0,2}['\"]"
rg -n "AKIA[0-9A-Z]{16}"
rg -n "-----BEGIN (RSA |EC |DSA |OPENSSH )?PRIVATE KEY"
rg -in "jwt.*secret\s*[=:]\s*['\"][^'\"]{8,}"
rg -in "(mongodb|mysql|postgres|redis|amqp)://[^:]+:[^@]+@"
Flag any match as CRITICAL. Secrets in committed files may be in git history even if removed — note this.
Pass 2 — Injection Vulnerabilities
SQL Injection
rg -n "SELECT.*\+|INSERT.*\+|UPDATE.*\+|DELETE.*\+" --type py
rg -n "SELECT.*\+|INSERT.*\+|UPDATE.*\+|DELETE.*\+" --type js
rg -n '`SELECT|`INSERT|`UPDATE|`DELETE' --type js
rg -n "String\.format.*SELECT|String\.format.*INSERT" --type java
rg -n 'fmt\.Sprintf\("(SELECT|INSERT|UPDATE|DELETE)' --type go
rg -in "raw\(|execute\(|query\(" --type py | rg -v "#"
Command Injection
rg -n "(subprocess|os\.system|os\.popen|exec|shell_exec|popen|Runtime\.exec)" --type py
rg -n "(exec\(|execSync\(|spawn\(|child_process)" --type js
rg -n "(Runtime\.getRuntime\(\)\.exec|ProcessBuilder)" --type java
rg -n "os/exec|exec\.Command" --type go
rg -n "(shell_exec|exec\(|system\(|passthru\(|proc_open)" --type php
Path Traversal
rg -n "\.\./|\.\.\\\\"
rg -in "open\(.*request\.|open\(.*param\.|open\(.*input\."
rg -in "File\(.*request\.|FileReader\(.*param\."
Template Injection
rg -n "(render_template_string|env\.from_string|Template\()" --type py
rg -n "(ejs\.render\(|pug\.render\(|handlebars\.compile\()" --type js
Pass 3 — Authentication & Authorization
rg -in "admin.*password|password.*admin|default.*password" \
--glob "!*.{md,txt}"
rg -B5 "@app.route" --type py | rg -v "(login_required|@auth|token_required)"
rg -B3 "app\.(get|post|put|delete)\(" --type js | rg -v "(auth|middleware|verify|protect)"
rg -in "algorithm.*none|verify.*false|HS256"
rg -in "secret.*123|secret.*password|secret.*test"
rg -in "secure.*false|httponly.*false|samesite.*none"
rg -in "SESSION_COOKIE_SECURE\s*=\s*False" --type py
Pass 4 — Cryptography
rg -in "\b(md5|sha1|sha-1|des|rc4|blowfish)\b" \
--glob "!*.{md,txt,lock}"
rg -n "random\(\)|Math\.random\(\)|rand\(\)" \
--glob "!*test*" --glob "!*spec*"
rg -n "iv\s*=\s*['\"]|salt\s*=\s*['\"]"
rg -in "AES.*ECB|ECB.*AES|MODE_ECB"
Pass 5 — Data Exposure
rg -in "log(ger)?\.(info|debug|warn|error|print)\(.*\b(password|token|secret|credit_card|ssn|dob)\b"
rg -in "(debug\s*=\s*true|DEBUG\s*=\s*True)" \
--glob "!*.{env.example,sample}"
rg -in "traceback\.print_exc\(\)|printStackTrace\(\)" \
--glob "!*test*"
rg -in "(email|phone|ssn|dob|credit)\s*=.*\?"
Pass 6 — Dependency Vulnerabilities
Check for known-vulnerable dependency versions using available tools:
pip-audit 2>/dev/null || safety check 2>/dev/null
npm audit --json 2>/dev/null
yarn audit 2>/dev/null
mvn dependency-check:check 2>/dev/null
bundle audit check 2>/dev/null
composer audit 2>/dev/null
dotnet list package --vulnerable 2>/dev/null
cargo audit 2>/dev/null
govulncheck ./... 2>/dev/null
If no tool available, note the dependency manifest files found:
rg --files | rg "(package\.json|requirements\.txt|Gemfile\.lock|go\.sum|pom\.xml|Cargo\.lock|composer\.lock)"
Pass 7 — Language-Specific Security Scanners
bandit -r . -ll -f text 2>/dev/null
npx semgrep --config=auto --lang=js . 2>/dev/null
npx eslint . --rulesdir=eslint-plugin-security 2>/dev/null
spotbugs -textui -high . 2>/dev/null
phpcs --standard=Security . 2>/dev/null
semgrep --config=auto . 2>/dev/null
Severity Classification
| Severity | Examples |
|---|
| CRITICAL | Hardcoded secrets, SQL injection, command injection with user input |
| HIGH | Broken auth, path traversal, insecure deserialization, weak crypto in auth flows |
| MEDIUM | Verbose error messages, missing CSRF, logging sensitive data |
| LOW | Weak random for non-security use, deprecated functions |
Output Format
## Security Scan Report
### CRITICAL
| Vulnerability | File | Line | Detail |
|---------------|------|------|--------|
| Hardcoded API key | src/config.py | 14 | `API_KEY = "sk-..."` |
| SQL injection | src/users/repo.py | 88 | String concat in SELECT |
### HIGH
| Vulnerability | File | Line | Detail |
### MEDIUM
| Vulnerability | File | Line | Detail |
### Dependency Audit
- npm audit: 3 critical, 7 high
- (tool not found): pip-audit
### Scanners Run
- bandit: yes
- semgrep: not installed
Windows Notes
- All
rg commands work natively
npm audit works on Windows
pip-audit, cargo audit, govulncheck all have Windows builds
- Replace POSIX pipes with sequential rg calls if needed
Common Mistakes
| Mistake | Fix |
|---|
| Only checking secrets | Always run all 7 passes — injection bugs are often more severe |
| Skipping dependency audit | Vulnerable dependencies are the most common real-world vector |
| Flagging test files | Exclude *test* / *spec* from most passes |
| Reporting all findings equally | Classify by severity; only CRITICAL/HIGH need immediate action |
| Missing git history for secrets | Note: even removed secrets may be in git log -p |