Registry
Ccodemod avatar

codemod/replace-vulnerable-regex-patterns

Identify and replace regex patterns vulnerable to ReDoS (Regular Expression Denial of Service)

codemod0 executions

  • security
  • regex
  • redos
  • vulnerability
  • transformation
Connect a repo
npx codemod @codemod/replace-vulnerable-regex-patterns

@codemod/replace-vulnerable-regex-patterns

Identify and replace regex patterns vulnerable to ReDoS (Regular Expression Denial of Service) attacks in JavaScript and TypeScript codebases.

About ReDoS Vulnerabilities

Regular Expression Denial of Service (ReDoS) attacks exploit vulnerable regex patterns to cause exponential backtracking, leading to:

  • Application freezing or crashing
  • Excessive CPU consumption
  • Denial of service to legitimate users

This codemod automatically detects and replaces common vulnerable patterns with safe alternatives while maintaining functionality.

Security References

  • CWE-1333: Inefficient Regular Expression Complexity
  • OWASP: Regular Expression DoS Prevention Cheat Sheet
  • CVE Examples: CVE-2019-16769, CVE-2020-7662, CVE-2021-23382

Installation

bash
# Run directly from registry
npx codemod@latest run @codemod/replace-vulnerable-regex-patterns

# Or clone and run locally
git clone <repo>
cd replace-vulnerable-regex-patterns
pnpm install
pnpm test

Usage

This codemod automatically transforms vulnerable regex patterns in JavaScript/TypeScript files:

Supported Patterns

Nested Quantifiers

javascript
// Before (vulnerable)
const regex = /(a+)+b/;

// After (safe)
const regex = /a+b/;

Exponential Backtracking

javascript
// Before (vulnerable)
const pattern = /(a*)*b/;

// After (safe)  
const pattern = /a*b/;

Complex Email Validation

javascript
// Before (vulnerable)
const email = /^([a-zA-Z0-9])(([\-.]|[_]+)?([a-zA-Z0-9]+))*(@){1}[a-z0-9]+[.]{1}(([a-z]{2,3})|([a-z]{2,3}[.]{1}[a-z]{2,3}))$/;

// After (safe)
const email = /^[a-zA-Z0-9][a-zA-Z0-9._-]*@[a-z0-9]+\.[a-z]{2,6}$/;

Alternation with Duplicates

javascript
// Before (vulnerable)
const regex = /^(a|a)*$/;

// After (safe)
const regex = /^a*$/;

Nested Groups with Quantifiers

javascript
// Before (vulnerable)
const pattern = /(.*a){10,}/;

// After (safe) 
const pattern = /(?=.*a).{10,}/;

RegExp Constructor Support

The codemod also handles RegExp constructor patterns:

javascript
// Before (vulnerable)
const regex = new RegExp('(a+)+b', 'g');

// After (safe)
const regex = new RegExp('a+b', 'g');

What Gets Transformed

✅ Regex literals: /pattern/flags
✅ RegExp constructor: new RegExp('pattern', 'flags')
✅ RegExp function: RegExp('pattern', 'flags')
✅ Template literals with regex patterns
✅ Object properties containing regex
✅ Function parameters with regex defaults

What Stays Unchanged

❌ Already safe patterns
❌ Optimized patterns with atomic groups (?>...)
❌ Possessive quantifiers *+, ++, ?+
❌ Patterns in comments (documentation examples)
❌ Test files (preserved for security testing)
❌ Third-party library code

File Support

  • JavaScript (.js)
  • TypeScript (.ts)
  • JSX (.jsx)
  • TSX (.tsx)

Safety Features

  • Non-destructive: Only transforms known vulnerable patterns
  • Functionality preserved: Replacements maintain matching behavior
  • Comment preservation: Documentation examples remain unchanged
  • Test file exclusion: Security test cases are not modified
  • Already-optimized detection: Skips patterns with atomic groups

Examples

Before Transformation

javascript
// Vulnerable email validation
const emailPattern = /^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;

// Nested quantifiers causing exponential backtracking
const userInput = input.match(/(a+)+b/);
const validation = new RegExp('([a-z]*)*$');

// Catastrophic backtracking with alternation
const parser = /^(x+x+)+y/;

After Transformation

javascript
// Safe email validation
const emailPattern = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;

// Linear time complexity
const userInput = input.match(/a+b/);
const validation = new RegExp('[a-z]*$');

// Efficient pattern matching
const parser = /x+y/;

Development

bash
# Test the transformation
pnpm test

# Run on specific test case
pnpm test --filter positive-nested-quantifiers

# Update test snapshots
pnpm test -u

# Validate the workflow
npx codemod@latest validate -w workflow.yaml

Contributing

  1. Add new vulnerable patterns to getSafePattern() function
  2. Create test cases in tests/ directory
  3. Run tests to ensure functionality
  4. Update README with new pattern examples

Limitations

  • Pattern detection: Only known vulnerable patterns are transformed
  • Dynamic patterns: Runtime-generated regex cannot be analyzed
  • Complex cases: Some edge cases may require manual review
  • Context awareness: Limited understanding of regex usage context

References

License

MIT

Ready to evolve your codebase?

Build tailored, compiler-aware skills to assess, plan, and automate complex codebase changes.