首页 > 解决方案 > 使用 vba 使用凭据访问 Web 服务

问题描述

我正在为 Access 编写更长的脚本,并且有一次需要检查 Web 服务以获取文件的最新版本(文件名)。此网络服务只能通过具有 URL 的浏览器访问,https://webservice.example.com:1234/Server/test.jsp?parameter=value然后必须使用标准浏览器用户名密码弹出来进行身份验证。当然,如果我使用类似的东西,我可以跳过这个弹出窗口https://user:password@webservice.example.com:1234/Server/test.jsp?parameter=value。(请注意,此时与安全性无关,密码只是为了拥有密码而存在,将其存储为明文是完全可以接受的)

目前我已经使用以下工作代码从另一个网站获取信息:

Dim appIE As Object
Dim sURL as String, infoStr as String
Set appIE = GetObject("new:{D5E8041D-920F-45e9-B8FB-B1DEB82C6E5E}") 'class id of InternetExplorerMedium
sURL = "https://webservice.example.com:1234/Server/test.jsp?parameter=value"
With appIE
    .Navigate sURL
    .Visible = False
End With

Do While appIE.Busy Or appIE.ReadyState <> 4
    DoEvents
Loop

infoStr = appIE.Document.getElementsByTagName("body").item.innerText

但是,如果我像在浏览器中那样将凭据添加到 URL, sURL = "https://user:password@webservice.example.com:1234/Server/test.jsp?parameter=value" 我将收到以下错误:

运行时错误“-2146697202 (800c000e)”:对象“IWebBrowser2”的方法“导航”失败

如果我添加凭据或有人知道如何以不同的方式执行此操作,有人知道为什么会失败吗?

标签: vbams-accessinternet-explorer

解决方案


如果您的网站需要基本身份验证,则使用基本身份验证标头进行身份验证相对容易。

我们需要能够对内容进行 Base64 编码,所以首先我们需要为此定义一个辅助函数:

Public Function ToBase64(Bytes() As Byte) As String
    Dim XMLElement As Object
    Set XMLElement = CreateObject("Msxml2.DOMDocument.6.0").createElement("tmp")
    XMLElement.DataType = "bin.base64"
    XMLElement.nodeTypedValue = Bytes
    ToBase64 = Replace(XMLElement.Text, vbLf, "")
End Function

然后,创建基本身份验证标头的第二个助手:

Public Function CreateBasicAuthHeader(Username As String, Password As String) As String
    'Assuming ASCII encoding, UTF-8 is harder
    CreateBasicAuthHeader = "Authorization: Basic " & ToBase64(StrConv(Username & ":" & Password, vbFromUnicode))
End Function

快速验证显示?CreateBasicAuthHeader("Aladdin", "OpenSesame")返回Authorization: Basic QWxhZGRpbjpPcGVuU2VzYW1l,这是根据Wikipedia的预期标题

然后,您可以在Navigate方法中使用它:

Dim appIE As Object
Dim sURL as String, infoStr as String
Set appIE = GetObject("new:{D5E8041D-920F-45e9-B8FB-B1DEB82C6E5E}") 'class id of InternetExplorerMedium
sURL = "https://webservice.example.com:1234/Server/test.jsp?parameter=value"
With appIE
    .Navigate sURL, Headers:=CreateBasicAuthHeader("MyUsername", "MyPassword")
    .Visible = False
End With

Do While appIE.Busy Or appIE.ReadyState <> 4
    DoEvents
Loop

infoStr = appIE.Document.getElementsByTagName("body").item.innerText

这假定服务器需要 ASCII 编码,或者您的用户名和密码都只是 ASCII 字符并且服务器需要 UTF-8 编码。


推荐阅读