我试图使用vba WinHttp.WinHttpRequest向kigo的api提出请求, 我能够发送请求,但WinHttpRequest更改内容类型添加 Charset = UTF-8发送请求时,kigo的api返回415错误。
我像这样设置内容类型
web_Http.SetRequestHeader "Content-Type", "application/json"
但是当我在Wireshark中查看请求时,content-type就是这样的
Content-Type: application/json; Charset=UTF-8
有什么想法吗?
我发现this,这与我的问题相似,但我不明白解决方案。
答案 0 :(得分:2)
我也遇到了这个问题。它似乎仅限于WinHttp.WinHttpRequest
COM接口。有几种不同的选择可以解决这个问题。
经过一番挖掘后,我发现了一名来自Microsoft员工的this post。它给出了明确的解释,并建议发送二进制数组。
如果使用WinHttpRequest对象发布字符串,则不能 覆盖它如何编码字符串以进行传输。 WinHttpRequest object始终将Unicode字符串转换为UTF-8。
但是,请注意只包含7位的Unicode字符串 编码为UTF-8时,LATIN-1 / ISO-8859-1字符将保持不变 ;-)在这种情况下,WinHttpRequest对象不会附加 "字符集= UTF-8"属性到您的Content-Type标头。 (而且我会想 服务器会认为POST数据是ISO-8859-1。)
因此,如果您正在POST的XML文本数据包含LATIN-1字母数字 或标点字符代码(每个小于十进制128),然后你所有 应该做的是指定" ISO-8859-1"内容类型中的字符集 头:
WinHttpReq.SetRequestHeader "Content-Type", "application/xml;Charset=ISO-8859-1"
但是,如果您的POST数据包含8位字符,则无法提供 数据作为Send方法的字符串。为了避免使用UTF-8 转换时,您的应用程序必须将字符串转换为字节数组,并且 提供相反的。 WinHttpRequest对象不会尝试任何数据 转换为字节数组。
此致
Stephen Sulzer
Microsoft Corporation
除了发送二进制数组外,第二个选项是切换到Msxml2.XMLHTTP
或Msxml2.ServerXMLHTTP
。这两个都没有Content-Type
标题。幸运的是,在创建WinHttp.WinHttpRequest
时,Microsoft故意使用Msxml2.XMLHTTP
作为接口的模板。因此,转换代码非常简单。
此外,Msxml2.ServerXMLHTTP
COM接口uses WinHTTP internally。因此,当您无法访问WinHttp.WinHttpRequest
专有的某些功能时,两者都使用相同的后端。
第三种选择是使用ADODB.Stream
。它允许您使用IStream
,这是您通常可以从VBA执行的操作。以下示例代码基于问题"How to create BinaryArray in VbScript?"的答案。
' Create a Binary Stream
Set objStreamBinary = CreateObject("ADODB.Stream")
objStreamBinary.Type = 1
objStreamBinary.Open
' Create a Text Stream
Set objStreamText = CreateObject("ADODB.Stream")
objStreamText.Type = 2
objStreamText.Open
' Copy the POST data to the Text Stream
objStreamText.WriteText strRequest
objStreamText.Position = 2
' Copy the Text Stream Contents to the Binary Stream
objStreamText.CopyTo objStreamBinary
objStreamText.Close
' Read the contents of the Binary Stream
' and send it to the WinHttpRequest object
web_Http.Send objStreamBinary.Read(-1)