如何在.NET Framework 4.5中阻止HttpClient/RestSharp将查询串%2D转为短横线
问题根因
.NET Framework 4.5 中Uri类默认会对URL编码后的非保留字符(包括短横线-,对应编码值%2D)执行自动解码,这个行为发生在Uri对象构造阶段,后续不管用HttpClient还是RestSharp,只要底层依赖Uri类就会触发该转换。
解决方案
方案1:全局配置关闭Uri自动解码(最推荐)
直接在项目的app.config(桌面端)或web.config(Web端)的<configuration>节点下添加如下配置,全局禁用http/https协议的Uri自动解码行为:
<configuration> <uri> <schemeSettings> <add name="http" genericUriParserOptions="DontUnescapePathDotsAndSlashes"/> <add name="https" genericUriParserOptions="DontUnescapePathDotsAndSlashes"/> </schemeSettings> </uri> </configuration>
配置生效后,原有代码不需要做任何修改,new Uri(httpUrl)时会保留%2D不会自动转成短横线,直接用HttpClient或RestSharp发起请求即可。
方案2:单个Uri实例反射修改(不需要改全局配置)
如果不想影响项目其他业务的Uri行为,可以针对单个需要保留%2D的Uri实例通过反射修改内部值:
var httpUrl = "https://theapiendpointwithhex.com/api/order?orderid=bee3d72e%2D8170%2D4bad%2Dba95632b09de42ad"; Uri rsUri = new Uri(httpUrl); // 反射修改m_Query字段,把短横线替换回%2D var queryField = typeof(Uri).GetField("m_Query", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); string originalQuery = rsUri.Query.Replace("-", "%2D"); queryField.SetValue(rsUri, originalQuery); // 刷新Uri的缓存值 var infoField = typeof(Uri).GetField("m_Info", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance); infoField.SetValue(rsUri, null); // 此时rsUri.Query已经保留%2D,直接传入HttpClient即可
方案3:RestSharp单独适配
如果只用RestSharp,也可以在添加查询参数时关闭自动编码:
RestClient rsClient = new RestClient(hostAndPath); RestRequest rsRequest = new RestRequest(Method.GET); // 最后一个参数encode设为false,禁止RestSharp自动编码参数值 rsRequest.AddQueryParameter("orderid","bee3d72e%2D8170%2D4bad%2Dba95632b09de42ad", false); var restResponse = rsClient.Execute(rsRequest);
注意:该方案需要同时配合方案1或方案2使用,否则底层Uri依然会自动把%2D转成短横线
内容的提问来源于stack exchange,提问作者tom.zavesky
相关产品推荐
相关产品推荐

