1919
2020using OpenQA . Selenium . Internal ;
2121using System ;
22- using System . Collections . Generic ;
2322using System . Diagnostics . CodeAnalysis ;
2423using System . Globalization ;
2524using System . Text . Json ;
25+ using System . Text . Json . Nodes ;
2626using System . Text . Json . Serialization ;
2727
2828#nullable enable
2929
3030namespace OpenQA . Selenium
3131{
3232 /// <summary>
33- /// Handles reponses from the browser
33+ /// Handles responses from the browser
3434 /// </summary>
3535 public class Response
3636 {
37- private static readonly JsonSerializerOptions s_jsonSerializerOptions = new ( )
38- {
39- TypeInfoResolver = ResponseJsonSerializerContext . Default ,
40- Converters = { new ResponseValueJsonConverter ( ) } // we still need it to make `Object` as `Dictionary`
41- } ;
42-
4337 /// <summary>
4438 /// Initializes a new instance of the <see cref="Response"/> class
4539 /// </summary>
@@ -82,18 +76,18 @@ public Response(string? sessionId, object? value, WebDriverResult status)
8276 /// <exception cref="JsonException">If <paramref name="value"/> is not a valid JSON object.</exception>
8377 public static Response FromJson ( string value )
8478 {
85- Dictionary < string , object ? > rawResponse = JsonSerializer . Deserialize < Dictionary < string , object ? > > ( value , s_jsonSerializerOptions )
86- ?? throw new WebDriverException ( "JSON success response returned \" null \" value" ) ;
79+ JsonObject rawResponse = JsonNode . Parse ( value ) as JsonObject
80+ ?? throw new WebDriverException ( $ "JSON success response did not return a dictionary { Environment . NewLine } { value } ") ;
8781
88- object ? contents ;
82+ JsonNode ? contents ;
8983 string ? sessionId = null ;
9084
91- if ( rawResponse . TryGetValue ( "sessionId" , out object ? s ) && s is not null )
85+ if ( rawResponse . TryGetPropertyValue ( "sessionId" , out JsonNode ? s ) && s is not null )
9286 {
9387 sessionId = s . ToString ( ) ;
9488 }
9589
96- if ( rawResponse . TryGetValue ( "value" , out object ? valueObj ) )
90+ if ( rawResponse . TryGetPropertyValue ( "value" , out JsonNode ? valueObj ) )
9791 {
9892 contents = valueObj ;
9993 }
@@ -107,7 +101,7 @@ public static Response FromJson(string value)
107101
108102 // Special-case for the new session command, where the "capabilities"
109103 // property of the response is the actual value we're interested in.
110- if ( rawResponse . TryGetValue ( "capabilities" , out object ? capabilities ) )
104+ if ( rawResponse . TryGetPropertyValue ( "capabilities" , out JsonNode ? capabilities ) )
111105 {
112106 contents = capabilities ;
113107 }
@@ -117,14 +111,14 @@ public static Response FromJson(string value)
117111 }
118112 }
119113
120- if ( contents is Dictionary < string , object ? > valueDictionary )
114+ if ( contents is JsonObject valueDictionary )
121115 {
122116 // Special case code for the new session command. If the response contains
123117 // sessionId and capabilities properties, fix up the session ID and value members.
124- if ( valueDictionary . TryGetValue ( "sessionId" , out object ? session ) )
118+ if ( valueDictionary . TryGetPropertyValue ( "sessionId" , out JsonNode ? session ) )
125119 {
126120 sessionId = session . ToString ( ) ;
127- if ( valueDictionary . TryGetValue ( "capabilities" , out object ? capabilities ) )
121+ if ( valueDictionary . TryGetPropertyValue ( "capabilities" , out JsonNode ? capabilities ) )
128122 {
129123 contents = capabilities ;
130124 }
@@ -135,7 +129,9 @@ public static Response FromJson(string value)
135129 }
136130 }
137131
138- return new Response ( sessionId , contents , WebDriverResult . Success ) ;
132+ var contentsDictionary = JsonSerializer . Deserialize ( contents , ResponseJsonSerializerContext . Default . Object ) ;
133+
134+ return new Response ( sessionId , contentsDictionary , WebDriverResult . Success ) ;
139135 }
140136
141137 /// <summary>
@@ -181,29 +177,30 @@ public WebDriverResult Status
181177 /// <exception cref="WebDriverException">If the JSON dictionary is not in the expected state, per spec.</exception>
182178 public static Response FromErrorJson ( string value )
183179 {
184- Dictionary < string , object ? > deserializedResponse = JsonSerializer . Deserialize < Dictionary < string , object ? > > ( value , s_jsonSerializerOptions )
185- ?? throw new WebDriverException ( "JSON error response returned \" null \" value" ) ;
180+ JsonObject responseObject = JsonNode . Parse ( value ) as JsonObject
181+ ?? throw new WebDriverException ( $ "JSON error response did not return an object { Environment . NewLine } { value } ") ;
186182
187- if ( ! deserializedResponse . TryGetValue ( "value" , out object ? valueObject ) )
183+ if ( ! responseObject . TryGetPropertyValue ( "value" , out JsonNode ? valueNode ) )
188184 {
189- throw new WebDriverException ( $ "The 'value' property was not found in the response: { Environment . NewLine } { value } ") ;
185+ throw new WebDriverException ( $ "The 'value' property was not found in the response{ Environment . NewLine } { value } ") ;
190186 }
191187
192- if ( valueObject is not Dictionary < string , object ? > valueDictionary )
188+ if ( valueNode is not JsonObject valueObject )
193189 {
194- throw new WebDriverException ( $ "The 'value' property is not a dictionary of <string, object> { Environment . NewLine } { value } ") ;
190+ throw new WebDriverException ( $ "The 'value' property is not a dictionary{ Environment . NewLine } { value } ") ;
195191 }
196192
197- if ( ! valueDictionary . TryGetValue ( "error" , out object ? errorObject ) )
193+ if ( ! valueObject . TryGetPropertyValue ( "error" , out JsonNode ? errorObject ) )
198194 {
199- throw new WebDriverException ( $ "The 'value > error' property was not found in the response: { Environment . NewLine } { value } ") ;
195+ throw new WebDriverException ( $ "The 'value > error' property was not found in the response{ Environment . NewLine } { value } ") ;
200196 }
201197
202- if ( errorObject is not string errorString )
198+ if ( errorObject is not JsonValue errorValue || ! errorValue . TryGetValue ( out string ? errorString ) )
203199 {
204200 throw new WebDriverException ( $ "The 'value > error' property is not a string{ Environment . NewLine } { value } ") ;
205201 }
206202
203+ var valueDictionary = JsonSerializer . Deserialize ( valueObject , ResponseJsonSerializerContext . Default . Object ) ;
207204 WebDriverResult status = WebDriverError . ResultFromError ( errorString ) ;
208205
209206 return new Response ( sessionId : null , valueDictionary , status ) ;
@@ -243,6 +240,7 @@ public override string ToString()
243240 }
244241 }
245242
246- [ JsonSerializable ( typeof ( Dictionary < string , object > ) ) ]
243+ [ JsonSerializable ( typeof ( object ) ) ]
244+ [ JsonSourceGenerationOptions ( Converters = [ typeof ( ResponseValueJsonConverter ) ] ) ] // we still need it to make `Object` as `Dictionary`
247245 internal sealed partial class ResponseJsonSerializerContext : JsonSerializerContext ;
248246}
0 commit comments