nsIWebContentHandlerRegistrar 编辑

xpfe/appshell/public/nsIWebContentHandlerRegistrar.idlScriptable Applications wishing to use web content handlers need to implement this interface. Typically they will prompt the user to confirm adding an entry to the local list. Inherits from: nsISupports Last changed in Gecko 8.0 (Firefox 8.0 / Thunderbird 8.0 / SeaMonkey 2.5)

Implemented by @mozilla.org/embeddor.implemented/web-content-handler-registrar;1 as a service:

var nsiwchr = Cc["@mozilla.org/embeddor.implemented/web-content-handler-registrar;1"]
                .getService(Ci.nsIWebContentHandlerRegistrar);

Method overview

void registerContentHandler(in DOMString mimeType, in DOMString uri, in DOMString title, in nsIDOMWindow contentWindow)
void registerProtocolHandler(in DOMString protocol,in DOMString uri, in DOMString title, in nsIDOMWindow contentWindow)

Methods

registerContentHandler

Summary of registerContentHandler

void registerContentHandler(
  in DOMString mimeType,
  in DOMString uri,
  in DOMString title,
  in nsIDOMWindow contentWindow
);
Parameters
mimeType
The desired MIME type as a string
uri
The URI to the handler as a string.
title
The title of the handler presented to the user as a string.
contentWindow
The DOM content window from which the method has been called.

registerProtocolHandler

Summary of registerProtocolHandler

void registerProtocolHandler(
  in DOMString protocol,
  in DOMString uri,
  in DOMString title,
  in nsIDOMWindow contentWindow
);
Parameters
protocol
The protocol the site wishes to handle, specified as a string.
uri
The URI to the handler as a string. You must include "%s" to indicate where to insert the escaped URI of the document to be handled. Otherwise NS_ERROR_DOM_SYNTAX_ERR will be thrown. This string must also be of either the httpor httpsschemes.
title
The title of the handler presented to the user as a string.
contentWindow
The DOM content window from which the method has been called.

Note: Script must execute from same domain as uri or else it will throw permission error. Can bypass this by openingabout:config and setting preference of gecko.handlerService.allowRegisterFromDifferentHost to true.

Examples

Register a webmail service as mailto handler

The following code aims to add "Outlook.com Live Mail" to list of webservice handlers. In the image below "Gmail" and "Yahoo! Mail" already exist as webservice handlers.

"Gmail" and "Yahoo! Mail" exist as webservice handlers. This example aims to add "Outlook.com Live Mail" to the list.

Cu.import('resource://gre/modules/Services.jsm');

var nsiwchr = Cc["@mozilla.org/embeddor.implemented/web-content-handler-registrar;1"]
                .getService(Ci.nsIWebContentHandlerRegistrar);

var htmlContentWindow = undefined;
var registerUri = 'http://mail.live.com/secure/start?action=compose&to=%s';
var myURIHostName = Services.io.newURI(registerUri, null, null).host;

// this section here is long and daunting, but its just finding a suitable contentWindow
var DOMWindows = Services.wm.getEnumerator(null);
while (DOMWindows.hasMoreElements()) {
    var aDOMWindow = DOMWindows.getNext();
    if (aDOMWindow.gBrowser) {
        if (aDOMWindow.gBrowser.tabContainer) {
            //aDOMWindow has tabs
            var tabs = aDOMWindow.gBrowser.tabContainer.childNodes;
            for (var i = 0; i < tabs.length; i++) {
                console.log(tabs[i].linkedBrowser.contentWindow.location);
                if (tabs[i].linkedBrowser.contentWindow.location.hostname == myURIHostName) {
                    htmlContentWindow = tabs[i].linkedBrowser.contentWindow;
                    break; //break for loop
                }
            }
            if (htmlContentWindow) {
                break; //break while loop
            }
        } else {
            //aDOMWindow doest have any tabs
            if (aDOMWindow.gBrowser.contentWindow.location.hostname == myURIHostName) {
                htmlContentWindow = aDOMWindow.contentWindow;
                break;
            }
        }
    } else {
        //aDOMWindow is a popup window
        if (aDOMWindow.location.hostname == myURIHostName) {
            htmlContentWindow = aDOMWindow;
            break;
        }
    }
}
// this section here is long and daunting, but its just finding a suitable contentWindow

if (!htmlContentWindow) {
    throw new Error('No suitable content window found, will not reigsterProtocolHandler. Must have a content window to pass to registerProtocolHandler as it prompts the user for permission');
}

nsiwchr.registerProtocolHandler("mailto", registerUri, "Outlook.com Live Mail", htmlContentWindow);

In this example the Services.wm.getEnumeratorwas used to find a window that had the same host name (contentWindow.location.hostname) as the uri(uri.host) we are trying to add. If it does not find anything with host name of mail.live.com then it aborts. If the host names do not match, this error will be thrown in the Error Console.

Permission denied to add http://mail.live.com/secure/start?action=compose&to=%s as a content or protocol handler'Permission denied to add http://mail.live.com/secure/start?action=compose&to=%s as a content or protocol handler' when calling method: [nsIWebContentHandlerRegistrar::registerProtocolHandler]

If the host names do match then a confirmation like this will be seen:

Confirmation message seen when contentWindow test passes for registerProtocolHandler. The location of the contentWindow is "http://mail.live.com/mail/postmaster.aspx" which matches that of "http://mail.live.com/secure/start?action=compose&amp;amp;amp;to=%s" which is the 2nd argument passed to registerProtocolHandler.

This domain check can be bypassed by setting the preference of gecko.handlerService.allowRegisterFromDifferentHostto trueas in this code here:

var {classes: Cc, interfaces: Ci, utils: Cu} = Components;
Cu.import("resource://gre/modules/Services.jsm");
var nsiwchr = Cc["@mozilla.org/embeddor.implemented/web-content-handler-registrar;1"]
                .getService(Ci.nsIWebContentHandlerRegistrar);

var allowRegisterFromDifferentHost = Services.prefs.getBoolPref('gecko.handlerService.allowRegisterFromDifferentHost');
if (!allowRegisterFromDifferentHost) {
  Services.prefs.setBoolPref('gecko.handlerService.allowRegisterFromDifferentHost', true);
}

var htmlContentWindow = Services.wm.getMostRecentWindow('navigator:browser'); //because we set the preference to true above, we need any window that has a browser, just pass the DOMWindow and the registerProtocolHandler will get the contentWindow from it

nsiwchr.registerProtocolHandler("mailto", "http://mail.live.com/secure/start?action=compose&to=%s", "Outlook.com Live Mail", htmlContentWindow);

if (!allowRegisterFromDifferentHost) {
  //it this variable is false, than we had set the pref to true obviously. so lets restore it back to false, which is the default value
  Services.prefs.clearUserPref('gecko.handlerService.allowRegisterFromDifferentHost');
}

Register a webmail service as mailto handler without contentWindow

Under construction. To take from:  http://mxr.mozilla.org/mozilla-release/source/browser/components/feeds/src/WebContentConverter.js#372 AND http://stackoverflow.com/questions/24900655/use-registerprotocolhandler-without-contentwindow

place holder

See also

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据

词条统计

浏览:90 次

字数:11021

最后编辑:7 年前

编辑次数:0 次

    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文