Engineering4 min read

Security Testing

Integrate security testing into your development workflow - SAST with Semgrep, dependency scanning, OWASP ZAP DAST, and threat modeling basics.

Security TestingOWASPSASTDASTPenetration Testing

skill: Security Testing category: Engineering tags: [Security Testing, OWASP, SAST, DAST, Penetration Testing] readingTime: 4

Security testing should be automatic, not manual. A security researcher finding a vulnerability after launch is 100× more expensive than a CI check finding it before. Shift security left - build SAST, dependency scanning, and basic penetration testing into the CI pipeline. Reserve manual penetration testing for critical pre-launch audits.

Workflow

  1. Add SAST with SemgrepStatic Application Security Testing (SAST) analyzes source code for vulnerabilities without executing it. Semgrep uses pattern matching to find SQL injection, XSS, hardcoded secrets, and framework-specific issues.
  2. Scan dependencies for vulnerabilitiesDependencies are the most common source of security vulnerabilities. npm audit, Snyk, and Trivy automatically identify known CVEs in your dependency tree.
  3. Test for OWASP Top 10 vulnerabilitiesThe OWASP Top 10 covers the most critical security risks. Writing specific security test cases prevents regression of these known vulnerabilities.
  4. Run DAST with OWASP ZAPDynamic Application Security Testing (DAST) scans a running application, simulating attacks that static analysis misses - timing attacks, race conditions, and configuration issues.
  5. Add security headers and reviewSecurity headers protect against common browser-based attacks. A security headers audit catches missing protections before they're exploited.

Output Format

Security testing: Semgrep SAST with p/owasp-top-ten, Trivy image scan with --exit-code 1 for CRITICAL, OWASP ZAP baseline scan on staging, security test cases for OWASP A1/A3/A7/A9, and helmet.js with CSP + HSTS.

semgrep --config=auto --config=p/owasp-top-ten src/
trivy fs . --severity HIGH,CRITICAL --exit-code 1
zaproxy/action-baseline → staging URL → fail_action:true
Test: 403 for wrong user, bcrypt hash, SQL injection params, no password in response
helmet({ contentSecurityPolicy: { directives: { defaultSrc: ["'self'"] } } })

Examples

Input

Output

Edge Cases & Gotchas

  • False positives in SAST - SAST tools generate false positives. Use inline suppressions (// nosemgrep: rule-id) for documented false positives. Review suppressions in PR - require comments explaining why it's safe.
  • DAST and authenticated endpoints - ZAP needs a valid auth token to test authenticated endpoints. Configure ZAP's authentication with a script that logs in and maintains session: zap-auth-script.js.
  • Dependency scanning false positives - Some CVEs in transitive dependencies are in code paths your app never exercises. Triage with Snyk's reachability analysis - it identifies which CVEs are in code paths actually called by your application.
  • Content Security Policy and third-party scripts - CSP breaks existing third-party integrations (analytics, chat, payment forms). Use Report-Only mode first to collect violations: Content-Security-Policy-Report-Only. Fix all violations, then switch to enforcement mode.

When to Break These Rules

  • Commission a manual penetration test instead of (or in addition to) DAST for applications handling sensitive financial, medical, or government data - automated tools miss business logic vulnerabilities.
  • Skip ZAP scanning in PR CI for speed - run it nightly on staging. Use Semgrep SAST in PR CI (fast, inline) and ZAP on a separate schedule (slow, but catches what SAST misses).

Reference Files

  • https://semgrep.dev/docs/
  • https://owasp.org/www-project-top-ten/

More skills in this library

Browse all technical skills - Mobile, AI/ML, Web, Backend, Design, and Product.