Loading [MathJax]/jax/output/CommonHTML/config.js
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >我又踩坑了!如何为HttpClient请求设置Content-Type标头?

我又踩坑了!如何为HttpClient请求设置Content-Type标头?

作者头像
有态度的马甲
发布于 2020-10-10 06:28:37
发布于 2020-10-10 06:28:37
9K00
代码可运行
举报
文章被收录于专栏:精益码农精益码农
运行总次数:0
代码可运行

最近在重构认证代码,认证过程相当常规:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
POST   /open-api/v1/user-info?client_id&timstamp&rd=12345&sign=***&method=hmac
content-type: application/json
payload: { "token":"AA2917B0-C23D-40AB-A43A-4C4B61CC7C74"}

平台显示 :签名校验失败, 排查到平台收到的Post Payload并非预期,阅读本文,解锁正确使用Content-Type标头的姿势。

1. 入坑

下面是构造HttpClient对象、发起请求的代码:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
// 初始化HttpClientFactory
context.Services.AddHttpClient("platform", c =>
{
    c.BaseAddress = new Uri("https://alpha-engage.demohost.com/");
    c.DefaultRequestHeaders.Accept
    .Add(new MediaTypeWithQualityHeaderValue("application/json"));
})...

// 产生命名HttpClient,发起请求
 var client = _clientFactory.CreateClient("platform");
 var response = await client.PostAsync($"open-api/v1/user-token/info?{req.AuthString()}",new StringContent(req.ReqPayload.ToString(),Encoding.UTF8) );

