ASP.NET Core 中的 PostAsJsonAsync 方法在哪里?

Posted

技术标签:

【中文标题】ASP.NET Core 中的 PostAsJsonAsync 方法在哪里?【英文标题】:Where is the PostAsJsonAsync method in ASP.NET Core? 【发布时间】:2016-10-13 17:23:34 【问题描述】:

我在 ASP.NET Core 中寻找 PostAsJsonAsync() 扩展方法。 Based on this article,它在 Microsoft.AspNet.WebApi.Client 程序集中可用。

我原以为 Microsoft 已将所有程序集名称从 Microsoft.AspNet 更改为 Microsoft.AspNetCore 以更具体地用于 .NET Core,但是,我找不到 Microsoft.AspNetCore.WebApi.Client 程序集。

ASP.NET Core 中的PostAsJsonAsync() 扩展方法在哪里?

【问题讨论】:

它不是 ASP.NET Core 项目的一部分,因此不遵循 Microsoft.AspNetCore.* 命名架构。它最初是基于System.Runtime 和.NET Core 的Windows 8/81./10/UWP/WinRT 应用程序的扩展 这样扩展在 .Net Core 中不可用? 除非您将此包添加到您的项目中,否则它不可用。这是HttpClient 分机号。与 ASP.NET 或 ASP.NET Core 完全无关。正如nuget.org/packages/Microsoft.AspNet.WebApi.Client 所见,它既不依赖于 ASP.NET MVC5,也不依赖于 ASP.NET Core MVC。不过,它应该适用于 .NET Core,因为它是针对 :NET 4.5 和 Win8/8.1 的 PCL。您只需要 project.json 中的 "import": [ "portable-net45+win8" ] 语句 Send HTTP POST message in ASP.NET Core using HttpClient PostAsJsonAsync的可能重复 【参考方案1】:

它是库的一部分 Microsoft.AspNet.WebApi.Client https://www.nuget.org/packages/Microsoft.AspNet.WebApi.Client/

【讨论】:

我想这应该是现在的正确答案了。该软件包可用并支持 .Net 标准 2.0 Microsoft.AspNet.WebApi.Client 不适用于 .net Core【参考方案2】:

我不应该为此获得任何荣誉。在以下链接中查看@danroth27 的答案。

https://github.com/aspnet/Docs/blob/master/aspnetcore/mvc/controllers/testing/sample/TestingControllersSample/tests/TestingControllersSample.Tests/IntegrationTests/HttpClientExtensions.cs

他使用了扩展方法。代码如下。 (从上面的github链接复制)。我在 .Net Core 2.0 上使用它。

using System.Net.Http;
using System.Net.Http.Headers;
using System.Threading.Tasks;
using Newtonsoft.Json;

namespace TestingControllersSample.Tests.IntegrationTests

    public static class HttpClientExtensions
    
        public static Task<HttpResponseMessage> PostAsJsonAsync<T>(
            this HttpClient httpClient, string url, T data)
        
            var dataAsString = JsonConvert.SerializeObject(data);
            var content = new StringContent(dataAsString);
            content.Headers.ContentType = new MediaTypeHeaderValue("application/json");
            return httpClient.PostAsync(url, content);
        

        public static async Task<T> ReadAsJsonAsync<T>(this HttpContent content)
        
            var dataAsString = await content.ReadAsStringAsync();
            return JsonConvert.DeserializeObject<T>(dataAsString);
        
    

【讨论】:

该链接不再有效。 github.com/dotnet/corefx/issues/26233 与上面投票率很高的评论一样,微软现在推荐 NuGet 包。【参考方案3】:

.NET 5.0 开始,这已通过 System.Net.Http.Json 命名空间作为 HttpClient 的扩展方法(重新)引入。有关详细信息,请参阅HttpClientJsonExtensions 类。

演示

它的工作原理如下:

var httpClient  = new HttpClient();
var url         = "https://***.com"
var data        = new MyDto();
var source      = new CancellationTokenSource();

