npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@angular-helpers/security

v21.0.3

Published

Angular security helpers for preventing ReDoS and other security vulnerabilities

Downloads

346

Readme

Leer en Español

🌐 Documentation & Demo: https://gaspar1992.github.io/angular-helpers/

Angular Security Helpers

Security package for Angular applications that prevents common attacks like ReDoS (Regular Expression Denial of Service) using Web Workers for safe execution.

🛡️ Features

ReDoS Prevention

  • Web Worker Execution: Regular expressions are executed in a separate thread.
  • Configurable Timeout: Prevents infinite executions.
  • Complexity Analysis: Detects dangerous patterns before execution.
  • Safe Mode: Only allows patterns verified as safe.

Builder Pattern

  • Fluent API: Intuitively build regular expressions.
  • Method Chaining: .pattern().group().quantifier()
  • Real-time Validation: Security analysis during construction.

📦 Installation

npm install @angular-helpers/security

🚀 Basic Usage

Configuration

import { provideSecurity } from '@angular-helpers/security';

bootstrapApplication(AppComponent, {
  providers: [
    provideSecurity({
      enableRegexSecurity: true,
      defaultTimeout: 5000,
      safeMode: false,
    }),
  ],
});

Service Injection

import { RegexSecurityService, inject } from '@angular-helpers/security';

@Component({...})
export class MyComponent {
  private regexSecurity = inject(RegexSecurityService);
}

📖 Usage Examples

1. Basic Regular Expression Test

async testEmail(email: string): Promise<boolean> {
  const result = await this.regexSecurity.testRegex(
    '^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,}$',
    email,
    { timeout: 3000 }
  );

  return result.match;
}

2. Builder Pattern

import { RegexSecurityService } from '@angular-helpers/security';

// Fluent regular expression construction
const { pattern, security } = RegexSecurityService.builder()
  .startOfLine()
  .characterSet('a-zA-Z0-9._%+-')
  .quantifier('+')
  .append('@')
  .characterSet('a-zA-Z0-9.-')
  .quantifier('+')
  .append('\\.')
  .characterSet('a-zA-Z')
  .quantifier('{2,}')
  .endOfLine()
  .timeout(5000)
  .safeMode()
  .build();

// Direct execution
const result = await RegexSecurityService.builder()
  .pattern('^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,}$')
  .timeout(3000)
  .execute(email, this.regexSecurity);

3. Security Analysis

async analyzePattern(pattern: string): Promise<void> {
  const analysis = await this.regexSecurity.analyzePatternSecurity(pattern);

  if (!analysis.safe) {
    console.warn('⚠️ Pattern not safe:', analysis.warnings);
    console.info('💡 Recommendations:', analysis.recommendations);

    if (analysis.risk === 'critical') {
      throw new Error('Pattern rejected due to critical security risk');
    }
  }

  console.log(`✅ Pattern complexity: ${analysis.complexity}`);
  console.log(`🎯 Risk level: ${analysis.risk}`);
}

4. Form Validation

@Component({...})
export class FormValidationComponent {
  constructor(private regexSecurity: RegexSecurityService) {}

  async validateUsername(username: string): Promise<boolean> {
    const result = await this.regexSecurity.testRegex(
      '^[a-zA-Z0-9_]{3,20}$',
      username,
      { timeout: 1000, safeMode: true }
    );

    if (result.timeout) {
      throw new Error('Username validation timeout - possible ReDoS attack');
    }

    if (result.error) {
      console.error('Validation error:', result.error);
      return false;
    }

    return result.match;
  }

  async validateComplexInput(input: string): Promise<boolean> {
    // Builder pattern for complex validation
    const result = await RegexSecurityService
      .builder()
      .startOfLine()
      .nonCapturingGroup('[a-zA-Z]') // First letter
      .characterSet('a-zA-Z0-9_') // Allowed characters
      .quantifier('{2,19}') // Between 3 and 20 characters total
      .endOfLine()
      .timeout(2000)
      .execute(input, this.regexSecurity);

    return result.match;
  }
}

🔧 Advanced Configuration

Security Options

interface RegexSecurityConfig {
  timeout?: number; // Timeout in ms (default: 5000)
  maxComplexity?: number; // Max complexity (default: 10)
  allowBacktracking?: boolean; // Allow backtracking (default: false)
  safeMode?: boolean; // Safe mode (default: false)
}

Builder Options

