2012-12-17 9 views
13

私は.NETのHttpClientを使用して、WebAPIにリクエストを行い、クライアントの側でカスタム逆シリアル化を少し必要とするJSONデータを返します。これについて私は自分自身でJsonConverterを作ったが、ReadAsAsync<T>メソッドがコンバータの存在を拾う方法を理解できない。.netカスタムJsonConverterを持つHttpClient

ReadAsStringAsyncを使用して応答を読み取った後、その文字列をJsonConvert.DeserializeObjectに渡して問題を解決しましたが、より洗練されたソリューションが必要なようです。ここで

は私のコードです:

public PrefsResponse GetAllPrefs(string sid) { 
    HttpClient client = CreateHttpClient(null, sid); 
    var response = client.GetAsync("api/sites/" + sid).Result; 

    // TODO : find a way to hook custom converters to this... 
    // return response.Content.ReadAsAsync<PrefsResponse>().Result; 

    var stringResult = response.Content.ReadAsStringAsync().Result; 

    return JsonConvert.DeserializeObject<PrefsResponse>(stringResult, new PrefClassJsonConverter()); 
} 

はこれが私にできる最善である、またはいくつかのよりエレガントな方法はありますか?

 private HttpClient CreateHttpClient(CommandContext ctx, string sid) { 
     var cookies = new CookieContainer(); 

     var handler = new HttpClientHandler { 
      CookieContainer = cookies, 
      UseCookies = true, 
      UseDefaultCredentials = false 
     }; 

     // Add identity cookies: 
     if (ctx != null && !ctx.UserExecuting.IsAnonymous) { 
      string userName = String.Format("{0} ({1})", ctx.RequestingUser.UserName, ctx.UserExecuting.Key); 
      cookies.Add(new Cookie(__userIdCookieName, userName)); 
      cookies.Add(new Cookie(__sidCookieName, sid)); 
      cookies.Add(new Cookie(__hashCookieName, 
            GenerateHash(userName, Prefs.Instance.UrlPrefs.SharedSecret))); 
     } 

     var client = new HttpClient(handler) { 
      BaseAddress = _prefServerBaseUrl 
     }; 

     client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); 



     return client; 
    } 

答えて

13

あなたはReadAsAsync<T>によって使用されますJsonMediaTypeFormatterにごコンバータのリストをJsonSerializerSettingsを渡すことができます。私は、デフォルトのフォーマッターにカスタムJsonConverterを追加することができました

var obj = await result.Content.ReadAsAsync<refsResponse>(
    new[] {new JsonMediaTypeFormatter { 
      SerializerSettings = new JsonSerializerSettings { 
       Converters = new List<JsonConverter> { 
       //list of your converters 
       } 
      } 
      } 
    }); 
+1

JSON.Netにはコンバーターという概念がありました。今は同じ仕事をすることができる3つのことがあります。派生したHttpContentクラス、派生MediaTypeFormatterおよび派生JsonConverter .... –

+0

これは私が探していたものです。最終的に私はもともと持っていたものと一緒に行くつもりです。なぜなら、将来のリクエストでのフェールオーバーの場合にも、ディスク上にレスポンスをキャッシュする必要があるからです。 –

+0

素敵です!他のJSON.NET設定をカスタマイズする必要がありました。これはパズルの欠けていた部分です:) –

1

はあなたをHttpClient.GetStringAsync Method (String)

var response = client.GetStringAsync("api/sites/" + sid); 
return JsonConvert.DeserializeObject<PrefsResponse>(response.Result, new PrefClassJsonConverter()); 

または何を正確に使用したいことがある:私ものHttpClientを作成していますどこ私はそれをフックする必要がある場所それはだ場合はここで

は、ですよりエレガントになりたいですか?

+0

これは、ネストしたイニシャライザを 'Content.ReadAsAsync()'に渡すよりも、はるかにエレガントです。唯一の欠点はおそらく、非常に大きなjsonパケットではない罰金以上のストリングにストリームを読み込むことです。私はコードエディタウィンドウの外に出た後、この方法でコードを変更しました。 –

1

すなわち

HttpClientを次のように使用します。

MediaTypeFormatterCollection formatters = new MediaTypeFormatterCollection(); 
formatters.JsonFormatter.SerializerSettings.Converters.Add(new MyCustomConverter()); 


var result = response.Content.ReadAsAsync<T>(formatters).Result; 

これは、カスタムコンバータをデフォルトコンバーター。

関連する問題