标签: dotnet-httpclient

while循环中的HttpClient只执行一次

我试图在 for 循环内调用 HttpClient 请求,如下所示。它需要对第三方rest api进行多次连续调用。但它只在循环退出时给我第一个服务调用结果,然后再从其余的服务调用中获取结果。

 private void Search()
            {
                try
                {
                    var i = 1;
                    using (var httpClient = new HttpClient())
                    {
                        while (i < 5)
                        {
                            string url = "https://jsonplaceholder.typicode.com/posts/" + i;
                            var response = httpClient.GetAsync(url).Result;
                            string jsonResult = response.Content.ReadAsStringAsync().Result;
                            Console.WriteLine(jsonResult.ToString());
                         i++;                     
                        }

                    }
                }
                catch (Exception ex)
                {
                    Console.WriteLine(ex.ToString());
                }
            }
Run Code Online (Sandbox Code Playgroud)

当我使用调试点运行时,程序会给出所有结果。但是当我在没有调试点的情况下运行它时,它只给出第一个结果。

我也尝试使用 async、await 方法。它也给了我同样的结果。

我觉得程序需要等待异步调用返回数据。

请帮我解决这个问题。

编辑-异步方式

private async Task<string> SearchNew()
        {
            try
            {
                var i = 1;
                var res = string.Empty;
                using (var httpClient = …
Run Code Online (Sandbox Code Playgroud)

c# dotnet-httpclient asp.net-core-mvc .net-core

3
推荐指数
1
解决办法
2965
查看次数

如何正确配置HttpClient的大文件流传输?

微软的HttpClient官方文档指出,如果我们想使用HttpClient下载大文件,我们应该

流式传输这些下载而不使用默认缓冲。如果使用默认缓冲,客户端内存使用量将变得非常大,可能导致性能大幅下降。

默认缓冲是什么?我们如何更改它,以便无论我们最终下载的文件大小如何,都不会遇到上述问题?

虚拟代码片段将不胜感激!

c# dotnet-httpclient

3
推荐指数
1
解决办法
2480
查看次数

如何将 Content-Type: application/octet-stream 添加到 .Net Core 标头

我想实现这个,有什么技巧吗

HttpClient c = new HttpClient();
c.DefaultRequestHeaders.Add("Content-type", "application/octet-stream"));
Run Code Online (Sandbox Code Playgroud)

dotnet-httpclient .net-core asp.net-core

3
推荐指数
1
解决办法
5689
查看次数

重新设置单例httpclient的证书(Reconfiguring IHttpclientFactory?)

使用 C#、.NET Core 3.1

httpclient通过 in添加一个单例startup.cs

services.AddHttpClient<IClientLogic, ClientLogicA>().ConfigurePrimaryHttpMessageHandler(() =>
{
   var handler = new HttpClientHandler();
   
   var cert= GetCertFromX();

   handler.ClientCertificates.Add(cert);

   return handler;
});
Run Code Online (Sandbox Code Playgroud)

但是,假设稍后在ClientLogicA课堂上,我想更改证书,我该如何执行此操作,并且更改是否会持续存在以供将来使用 httpclient 单例?

c# dependency-injection dotnet-httpclient asp.net-core httpclientfactory

3
推荐指数
1
解决办法
1595
查看次数

使用具有不同配置的自定义 HttpMessageHandler

我有一个自定义HttpMessageHandler实现:

public class MyHandler : DelegatingHandler
{
    private readonly HttpClient _httpClient;
    private readonly MyHandlerOptions _config;

    public MyHandler(
        HttpClient httpClient,
        IOptions<MyHandlerOptions> options)
    {
        _httpClient = httpClient;
        _config = options.Value;
    }

    protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
    {
        request.Headers.Authorization = await GetAccessToken()
        return await base.SendAsync(request, cancellationToken);
    }

    private async Task<string> GetAccessToken()
    {
        //some logic to get access token using _httpClient and _config
    }

}
Run Code Online (Sandbox Code Playgroud)

它需要配置对象MyHandlerOptions。它的形式在这里并不那么重要。它基本上包含处理程序需要的 clientId、clientSecret 等,以了解如何获取访问令牌。

我有一些需要使用的服务(类型化的http客户端)MyHandler

//registration of MyHandler itself
builder.Services.AddHttpClient<MyHandler>();

//configuration …
Run Code Online (Sandbox Code Playgroud)

.net c# dependency-injection dotnet-httpclient

3
推荐指数
1
解决办法
1857
查看次数

HttpClient在某些情况下修改BaseAddress

在基本层面上,我应该能够设置绝对值BaseAddressHttpClient然后使用相对值发送 Http 请求Uri。期望的是相对的Uri将附加到基地址以进行 Http 调用。大多数情况下它都会这样做。这个例子效果很好。

编辑:见底部。从 Uris 的构建方式来看,这似乎是一种奇怪的行为。

var httpClient = new HttpClient() { BaseAddress = new Uri("http://restcountries.eu/rest/", UriKind.Absolute) };
var requestMessage = new HttpRequestMessage(HttpMethod.Get, new Uri("v2", UriKind.Relative));
var httpResponseMessage = await httpClient.SendAsync(requestMessage);
var json = await httpResponseMessage.Content.ReadAsStringAsync();
Run Code Online (Sandbox Code Playgroud)

提琴手网址:

获取http://restcountries.eu/rest/v2 HTTP/1.1

我有一个本地 API。当我在本地 API 上运行等效项时,调用会截断部分基地址(“Api”)。

var httpClient = new HttpClient() { BaseAddress = new Uri($"http://localhost/JsonPerson/Api", UriKind.Absolute) };
var requestMessage = new HttpRequestMessage(HttpMethod.Get, new Uri("GetApiPerson", UriKind.Relative));
var httpResponseMessage = await httpClient.SendAsync(requestMessage);
var …
Run Code Online (Sandbox Code Playgroud)

.net c# uri dotnet-httpclient

3
推荐指数
1
解决办法
1270
查看次数

在 HttpClient 上使用 DelegatingHandler 和自定义数据

考虑到使用 HttpClient 的众所周知的困境和问题 - 即套接字耗尽和不尊重 DNS 更新,最好的做法是使用 IHttpClientFactory 并让容器决定何时以及如何利用 http 池连接效率。这一切都很好,但现在我无法在每个请求上使用自定义数据实例化自定义 DelegatingHandler。

下面的示例说明了我在使用工厂方法之前是如何做到的:

public class HttpClientInterceptor : DelegatingHandler
{
    private readonly int _id;
    public HttpClientInterceptor(int id)
    {
        _id = id;
    }

    protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
    {
        // associate the id with this request
        Database.InsertEnquiry(_id, request);
        return await base.SendAsync(request, cancellationToken);
    }
}
Run Code Online (Sandbox Code Playgroud)

每次实例化 HttpClient 时,都可以传递一个 Id:

public void DoEnquiry()
{
    // Insert a new enquiry hypothetically 
    int id = Database.InsertNewEnquiry();
    using (var http = new HttpClient(new HttpClientInterceptor(id))) …
Run Code Online (Sandbox Code Playgroud)

c# dotnet-httpclient .net-core

3
推荐指数
1
解决办法
3794
查看次数

如何“独立”使用PolicyHttpMessageHandler?

我只是想创建一个简单的测试,在其中实例DelegateHandlers化 aHttpClient而不带 Asp.net Core 包。我有 2 个删除处理程序

  • ThrottlingDelegatingHandler
  • PolicyHttpMessageHandler(来自波莉包)

我怎样才能将两者结合起来并传递给HttpClient

var policy = HttpPolicyExtensions.HandleTransientHttpError().CircuitBreakerAsync(5, TimeSpan.FromSeconds(30));
var pollyHandler = new PolicyHttpMessageHandler(policy);
var http = new HttpClient(new ThrottlingDelegatingHandler(MaxParallelism, pollyHandler));
Run Code Online (Sandbox Code Playgroud)

上面给了我一个错误:System.InvalidOperationException : The inner handler has not been assigned.

没有PolicyHttpMessageHandler可以传递 的构造函数innerHandler

我怎样才能做到这一点?

.net c# dotnet-httpclient polly .net-6.0

3
推荐指数
1
解决办法
1491
查看次数

Polly 重试不会关闭现有的 HttpClient 调用

我使用 Polly 来处理一些场景,例如请求限制和超时。这些策略直接添加到 Startup.cs 中,如下所示:

var retries = //applying the retries, let say I set to 25 times with 10s delay. Total 250s.

serviceCollection
    .AddHttpClient<IApplicationApi, ApplicationApi>()
    .AddPolicyHandler((services, request) => GetRetryPolicy<ApplicationApi>(retries, services));
Run Code Online (Sandbox Code Playgroud)

政策:

static IAsyncPolicy<HttpResponseMessage> GetRetryPolicy<T>(List<TimeSpan> retries, IServiceProvider services)
{
    return HttpPolicyExtensions
        .HandleTransientHttpError()
        .OrResult(msg => msg.StatusCode == System.Net.HttpStatusCode.TooManyRequests)
        .WaitAndRetryAsync(retries,
            onRetry: (outcome, timespan, retryAttempt, context) =>
            {
                //do some logging
            }
}
Run Code Online (Sandbox Code Playgroud)

在 ApplicationApi.cs 中执行如下操作:

private readonly HttpClient _httpClient;
public ApplicationApi(HttpClient httpClient)
{
    _httpClient = httpClient;
}
       
public void CallApi()
{ 
      var …
Run Code Online (Sandbox Code Playgroud)

.net c# dotnet-httpclient .net-core polly

3
推荐指数
1
解决办法
2043
查看次数

Blazor WASM Http 调用未命中某些 API 端点。而是接收index.html

我有一个 Blazor WASM 页面,需要进行调用以从 API 获取一些数据。Blazor 应用程序由 ASPNetCore 托管,并且托管应用程序包含 API。

我的一些端点可以工作,但一些调用会引发 Json 序列化异常。

渲染组件未处理的异常:“<”是值的无效开头。路径: $ | 行号: 0 | 内联字节位置:0。

如果我查看服务器的实际响应,它看起来像是从我的 WASM 应用程序返回 index.html 的内容。

控制器示例

[Authorize]
[ApiController]
[Route("api/[controller]")]
public class CompanyController : ControllerBase
{
    private readonly ApplicationDbContext _context;

    public CompanyController(ApplicationDbContext context)
    {
         _context = context;
    }

    [HttpGet("{id}")]
    public async Task<IActionResult> Get(long id)
    {
        Company? company = await _context.Companies.FindAsync(id);
        if (company == null)
        {
            return NotFound();
        }

        return Ok(company);
    }
}
Run Code Online (Sandbox Code Playgroud)

Blazor 页面示例


@page "/companies/{id:long}"
@attribute [Authorize]
@inject HttpClient Http …
Run Code Online (Sandbox Code Playgroud)

dotnet-httpclient asp.net-core blazor blazor-webassembly

3
推荐指数
1
解决办法
1446
查看次数