interface RegexBuilderOptions {
  global?: boolean; // 'g' flag
  ignoreCase?: boolean; // 'i' flag
  multiline?: boolean; // 'm' flag
  dotAll?: boolean; // 's' flag
  unicode?: boolean; // 'u' flag
  sticky?: boolean; // 'y' flag
}

🛡️ Security Features

Dangerous Pattern Detection

The service automatically detects:

  • Nested quantifiers: **, ++ (catastrophic backtracking)
  • Lookaheads/lookbehinds: (?=), (?!), (?<=), (?<!)
  • Atomic groups: (?>)
  • Recursive patterns: Deeply nested groups
  • Complex quantifiers: {n,m} with high values
  • Greedy wildcards: .*, .+ with variable characters

Risk Levels

  • 🟢 Low: Simple and safe patterns
  • 🟡 Medium: Patterns with lookahead/lookbehind
  • 🟠 High: Patterns with complex quantifiers
  • 🔴 Critical: Patterns with catastrophic backtracking

Attack Prevention

  • Timeout: Stops execution after the time limit
  • Web Worker: Isolates execution from the main thread
  • Pre-analysis: Rejects dangerous patterns before execution
  • Match limit: Prevents infinite loops

📊 Metrics and Monitoring

Execution Results

interface RegexTestResult {
  match: boolean; // If there was a match
  matches?: RegExpMatchArray[]; // All matches found
  groups?: { [key: string]: string }; // Captured groups
  executionTime: number; // Execution time in ms
  timeout: boolean; // If there was a timeout
  error?: string; // Error if one occurred
}

Security Analysis

interface RegexSecurityResult {
  safe: boolean; // If the pattern is safe
  complexity: number; // Complexity level (0-∞)
  risk: 'low' | 'medium' | 'high' | 'critical';
  warnings: string[]; // Security warnings
  recommendations: string[]; // Improvement recommendations
}

🔄 Form Integration

Angular Validators

import { AbstractControl, ValidationErrors } from '@angular/forms';

export class SecurityValidators {
  constructor(private regexSecurity: RegexSecurityService) {}

  async securePattern(pattern: string, config?: RegexSecurityConfig) {
    return async (control: AbstractControl): Promise<ValidationErrors | null> => {
      const value = control.value;

      if (!value) return null;

      try {
        const result = await this.regexSecurity.testRegex(pattern, value, config);

        if (!result.match) {
          return { securePattern: { value, reason: 'Pattern does not match' } };
        }

        if (result.timeout) {
          return { securePattern: { value, reason: 'Pattern execution timeout' } };
        }

        return null;
      } catch (error) {
        return { securePattern: { value, reason: (error as Error).message } };
      }
    };
  }
}

Usage in Template Forms

@Component({...})
export class SecureFormComponent {
  private regexSecurity = inject(RegexSecurityService);
  private securityValidators = inject(SecurityValidators);

  emailValidator = this.securityValidators.securePattern(
    '^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,}$',
    { timeout: 3000, safeMode: true }
  );
}

🚨 Best Practices

1. Use Safe Mode in Production

// In production, always use safeMode
const config = { safeMode: true, timeout: 3000 };

2. Appropriate Timeout

// For form validations: 1-3 seconds
// For text processing: 5-10 seconds
// Never more than 30 seconds

3. Pre-analysis

// Always analyze user-provided patterns
const analysis = await this.regexSecurity.analyzePatternSecurity(pattern);
if (!analysis.safe) {
  // Consider using a safer alternative pattern
}

4. Error Handling

try {
  const result = await this.regexSecurity.testRegex(pattern, text, config);
  // Process result
} catch (error) {
  // Handle error safely
  console.error('Regex security error:', error);
  // Fallback to a simpler validation
}

🔍 Debugging

Security Logging

The service includes automatic logging:

// Enables detailed logging
console.log('Regex security initialized');
console.log('Pattern analysis completed:', analysis);
console.log('Pattern execution completed:', result);

Performance Monitoring

// Monitor execution times
if (result.executionTime > 1000) {
  console.warn('Slow regex pattern:', pattern, result.executionTime + 'ms');
}

📝 License

MIT License - see the LICENSE file for details.

🤝 Contributions

Contributions are welcome. Please:

  1. Create an issue to discuss changes
  2. Fork the repository
  3. Create a feature branch
  4. Send a pull request

📚 Additional Resources


⚠️ Warning: This package helps prevent ReDoS but does not replace other security practices. Always validate and sanitize user inputs.