summaryrefslogtreecommitdiffstats
path: root/browser/components/newtab/test/browser/browser_asrouter_group_frequency.js
diff options
context:
space:
mode:
Diffstat (limited to 'browser/components/newtab/test/browser/browser_asrouter_group_frequency.js')
-rw-r--r--browser/components/newtab/test/browser/browser_asrouter_group_frequency.js190
1 files changed, 190 insertions, 0 deletions
diff --git a/browser/components/newtab/test/browser/browser_asrouter_group_frequency.js b/browser/components/newtab/test/browser/browser_asrouter_group_frequency.js
new file mode 100644
index 0000000000..5957a5905e
--- /dev/null
+++ b/browser/components/newtab/test/browser/browser_asrouter_group_frequency.js
@@ -0,0 +1,190 @@
+const { ASRouter } = ChromeUtils.import(
+ "resource://activity-stream/lib/ASRouter.jsm"
+);
+const { RemoteSettings } = ChromeUtils.importESModule(
+ "resource://services-settings/remote-settings.sys.mjs"
+);
+const { CFRMessageProvider } = ChromeUtils.importESModule(
+ "resource://activity-stream/lib/CFRMessageProvider.sys.mjs"
+);
+const { CFRPageActions } = ChromeUtils.import(
+ "resource://activity-stream/lib/CFRPageActions.jsm"
+);
+
+/**
+ * Load and modify a message for the test.
+ */
+add_setup(async function () {
+ const initialMsgCount = ASRouter.state.messages.length;
+ const heartbeatMsg = (await CFRMessageProvider.getMessages()).find(
+ m => m.id === "HEARTBEAT_TACTIC_2"
+ );
+ const testMessage = {
+ ...heartbeatMsg,
+ groups: ["messaging-experiments"],
+ targeting: "true",
+ // Ensure no overlap due to frequency capping with other tests
+ id: `HEARTBEAT_MESSAGE_${Date.now()}`,
+ };
+ const client = RemoteSettings("cfr");
+ await client.db.importChanges({}, Date.now(), [testMessage], {
+ clear: true,
+ });
+
+ // Force the CFR provider cache to 0 by modifying updateCycleInMs
+ await SpecialPowers.pushPrefEnv({
+ set: [
+ [
+ "browser.newtabpage.activity-stream.asrouter.providers.cfr",
+ `{"id":"cfr","enabled":true,"type":"remote-settings","collection":"cfr","updateCycleInMs":0}`,
+ ],
+ ],
+ });
+
+ // Reload the providers
+ await ASRouter._updateMessageProviders();
+ await ASRouter.loadMessagesFromAllProviders();
+ await BrowserTestUtils.waitForCondition(
+ () => ASRouter.state.messages.length > initialMsgCount,
+ "Should load the extra heartbeat message"
+ );
+
+ BrowserTestUtils.waitForCondition(
+ () => ASRouter.state.messages.find(m => m.id === testMessage.id),
+ "Wait to load the message"
+ );
+
+ const msg = ASRouter.state.messages.find(m => m.id === testMessage.id);
+ Assert.equal(msg.targeting, "true");
+ Assert.equal(msg.groups[0], "messaging-experiments");
+
+ registerCleanupFunction(async () => {
+ await client.db.clear();
+ // Reload the providers
+ await ASRouter._updateMessageProviders();
+ await ASRouter.loadMessagesFromAllProviders();
+ await BrowserTestUtils.waitForCondition(
+ () => ASRouter.state.messages.length === initialMsgCount,
+ "Should reset messages"
+ );
+ await SpecialPowers.popPrefEnv();
+ });
+});
+
+/**
+ * Test group frequency capping.
+ * Message has a lifetime frequency of 3 but it's group has a lifetime frequency
+ * of 2. It should only show up twice.
+ * We update the provider to remove any daily limitations so it should show up
+ * on every new tab load.
+ */
+add_task(async function test_heartbeat_tactic_2() {
+ const TEST_URL = "http://example.com";
+ const msg = ASRouter.state.messages.find(m =>
+ m.groups.includes("messaging-experiments")
+ );
+ Assert.ok(msg, "Message found");
+ const groupConfiguration = {
+ id: "messaging-experiments",
+ enabled: true,
+ frequency: { lifetime: 2 },
+ };
+ const client = RemoteSettings("message-groups");
+ await client.db.importChanges({}, Date.now(), [groupConfiguration], {
+ clear: true,
+ });
+
+ // Force the WNPanel provider cache to 0 by modifying updateCycleInMs
+ await SpecialPowers.pushPrefEnv({
+ set: [
+ [
+ "browser.newtabpage.activity-stream.asrouter.providers.message-groups",
+ `{"id":"message-groups","enabled":true,"type":"remote-settings","collection":"message-groups","updateCycleInMs":0}`,
+ ],
+ ],
+ });
+
+ await BrowserTestUtils.waitForCondition(async () => {
+ const msgs = await client.get();
+ return msgs.find(m => m.id === groupConfiguration.id);
+ }, "Wait for RS message");
+
+ // Reload the providers
+ await ASRouter._updateMessageProviders();
+ await ASRouter.loadAllMessageGroups();
+
+ let groupState = await BrowserTestUtils.waitForCondition(
+ () => ASRouter.state.groups.find(g => g.id === groupConfiguration.id),
+ "Wait for group config to load"
+ );
+ Assert.ok(groupState, "Group config found");
+ Assert.ok(groupState.enabled, "Group is enabled");
+
+ let tab1 = await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_URL);
+ BrowserTestUtils.loadURIString(tab1.linkedBrowser, TEST_URL);
+
+ let chiclet = document.getElementById("contextual-feature-recommendation");
+ Assert.ok(chiclet, "CFR chiclet element found (tab1)");
+ await BrowserTestUtils.waitForCondition(
+ () => !chiclet.hidden,
+ "Chiclet should be visible (tab1)"
+ );
+
+ await BrowserTestUtils.waitForCondition(
+ () =>
+ ASRouter.state.messageImpressions[msg.id] &&
+ ASRouter.state.messageImpressions[msg.id].length === 1,
+ "First impression recorded"
+ );
+
+ BrowserTestUtils.removeTab(tab1);
+
+ let tab2 = await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_URL);
+ BrowserTestUtils.loadURIString(tab2.linkedBrowser, TEST_URL);
+
+ Assert.ok(chiclet, "CFR chiclet element found (tab2)");
+ await BrowserTestUtils.waitForCondition(
+ () => !chiclet.hidden,
+ "Chiclet should be visible (tab2)"
+ );
+
+ await BrowserTestUtils.waitForCondition(
+ () =>
+ ASRouter.state.messageImpressions[msg.id] &&
+ ASRouter.state.messageImpressions[msg.id].length === 2,
+ "Second impression recorded"
+ );
+
+ Assert.ok(
+ !ASRouter.isBelowFrequencyCaps(msg),
+ "Should have reached freq limit"
+ );
+
+ BrowserTestUtils.removeTab(tab2);
+
+ let tab3 = await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_URL);
+ BrowserTestUtils.loadURIString(tab3.linkedBrowser, TEST_URL);
+
+ await BrowserTestUtils.waitForCondition(
+ () => chiclet.hidden,
+ "Heartbeat button should be hidden"
+ );
+ Assert.equal(
+ ASRouter.state.messageImpressions[msg.id] &&
+ ASRouter.state.messageImpressions[msg.id].length,
+ 2,
+ "Number of impressions did not increase"
+ );
+
+ BrowserTestUtils.removeTab(tab3);
+
+ info("Cleanup");
+ await client.db.clear();
+ // Reset group impressions
+ await ASRouter.resetGroupsState();
+ // Reload the providers
+ await ASRouter._updateMessageProviders();
+ await ASRouter.loadMessagesFromAllProviders();
+ await SpecialPowers.popPrefEnv();
+ CFRPageActions.clearRecommendations();
+});