var response    = await httpClient.PostAsJsonAsync<MyDto>(url, data, source.Token);

当然,您还需要引用一些命名空间:

using System.Net.Http;          //HttpClient, HttpResponseMessage
using System.Net.Http.Json;     //HttpClientJsonExtensions
using System.Threading;         //CancellationToken
using System.Threading.Tasks;   //Task

或者,如果您使用的是.NET 6 SDK's implicit using directives,则会为您提供其中三个,因此您只需要:

using System.Net.Http.Json;     //HttpClientJsonExtensions

背景

这是基于 the design document,以前是 referenced by @erandac — 尽管设计已经改变,特别是对于 PostAsJsonAsync() 方法。

显然,这并不能解决仍在使用 .NET Core 的任何人的问题,但使用 .NET 5.0 released,这是现在的最佳选择。

【讨论】:

此解决方案也适用于 .NET Core 3.0 及更高版本。需要添加 NuGet 包System.Net.Http.Json【参考方案4】:

这不是 ASP.NET Core 项目的一部分。但是您可以继续:

HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Post, "http://myurl/api");

string json = JsonConvert.SerializeObject(myObj);

request.Content = new StringContent(json, System.Text.Encoding.UTF8, "application/json");

HttpClient http = new HttpClient();
HttpResponseMessage response = await http.SendAsync(request);

if (response.IsSuccessStatusCode)
                    
    
else
    
    

【讨论】:

记得释放 request 和 http 变量。【参考方案5】:

您可以使用此扩展在 ASP.NET 核心中使用 PostAsJsonAsync 方法

using System.Net.Http;
using System.Net.Http.Headers;
using System.Threading.Tasks;
using Newtonsoft.Json;
public static class HttpClientExtensions

    public static Task<HttpResponseMessage> PostAsJsonAsync<T>(this HttpClient httpClient, string url, T data)
    
        var dataAsString = JsonConvert.SerializeObject(data);
        var content = new StringContent(dataAsString);
        content.Headers.ContentType = new MediaTypeHeaderValue("application/json");

        return httpClient.PostAsync(url, content);
    

    public static Task<HttpResponseMessage> PutAsJsonAsync<T>(this HttpClient httpClient, string url, T data)
    
        var dataAsString = JsonConvert.SerializeObject(data);
        var content = new StringContent(dataAsString);
        content.Headers.ContentType = new MediaTypeHeaderValue("application/json");

        return httpClient.PutAsync(url, content);
    

    public static async Task<T> ReadAsJsonAsync<T>(this HttpContent content)
    
        var dataAsString = await content.ReadAsStringAsync().ConfigureAwait(false);

        return JsonConvert.DeserializeObject<T>(dataAsString);
    

见:httpclient-extensions

【讨论】:

【参考方案6】:

这来晚了,但我认为它可能会帮助某人。所以*AsJsonAsync() 方法不是 ASP.NET Core 项目的一部分。我创建了一个为您提供功能的包。你可以在 Nuget 上获得它。

https://www.nuget.org/packages/AspNetCore.Http.Extensions

using AspNetCore.Http.Extensions;
...
HttpClient client = new HttpClient();
client.PostAsJsonAsync('url', payload);

【讨论】:

【参考方案7】:

您需要将 Nuget 包 System.Net.Http.Formatting.Extension 添加到您的项目中。

或者你可以使用

client.PostAsync(uri, new StringContent(data, Encoding.UTF8, "application/json"));

【讨论】:

这个问题专门围绕辅助方法PostAsJsonAsync【参考方案8】:

方法PostAsJsonAsync(以及HttpClient 类的其他*Async 方法) 确实是开箱即用的 - 无需使用指令。

您的.csproj 文件应以&lt;Project Sdk="Microsoft.NET.Sdk.Web"&gt; 开头, 并包含行

<ItemGroup>
    <PackageReference Include="Microsoft.AspNetCore.App" />
</ItemGroup>

