Skip to content

Commit

Permalink
Extend ParseException with InnerException and StackTrace (#717)
Browse files Browse the repository at this point in the history
* Extend ParseException with InnerException and StackTrace.

* x
  • Loading branch information
StefH authored Jun 17, 2023
1 parent 586ba45 commit ab20e22
Show file tree
Hide file tree
Showing 3 changed files with 33 additions and 18 deletions.
33 changes: 22 additions & 11 deletions src/System.Linq.Dynamic.Core/Exceptions/ParseException.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,39 +9,50 @@ namespace System.Linq.Dynamic.Core.Exceptions
/// <summary>
/// Represents errors that occur while parsing dynamic linq string expressions.
/// </summary>
#if !(SILVERLIGHT || WINDOWS_APP || UAP10_0 || NETSTANDARD || PORTABLE || WPSL || NETSTANDARD2_0)
#if !(SILVERLIGHT || WINDOWS_APP || UAP10_0 || NETSTANDARD || PORTABLE || WPSL || NETSTANDARD2_0)
[Serializable]
#endif
public sealed class ParseException : Exception
{
/// <summary>
/// The location in the parsed string that produced the <see cref="ParseException"/>.
/// </summary>
public int Position { get; }

/// <summary>
/// Initializes a new instance of the <see cref="ParseException"/> class with a specified error message and position.
/// </summary>
/// <param name="message">The message that describes the error.</param>
/// <param name="position">The location in the parsed string that produced the <see cref="ParseException"/></param>
public ParseException(string message, int position)
: base(message)
/// <param name="innerException">The exception that is the cause of the current exception, or a null reference if no inner exception is specified.</param>
public ParseException(string message, int position, Exception? innerException = null) : base(message, innerException)
{
Position = position;
}

/// <summary>
/// The location in the parsed string that produced the <see cref="ParseException"/>.
/// </summary>
public int Position { get; }

/// <summary>
/// Creates and returns a string representation of the current exception.
/// </summary>
/// <returns>A string representation of the current exception.</returns>
public override string ToString()
{
return string.Format(CultureInfo.CurrentCulture, Res.ParseExceptionFormat, Message, Position);
var text = string.Format(CultureInfo.CurrentCulture, Res.ParseExceptionFormat, Message, Position);

if (InnerException != null)
{
text = $"{text} ---> {InnerException}{Environment.NewLine} --- End of inner exception stack trace ---";
}

if (StackTrace != null)
{
text = $"{text}{Environment.NewLine}{StackTrace}";
}

return text;
}

#if !(SILVERLIGHT || WINDOWS_APP || UAP10_0 || NETSTANDARD || PORTABLE || WPSL || NETSTANDARD2_0)
ParseException(SerializationInfo info, StreamingContext context)
: base(info, context)
private ParseException(SerializationInfo info, StreamingContext context) : base(info, context)
{
Position = (int)info.GetValue("position", typeof(int));
}
Expand Down
4 changes: 2 additions & 2 deletions src/System.Linq.Dynamic.Core/Parser/StringParser.cs
Original file line number Diff line number Diff line change
Expand Up @@ -34,8 +34,8 @@ public static string ParseString(string s)
}
catch (Exception ex)
{
throw new ParseException(ex.Message, 0);
throw new ParseException(ex.Message, 0, ex);
}
}
}
}
}
14 changes: 9 additions & 5 deletions test/System.Linq.Dynamic.Core.Tests/Parser/StringParserTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -48,13 +48,17 @@ public void StringParser_With_InvalidStringQuoteCharacter_ThrowsException(string
public void StringParser_With_UnexpectedUnrecognizedEscapeSequence_ThrowsException()
{
// Arrange
string input = new string(new[] { '"', '\\', 'u', '?', '"' });
var input = new string(new[] { '"', '\\', 'u', '?', '"' });

// Act
Action action = () => StringParser.ParseString(input);

// Assert
action.Should().Throw<ParseException>();
var parseException = action.Should().Throw<ParseException>();

parseException.Which.InnerException!.Message.Should().Contain("Insufficient hexadecimal digits");

parseException.Which.StackTrace.Should().Contain("at System.Linq.Dynamic.Core.Parser.StringParser.ParseString(String s) in ").And.Contain("System.Linq.Dynamic.Core\\Parser\\StringParser.cs:line ");
}

[Theory]
Expand All @@ -65,7 +69,7 @@ public void StringParser_With_UnexpectedUnrecognizedEscapeSequence_ThrowsExcepti
public void StringParser_Parse_SingleQuotedString(string input, string expectedResult)
{
// Act
string result = StringParser.ParseString(input);
var result = StringParser.ParseString(input);

// Assert
result.Should().Be(expectedResult);
Expand All @@ -92,10 +96,10 @@ public void StringParser_Parse_SingleQuotedString(string input, string expectedR
public void StringParser_Parse_DoubleQuotedString(string input, string expectedResult)
{
// Act
string result = StringParser.ParseString(input);
var result = StringParser.ParseString(input);

// Assert
result.Should().Be(expectedResult);
}
}
}
}

0 comments on commit ab20e22

Please # to comment.