您可以指定不同的 URL。例如,您可以将内容提取到临时文件并导航到它。这不会将您的内容放入受信任区域,但它比您通过 about 协议获得的 Internet 区域要好。
如果您不想保存内容,可以先导航到 about:blank,然后在 DocumentComplete 中,为 IPersistMoniker 查询文档,然后使用基本上模拟 url 名字对象的 TInterfacedObject 调用 Load。
-
IMoniker.GetDisplayName 实现需要返回 URL。该网址需要位于受信任的区域中。
-
IMoniker.BindToStorage 实现需要在请求 IStream 时发回对 TMemoryStream 的引用。
还有第三种方法,写一个process-wide security manager,将您的网址放在受信任的区域中。
解决方案是实现您自己的 Internet 安全管理器服务,创建一个实现IInternetSecurityManager 的对象(请参阅MSDN: Implementing a Custom Security Manager)。有五个安全区域:
- 本地:
URLZONE_LOCAL_MACHINE (0)
- 内网:
URLZONE_INTRANET(1)
- 信任:
URLZONE_TRUSTED (2)
- 互联网:
URLZONE_INTERNET (3)
- 受限:
URLZONE_UNTRUSTED (4)
你真正需要担心的唯一方法是MapUrlToZone:
TEmbeddedSecurityManager = class(TInterfacedObject, IInternetSecurityManager)
public
//...
function MapUrlToZone(pwszUrl: LPCWSTR; out dwZone: DWORD; dwFlags: DWORD): HResult; virtual; stdcall;
//...
end;
此方法检查 Url 是否以 about:security
开头
关于:security_Contoso.exe
如果是,则返回该区域应该是本地:
function TEmbeddedSecurityManager.MapUrlToZone(pwszUrl: LPCWSTR; out dwZone: DWORD; dwFlags: DWORD): HResult;
var
url: UnicodeString;
begin
Result := INET_E_DEFAULT_ACTION;
{
https://msdn.microsoft.com/en-us/library/ms537133(v=vs.85).aspx
}
url := pwszUrl;
{
When IE Enchanced Security is enabled, the url goes from
about:blank_xxxx
to
about:security_xxxx
In that case we will put the page in the "Local" zone
}
if url.StartsWith('about:security') then
begin
dwZone := URLZONE_LOCAL_MACHINE; //Local
Result := S_OK;
end;
end;
所有其他方法必须返回INET_E_DEFAULT_ACTION(即不是 S_OK 或 E_NOTIMPL),例如:
function TEmbeddedSecurityManager.SetSecuritySite(Site: IInternetSecurityMgrSite): HResult;
begin
Result := INET_E_DEFAULT_ACTION;
end;
当嵌入式 WebBrowser 调用 IServiceProvider.QueryService 时,您为它提供了此服务。以Delphi的TEmbeddedWB控件为例,在OnQueryService事件中暴露:
function TForm1.EmbeddedWBQueryService(const rsid, iid: TGUID; out Obj: IInterface): HRESULT;
var
sam: IInternetSecurityManager;
begin
Result := E_NOINTERFACE;
//rsid ==> Service Identifier
//iid ==> Interface identifier
if IsEqualGUID(rsid, IInternetSecurityManager) and IsEqualGUID(iid, IInternetSecurityManager) then
begin
sam := TEmbeddedSecurityManager.Create;
Obj := sam;
Result := S_OK;
end;
end;