Skip to content

Commit

Permalink
Fix bad replacement pattern parse
Browse files Browse the repository at this point in the history
$n wasn't interpreted correctly when it was at the end of a pattern.
  • Loading branch information
ltrzesniewski committed May 7, 2019
1 parent 72a3158 commit 327f19f
Show file tree
Hide file tree
Showing 2 changed files with 49 additions and 17 deletions.
36 changes: 36 additions & 0 deletions src/PCRE.NET.Tests/PcreNet/ReplaceTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,42 @@ public void should_replace_matches_with_pattern()
Assert.That(result, Is.EqualTo("foo <aabb><bb><aabb> bar <aaabb><bb><aaabb><ab><b><ab> baz"));
}

[Test]
public void should_replace_indexed_groups_with_braces()
{
var re = new PcreRegex(@"a+(?<grp>b+)", PcreOptions.IgnoreCase);
var result = re.Replace("foo aabb bar aaabbab baz", "<${1}>");

Assert.That(result, Is.EqualTo("foo <bb> bar <bb><b> baz"));
}

[Test]
public void should_replace_indexed_groups_without_braces()
{
var re = new PcreRegex(@"a+(?<grp>b+)", PcreOptions.IgnoreCase);
var result = re.Replace("foo aabb bar aaabbab baz", "<$1>");

Assert.That(result, Is.EqualTo("foo <bb> bar <bb><b> baz"));
}

[Test]
public void should_replace_indexed_groups_with_braces_at_end_of_pattern()
{
var re = new PcreRegex(@"a+(?<grp>b+)", PcreOptions.IgnoreCase);
var result = re.Replace("foo aabb bar aaabbab baz", "#${1}");

Assert.That(result, Is.EqualTo("foo #bb bar #bb#b baz"));
}

[Test]
public void should_replace_indexed_groups_without_braces_at_end_of_pattern()
{
var re = new PcreRegex(@"a+(?<grp>b+)", PcreOptions.IgnoreCase);
var result = re.Replace("foo aabb bar aaabbab baz", "#$1");

Assert.That(result, Is.EqualTo("foo #bb bar #bb#b baz"));
}

[Test]
public void should_replace_named_groups()
{
Expand Down
30 changes: 13 additions & 17 deletions src/PCRE.NET/Internal/ReplacementPattern.cs
Original file line number Diff line number Diff line change
Expand Up @@ -106,15 +106,11 @@ public static Func<PcreMatch, string> Parse(string replacementPattern)

var fallback = new LiteralPart(replacementPattern, startIdx - 1, idx - startIdx + 1);

if (idx < replacementPattern.Length)
var groupIndexString = replacementPattern.Substring(startIdx, idx - startIdx);
if (int.TryParse(groupIndexString, NumberStyles.None, CultureInfo.InvariantCulture, out var groupIndex))
{
var groupIndexString = replacementPattern.Substring(startIdx, idx - startIdx);
int groupIndex;
if (Int32.TryParse(groupIndexString, NumberStyles.None, CultureInfo.InvariantCulture, out groupIndex))
{
parts.Add(new IndexedGroupPart(groupIndex, fallback));
break;
}
parts.Add(new IndexedGroupPart(groupIndex, fallback));
break;
}

parts.Add(fallback);
Expand Down Expand Up @@ -174,10 +170,10 @@ public LiteralPart(string text, int startIndex, int length)
_length = length;
}

public override void Append(PcreMatch match, StringBuilder sb)
public override void Append(PcreMatch match, StringBuilder sb)
=> sb.Append(_text, _startIndex, _length);

public override string ToString()
public override string ToString()
=> $"Literal: {_text.Substring(_startIndex, _length)}";
}

Expand Down Expand Up @@ -243,18 +239,18 @@ public override void Append(PcreMatch match, StringBuilder sb)
sb.Append(match.Subject, group.Index, group.Length);
}

public override string ToString()
public override string ToString()
=> $"Group: {_name}";
}

private sealed class PreMatchPart : ReplacementPart
{
public static readonly PreMatchPart Instance = new PreMatchPart();

public override void Append(PcreMatch match, StringBuilder sb)
public override void Append(PcreMatch match, StringBuilder sb)
=> sb.Append(match.Subject, 0, match.Index);

public override string ToString()
public override string ToString()
=> "Pre match";
}

Expand All @@ -268,18 +264,18 @@ public override void Append(PcreMatch match, StringBuilder sb)
sb.Append(match.Subject, endOfMatch, match.Subject.Length - endOfMatch);
}

public override string ToString()
public override string ToString()
=> "Post match";
}

private sealed class FullInputPart : ReplacementPart
{
public static readonly FullInputPart Instance = new FullInputPart();

public override void Append(PcreMatch match, StringBuilder sb)
public override void Append(PcreMatch match, StringBuilder sb)
=> sb.Append(match.Subject);

public override string ToString()
public override string ToString()
=> "Full input";
}

Expand All @@ -300,7 +296,7 @@ public override void Append(PcreMatch match, StringBuilder sb)
}
}

public override string ToString()
public override string ToString()
=> "Last matched group";
}
}
Expand Down

0 comments on commit 327f19f

Please sign in to comment.