applyRegexpTransform function

dynamic applyRegexpTransform(
  1. PageNode node,
  2. dynamic value,
  3. String pattern
)

Apply regexp transform to a value

Performs pattern matching and optional replacement using regular expressions. Supports both extraction mode (pattern only) and replacement mode.

Parameters

  • node - PageNode for accessing page context (URL information)
  • value - The input value to transform
  • pattern - Regexp pattern in format /pattern/ or /pattern/replacement/

Modes

Extraction Mode

When only pattern is provided (no replacement), returns the first match:

applyRegexpTransform(node, 'abc123def', r'/\d+/');  // '123'

Replacement Mode

When replacement is provided, replaces all matches:

applyRegexpTransform(node, 'hello', r'/l/L/');  // 'heLLo'

Special Features

  • Capture groups: Use $0, $1, $2 in replacements
  • \ALL keyword: Matches entire string including newlines
  • Page context: Use ${pageUrl} and ${rootUrl} in replacements
  • Multiline: Patterns use multiline mode by default

Returns

  • Extraction mode: First match or null if no match
  • Replacement mode: String with all matches replaced
  • null if input is null
  • Original value if pattern is invalid

Examples

// Extract
applyRegexpTransform(node, 'Price: $19.99', r'/\$[\d.]+/');  // '$19.99'

// Replace
applyRegexpTransform(node, 'hello', r'/l/L/');  // 'heLLo'

// Capture groups
applyRegexpTransform(node, 'John Doe', r'/(\w+) (\w+)/$2, $1/');  // 'Doe, John'

// Page context
applyRegexpTransform(node, '/path', r'/^//${rootUrl}/');  // 'https://example.com/path'

Implementation

dynamic applyRegexpTransform(PageNode node, dynamic value, String pattern) {
  if (value == null) return null;

  // Parse the pattern to extract pattern and replacement parts
  final parsed = parseRegexpPattern(pattern);
  if (parsed == null) {
    _log.warning(
        'Invalid regexp format. Use: /pattern/ or /pattern/replacement/');
    return value;
  }

  final regexPattern = parsed.pattern;
  final replacement = parsed.replacement;

  try {
    final regexp = RegExp(regexPattern, multiLine: true);
    final valueStr = value.toString();

    // Pattern-only mode (empty replacement part)
    if (replacement.isEmpty) {
      final match = regexp.firstMatch(valueStr);
      return match?.group(0);
    }

    // Replace mode
    final preparedReplacement = prepareReplacement(node, replacement);
    return valueStr.replaceAllMapped(regexp, (Match match) {
      var result = preparedReplacement;
      for (var i = 1; i <= match.groupCount; i++) {
        result = result.replaceAll('\$$i', match.group(i) ?? '');
      }
      return result.replaceAll(r'$0', match.group(0) ?? '');
    });
  } catch (e) {
    _log.warning('Failed to apply regexp: $regexPattern, error: $e');
    return value;
  }
}