gecko-dev/dom/notification/NotificationStorage.jsm

259 строки
5.8 KiB
JavaScript

/* 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/. */
"use strict";
const DEBUG = false;
function debug(s) {
dump("-*- NotificationStorage.js: " + s + "\n");
}
ChromeUtils.defineModuleGetter(
this,
"Services",
"resource://gre/modules/Services.jsm"
);
const kMessageNotificationGetAllOk = "Notification:GetAll:Return:OK";
const kMessageNotificationGetAllKo = "Notification:GetAll:Return:KO";
const kMessageNotificationSaveKo = "Notification:Save:Return:KO";
const kMessageNotificationDeleteKo = "Notification:Delete:Return:KO";
const kMessages = [
kMessageNotificationGetAllOk,
kMessageNotificationGetAllKo,
kMessageNotificationSaveKo,
kMessageNotificationDeleteKo,
];
function NotificationStorage() {
this._requests = {};
this._requestCount = 0;
Services.obs.addObserver(this, "xpcom-shutdown");
// Register for message listeners.
this.registerListeners();
}
NotificationStorage.prototype = {
registerListeners() {
for (let message of kMessages) {
Services.cpmm.addMessageListener(message, this);
}
},
unregisterListeners() {
for (let message of kMessages) {
Services.cpmm.removeMessageListener(message, this);
}
},
observe(aSubject, aTopic, aData) {
if (DEBUG) {
debug("Topic: " + aTopic);
}
if (aTopic === "xpcom-shutdown") {
Services.obs.removeObserver(this, "xpcom-shutdown");
this.unregisterListeners();
}
},
put(
origin,
id,
title,
dir,
lang,
body,
tag,
icon,
alertName,
data,
behavior,
serviceWorkerRegistrationScope
) {
if (DEBUG) {
debug("PUT: " + origin + " " + id + ": " + title);
}
var notification = {
id,
title,
dir,
lang,
body,
tag,
icon,
alertName,
timestamp: new Date().getTime(),
origin,
data,
mozbehavior: behavior,
serviceWorkerRegistrationScope,
};
Services.cpmm.sendAsyncMessage("Notification:Save", {
origin,
notification,
});
},
get(origin, tag, callback) {
if (DEBUG) {
debug("GET: " + origin + " " + tag);
}
this._fetchFromDB(origin, tag, callback);
},
getByID(origin, id, callback) {
if (DEBUG) {
debug("GETBYID: " + origin + " " + id);
}
var GetByIDProxyCallback = function(id, originalCallback) {
this.searchID = id;
this.originalCallback = originalCallback;
var self = this;
this.handle = function(
id,
title,
dir,
lang,
body,
tag,
icon,
data,
behavior,
serviceWorkerRegistrationScope
) {
if (id == this.searchID) {
self.originalCallback.handle(
id,
title,
dir,
lang,
body,
tag,
icon,
data,
behavior,
serviceWorkerRegistrationScope
);
}
};
this.done = function() {
self.originalCallback.done();
};
};
return this.get(origin, "", new GetByIDProxyCallback(id, callback));
},
delete(origin, id) {
if (DEBUG) {
debug("DELETE: " + id);
}
Services.cpmm.sendAsyncMessage("Notification:Delete", {
origin,
id,
});
},
receiveMessage(message) {
var request = this._requests[message.data.requestID];
switch (message.name) {
case kMessageNotificationGetAllOk:
delete this._requests[message.data.requestID];
this._returnNotifications(
message.data.notifications,
request.origin,
request.tag,
request.callback
);
break;
case kMessageNotificationGetAllKo:
delete this._requests[message.data.requestID];
try {
request.callback.done();
} catch (e) {
debug("Error calling callback done: " + e);
}
break;
case kMessageNotificationSaveKo:
case kMessageNotificationDeleteKo:
if (DEBUG) {
debug(
"Error received when treating: '" +
message.name +
"': " +
message.data.errorMsg
);
}
break;
default:
if (DEBUG) {
debug("Unrecognized message: " + message.name);
}
break;
}
},
_fetchFromDB(origin, tag, callback) {
var request = {
origin,
tag,
callback,
};
var requestID = this._requestCount++;
this._requests[requestID] = request;
Services.cpmm.sendAsyncMessage("Notification:GetAll", {
origin,
tag,
requestID,
});
},
_returnNotifications(notifications, origin, tag, callback) {
// Pass each notification back separately.
// The callback is called asynchronously to match the behaviour when
// fetching from the database.
notifications.forEach(function(notification) {
try {
Services.tm.dispatchToMainThread(
callback.handle.bind(
callback,
notification.id,
notification.title,
notification.dir,
notification.lang,
notification.body,
notification.tag,
notification.icon,
notification.data,
notification.mozbehavior,
notification.serviceWorkerRegistrationScope
)
);
} catch (e) {
if (DEBUG) {
debug("Error calling callback handle: " + e);
}
}
});
try {
Services.tm.dispatchToMainThread(callback.done);
} catch (e) {
if (DEBUG) {
debug("Error calling callback done: " + e);
}
}
},
QueryInterface: ChromeUtils.generateQI([Ci.nsINotificationStorage]),
};
var EXPORTED_SYMBOLS = ["NotificationStorage"];