diff --git a/core/test/utils/redos_vulnerability_test.dart b/core/test/utils/redos_vulnerability_test.dart index 672e7a3a9..2cba1ab11 100644 --- a/core/test/utils/redos_vulnerability_test.dart +++ b/core/test/utils/redos_vulnerability_test.dart @@ -33,14 +33,26 @@ void main() { }); test('should handle style with many nested parentheses', () { + // Primary purpose: Verify that processing malformed input with many nested + // parentheses doesn't cause catastrophic backtracking (ReDoS vulnerability). + // This pattern would freeze the old unbounded regex. + // + // Note: The current implementation is permissive - it extracts the URL content + // even with malformed nesting. This is acceptable for a parser that prioritizes + // resilience over strict validation. final style = 'background-image: url(${'(' * 1000}example.jpg${')' * 1000})'; final stopwatch = Stopwatch()..start(); final result = transformer.findImageUrlFromStyleTag(style); stopwatch.stop(); - expect(stopwatch.elapsedMilliseconds, lessThan(100)); - expect(result, isNotNull); + // Performance: Should complete quickly without catastrophic backtracking + expect(stopwatch.elapsedMilliseconds, lessThan(100), + reason: 'Should process quickly despite nested parentheses'); + + // Functional: Current implementation extracts URL despite malformed nesting + expect(result, isNotNull, + reason: 'Parser is permissive and extracts URL from malformed input'); }); test('should reject malformed background-image patterns quickly', () { @@ -395,6 +407,7 @@ void main() { final stopwatch2 = Stopwatch()..start(); final plainText2 = HtmlUtils.extractPlainText(extremeNesting); + final linked2 = HtmlUtils.wrapPlainTextLinks(extremeNesting); stopwatch2.stop(); // Performance checks @@ -407,6 +420,10 @@ void main() { expect(plainText1, contains('Deep content')); expect(linked1, contains('