Skip to content

Commit ae12284

Browse files
committed
refactor: replace regex matcher with linear-time two-ended scan
The regex-based URI template matcher required an ever-growing set of parse-time adjacency checks to reject templates that would cause catastrophic backtracking. Python's re module is a backtracking engine, so any pair of greedy groups with overlapping character classes and a failing suffix produces O(n^k) match time. Enumerating every such combination proved intractable — each fix revealed another bypass. This replaces the regex matcher with a two-ended linear scan: - Templates are flattened into a sequence of literal and capture atoms, with operator prefixes/separators lowered to explicit literals. - A template may contain at most one multi-segment variable ({+var}, {#var}, or explode). This is the only structural restriction. - The suffix is scanned right-to-left: literals via endswith, bounded variables via rfind of the preceding literal. This matches regex greedy-first semantics exactly for templates without a greedy var. - If a greedy var exists, the prefix is scanned left-to-right with lazy anchor-finding, and the greedy var gets whatever remains between prefix_end and suffix_start. Every URI character is visited O(1) times per atom. There is no backtracking; a failed anchor search returns None immediately. Removes _check_ambiguous_adjacency (80 lines of state tracking), _build_pattern, _expression_pattern, and the _pattern field. Templates previously rejected for adjacency ({+a}{b}, {a}{+b}, prefix/{+path}{.ext}) are now accepted and match in linear time. The only rejected patterns are those with two or more multi-segment variables, which are inherently ambiguous regardless of algorithm.
1 parent 19822fb commit ae12284

2 files changed

Lines changed: 446 additions & 264 deletions

File tree

0 commit comments

Comments
 (0)