跳转到主内容
新派编程网 - 新潮编程理念,全新技术课堂!

C#怎么使用HttpRequestMessage自定义请求_C#高级HTTP请求构建方法【进阶】

HttpRequestMessage本身不发送请求,仅作为请求容器;必须交由HttpClient.SendAsync执行,否则仅为“空壳”,常见错误是构造后未调用SendAsync导致静默卡住或ObjectDisposedException。 HttpRequestMessage 本身不发送请求,必须配 HttpClient.SendAsync
HttpRequestMessage
只是一个请求容器,它不包含网络能力。直接 new 它出来、设置
RequestUri
和
Headers
后,如果不交给
HttpClient
执行,就只是个“空壳”。常见错误是写完
var req = new HttpRequestMessage(...)
就以为万事大吉,结果没调用
client.SendAsync(req)
,程序静默卡住或抛
ObjectDisposedException
(因后续又用了已释放的 client)。 正确链路只有这一种: 创建
HttpClient
实例(推荐复用,别每次 new) 构造
HttpRequestMessage
,填好
Method
、
RequestUri
、
Content
(如有)、
Headers
传给
client.SendAsync(req)
,await 等待响应 手动调用
response.EnsureSuccessStatusCode()
检查状态码(
HttpClient
默认不抛异常) POST 带 JSON Body 时,Content-Type 必须显式设为 application/json 用
HttpRequestMessage
发送 JSON 数据,不能只靠
StringContent
构造时传入
"application/json"
,还要确认
Content.Headers.ContentType
确实生效。某些旧版 .NET Framework 下,如果没设或拼错,服务器可能返回 415 Unsupported Media Type。 安全写法:
var json = JsonSerializer.Serialize(data); var content = new StringContent(json, Encoding.UTF8, "application/json"); // 强制覆盖 ContentType,避免被中间层篡改 content.Headers.ContentType = new MediaTypeHeaderValue("application/json"); var request = new HttpRequestMessage(HttpMethod.Post, url) { Content = content };
注意:
StringContent
构造函数第三个参数是 MIME 类型,但内部不一定严格绑定到
Headers.ContentType
;显式赋值更可靠。 Authorization 头要加在 RequestMessage.Headers,不是 DefaultRequestHeaders 如果你用的是单次请求专用的
HttpRequestMessage
(比如不同请求带不同 token),授权头必须加在该实例的
Headers
上,而不是
HttpClient.DefaultRequestHeaders
。后者是全局默认头,一旦设置会污染所有后续请求——尤其在并发场景下极易导致 token 错乱。 C知道 CSDN推出的一款AI技术问答工具 下载 正确做法: 需要 per-request 鉴权:用
request.Headers.Add("Authorization", "Bearer xxx")
需要全局固定鉴权(如服务间调用统一 token):才设
client.DefaultRequestHeaders.Authorization
混用时注意清除:若某次请求不需要 auth,得手动
request.Headers.Remove("Authorization")
,否则继承了 client 的默认头 GET 请求带 Query 参数,别拼字符串,用 UriBuilder 或 QueryHelpers 手写
url + "?key=value&..."
容易出编码问题。中文、特殊符号(如
&
、
=
、空格)不 encode 会导致 400 Bad Request 或参数截断。 推荐两种方式: .NET Core 2.1+:用
Microsoft.AspNetCore.WebUtilities.QueryHelpers
(即使非 ASP.NET 项目也可 NuGet 引入
Microsoft.AspNetCore.WebUtilities
) 全平台兼容:用
UriBuilder
+
HttpUtility.ParseQueryString
示例(QueryHelpers):
var query = new Dictionary { ["q"] = "c# http", ["page"] = "1" }; var uri = new Uri($"{baseUrl}?{QueryHelpers.AddQueryString("", query)}"); var request = new HttpRequestMessage(HttpMethod.Get, uri);
这个细节在调试时很难定位——请求发出去了,服务器收不到完整参数,日志里也看不出拼接痕迹。

相关文章