11using System ;
22using System . Collections . Generic ;
33using FluentAssertions . Formatting ;
4+ using Newtonsoft . Json ;
45using Newtonsoft . Json . Linq ;
56using Xunit ;
67using Xunit . Sdk ;
@@ -75,67 +76,67 @@ public void When_objects_differ_BeEquivalentTo_should_fail()
7576 Tuple . Create (
7677 ( string ) null ,
7778 "{ id: 2 }" ,
78- "it is null" )
79+ "is null" )
7980 ,
8081 Tuple . Create (
8182 "{ id: 1 }" ,
8283 ( string ) null ,
83- "it is not null" )
84+ "is not null" )
8485 ,
8586 Tuple . Create (
8687 "{ items: [] }" ,
8788 "{ items: 2 }" ,
88- "the type is different at $.items" )
89+ "has a different type at $.items" )
8990 ,
9091 Tuple . Create (
9192 "{ items: [ \" fork\" , \" knife\" , \" spoon\" ]}" ,
9293 "{ items: [ \" fork\" , \" knife\" ]}" ,
93- "the length is different at $.items" )
94+ "has a different length at $.items" )
9495 ,
9596 Tuple . Create (
96- "{ items: [ \" fork\" , \" knife\" , \" spoon\" ]}" ,
9797 "{ items: [ \" fork\" , \" knife\" ]}" ,
98- "the length is different at $.items" )
98+ "{ items: [ \" fork\" , \" knife\" , \" spoon\" ]}" ,
99+ "has a different length at $.items" )
99100 ,
100101 Tuple . Create (
101102 "{ items: [ \" fork\" , \" knife\" , \" spoon\" ]}" ,
102103 "{ items: [ \" fork\" , \" spoon\" , \" knife\" ]}" ,
103- "the value is different at $.items[1]" )
104+ "has a different value at $.items[1]" )
104105 ,
105106 Tuple . Create (
106107 "{ tree: { } }" ,
107108 "{ tree: \" oak\" }" ,
108- "the type is different at $.tree" )
109+ "has a different type at $.tree" )
109110 ,
110111 Tuple . Create (
111112 "{ tree: { leaves: 10} }" ,
112113 "{ tree: { branches: 5, leaves: 10 } }" ,
113- "it misses property $.tree.branches" )
114+ "misses property $.tree.branches" )
114115 ,
115116 Tuple . Create (
116117 "{ tree: { branches: 5, leaves: 10 } }" ,
117118 "{ tree: { leaves: 10} }" ,
118- "it has extra property $.tree.branches" )
119+ "has extra property $.tree.branches" )
119120 ,
120121 Tuple . Create (
121122 "{ tree: { leaves: 5 } }" ,
122123 "{ tree: { leaves: 10} }" ,
123- "the value is different at $.tree.leaves" )
124+ "has a different value at $.tree.leaves" )
124125 ,
125126 Tuple . Create (
126127 "{ eyes: \" blue\" }" ,
127128 "{ eyes: [] }" ,
128- "the type is different at $.eyes" )
129+ "has a different type at $.eyes" )
129130 ,
130131 Tuple . Create (
131132 "{ eyes: \" blue\" }" ,
132133 "{ eyes: 2 }" ,
133- "the type is different at $.eyes" )
134+ "has a different type at $.eyes" )
134135 ,
135136 Tuple . Create (
136137 "{ id: 1 }" ,
137138 "{ id: 2 }" ,
138- "the value is different at $.id" )
139+ "has a different value at $.id" )
139140 } ;
140141
141142 foreach ( var testCase in testCases )
@@ -148,9 +149,11 @@ public void When_objects_differ_BeEquivalentTo_should_fail()
148149 var expected = ( expectedJson != null ) ? JToken . Parse ( expectedJson ) : null ;
149150
150151 var expectedMessage =
151- $ "Expected JSON document { Format ( actual , true ) } " +
152- $ "to be equivalent to { Format ( expected , true ) } , " +
153- "but " + expectedDifference + "." ;
152+ $ "JSON document { expectedDifference } ." +
153+ $ "Expected" +
154+ $ "{ Format ( actual , true ) } " +
155+ $ "to be equivalent to" +
156+ $ "{ Format ( expected , true ) } .";
154157
155158 //-----------------------------------------------------------------------------------------------------------
156159 // Act & Assert
@@ -172,29 +175,32 @@ public void When_properties_differ_BeEquivalentTo_should_fail()
172175 Tuple . Create < JToken , JToken , string > (
173176 new JProperty ( "eyes" , "blue" ) ,
174177 new JArray ( ) ,
175- "the type is different at $" )
178+ "has a different type at $" )
176179 ,
177180 Tuple . Create < JToken , JToken , string > (
178181 new JProperty ( "eyes" , "blue" ) ,
179182 new JProperty ( "hair" , "black" ) ,
180- "the name is different at $" )
183+ "has a different name at $" )
181184 ,
182185 } ;
183186
184187 foreach ( var testCase in testCases )
185188 {
186- var a = testCase . Item1 ;
187- var b = testCase . Item2 ;
188-
189+ var actual = testCase . Item1 ;
190+ var expected = testCase . Item2 ;
191+ var expectedDifference = testCase . Item3 ;
192+
189193 var expectedMessage =
190- $ "Expected JSON document { Format ( a , true ) } " +
191- $ "to be equivalent to { Format ( b , true ) } , " +
192- "but " + testCase . Item3 + "." ;
194+ $ "JSON document { expectedDifference } ." +
195+ $ "Expected" +
196+ $ "{ Format ( actual , true ) } " +
197+ $ "to be equivalent to" +
198+ $ "{ Format ( expected , true ) } .";
193199
194200 //-----------------------------------------------------------------------------------------------------------
195201 // Act & Assert
196202 //-----------------------------------------------------------------------------------------------------------
197- a . Should ( ) . Invoking ( x => x . BeEquivalentTo ( b ) )
203+ actual . Should ( ) . Invoking ( x => x . BeEquivalentTo ( expected ) )
198204 . Should ( ) . Throw < XunitException > ( )
199205 . WithMessage ( expectedMessage ) ;
200206 }
@@ -312,6 +318,42 @@ public void When_checking_whether_a_JToken_is_equivalent_to_the_string_represent
312318 //-----------------------------------------------------------------------------------------------------------
313319 actualJSON . Should ( ) . BeEquivalentTo ( jsonString ) ;
314320 }
321+
322+ [ Fact ]
323+ public void When_checking_equivalency_with_an_invalid_expected_string_it_should_provide_a_clear_error_message ( )
324+ {
325+ //-----------------------------------------------------------------------------------------------------------
326+ // Arrange
327+ //-----------------------------------------------------------------------------------------------------------
328+ var actualJson = JToken . Parse ( "{ \" id\" : null }" ) ;
329+ var expectedString = "{ invalid JSON }" ;
330+
331+ //-----------------------------------------------------------------------------------------------------------
332+ // Act & Assert
333+ //-----------------------------------------------------------------------------------------------------------
334+ actualJson . Should ( ) . Invoking ( x => x . BeEquivalentTo ( expectedString ) )
335+ . Should ( ) . Throw < ArgumentException > ( )
336+ . WithMessage ( $ "Unable to parse expected JSON string:{ expectedString } *")
337+ . WithInnerException < JsonReaderException > ( ) ;
338+ }
339+
340+ [ Fact ]
341+ public void When_checking_non_equivalency_with_an_invalid_unexpected_string_it_should_provide_a_clear_error_message ( )
342+ {
343+ //-----------------------------------------------------------------------------------------------------------
344+ // Arrange
345+ //-----------------------------------------------------------------------------------------------------------
346+ var actualJson = JToken . Parse ( "{ \" id\" : null }" ) ;
347+ var unexpectedString = "{ invalid JSON }" ;
348+
349+ //-----------------------------------------------------------------------------------------------------------
350+ // Act & Assert
351+ //-----------------------------------------------------------------------------------------------------------
352+ actualJson . Should ( ) . Invoking ( x => x . NotBeEquivalentTo ( unexpectedString ) )
353+ . Should ( ) . Throw < ArgumentException > ( )
354+ . WithMessage ( $ "Unable to parse unexpected JSON string:{ unexpectedString } *")
355+ . WithInnerException < JsonReaderException > ( ) ;
356+ }
315357
316358 [ Fact ]
317359 public void When_specifying_a_reason_why_object_should_be_equivalent_it_should_use_that_in_the_error_message ( )
@@ -323,10 +365,12 @@ public void When_specifying_a_reason_why_object_should_be_equivalent_it_should_u
323365 var expected = JToken . Parse ( "{ child: { expected: 'bar' } }" ) ;
324366
325367 var expectedMessage =
326- $ "Expected JSON document { Format ( subject , true ) } " +
327- $ "to be equivalent to { Format ( expected , true ) } " +
328- "because we want to test the failure message, " +
329- "but it misses property $.child.expected." ;
368+ $ "JSON document misses property $.child.expected." +
369+ $ "Expected" +
370+ $ "{ Format ( subject , true ) } " +
371+ $ "to be equivalent to" +
372+ $ "{ Format ( expected , true ) } " +
373+ "because we want to test the failure message." ;
330374
331375 //-----------------------------------------------------------------------------------------------------------
332376 // Act & Assert
@@ -1021,6 +1065,24 @@ public void When_property_types_dont_match_ContainSubtree_should_fail()
10211065 act . Should ( ) . Throw < XunitException > ( ) ;
10221066 }
10231067
1068+ [ Fact ]
1069+ public void When_checking_subtree_with_an_invalid_expected_string_it_should_provide_a_clear_error_message ( )
1070+ {
1071+ //-----------------------------------------------------------------------------------------------------------
1072+ // Arrange
1073+ //-----------------------------------------------------------------------------------------------------------
1074+ var actualJson = JToken . Parse ( "{ \" id\" : null }" ) ;
1075+ var invalidSubtree = "{ invalid JSON }" ;
1076+
1077+ //-----------------------------------------------------------------------------------------------------------
1078+ // Act & Assert
1079+ //-----------------------------------------------------------------------------------------------------------
1080+ actualJson . Should ( ) . Invoking ( x => x . ContainSubtree ( invalidSubtree ) )
1081+ . Should ( ) . Throw < ArgumentException > ( )
1082+ . WithMessage ( $ "Unable to parse expected JSON string:{ invalidSubtree } *")
1083+ . WithInnerException < JsonReaderException > ( ) ;
1084+ }
1085+
10241086 #endregion
10251087
10261088 private static string Format ( JToken value , bool useLineBreaks = false )
0 commit comments