Asp.net core 学习笔记 ( HttpClient )

2018-09-18html

core 2.1 以后有新的方案咯web

http://www.talkingdotnet.com/3-ways-to-use-httpclientfactory-in-asp-net-core-2-1/api

就是解决以前单列等等的问题.安全

给个例子 服务器

定义一个 serviceasync

public class ServerTaskHttpClient
{
    public HttpClient Client { get; private set; }

    public ServerTaskHttpClient(
        HttpClient httpClient,
        IConfiguration configuration
    )
    {
        httpClient.BaseAddress = new Uri(configuration["Origin"] + "/api");
        httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue(MediaTypeNames.Application.Json));
     // httpClient.DefaultRequestHeaders.Add(HeaderNames.ContentType, MediaTypeNames.Application.Json);  //注意, 放这里是错的, content-type 不是这里 set 的,而是经过 content Client
= httpClient; } }

startup.cs ide

加入依赖 providers学习

 services.AddHttpClient<ServerTaskHttpClient>();

在 controller 调用this

public class ResponseData {
    public bool successful { get; set; }
}
public async Task<IActionResult> Index()
{
    var content = new StringContent(JsonConvert.SerializeObject(new { name = "dada" }), Encoding.UTF8, MediaTypeNames.Application.Json);
    var result = await ServerTaskHttpClient.Client.PostAsync("/api/debug/clearImage", content);
    if (result.IsSuccessStatusCode)
    {
        var responseData = JsonConvert.DeserializeObject<ResponseData>(await result.Content.ReadAsStringAsync());
    }
    return View();
}

api spa

[HttpPost("clearImage")]
public async Task<IActionResult> ClearImage(Data data)
{
    return Ok(new { successful = true });
}

 

 

 

 

 

2017-09-25 

core 和 .net 4.5 同样均可以使用 HttpClient 

没什么特别的, 只是在学习的时候发现一个以前没留意到的问题. 

refer : 

https://aspnetmonsters.com/2016/08/2016-08-27-httpclientwrong/

http://byterot.blogspot.my/2016/07/singleton-httpclient-dns.html

http://www.cnblogs.com/dudu/p/csharp-httpclient-attention.html

https://docs.microsoft.com/en-us/aspnet/web-api/overview/advanced/calling-a-web-api-from-a-net-client

http://www.cnblogs.com/Wddpct/p/6229090.html

大体上说的是, HttpClient 不要使用 using, 由于它并不会释放 TCP 链接, 应该在整个应用里把 HttpClient 设置成单列 

 

core 要设置单列对象很容易 

public class VisautoHttpClient : HttpClient
{
    public VisautoHttpClient()
    {
        BaseAddress = new Uri("http://visauto.stooges.com.my");
        Timeout = TimeSpan.FromSeconds(30);
        DefaultRequestHeaders.Clear();
        DefaultRequestHeaders.Add("Accept", "text/html");
        DefaultRequestHeaders.Connection.Add("Keep-Alive"); 
    } 
}

定义好类, 因为每一个 TCP 的 baseAddress 不能换的,因此若是你有不少个不一样区的请求要发, 那么建议开多几个 HttpClient 实例.

keep-alive 的目的是让服务端知道咱们的链接不要立刻断开, 这样发多个请求的话能够快一些. 

而后在 startup.cs 提供服务就能够了. 

public void ConfigureServices(IServiceCollection services)
{ 
    // services 
    services.AddSingleton<VisautoHttpClient, VisautoHttpClient>();
}

core 会帮咱们搞定 singleton 的线程安全等问题. 不须要像从前还要用 lock 什么的那么麻烦了.

并且这里只是定义,一直到控制器注入时才会初始化实例哦.

在控制器注入了就能够发请求咯~

[Area("Web")]
public class HttpController : Controller
{
    public HttpController(
        VisautoHttpClient httpClient 
    )
    {
        this.httpClient = httpClient;
    }

    private HttpClient httpClient { get; set; }
        

    [Route("http")]
    public async Task<IActionResult> Index()
    {
        try
        {
            string x = await httpClient.GetStringAsync("");
        }
        catch (Exception ex)
        {

        }
        return View();
    }
}

 

note : 若是服务器 restart, 咱们的链接并不须要任何处理, 都是自动的. 放心, dns 的问题我没有遇到, 遇到了才打算呗. 

相关文章
相关标签/搜索