147 lines
3.6 KiB
JavaScript
147 lines
3.6 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 https://mozilla.org/MPL/2.0/. */
|
|
|
|
import {
|
|
actionTypes as at,
|
|
actionCreators as ac,
|
|
} from "resource://newtab/common/Actions.mjs";
|
|
|
|
export class NewTabMessaging {
|
|
constructor() {
|
|
this.initialized = false;
|
|
this.ASRouterDispatch = null;
|
|
}
|
|
|
|
init() {
|
|
if (!this.initialized) {
|
|
Services.obs.addObserver(this, "newtab-message");
|
|
this.initialized = true;
|
|
}
|
|
}
|
|
|
|
uninit() {
|
|
Services.obs.removeObserver(this, "newtab-message");
|
|
}
|
|
|
|
observe(subject, topic, _data) {
|
|
if (topic === "newtab-message") {
|
|
let { targetBrowser, message, dispatch } = subject.wrappedJSObject;
|
|
this.ASRouterDispatch = dispatch;
|
|
this.showMessage(targetBrowser, message);
|
|
}
|
|
}
|
|
|
|
async showMessage(targetBrowser, message) {
|
|
if (targetBrowser) {
|
|
let actor =
|
|
targetBrowser.browsingContext.currentWindowGlobal.getActor(
|
|
"AboutNewTab"
|
|
);
|
|
if (actor) {
|
|
let tabDetails = actor.getTabDetails();
|
|
if (tabDetails) {
|
|
// Only send the message for the tab that triggered the message
|
|
this.store.dispatch(
|
|
ac.OnlyToOneContent(
|
|
{
|
|
type: at.MESSAGE_SET,
|
|
// send along portID as well so that the child process can easily just update the single tab
|
|
data: {
|
|
message,
|
|
portID: tabDetails.portID,
|
|
},
|
|
},
|
|
tabDetails.portID
|
|
)
|
|
);
|
|
}
|
|
}
|
|
} else {
|
|
// if targetBrowser is null, send to the preloaded tab / main process
|
|
// This should only run if message is triggered from asrouter during dev
|
|
this.store.dispatch(
|
|
ac.AlsoToPreloaded({
|
|
type: at.MESSAGE_SET,
|
|
data: {
|
|
message,
|
|
},
|
|
})
|
|
);
|
|
// Also force visibility for messages sent from about:asrouter during dev
|
|
this.store.dispatch(
|
|
ac.AlsoToPreloaded({
|
|
type: at.MESSAGE_TOGGLE_VISIBILITY,
|
|
data: false,
|
|
})
|
|
);
|
|
}
|
|
}
|
|
|
|
/**
|
|
*
|
|
* @param {string} id ID of message to be blocked
|
|
*/
|
|
blockMessage(id) {
|
|
if (id) {
|
|
this.ASRouterDispatch?.({
|
|
type: "BLOCK_MESSAGE_BY_ID",
|
|
data: {
|
|
id,
|
|
},
|
|
});
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Send impression to ASRouter
|
|
* @param {Object} message
|
|
*/
|
|
handleImpression(message) {
|
|
this.sendTelemetry("IMPRESSION", message);
|
|
this.ASRouterDispatch?.({
|
|
type: "IMPRESSION",
|
|
data: message,
|
|
});
|
|
}
|
|
|
|
/**
|
|
* Sends telemetry data through ASRouter to
|
|
* match pattern with ASRouterTelemetry
|
|
*/
|
|
sendTelemetry(event, message, source = "newtab") {
|
|
const data = {
|
|
action: "newtab_message_user_event",
|
|
event,
|
|
event_context: { source, page: "about:newtab" },
|
|
message_id: message.id,
|
|
};
|
|
this.ASRouterDispatch?.({
|
|
type: "NEWTAB_MESSAGE_TELEMETRY",
|
|
data,
|
|
});
|
|
}
|
|
|
|
async onAction(action) {
|
|
switch (action.type) {
|
|
case at.INIT:
|
|
this.init();
|
|
break;
|
|
case at.UNINIT:
|
|
this.uninit();
|
|
break;
|
|
case at.MESSAGE_IMPRESSION:
|
|
this.handleImpression(action.data);
|
|
break;
|
|
case at.MESSAGE_DISMISS:
|
|
this.sendTelemetry("DISMISS", action.data.message);
|
|
break;
|
|
case at.MESSAGE_CLICK:
|
|
this.sendTelemetry("CLICK", action.data.message, action.data.source);
|
|
break;
|
|
case at.MESSAGE_BLOCK:
|
|
this.blockMessage(action.data);
|
|
break;
|
|
}
|
|
}
|
|
}
|