Skip to content

Commit 56d29b5

Browse files
committed
Skip abutting empty replace_all matches
1 parent 43677ba commit 56d29b5

2 files changed

Lines changed: 17 additions & 0 deletions

File tree

vibes/builtins.go

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -499,11 +499,23 @@ func regexReplaceAllWithLimit(re *regexp.Regexp, text string, replacement string
499499
out := make([]byte, 0, len(text))
500500
lastAppended := 0
501501
searchStart := 0
502+
lastMatchEnd := -1
502503
for searchStart <= len(text) {
503504
loc, found := nextRegexReplaceAllSubmatchIndex(re, text, searchStart)
504505
if !found {
505506
break
506507
}
508+
if loc[0] == loc[1] && loc[0] == lastMatchEnd {
509+
if loc[0] >= len(text) {
510+
break
511+
}
512+
_, size := utf8.DecodeRuneInString(text[loc[0]:])
513+
if size == 0 {
514+
size = 1
515+
}
516+
searchStart = loc[0] + size
517+
continue
518+
}
507519

508520
segmentLen := loc[0] - lastAppended
509521
if len(out) > maxRegexInputBytes-segmentLen {
@@ -515,6 +527,7 @@ func regexReplaceAllWithLimit(re *regexp.Regexp, text string, replacement string
515527
return "", fmt.Errorf("%s output exceeds limit %d bytes", method, maxRegexInputBytes)
516528
}
517529
lastAppended = loc[1]
530+
lastMatchEnd = loc[1]
518531

519532
if loc[1] > loc[0] {
520533
searchStart = loc[1]

vibes/runtime_test.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1956,6 +1956,7 @@ func TestRegexBuiltins(t *testing.T) {
19561956
replace_all: Regex.replace_all("ID-12 ID-34", "ID-[0-9]+", "X"),
19571957
replace_all_anchor: Regex.replace_all("abc", "^", "X"),
19581958
replace_all_boundary: Regex.replace_all("ab", "\\b", "X"),
1959+
replace_all_abutting_empty: Regex.replace_all("aa", "aa|", "X"),
19591960
replace_capture: Regex.replace("ID-12 ID-34", "ID-([0-9]+)", "X-$1"),
19601961
replace_boundary: Regex.replace("ab", "\\Bb", "X")
19611962
}
@@ -1992,6 +1993,9 @@ func TestRegexBuiltins(t *testing.T) {
19921993
if !out["replace_all_boundary"].Equal(NewString("XabX")) {
19931994
t.Fatalf("replace_all_boundary mismatch: %v", out["replace_all_boundary"])
19941995
}
1996+
if !out["replace_all_abutting_empty"].Equal(NewString("X")) {
1997+
t.Fatalf("replace_all_abutting_empty mismatch: %v", out["replace_all_abutting_empty"])
1998+
}
19951999
if !out["replace_capture"].Equal(NewString("X-12 ID-34")) {
19962000
t.Fatalf("replace_capture mismatch: %v", out["replace_capture"])
19972001
}

0 commit comments

Comments
 (0)