平台日志显示,收到的请求payload:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
{\"token\":\"AA2917B0-C23D-40AB-A43A-4C4B61CC7C74\"}

额,平台收到的JSON数据被转码了,没有识别出JSON? 明眼人一看,HttpClient请求没有设置Content-Type,接收端没有识别出JSON 格式的payload , 进行了转码,生成了错误签名。

① Content-Type是一个Entity Header,指示资源的mediaType ,可用在请求/响应中 ② 代码中new StringContent(req.ReqPayload.ToString(),Encoding.UTF8) 没有指定mediaType参数,故函数会使用text/plain默认值

------------------------------------------

当我尝试添加Content-Type时(下面黄色背景行代码):

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
context.Services.AddHttpClient("platform", c =>
{
    c.BaseAddress = new Uri("https://alpha-engage.demohost.com/");
    c.DefaultRequestHeaders.Accept
         .Add(new MediaTypeWithQualityHeaderValue("application/json"));//ACCEPT header
    c.DefaultRequestHeaders.Add("content-type", "application/json");
})

此时抛出以下异常:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
InvalidOperationException: Misused header name. Make sure request headers are used with
HttpRequestMessage, response headers with HttpResponseMessage, and
content headers with HttpContent objects. 

纳尼,HttpContent Headers是啥?Chrome dev tools显示只有两种Header啊?

2. 爬坑

官方资料显示:HTTP Headers被分为如下四类:

---

信息

举例

.NET类型

General Header

可同时作用在请求/响应中,但是与传输数据无关

Upgrade、Connection

---

Request Header

将要获取的资源或客户端本身的信息

Accept、Authorization

HttpRequestHeaders

Response Header

响应信息

Location、ETag

HttpResponseHeaders

EntityHeader

实体Body额外的信息

Content-Length、Connection

HttpContentHeaders

Content-Type属于Entity Header的一种,对应.NET类型 HttpContent Header;

虽然Entity Header不是请求标头也不是响应标头,它们还是会包含在请求/响应标头术语中(此说法来自官方)。

所以我们在Chrome DevTools没有看到Entity Headers分组, 却常在请求/响应标头中看到Content-Type标头。

回到上面的异常,.NET 严格区分四种标头,所以c.DefaultRequestHeaders.Add("content-type", "application/json") 尝试将content-type添加到请求头,姿势不正确,.NET提示InvalidOperationException。

3. 填坑

给这个常规的Post请求设置正确的Content-Type标头。

方法① 对HttpRequestMessage对象Content属性添加Header

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 using (var request = new HttpRequestMessage())
{
     request.Method = new HttpMethod(method);
     request.RequestUri = new Uri(url);
     request.Content = new StringContent(payload);
     request.Content.Headers.ContentType = new MediaTypeHeaderValue("application/json");
     var response = await _httpClient.SendAsync(request);
     return response;
}

使用HttpClient.SendAsync(request)

方法② 写入HttpContent时传入媒体类型

StringContent某个重载构造函数 : 参数3 可直接设置media type

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
var response = await client.PostAsync($"open-api/v1/user-token/info?{req.AuthString()}",new StringContent(req.ReqPayload.ToString(),Encoding.UTF8,"application/json") );

4.干货旁白

  1. 小编对于Http协议有知识漏洞,搬砖时一直关注Chrome DevTools,忽略了还有Entity Header一说。
  2. Content-Type 这个实体标头,会出现了请求/响应标头,指示资源的媒体类型。
  3. .NTE针对4种HTTP Header强化了区别,在实际开发中要区别使用。
  • https://tools.ietf.org/html/rfc2616#page-41
  • https://developer.mozilla.org/en-US/docs/Glossary/Entity_header
本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2020-09-29,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 精益码农 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
ASP.NET Core 中简单使用 HttpClient 集成 Elasticsearch 实现日志记录与查询
在开发中,将系统日志集中管理并支持实时搜索是提升运维效率的重要手段。本文将介绍如何在 ASP.NET Core 项目中通过 HttpClient 与 Elasticsearch 进行集成,实现日志的自动记录、索引和查询功能。
郑子铭
2025/07/12
870
ASP.NET Core 中简单使用 HttpClient 集成 Elasticsearch 实现日志记录与查询
C# HttpClient 请求认证、数据传输笔记
客户端请求服务器时,需要通过授权认证许可,方能获取服务器资源,目前比较常见的认证方式有 Basic 、JWT、Cookie。
痴者工良
2021/04/26
2.8K0
win10 uwp httpClient 登陆CSDN
我们可以使用下面代码让 HttpClient 使用 Cookie ,有了这个才可以保存登陆,不然登陆成功下次访问网页还是没登陆。
林德熙
2022/08/04
4800
HttpClient的用法
HttpClient 是 .NET 平台上用于发出 HTTP 请求和处理响应的常用工具。它提供了异步友好的代码编写方式,并且可以配置各种选项以满足不同的需求。
软件架构师Michael
2025/07/16
1890
HttpClient 调用WebAPI时—传参的三种方式(ASP.NET MVC&CORE均适用)
代码里有注释: 方法一,传json参数 方法二,传表单参数 方法三,传字节流 public void Post() { //方法一,传json参数 var d = new { username = " ", password = " ", grant_type = "password", appcode = " ",
红目香薰
2022/11/29
1.2K0
Apache HttpClient 5 使用详细教程
超文本传输协议(HTTP)可能是当今互联网上最重要的协议之一,Web 服务、微服务以及支持网络的各种设备上的服务几乎都是 HTTP 协议,HTTP 协议已经从 Web 浏览器走向了更广泛的使用场景。
未读代码
2022/11/21
7.6K0
Apache HttpClient 5 使用详细教程
调用HttpClient.PostAsync时传token等值
GoodTime
2023/10/31
3960
HttpClient测试框架
HttpClient是模拟Http协议客户端请求的一种技术,可以发送Get/Post等请求。 所以在学习HttpClient测试框架之前,先来看一下Http协议请求,主要看请求头信息。
yuanyuan
2019/09/02
1.2K0
HttpClient测试框架
HttpClient介绍
使用RestSharp 库消费Restful Service 中介绍了一个开源的Http Client库RestSharp。在ASP.NET MVC 4中也带来.NET框架中的Http Client。它提供了一个灵活的、可扩展的API来访问一切通过HTTP公开的RESTful服务。HttpClient是ASP.NET Web API 的一部分,直接包含在.NET 4.5中,也可以单独安装ASP.NET MVC4,可以通过Nuget包获取,包里面包含以下3部分: System.Net.Http: The ma
张善友
2018/01/19
1.5K0
HttpClient介绍
四种为HttpClient添加默认请求报头的解决方案
HttpClient在Web调用中具有广泛的应用,而为它添加默认请求头是我们经常遇到的需求,本文介绍4种为HttpClient添加默认请求头的方式。
蒋金楠
2019/09/29
1.1K0
封装httpClient工具类进行get、post、put、delete的http接口请求,可添加请求头与参数,支持多线程
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/157763.html原文链接:https://javaforall.cn
全栈程序员站长
2022/09/18
3K0
.Net Core HttpClient处理响应压缩「建议收藏」
在上篇文章[ASP.NET Core中的响应压缩]中我们谈到了在ASP.NET Core服务端处理关于响应压缩的请求,服务端的主要工作就是根据Content-Encoding头信息判断采用哪种方式压缩并返回。之前在群里有人问道过,现在的网络带宽这么高了还有必要在服务端针对请求进行压缩吗?确实,如今分布式和负载均衡技术这么成熟,很多需要处理高并发大数据的场景都可以通过增加服务器节点来进行。但是,在资源受限的情况下,或者是还没必要为了某一个点去增加新的服务器节点的时候,我们还是要采用一些程序本身的常规处理手段来进行处理。笔者个人认为响应压缩的使用场景是这样的,在带宽压力比较紧张的情况,且CPU资源比较充足的情况下,使用响应压缩整体效果还是比较明显的。
全栈程序员站长
2022/09/14
8040
.NET Core 3.0深入源码理解HttpClientFactory之实战
前面两篇文章透过源码角度,理解了HttpClientFactory的内部实现,当我们在项目中使用时,总会涉及以下几个问题:
AI.NET 极客圈
2019/08/06
1.3K0
asp.net web api客户端调用
服务接口 接口1: //Post:http://127.0.0.1/HY_WebApi/api/V2/Key/FunctionTest1 [HttpPost] public HttpResponseMessage FunctionTest1(Model1 model) { ...... } 接口2: //Post:http://127.0.0.1/HY_WebApi/api/V2/Key/FunctionTest2 [HttpPost] public HttpResponseMess
甜橙很酸
2018/03/08
3.7K0
花样试用微软语音服务晓晓
受微软美女员工 Grace Peng 邀请(也可能是套路???),参加微软神经语音(没错,就是神经)晓晓的试用,首先是看到了群里面的消息,然后就是发送申请,等待回复,过了几天后,收到了一个机器人发来的账号密码,告诉我已经帮我申请了免费试用的账号,直接登录即可使用了。其实一直都有接触各种 TTS 的服务,但是在测试微软晓晓的过程中发现,在拟人方面,晓晓的发音似乎被训练得很不错,在语法方面,晓晓支持 SSML 语法,具体参见:https://www.w3.org/TR/speech-synthesis/ 什么是 SSML,来自百度百科 语音合成标记语言 的解释。
梁规晓
2019/04/22
5.8K0
花样试用微软语音服务晓晓
Java:HttpClient篇,HttpClient4.2在Java中的几则应用:Get、Post参数、Session(会话)保持、Proxy(代理服务器)设置,多线程设置...
新版HttpClient4.2与之前的3.x版本有了很大变化,建议从http://hc.apache.org/处以得到最新的信息。
bear_fish
2018/09/19
2.7K0
win10 uwp httpClient 登陆CSDN
我们可以使用下面代码让 HttpClient 使用 Cookie ,有了这个才可以保存登陆,不然登陆成功下次访问网页还是没登陆。
林德熙
2018/09/19
6470
win10 uwp httpClient 登陆CSDN
C#中的HTTP客户端:专家级最佳实践与性能优化指南
在微服务架构中,或与外部API通信时,HTTP客户端是必不可少的组件。然而,许多开发人员在实现HTTP客户端时未能充分考虑性能和可用性。
郑子铭
2025/04/21
3440
C#中的HTTP客户端:专家级最佳实践与性能优化指南
Asp.Net WebAPI核心对象解析(三)
该文章介绍了.NET 4.5之前和之后版本对HTTP编程模型的不同之处,主要从请求和响应方面进行对比,并分析了.NET 4.5版本对HTTP编程模型的改进和优化。
彭泽0902
2018/01/04
3.4K0
Asp.Net WebAPI核心对象解析(三)
ASP.NET Web API编程——控制器
1控制器操作的参数 控制器操作的参数可以是内置类型也可以是自定义类型,无参也是允许的。 2控制器操作返回值 类型 说明 void 操作返回值为void时,Web API返回空HTTP响应,其状态码为204(无内容) HttpResponseMessage Web api会将此返回值直接转换为HTTP消息 IHttpActionResult 接口形式 内置类型或自定义类型 无 2.1返回值为HttpResponseMess
甜橙很酸
2018/04/17
2.7K0
推荐阅读
相关推荐
ASP.NET Core 中简单使用 HttpClient 集成 Elasticsearch 实现日志记录与查询
更多 >
交个朋友
加入[后端] 腾讯云技术交流站
后端架构设计 高可用系统实现
加入腾讯云运维技术交流群
云平台运维技巧 分布式系统排障
加入云开发企业交流群
企业云开发实战交流 探讨技术架构优化
换一批
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验