Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
45 changes: 45 additions & 0 deletions Robust.Shared.Tests/Utility/FormattedMessage_Test.cs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
using System.Collections.Generic;
using NUnit.Framework;
using Robust.Shared.Maths;
using Robust.Shared.Utility;
Expand Down Expand Up @@ -61,6 +62,7 @@ public string TestRemoveMarkup(string test)

[Test]
[TestCase("Foo")]
[TestCase("foo\"bar")]
[TestCase("[color=#FF000000]Foo[/color]")]
[TestCase("[color=lime]Foo[/color]bar")]
public static void TestToMarkup(string text)
Expand All @@ -69,6 +71,48 @@ public static void TestToMarkup(string text)
Assert.That(message.ToMarkup(), NUnit.Framework.Is.EqualTo(text));
}

[Test]
[TestCase("te\"xt")]
[TestCase("te\\\"xt")]
[TestCase("te\\xt")]
[TestCase("te[xt")]
[TestCase("te\"[\\xt")]
public static void TestEscapedStringParameters(string value)
{
var escaped = FormattedMessage.EscapeText(value).Replace("\"", "\\\"");
var parameterMessage = FormattedMessage.FromMarkupOrThrow($"[tag=\"{escaped}\"]");
var attributeMessage = FormattedMessage.FromMarkupOrThrow($"[tag attr=\"{escaped}\"]");

Assert.That(parameterMessage[0].Value.StringValue, Is.EqualTo(value));
Assert.That(attributeMessage[0].Attributes["attr"].StringValue, Is.EqualTo(value));
}

[Test]
public static void TestEscapedQuotesOnlyInStringParameters()
{
Assert.That(FormattedMessage.EscapeText("foo\"bar"), Is.EqualTo("foo\"bar"));

var message = FormattedMessage.FromMarkupOrThrow("[tag=\"foo\\\"bar\"]");
Assert.That(message[0].Value.StringValue, Is.EqualTo("foo\"bar"));
}

[Test]
[TestCase("te\"xt")]
[TestCase("te\\\"xt")]
[TestCase("te\\xt")]
[TestCase("te[xt")]
[TestCase("te\"[\\xt")]
public static void TestStringParameterToMarkupRoundTrip(string value)
{
var message = new FormattedMessage();
message.PushTag(new MarkupNode("tag",
new MarkupParameter(value),
new Dictionary<string, MarkupParameter> { { "attr", new MarkupParameter(value) } }));

var roundTrip = FormattedMessage.FromMarkupOrThrow(message.ToMarkup());
Assert.That(roundTrip, Is.EqualTo(message));
}

[Test]
[TestCase("Foo")]
[TestCase("[color=#FF000000]Foo[/color]")]
Expand All @@ -88,6 +132,7 @@ public static void TestEnumerateRunes(string text)
/// </summary>
[Test]
[TestCase("\\[whaaaaa")]
[TestCase("foo\"bar")]
public static void TestRoundTrip(string markup)
{
var message = FormattedMessage.FromMarkupOrThrow(markup);
Expand Down
8 changes: 6 additions & 2 deletions Robust.Shared/Utility/FormattedMessage.MarkupParser.cs
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,10 @@ public static List<MarkupNode> ParsePermissive(string input, out string? error)
private static readonly Parser<char, char> EscapeSequence =
Try(Escape.Then(OneOf(Escape, Begin, End, Slash)));

//This checks for a backslash and one reserved character inside a string parameter
private static readonly Parser<char, char> ParameterEscapeSequence =
Try(Escape.Then(OneOf(Escape, Begin, End, Quote, Slash)));

//Parses text by repeatedly parsing escape sequences or any character except [ and \
//The result is put into a new markup node representing text (it has no name)
private static readonly Parser<char, List<MarkupNode>> Text =
Expand All @@ -140,9 +144,9 @@ public static List<MarkupNode> ParsePermissive(string input, out string? error)
Token(char.IsLetterOrDigit).ManyString()
);

//Parses any character except ". Used for parsing a string parameter wrapped in ""
//Parses parameter escape sequences or any character except ". Used for parsing a string parameter wrapped in ""
private static readonly Parser<char, string> ParameterString =
Token(c => c != '"').ManyString();
ParameterEscapeSequence.Or(Token(c => c != '"')).ManyString();

//Parses eiter a string not wrapped by "" or a hexadecimal value beginning with #
//The distinction is made by checking if the first character is a pound sign
Expand Down
2 changes: 1 addition & 1 deletion Robust.Shared/Utility/MarkupNode.cs
Original file line number Diff line number Diff line change
Expand Up @@ -137,7 +137,7 @@ public bool TryGetColor([NotNullWhen(true)] out Color? value)
public override string ToString()
{
if (StringValue != null)
return $"=\"{StringValue}\"";
return $"=\"{FormattedMessage.EscapeText(StringValue).Replace("\"", "\\\"")}\"";

if (LongValue.HasValue)
return LongValue?.ToString().Insert(0, "=") ?? "";
Expand Down
Loading