From c75b8dba126778841025a9c7b4e0eea6b8feae5a Mon Sep 17 00:00:00 2001 From: Anirudh Mani Date: Mon, 26 Aug 2024 15:06:03 -0700 Subject: [PATCH] feat: add test selector for banner component --- packages/odyssey-react-mui/src/Banner.tsx | 31 +++++++++++++++++++ .../test-selectors/odysseyTestSelectors.ts | 2 ++ .../odyssey-mui/Banner/Banner.stories.tsx | 29 +++++++++++++++++ 3 files changed, 62 insertions(+) diff --git a/packages/odyssey-react-mui/src/Banner.tsx b/packages/odyssey-react-mui/src/Banner.tsx index 3c87dc8e12..0d1b4dab11 100644 --- a/packages/odyssey-react-mui/src/Banner.tsx +++ b/packages/odyssey-react-mui/src/Banner.tsx @@ -14,6 +14,7 @@ import { memo } from "react"; import { useTranslation } from "react-i18next"; import { Alert, AlertColor, AlertTitle, AlertProps } from "@mui/material"; +import { type FeatureTestSelector } from "./test-selectors"; import type { HtmlProps } from "./HtmlProps"; import { Link } from "./Link"; import { ScreenReaderText } from "./ScreenReaderText"; @@ -26,6 +27,36 @@ export const bannerSeverityValues: AlertColor[] = [ "error", ]; +export const BannerTestSelectors = { + feature: { + link: { + selector: { + method: "ByRole", + options: { + name: "${linkText}", + }, + role: "link", + templateVariableNames: ["linkText"], + }, + }, + closeButton: { + selector: { + method: "ByRole", + options: { + name: "${labelText}", + }, + role: "button", + templateVariableNames: ["labelText"], + }, + }, + }, + selector: { + method: "ByRole", + role: "${role}", + templateVariableNames: ["role"], + }, +} as const satisfies FeatureTestSelector; + export type BannerProps = { /** * If linkUrl is not undefined, this is the text of the link. diff --git a/packages/odyssey-react-mui/src/test-selectors/odysseyTestSelectors.ts b/packages/odyssey-react-mui/src/test-selectors/odysseyTestSelectors.ts index a096f84929..348d0b4b67 100644 --- a/packages/odyssey-react-mui/src/test-selectors/odysseyTestSelectors.ts +++ b/packages/odyssey-react-mui/src/test-selectors/odysseyTestSelectors.ts @@ -11,11 +11,13 @@ */ import { type FeatureTestSelector } from "./featureTestSelector"; +import { BannerTestSelectors } from "../Banner"; import { CalloutTestSelectors } from "../Callout"; import { TabsTestSelectors } from "../Tabs"; import { TextFieldTestSelectors } from "../TextField"; export const odysseyTestSelectors = { + Banner: BannerTestSelectors, Callout: CalloutTestSelectors, Tabs: TabsTestSelectors, TextField: TextFieldTestSelectors, diff --git a/packages/odyssey-storybook/src/components/odyssey-mui/Banner/Banner.stories.tsx b/packages/odyssey-storybook/src/components/odyssey-mui/Banner/Banner.stories.tsx index 9e704b1ac0..d793f66d24 100644 --- a/packages/odyssey-storybook/src/components/odyssey-mui/Banner/Banner.stories.tsx +++ b/packages/odyssey-storybook/src/components/odyssey-mui/Banner/Banner.stories.tsx @@ -18,6 +18,7 @@ import { } from "@okta/odyssey-react-mui"; import { Meta, StoryObj } from "@storybook/react"; +import { queryOdysseySelector } from "@okta/odyssey-react-mui/test-selectors"; import { MuiThemeDecorator } from "../../../../.storybook/components"; import { userEvent, within } from "@storybook/testing-library"; import { expect, jest } from "@storybook/jest"; @@ -145,6 +146,20 @@ export const Linked: StoryObj = { await expect(link?.tagName).toBe("A"); await expect(link?.href).toBe(`${link?.baseURI}#anchor`); }); + + await step("has visible link", async () => { + const element = queryOdysseySelector({ + canvas: within(canvasElement), + componentName: "Banner", + templateArgs: { + role: "status", + }, + }).select?.("link", { + linkText: "View report", + }).element; + + expect(element).toBeVisible(); + }); }, }; @@ -161,5 +176,19 @@ export const Dismissible: StoryObj = { await expect(args.onClose).toHaveBeenCalled(); await axeRun("Dismissible Banner"); }); + + await step("has visible close button", async () => { + const element = queryOdysseySelector({ + canvas: within(canvasElement), + componentName: "Banner", + templateArgs: { + role: "alert", + }, + }).select?.("closeButton", { + labelText: "Close", + }).element; + + expect(element).toBeVisible(); + }); }, };