From 6bf0a5cb5034a7e684dcc3500e841785237ce2dd Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Sun, 7 Apr 2024 19:32:43 +0200 Subject: Adding upstream version 1:115.7.0. Signed-off-by: Daniel Baumann --- .../unit/asrouter/templates/SimpleSnippet.test.jsx | 259 +++++++++++++++++++++ 1 file changed, 259 insertions(+) create mode 100644 browser/components/newtab/test/unit/asrouter/templates/SimpleSnippet.test.jsx (limited to 'browser/components/newtab/test/unit/asrouter/templates/SimpleSnippet.test.jsx') diff --git a/browser/components/newtab/test/unit/asrouter/templates/SimpleSnippet.test.jsx b/browser/components/newtab/test/unit/asrouter/templates/SimpleSnippet.test.jsx new file mode 100644 index 0000000000..7c169525e4 --- /dev/null +++ b/browser/components/newtab/test/unit/asrouter/templates/SimpleSnippet.test.jsx @@ -0,0 +1,259 @@ +import { mount } from "enzyme"; +import React from "react"; +import { FluentBundle, FluentResource } from "@fluent/bundle"; +import { LocalizationProvider, ReactLocalization } from "@fluent/react"; +import schema from "content-src/asrouter/templates/SimpleSnippet/SimpleSnippet.schema.json"; +import { SimpleSnippet } from "content-src/asrouter/templates/SimpleSnippet/SimpleSnippet.jsx"; + +const DEFAULT_CONTENT = { text: "foo" }; + +describe("SimpleSnippet", () => { + let sandbox; + let onBlockStub; + let sendUserActionTelemetryStub; + + function mockL10nWrapper(content) { + const bundle = new FluentBundle("en-US"); + for (const [id, value] of Object.entries(content)) { + if (typeof value === "string") { + bundle.addResource(new FluentResource(`${id} = ${value}`)); + } + } + const l10n = new ReactLocalization([bundle]); + return { + wrappingComponent: LocalizationProvider, + wrappingComponentProps: { l10n }, + }; + } + + /** + * mountAndCheckProps - Mounts a SimpleSnippet with DEFAULT_CONTENT extended with any props + * passed in the content param and validates props against the schema. + * @param {obj} content Object containing custom message content (e.g. {text, icon, title}) + * @returns enzyme wrapper for SimpleSnippet + */ + function mountAndCheckProps(content = {}, provider = "test-provider") { + const props = { + content: Object.assign({}, DEFAULT_CONTENT, content), + provider, + onBlock: onBlockStub, + sendUserActionTelemetry: sendUserActionTelemetryStub, + onAction: sandbox.stub(), + }; + assert.jsonSchema(props.content, schema); + return mount(, mockL10nWrapper(props.content)); + } + + beforeEach(() => { + sandbox = sinon.createSandbox(); + onBlockStub = sandbox.stub(); + sendUserActionTelemetryStub = sandbox.stub(); + }); + + afterEach(() => { + sandbox.restore(); + }); + + it("should have the correct defaults", () => { + const wrapper = mountAndCheckProps(); + [["button", "title", "block_button_text"]].forEach(prop => { + const props = wrapper.find(prop[0]).props(); + assert.propertyVal(props, prop[1], schema.properties[prop[2]].default); + }); + }); + + it("should render .text", () => { + const wrapper = mountAndCheckProps({ text: "bar" }); + assert.equal(wrapper.find(".body").text(), "bar"); + }); + it("should not render title element if no .title prop is supplied", () => { + const wrapper = mountAndCheckProps(); + assert.lengthOf(wrapper.find(".title"), 0); + }); + it("should render .title", () => { + const wrapper = mountAndCheckProps({ title: "Foo" }); + assert.equal(wrapper.find(".title").text().trim(), "Foo"); + }); + it("should render a light theme variant .icon", () => { + const wrapper = mountAndCheckProps({ + icon: "data:image/gif;base64,R0lGODl", + }); + assert.equal( + wrapper.find(".icon-light-theme").prop("src"), + "data:image/gif;base64,R0lGODl" + ); + }); + it("should render a dark theme variant .icon", () => { + const wrapper = mountAndCheckProps({ + icon_dark_theme: "data:image/gif;base64,R0lGODl", + }); + assert.equal( + wrapper.find(".icon-dark-theme").prop("src"), + "data:image/gif;base64,R0lGODl" + ); + }); + it("should render a light theme variant .icon as fallback", () => { + const wrapper = mountAndCheckProps({ + icon_dark_theme: "", + icon: "data:image/gif;base64,R0lGODp", + }); + assert.equal( + wrapper.find(".icon-dark-theme").prop("src"), + "data:image/gif;base64,R0lGODp" + ); + }); + it("should render .button_label and default className", () => { + const wrapper = mountAndCheckProps({ + button_label: "Click here", + button_action: "OPEN_APPLICATIONS_MENU", + button_action_args: "appMenu", + }); + + const button = wrapper.find("button.ASRouterButton"); + button.simulate("click"); + + assert.equal(button.text(), "Click here"); + assert.equal(button.prop("className"), "ASRouterButton secondary"); + assert.calledOnce(wrapper.props().onAction); + assert.calledWithExactly(wrapper.props().onAction, { + type: "OPEN_APPLICATIONS_MENU", + data: { args: "appMenu" }, + }); + }); + it("should not wrap the main content if a section header is not present", () => { + const wrapper = mountAndCheckProps({ text: "bar" }); + assert.lengthOf(wrapper.find(".innerContentWrapper"), 0); + }); + it("should wrap the main content if a section header is present", () => { + const wrapper = mountAndCheckProps({ + section_title_icon: "data:image/gif;base64,R0lGODl", + section_title_text: "Messages from Mozilla", + }); + + assert.lengthOf(wrapper.find(".innerContentWrapper"), 1); + }); + it("should render a section header if text and icon (light-theme) are specified", () => { + const wrapper = mountAndCheckProps({ + section_title_icon: "data:image/gif;base64,R0lGODl", + section_title_text: "Messages from Mozilla", + }); + + assert.equal( + wrapper.find(".section-title .icon-light-theme").prop("style") + .backgroundImage, + 'url("data:image/gif;base64,R0lGODl")' + ); + assert.equal( + wrapper.find(".section-title-text").text().trim(), + "Messages from Mozilla" + ); + // ensure there is no when a section_title_url is not specified + assert.lengthOf(wrapper.find(".section-title a"), 0); + }); + it("should render a section header if text and icon (light-theme) are specified", () => { + const wrapper = mountAndCheckProps({ + section_title_icon: "data:image/gif;base64,R0lGODl", + section_title_icon_dark_theme: "data:image/gif;base64,R0lGODl", + section_title_text: "Messages from Mozilla", + }); + + assert.equal( + wrapper.find(".section-title .icon-dark-theme").prop("style") + .backgroundImage, + 'url("data:image/gif;base64,R0lGODl")' + ); + assert.equal( + wrapper.find(".section-title-text").text().trim(), + "Messages from Mozilla" + ); + // ensure there is no when a section_title_url is not specified + assert.lengthOf(wrapper.find(".section-title a"), 0); + }); + it("should render a section header wrapped in an tag if a url is provided", () => { + const wrapper = mountAndCheckProps({ + section_title_icon: "data:image/gif;base64,R0lGODl", + section_title_text: "Messages from Mozilla", + section_title_url: "https://www.mozilla.org", + }); + + assert.equal( + wrapper.find(".section-title a").prop("href"), + "https://www.mozilla.org" + ); + }); + it("should send an OPEN_URL action when button_url is defined and button is clicked", () => { + const wrapper = mountAndCheckProps({ + button_label: "Button", + button_url: "https://mozilla.org", + }); + + const button = wrapper.find("button.ASRouterButton"); + button.simulate("click"); + + assert.calledOnce(wrapper.props().onAction); + assert.calledWithExactly(wrapper.props().onAction, { + type: "OPEN_URL", + data: { args: "https://mozilla.org" }, + }); + }); + it("should send an OPEN_ABOUT_PAGE action with entrypoint when the button is clicked", () => { + const wrapper = mountAndCheckProps({ + button_label: "Button", + button_action: "OPEN_ABOUT_PAGE", + button_entrypoint_value: "snippet", + button_entrypoint_name: "entryPoint", + button_action_args: "logins", + }); + + const button = wrapper.find("button.ASRouterButton"); + button.simulate("click"); + + assert.calledOnce(wrapper.props().onAction); + assert.calledWithExactly(wrapper.props().onAction, { + type: "OPEN_ABOUT_PAGE", + data: { args: "logins", entrypoint: "entryPoint=snippet" }, + }); + }); + it("should send an OPEN_PREFERENCE_PAGE action with entrypoint when the button is clicked", () => { + const wrapper = mountAndCheckProps({ + button_label: "Button", + button_action: "OPEN_PREFERENCE_PAGE", + button_entrypoint_value: "entry=snippet", + button_action_args: "home", + }); + + const button = wrapper.find("button.ASRouterButton"); + button.simulate("click"); + + assert.calledOnce(wrapper.props().onAction); + assert.calledWithExactly(wrapper.props().onAction, { + type: "OPEN_PREFERENCE_PAGE", + data: { args: "home", entrypoint: "entry=snippet" }, + }); + }); + it("should call props.onBlock and sendUserActionTelemetry when CTA button is clicked", () => { + const wrapper = mountAndCheckProps({ text: "bar" }); + + wrapper.instance().onButtonClick(); + + assert.calledOnce(onBlockStub); + assert.calledOnce(sendUserActionTelemetryStub); + }); + + it("should not call props.onBlock if do_not_autoblock is true", () => { + const wrapper = mountAndCheckProps({ text: "bar", do_not_autoblock: true }); + + wrapper.instance().onButtonClick(); + + assert.notCalled(onBlockStub); + }); + + it("should not call sendUserActionTelemetry for preview message when CTA button is clicked", () => { + const wrapper = mountAndCheckProps({ text: "bar" }, "preview"); + + wrapper.instance().onButtonClick(); + + assert.calledOnce(onBlockStub); + assert.notCalled(sendUserActionTelemetryStub); + }); +}); -- cgit v1.2.3