我认为这是重复的,并在以下位置给出了更详细的答案 https://***.com/questions/37750451#58169080.

(.NET Core 3.0 不再需要 PackageReference。)

【讨论】:

【参考方案9】:

为了继续上面的答案,我需要添加一个小补充来让它工作。

以前我使用PostAsJsonAsync() 方法使用.NET Core 2.1 Web 应用程序,当我升级到.NET Core 3.1 时它不再工作。

我无法得到上述答案,结果证明是因为要发布的文本必须用引号括起来,并且其中的任何引号都必须转义。我做了以下扩展方法,解决了我的问题:

public static async Task<HttpResponseMessage> PostJsonAsync(this HttpClient client, string uri, string json)

    //For some reason, not doing this will cause it to fail:
    json = $"\"json.Replace("\"", "\\\"")\"";

    return await client.PostAsync(uri, new StringContent(json, Encoding.UTF8, "application/json"));

请注意,我使用的是 System.Text.Json.JsonSerializer,而不是 Newtonsoft 版本。

【讨论】:

【参考方案10】:

使扩展方法真正异步:

public static async Task<HttpResponseMessage> PostAsJsonAsync<T>(
    this HttpClient httpClient, string url, T data)

    var dataAsString = JsonConvert.SerializeObject(data);
    var content = new StringContent(dataAsString);
    content.Headers.ContentType = new MediaTypeHeaderValue("application/json");
    return await httpClient.PostAsync(url, content);

【讨论】:

【参考方案11】:

如果您尝试在 Blazor 中使用 PostJsonAsync、PutJsonAsync 或任何其他 json 扩展方法,则需要添加以下语句

using Microsoft.AspNetCore.Components;

【讨论】:

【参考方案12】:

Dotnet core 3.x 运行时本身将为使用 System.Text.Json Serializer 的 HttpClient 提供一组扩展方法

https://github.com/dotnet/designs/blob/main/accepted/2020/json-http-extensions/json-http-extensions.md

【讨论】:

【参考方案13】:

如果您在 2021 年并且拥有 .Net Core 3.1,请确保在您的项目文件 csproj 中,Microsoft.AspNetCore.App 是最新的,最新的是 2.2.8。您可以检查和更新包如下:

<ItemGroup>
    ...
    <PackageReference Include="Microsoft.AspNetCore.App" Version="2.2.8" />
    ...
</ItemGroup>

然后像这样从 cli 恢复您的项目:

dotnet restore

【讨论】:

这与PostAsJsonAsync() 方法有什么关系?目前尚不清楚这如何解决这个问题。【参考方案14】:

我在标准 2.0 库中使用了这个

System.Net.Http.Json

【讨论】:

【参考方案15】:
using Microsoft.AspNetCore.Blazor.HttpClient

【讨论】:

我找不到任何证据表明该课程存在于此类中——或者,事实上,甚至找不到此类的文档。我并不是说它不存在,只是读者很难找到有关如何仅通过命名空间引用使用它的信息。您能否更新您的答案以至少包括一个工作示例,最好是文档链接?另外,这是否依赖于Microsoft.AspNetCore.Blazor.HttpClient(预览版)包?如果是这样,请务必注意。 The best documentation I can find 实际上指向 .NET 5.0(预览版)BCL — 如果您使用它,则不需要依赖 Blazor 包。我有 added an answer,它为那些正在从 .NET Core 迁移到 .NET 5.0 的人提供有关 .NET 5.0 版本的信息。

以上是关于ASP.NET Core 中的 PostAsJsonAsync 方法在哪里?的主要内容,如果未能解决你的问题,请参考以下文章

Asp.Net Core 中的静态文件

ASP.NET Core 2.0中的HttpContext

Asp.Net Core 中的静态文件

详解Asp.Net Core中的Cookies

ASP.NET Web API 与 ASP.NET Core 中的 URL 匹配差异

如何仅为 ASP.NET 5 (ASP.NET Core) 中的受保护操作添加令牌验证