nwave-ai/nw-security-by-design
Security design principles, STRIDE threat modeling, OWASP Top 10 architectural mitigations, and secure patterns. Load when designing systems or reviewing architecture for security.
npx skills add https://github.com/nWave-ai/nWave --skill nw-security-by-design
Apply these during design -- retrofitting security is 10-100x more expensive.
| # | Principle | Architect Action |
|---|-----------|-----------------|
| 1 | Security by Design | Include security requirements in architecture documents |
| 2 | Security by Default | Ship restrictive defaults; require explicit opt-in for relaxed settings |
| 3 | Defense in Depth | Layer controls: WAF + input validation + output encoding + parameterized queries |
| 4 | Fail Secure | Deny access on error; closed-by-default network policies |
| 5 | Least Privilege | Scoped service accounts; time-limited tokens; minimum permissions |
| 6 | Compartmentalize | Network segmentation; separate databases per trust level |
| 7 | Separation of Duties | Separate deployment approval from code authorship |
| 8 | Economy of Mechanism | Minimize attack surface; simple, auditable security code |
| 9 | Complete Mediation | Check authorization on every request; no cached auth decisions |
| 10 | Open Design | Use published, peer-reviewed algorithms; no security-through-obscurity |
| 11 | Least Common Mechanism | Separate admin and user interfaces |
| 12 | Psychological Acceptability | Make the secure path the easy path; minimize user friction |
Apply STRIDE to every component in a Data Flow Diagram (DFD). Four questions drive every session:
| Threat | Violated Property | Architectural Mitigation |
|--------|-------------------|--------------------------|
| Spoofing | Authentication | MFA, mutual TLS, certificate pinning, OAuth2+PKCE |
| Tampering | Integrity | Input validation, HMAC, parameterized queries, immutable infra |
| Repudiation | Non-repudiation | Tamper-evident logging (append-only), digital signatures, SIEM |
| Info Disclosure | Confidentiality | Encryption at rest+transit, least privilege, generic error messages |
| Denial of Service | Availability | Rate limiting, circuit breakers, auto-scaling, query complexity limits |
| Elevation of Privilege | Authorization | Least privilege, RBAC/ABAC, signed tokens verified server-side |
| DFD Element | Most Relevant Threats |
|-------------|----------------------|
| External Entity | Spoofing |
| Process | All six STRIDE threats |
| Data Store | Tampering, Info Disclosure, Repudiation, DoS |
| Data Flow | Tampering, Info Disclosure, DoS |
| Trust Boundary | Spoofing, Tampering, Elevation of Privilege |
| Response | When | Example |
|----------|------|---------|
| Mitigate | Probable and impactful; controls feasible | Add MFA for spoofing on admin login |
| Eliminate | Remove feature/component entirely | Remove unused admin API endpoint |
| Transfer | Better managed by another party | Use managed IdP (Auth0, Cognito) |
| Accept | Low risk; mitigation cost exceeds impact | Accept DoS risk on internal status page |
Focus on what the architect decides at design time, not implementation details.
Core: "Never trust, always verify" -- no implicit trust from network location.
| Component | Implementation |
|-----------|---------------|
| Identity verification | OAuth2/OIDC for users; mTLS for services |
| Transport security | mTLS everywhere; service mesh (Istio, Linkerd) |
| Micro-segmentation | Network policies limiting service-to-service |
| Continuous verification | Re-authenticate and re-authorize every request |
| Least privilege access | Scoped tokens; just-in-time access |
User Input
-> Validation (allowlist, type, length, format)
-> Business Logic (parameterized queries, ORM)
-> Output Encoding (context-aware: HTML, JS, URL, CSS)
-> Client
Key: input validation is complementary, not primary defense. Output encoding prevents XSS. Parameterized queries prevent SQLi. Validation adds defense in depth.
| Pattern | Implementation |
|---------|---------------|
| Centralized vault | HashiCorp Vault, AWS Secrets Manager, Azure Key Vault |
| Sidecar injection | Vault agent injects secrets into pods at runtime |
| Encrypted in repo | SOPS + KMS for GitOps workflows |
| Pre-commit scanning | gitleaks or TruffleHog blocks secrets before they reach git |
Rules: never in source code | never in container images | rotate automatically | separate per environment | audit all access.
| Header | Value | Purpose |
|--------|-------|---------|
| Content-Security-Policy | Strict nonce-based | Prevent XSS |
| Strict-Transport-Security | max-age=63072000; includeSubDomains; preload | Force HTTPS |
| X-Content-Type-Options | nosniff | Prevent MIME sniffing |
| X-Frame-Options | DENY or SAMEORIGIN | Prevent clickjacking |
| Referrer-Policy | strict-origin-when-cross-origin | Control referrer |
| Permissions-Policy | Feature-specific | Limit browser APIs |
| Type | Tests | Pipeline Stage | Tools |
|------|-------|---------------|-------|
| SAST | Source code vulnerabilities | Every commit/PR | Semgrep, CodeQL, SonarQube |
| SCA | Dependency CVEs | Build stage | Snyk, Dependabot, Trivy |
| DAST | Running application | Staging | OWASP ZAP, Burp Suite |
| Secrets | Leaked credentials | Pre-commit + CI | gitleaks, TruffleHog |
Strategy: SAST pre-commit (fast) -> SCA at build -> container scan -> DAST on staging -> block on critical/high findings.
| # | Threat | Architect Decision |
|---|--------|--------------------|
| API1 | BOLA (~40% of API attacks) | Object-level authorization in service layer, not just routes |
| API4 | Unrestricted resource consumption | Rate limiting per-object, not just per-endpoint |
| API5 | BFLA | Separate admin and user API surfaces |
| API6 | Sensitive business flow abuse | State machine enforcement, idempotency keys |
| API9 | Improper inventory management | API versioning with sunset policies; deprecate old versions |
| API10 | Unsafe API consumption | Never trust third-party API responses; validate and sanitize |
| Risk | Vulnerable Pattern | Secure Alternative |
|------|-------------------|-------------------|
| SQL Injection | f"SELECT * FROM users WHERE name = '{name}'" | Parameterized: cursor.execute("... WHERE name = %s", (name,)) |
| Deserialization | pickle.loads(untrusted) | json.loads(untrusted) or Pydantic schema validation |
| Command Injection | os.system(f"cmd {input}") | subprocess.run(["cmd", input], shell=False) |
| SSTI | Template(user_input) | env.from_string(trusted).render(data=user_input) |
| Mass Assignment | User(**request.json()) | DTO with explicit fields, server-set for sensitive |
| TOCTOU Race | Read-check-write in separate steps | Atomic conditional update (UPDATE ... WHERE condition) |
| Prototype Pollution (JS) | Object.assign(target, untrusted) | Map, null-prototype objects, strict schema validation |
Take nwave-ai/nw-security-by-design from the repository into ~/.claude/skills for personal
use, or into .claude/skills inside a project.
The agent identifies a skill by the name field in its header. Two skills with the
same name cannot sit side by side — one of them will be ignored.