簡體   English   中英

為什么POST和PUT ReadAsAsync()為空,但ReadAsStringAsync()已填充? 又稱為“如何關閉分塊?”

[英]Why are POSTs and PUTs ReadAsAsync() null, but ReadAsStringAsync() filled? AKA “How do I turn Chunking Off?”

我有一個Web API項目,該項目具有數十種RESTful方法,在GET,POST和PUT之間平均分配。 系統使用Entity Framework對象和Nuget(版本9.0.1)中的Newtonsoft的JSON。

我最近完成的操作突然破壞了所有POST和PUT。 我發現我正在POST / PUTTING的[FromBody]對象以null形式到達。

所以我的“更新用戶”方法看起來像這樣...

    [HttpPut]
    public IHttpActionResult Put([FromBody] User user)

...但是“用戶”總是到達null。 同樣如果我這樣做...

  var obj = Request.Content.ReadAsAsync<object>().Result;

...那么obj為空。

但是如果我這樣做

var jsonString = Request.Content.ReadAsStringAsync().Result;

...然后我得到了預期的JSON。 (但是對於我的體系結構,我不需要JSON,我想要對象。)

據我了解,如果某些內容已經讀取了Request.Content,這就是我期望的行為。 內容流不可倒帶,並設置為最后一個字節; 但是.ReadAsStringAsync()和.ReadAsByteArrayAsync()通過(我認為)復制流並自己處理流來解決此問題。

我從使用HttpClient的WPF應用程序調用此方法。 樣品通話...

using (HttpClient http = API.GetHttpClient())
{
  string url = string.Format("{0}/User", thisApp.WebAPI_BaseUrl);
  RILogManager.Default.SendString("url", url);

  JsonMediaTypeFormatter formatter = new JsonMediaTypeFormatter() ;
  formatter.SerializerSettings.ReferenceLoopHandling = Newtonsoft.Json.ReferenceLoopHandling.Ignore;

  HttpResponseMessage response;

  response = http.PutAsync<User>(url, user, formatter, "application/json").Result;
  ...

我的“ API.GetHttpClient()”例程如下所示。 您可以看到我正在使用DelegateHandler在客戶端進行一些JWT工作,但是我認為這並不重要。 它不涉及傳出的請求,僅涉及傳入的響應。

 public static HttpClient GetHttpClient(bool WithAuthToken = true)
 {
     App thisApp = (App)System.Windows.Application.Current;

     //HttpClient http = new HttpClient();
     HttpClient http = HttpClientFactory.Create(new JWTExpirationHandler());

     http.BaseAddress = new Uri(thisApp.WebAPI_BaseUrl);
     http.DefaultRequestHeaders.Accept.Clear();
     http.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));

     if(WithAuthToken)
         http.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", JWT);

     return http;

 }

我已經確認傳入請求是“ application / json”和UTF-8的Content-type。

我在Web服務器上有兩個DelegatingHandlers,但這似乎不是問題,因為當我在第一個的頂部執行ReadAsAsync()時,它也為null。 ReadAsStringAsync()返回JSON。

所以...我在做什么錯? 再次,這很好,並且發生了一些變化,我所有的 POST和PUT都以這種方式破壞了。

我看到一些鏈接說要從我的類中刪除[Serializable],但是這些鏈接是我在很多地方使用的Entity Framework類,所以我不想這樣做。

最后...當我通過郵遞員將此更新稱為PUT時,它可以工作。

UPDATE
比較我自己的客戶端和Postman的HttpRequest,我發現前者是“分塊的”,而后者則不是。 這似乎是一個重要的線索。 我看到其他一些人正在處理相同的問題:

ASP.NET Web Api-使用分塊傳輸編碼時,框架未將JSON轉換為對象

我找不到任何有關如何關閉分塊的明確指示。 確實看到有一個屬性可以關閉分塊,但是這樣做沒有幫助。

問題:觸發“選擇”的原因是什么? 是客戶選擇執行此操作,還是選擇Controller,還是兩者之間進行一些協商?

那是一個漫長的過程。

不知道它是怎么到達那里的,但是在我的.csproj中,我有這個:

<Reference Include="System.Net.Http, Version=4.1.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
  <HintPath>..\packages\System.Net.Http.4.3.0\lib\net46\System.Net.Http.dll</HintPath>
  <Private>True</Private>
</Reference>

而不是這樣:

<Reference Include="System.Net.Http" />

在我的App.config中,我有以下內容:

  <dependentAssembly>
    <assemblyIdentity name="System.Net.Http" publicKeyToken="b03f5f7f11d50a3a" culture="neutral" />
    <bindingRedirect oldVersion="0.0.0.0-4.1.1.0" newVersion="4.1.1.0" />
  </dependentAssembly>
  <dependentAssembly>
    <assemblyIdentity name="System.Diagnostics.DiagnosticSource" publicKeyToken="cc7b13ffcd2ddd51" culture="neutral" />
    <bindingRedirect oldVersion="0.0.0.0-4.0.1.0" newVersion="4.0.1.0" />
  </dependentAssembly>

...而不是... 不是這個。 我不需要這個東西。 我剛拿出來

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM