зеркало из https://github.com/mozilla/gecko-dev.git
Bug 778668 - Bubble the application name/origin/manifest in the desktop-notification mozChromeEvent [r=wchen]
This commit is contained in:
Родитель
3a71f140c0
Коммит
7ba8fb1e08
|
@ -263,6 +263,7 @@ var shell = {
|
|||
ppmm.addMessageListener("dial-handler", this);
|
||||
ppmm.addMessageListener("sms-handler", this);
|
||||
ppmm.addMessageListener("mail-handler", this);
|
||||
ppmm.addMessageListener("app-notification-send", AlertsHelper);
|
||||
},
|
||||
|
||||
stop: function shell_stop() {
|
||||
|
@ -609,8 +610,19 @@ var AlertsHelper = {
|
|||
return;
|
||||
|
||||
let listener = this._listeners[detail.id];
|
||||
let topic = detail.type == "desktop-notification-click" ? "alertclickcallback" : "alertfinished";
|
||||
listener.observer.observe(null, topic, listener.cookie);
|
||||
if (!listener)
|
||||
return;
|
||||
|
||||
let topic = detail.type == "desktop-notification-click" ? "alertclickcallback"
|
||||
: "alertfinished";
|
||||
|
||||
if (detail.id.startsWith("alert")) {
|
||||
listener.observer.observe(null, topic, listener.cookie);
|
||||
} else {
|
||||
listener.mm.sendAsyncMessage("app-notification-return",
|
||||
{ id: detail.id,
|
||||
type: detail.type });
|
||||
}
|
||||
|
||||
// we're done with this notification
|
||||
if (topic === "alertfinished")
|
||||
|
@ -623,23 +635,71 @@ var AlertsHelper = {
|
|||
return id;
|
||||
},
|
||||
|
||||
registerAppListener: function alertRegisterAppListener(id, mm, title, text,
|
||||
manifestURL, imageURL) {
|
||||
this._listeners[id] = {
|
||||
mm: mm,
|
||||
title: title,
|
||||
text: text,
|
||||
manifestURL: manifestURL,
|
||||
imageURL: imageURL
|
||||
};
|
||||
},
|
||||
|
||||
showNotification: function alert_showNotification(imageUrl,
|
||||
title,
|
||||
text,
|
||||
textClickable,
|
||||
cookie,
|
||||
id,
|
||||
name,
|
||||
manifestUrl) {
|
||||
function send(appName, appIcon) {
|
||||
shell.sendChromeEvent({
|
||||
type: "desktop-notification",
|
||||
id: id,
|
||||
icon: imageUrl,
|
||||
title: title,
|
||||
text: text,
|
||||
appName: appName,
|
||||
appIcon: appIcon
|
||||
});
|
||||
}
|
||||
|
||||
// If we have a manifest URL, get the icon and title from the manifest
|
||||
// to prevent spoofing.
|
||||
if (manifestUrl && manifestUrl.length) {
|
||||
let app = DOMApplicationRegistry.getAppByManifestURL(manifestUrl);
|
||||
DOMApplicationRegistry.getManifestFor(app.origin, function(aManifest) {
|
||||
let helper = new ManifestHelper(aManifest, app.origin);
|
||||
send(helper.name, helper.iconURLForSize(128));
|
||||
});
|
||||
} else {
|
||||
send(null, null);
|
||||
}
|
||||
},
|
||||
|
||||
showAlertNotification: function alert_showAlertNotification(imageUrl,
|
||||
title,
|
||||
text,
|
||||
textClickable,
|
||||
cookie,
|
||||
alertListener,
|
||||
name)
|
||||
{
|
||||
let id = this.registerListener(cookie, alertListener);
|
||||
shell.sendChromeEvent({
|
||||
type: "desktop-notification",
|
||||
id: id,
|
||||
icon: imageUrl,
|
||||
title: title,
|
||||
text: text
|
||||
});
|
||||
}
|
||||
name) {
|
||||
let id = this.registerListener(null, alertListener);
|
||||
this.showNotification(imageUrl, title, text, textClickable, cookie,
|
||||
id, name, null);
|
||||
},
|
||||
|
||||
receiveMessage: function alert_receiveMessage(message) {
|
||||
let data = message.data;
|
||||
|
||||
this.registerAppListener(data.id, message.target, data.title, data.text,
|
||||
data.manifestURL, data.imageURL);
|
||||
this.showNotification(data.imageURL, data.title, data.text,
|
||||
data.textClickable, null,
|
||||
data.id, null, data.manifestURL);
|
||||
},
|
||||
}
|
||||
|
||||
var WebappsHelper = {
|
||||
|
|
|
@ -1,26 +1,85 @@
|
|||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
|
||||
const Ci = Components.interfaces;
|
||||
const Cu = Components.utils;
|
||||
const Cc = Components.classes;
|
||||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "cpmm", function() {
|
||||
return Cc["@mozilla.org/childprocessmessagemanager;1"]
|
||||
.getService(Ci.nsIMessageSender);
|
||||
});
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
// Alerts Service
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
function AlertsService() { }
|
||||
function AlertsService() {
|
||||
cpmm.addMessageListener("app-notification-return", this);
|
||||
this._id = 0;
|
||||
}
|
||||
|
||||
AlertsService.prototype = {
|
||||
classID: Components.ID("{fe33c107-82a4-41d6-8c64-5353267e04c9}"),
|
||||
QueryInterface: XPCOMUtils.generateQI([Ci.nsIAlertsService]),
|
||||
QueryInterface: XPCOMUtils.generateQI([Ci.nsIAlertsService,
|
||||
Ci.nsIAppNotificationService]),
|
||||
|
||||
showAlertNotification: function(aImageUrl, aTitle, aText, aTextClickable, aCookie, aAlertListener, aName) {
|
||||
// nsIAlertsService
|
||||
showAlertNotification: function showAlertNotification(aImageUrl,
|
||||
aTitle,
|
||||
aText,
|
||||
aTextClickable,
|
||||
aCookie,
|
||||
aAlertListener,
|
||||
aName) {
|
||||
let browser = Services.wm.getMostRecentWindow("navigator:browser");
|
||||
browser.AlertsHelper.showAlertNotification(aImageUrl, aTitle, aText, aTextClickable, aCookie, aAlertListener, aName);
|
||||
browser.AlertsHelper.showAlertNotification(aImageUrl, aTitle, aText,
|
||||
aTextClickable, aCookie,
|
||||
aAlertListener, aName);
|
||||
},
|
||||
|
||||
// nsIAppNotificationService
|
||||
_listeners: [],
|
||||
|
||||
receiveMessage: function receiveMessage(aMessage) {
|
||||
let data = aMessage.data;
|
||||
if (aMessage.name !== "app-notification-return" ||
|
||||
!this._listeners[data.id]) {
|
||||
return;
|
||||
}
|
||||
|
||||
let obs = this._listeners[data.id];
|
||||
let topic = data.type == "desktop-notification-click" ? "alertclickcallback"
|
||||
: "alertfinished";
|
||||
obs.observe(null, topic, null);
|
||||
|
||||
// we're done with this notification
|
||||
if (topic === "alertfinished")
|
||||
delete this._listeners[data.id];
|
||||
},
|
||||
|
||||
// This method is called in the content process, so we remote the call
|
||||
// to shell.js
|
||||
showAppNotification: function showAppNotification(aImageURL,
|
||||
aTitle,
|
||||
aText,
|
||||
aTextClickable,
|
||||
aManifestURL,
|
||||
aAlertListener) {
|
||||
let id = "app-notif" + this._id++;
|
||||
this._listeners[id] = aAlertListener;
|
||||
cpmm.sendAsyncMessage("app-notification-send", {
|
||||
imageURL: aImageURL,
|
||||
title: aTitle,
|
||||
text: aText,
|
||||
textClickable: aTextClickable,
|
||||
manifestURL: aManifestURL,
|
||||
id: id
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -64,7 +64,6 @@
|
|||
#include "nsIDOMTouchEvent.h"
|
||||
#include "nsIInlineEventHandlers.h"
|
||||
#include "nsWrapperCacheInlines.h"
|
||||
#include "nsIDOMApplicationRegistry.h"
|
||||
#include "nsIIdleObserver.h"
|
||||
#include "nsIDOMWakeLock.h"
|
||||
|
||||
|
@ -1111,6 +1110,7 @@ protected:
|
|||
friend class nsDOMScriptableHelper;
|
||||
friend class nsDOMWindowUtils;
|
||||
friend class PostMessageEvent;
|
||||
friend class nsDOMDesktopNotification;
|
||||
|
||||
static WindowByIdTable* sWindowsById;
|
||||
static bool sWarnedAboutWindowInternal;
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
|
||||
interface nsIDOMEventListener;
|
||||
interface nsIDOMDesktopNotification;
|
||||
|
||||
interface nsIObserver;
|
||||
|
||||
[scriptable, uuid(CCEA6185-0A3D-45AB-9058-1004DD4B8C50)]
|
||||
interface nsIDOMDesktopNotificationCenter : nsISupports
|
||||
|
@ -25,3 +25,15 @@ interface nsIDOMDesktopNotification : nsISupports
|
|||
[implicit_jscontext] attribute jsval onclick;
|
||||
[implicit_jscontext] attribute jsval onclose;
|
||||
};
|
||||
|
||||
// Notification service that also provides the manifest URL
|
||||
[scriptable, uuid(7fb4f0f9-ff5b-4620-8e1b-d82d723605af)]
|
||||
interface nsIAppNotificationService : nsISupports
|
||||
{
|
||||
void showAppNotification(in AString imageUrl,
|
||||
in AString title,
|
||||
in AString text,
|
||||
[optional] in boolean textClickable,
|
||||
[optional] in AString manifestURL,
|
||||
[optional] in nsIObserver alertListener);
|
||||
};
|
||||
|
|
|
@ -10,6 +10,9 @@
|
|||
#include "mozilla/dom/PBrowserChild.h"
|
||||
#include "TabChild.h"
|
||||
#include "mozilla/Preferences.h"
|
||||
#include "nsGlobalWindow.h"
|
||||
#include "nsIAppsService.h"
|
||||
#include "nsIDOMDesktopNotification.h"
|
||||
|
||||
using namespace mozilla;
|
||||
using namespace mozilla::dom;
|
||||
|
@ -27,13 +30,32 @@ NS_IMPL_ISUPPORTS1(AlertServiceObserver, nsIObserver)
|
|||
nsresult
|
||||
nsDOMDesktopNotification::PostDesktopNotification()
|
||||
{
|
||||
if (!mObserver)
|
||||
mObserver = new AlertServiceObserver(this);
|
||||
|
||||
#ifdef MOZ_B2G
|
||||
nsCOMPtr<nsIAppNotificationService> appNotifier =
|
||||
do_GetService("@mozilla.org/system-alerts-service;1");
|
||||
if (appNotifier) {
|
||||
nsCOMPtr<nsPIDOMWindow> window = GetOwner();
|
||||
uint32_t appId = (window.get())->GetDoc()->NodePrincipal()->GetAppId();
|
||||
|
||||
if (appId != nsIScriptSecurityManager::UNKNOWN_APP_ID) {
|
||||
nsCOMPtr<nsIAppsService> appsService = do_GetService("@mozilla.org/AppsService;1");
|
||||
nsString manifestUrl = EmptyString();
|
||||
appsService->GetManifestURLByLocalId(appId, manifestUrl);
|
||||
return appNotifier->ShowAppNotification(mIconURL, mTitle, mDescription,
|
||||
true,
|
||||
manifestUrl,
|
||||
mObserver);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
nsCOMPtr<nsIAlertsService> alerts = do_GetService("@mozilla.org/alerts-service;1");
|
||||
if (!alerts)
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
|
||||
if (!mObserver)
|
||||
mObserver = new AlertServiceObserver(this);
|
||||
|
||||
return alerts->ShowAlertNotification(mIconURL, mTitle, mDescription,
|
||||
true,
|
||||
EmptyString(),
|
||||
|
|
Загрузка…
Ссылка в новой задаче