@evenicanpm/storefront-core 2.0.0 → 2.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.storybook/main.ts +2 -3
- package/.storybook/preview.tsx +0 -2
- package/__mocks__/create-mutation.ts +16 -8
- package/__mocks__/next-image.tsx +12 -3
- package/package.json +2 -2
- package/src/api-manager/datasources/d365/d365-categories.datasource.ts +2 -3
- package/src/api-manager/datasources/d365/d365-order.datasource.ts +4 -4
- package/src/api-manager/datasources/d365/d365-organization.datasource.ts +15 -8
- package/src/api-manager/datasources/d365/d365-product.datasource.ts +31 -19
- package/src/api-manager/datasources/d365/d365-user.datasource.ts +47 -19
- package/src/api-manager/datasources/e4/address/e4-address.remaps.ts +2 -2
- package/src/api-manager/datasources/e4/cart/e4-cart.remaps.ts +1 -1
- package/src/api-manager/datasources/e4/product/e4-product.remaps.ts +3 -3
- package/src/api-manager/datasources/e4/user/e4-user.datasource.ts +4 -8
- package/src/api-manager/index.ts +10 -127
- package/src/api-manager/lib/get-graphql-client.ts +2 -2
- package/src/api-manager/schemas/product.schema.ts +9 -0
- package/src/api-manager/services/create-extension-query.ts +1 -1
- package/src/api-manager/services/create-query.ts +106 -266
- package/src/api-manager/types/Datasource.ts +0 -3
- package/src/cms/blocks/components/category-card.tsx +0 -1
- package/src/cms/blocks/components/category-carousel/index.tsx +0 -1
- package/src/cms/blocks/components/featured-categories.tsx +1 -2
- package/src/cms/blocks/components/featured-products.tsx +1 -2
- package/src/cms/blocks/components/footer/index.tsx +0 -1
- package/src/cms/blocks/components/footer/sections/footer-app-store.tsx +1 -1
- package/src/cms/blocks/components/footer/sections/footer-contact.tsx +0 -1
- package/src/cms/blocks/components/footer/sections/footer-links.tsx +1 -1
- package/src/cms/blocks/components/footer/sections/footer-logo.tsx +0 -1
- package/src/cms/blocks/components/footer/sections/footer-social-links.tsx +0 -1
- package/src/cms/blocks/components/footer.tsx +0 -1
- package/src/cms/blocks/components/hero-carousel/index.tsx +0 -1
- package/src/cms/blocks/components/hero.tsx +0 -1
- package/src/cms/blocks/components/image.tsx +0 -1
- package/src/cms/blocks/components/media-card.tsx +0 -1
- package/src/cms/blocks/components/product-carousel/index.tsx +0 -1
- package/src/cms/blocks/components/product-section-fullwidth/index.tsx +0 -1
- package/src/cms/blocks/components/rich-text.tsx +0 -1
- package/src/cms/blocks/components/seo/index.tsx +1 -2
- package/src/cms/blocks/components/services/index.tsx +0 -1
- package/src/cms/blocks/components/services/service-card.tsx +0 -1
- package/src/cms/blocks/components/shared/featured-product-card.tsx +0 -1
- package/src/cms/blocks/components/shared/product-category-item.tsx +1 -1
- package/src/cms/blocks/components/shared/product-grid.tsx +0 -1
- package/src/cms/blocks/components/shared/top-categories-card.tsx +0 -1
- package/src/cms/blocks/components/shared/top-rating-product-card.tsx +0 -1
- package/src/cms/blocks/icons/components/category.tsx +0 -1
- package/src/cms/blocks/icons/components/dotted-star.tsx +0 -1
- package/src/cms/blocks/icons/components/fallback-icon.tsx +0 -1
- package/src/cms/blocks/icons/components/gift-box.tsx +0 -1
- package/src/cms/blocks/icons/components/light.tsx +0 -1
- package/src/cms/blocks/icons/components/new-arrival.tsx +0 -1
- package/src/cms/blocks/icons/components/rank-badge.tsx +0 -1
- package/src/components/BazaarTextField.tsx +7 -7
- package/src/components/CountryInput.stories.tsx +4 -2
- package/src/components/T/__tests__/T.test.tsx +9 -13
- package/src/components/T/index.tsx +0 -1
- package/src/components/Typography.tsx +0 -1
- package/src/components/_tests_/site-logo.test.tsx +4 -5
- package/src/components/categories/category-list/category-list.tsx +1 -1
- package/src/components/countries-input.tsx +1 -1
- package/src/components/nav-link/nav-link.tsx +2 -8
- package/src/components/navbar/mega-menu/mega-menu.tsx +7 -1
- package/src/components/navbar/mobile-menu/mobile-menu.test.tsx +2 -1
- package/src/components/navbar/nav-list/cms-nav.test.tsx +0 -1
- package/src/components/no-records.tsx +0 -1
- package/src/components/product-cards/favorite-button.tsx +0 -1
- package/src/components/product-cards/product-card/styles/index.ts +2 -2
- package/src/components/product-cards/product-card-plp-list/ProductCardPlpList.stories.tsx +0 -1
- package/src/components/product-cards/product-card-search/ProductCardSearch.stories.tsx +0 -1
- package/src/components/product-dimensions/Dimensions.stories.tsx +2 -4
- package/src/components/product-dimensions/compound/dimensions-group-list-chip.tsx +1 -1
- package/src/components/product-dimensions/compound/dimensions.tsx +1 -1
- package/src/components/product-quantity-buttons/ProductQuantity.stories.tsx +1 -3
- package/src/components/product-quantity-buttons/__tests__/product-quantity-buttons.test.tsx +3 -2
- package/src/components/product-quantity-buttons/compound/quantity-buttons-root.tsx +1 -1
- package/src/components/product-quantity-buttons/index.tsx +0 -1
- package/src/components/product-quantity-variants/ProductQuantity.stories.tsx +1 -3
- package/src/components/products-view/ProductsGrid.stories.tsx +1 -3
- package/src/components/products-view/ProductsList.stories.tsx +1 -3
- package/src/components/products-view/__tests__/products-view.test.tsx +20 -9
- package/src/components/products-view/index.tsx +1 -1
- package/src/components/scrollbar/Scrollbar.stories.tsx +1 -3
- package/src/components/scrollbar/__tests__/scrollbar.test.tsx +7 -1
- package/src/components/search-bar/SearchBarLarge.stories.tsx +1 -3
- package/src/components/search-bar/compound/results-item-lg.tsx +0 -1
- package/src/components/search-bar/compound/results-item-sm.tsx +0 -1
- package/src/components/search-bar/compound/textfield-adornment-category.tsx +0 -1
- package/src/components/search-bar/compound/textfield.tsx +0 -1
- package/src/components/search-bar/utils/findCategoryNameById.ts +3 -3
- package/src/components/section/__tests__/section.test.tsx +14 -7
- package/src/components/side-nav/SideNav.stories.tsx +1 -1
- package/src/components/site-logo.tsx +8 -1
- package/src/components/wishlist-dialogs/add-to-wishlist/add-to-wishlist-button.tsx +1 -1
- package/src/components/wishlist-dialogs/add-to-wishlist/compound/add-to-wishlist-bottom-ui.tsx +1 -1
- package/src/components/wishlist-dialogs/add-to-wishlist/compound/wishlist-dialog-header.tsx +0 -1
- package/src/components/wishlist-dialogs/create-wishlist/compound/create-wishlist-bottom-ui.tsx +1 -1
- package/src/hooks/use-nextauth-session.ts +4 -1
- package/src/lib/lib.ts +1 -1
- package/src/lib/page-slugs.ts +0 -2
- package/src/lib/refiner-utils.ts +3 -3
- package/src/pages/account/account-navigation.tsx +17 -20
- package/src/pages/account/addresses/address-form.tsx +15 -7
- package/src/pages/account/dashboard-header.tsx +1 -1
- package/src/pages/cart/checkout-form.tsx +1 -1
- package/src/pages/checkout/checkout-alt-form/checkout-step.tsx +1 -1
- package/src/pages/checkout/checkout-alt-form/steps/address/new-address-form.tsx +1 -1
- package/src/pages/checkout/checkout-alt-form/steps/payment/payment-details.tsx +5 -2
- package/src/pages/checkout/checkout-alt-summary/cart-item.tsx +1 -1
- package/src/pages/checkout/checkout-alt-summary/checkout-alt-summary.tsx +1 -1
- package/src/pages/confirmation/address.tsx +1 -1
- package/src/pages/confirmation/confirmation-summary.tsx +1 -1
- package/src/pages/product-details/currency.ts +1 -1
- package/src/pages/product-details/product-intro/compound/thumbnail-with-skeleton.tsx +4 -1
- package/src/pages/product-list/breadcrumbs.tsx +0 -1
- package/src/pages/product-list/list-filter.tsx +0 -1
- package/src/pages/product-list/product-list-context.tsx +1 -1
- package/src/pages/product-list/product-list-view.tsx +2 -2
- package/src/pages/product-list/selected-facets.tsx +1 -1
- package/src/pages/quickorder/context.ts +8 -2
- package/src/pages/quickorder/order-upload.tsx +26 -8
- package/src/pages/quickorder/provider.tsx +8 -9
- package/src/pages/quickorder/quick-order.tsx +17 -11
- package/src/providers/nav-provider/index.tsx +1 -1
- package/tsconfig.json +0 -1
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import { Box, Container } from "@mui/material";
|
|
2
2
|
import Grid from "@mui/material/Grid2";
|
|
3
|
-
import React from "react";
|
|
4
3
|
|
|
5
4
|
// Local components
|
|
6
5
|
import MediaCard from "@/cms/blocks/components/media-card";
|
|
@@ -23,7 +22,7 @@ const FeaturedProducts = (productsData: FeaturedProductsBlock) => {
|
|
|
23
22
|
size={3}
|
|
24
23
|
display="flex"
|
|
25
24
|
justifyContent="center"
|
|
26
|
-
key={
|
|
25
|
+
key={`product_index_${i}`}
|
|
27
26
|
>
|
|
28
27
|
<MediaCard
|
|
29
28
|
name={product?.description ?? ""}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import FlexBox from "@evenicanpm/storefront-core/src/components/flex-box/flex-box";
|
|
2
2
|
import { Box } from "@mui/material";
|
|
3
|
-
import
|
|
3
|
+
import { Fragment } from "react";
|
|
4
4
|
import { MdFacebook as Facebook } from "react-icons/md";
|
|
5
5
|
import { Link } from "react-router-dom";
|
|
6
6
|
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import { Paragraph } from "@evenicanpm/storefront-core/src/components/Typography";
|
|
2
2
|
import Grid from "@mui/material/Grid2";
|
|
3
|
-
import React from "react";
|
|
4
3
|
import type { SocialLink } from "@/cms/blocks/components/footer/interfaces";
|
|
5
4
|
import SocialLinks from "@/cms/blocks/components/footer/sections/footer-social-links";
|
|
6
5
|
import { Heading } from "@/cms/blocks/components/footer/styles/index";
|
|
@@ -5,7 +5,6 @@ import { Paragraph } from "@evenicanpm/storefront-core/src/components/Typography
|
|
|
5
5
|
import Grid from "@mui/material/Grid2";
|
|
6
6
|
import useTheme from "@mui/material/styles/useTheme";
|
|
7
7
|
import useMediaQuery from "@mui/material/useMediaQuery";
|
|
8
|
-
import React from "react";
|
|
9
8
|
|
|
10
9
|
interface Props {
|
|
11
10
|
description: string;
|
|
@@ -4,7 +4,6 @@
|
|
|
4
4
|
import FlexBox from "@evenicanpm/storefront-core/src/components/flex-box/flex-box";
|
|
5
5
|
import IconButton from "@mui/material/IconButton";
|
|
6
6
|
import styled from "@mui/material/styles/styled";
|
|
7
|
-
import React from "react";
|
|
8
7
|
import {
|
|
9
8
|
FaGoogle as Google,
|
|
10
9
|
FaInstagram as Instagram,
|
|
@@ -5,7 +5,6 @@
|
|
|
5
5
|
import { Carousel } from "@evenicanpm/storefront-core/src/components/carousel/index";
|
|
6
6
|
import CarouselCard1 from "@evenicanpm/storefront-core/src/components/carousel-cards/carousel-card-1/index";
|
|
7
7
|
import { Box, Container } from "@mui/material";
|
|
8
|
-
import React from "react";
|
|
9
8
|
import type { HeroCarouselBlock, Slide } from "@/cms/blocks/interfaces";
|
|
10
9
|
import { getImageUrl } from "@/cms/endpoints";
|
|
11
10
|
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import { Box, Button, Container, Typography } from "@mui/material";
|
|
2
2
|
import Image from "next/image";
|
|
3
3
|
import NextLink from "next/link";
|
|
4
|
-
import React from "react";
|
|
5
4
|
import type { HeroSectionBlock } from "@/cms/blocks/interfaces";
|
|
6
5
|
import cmsEndPoints from "@/cms/endpoints";
|
|
7
6
|
|
|
@@ -6,7 +6,6 @@ import ProductCard from "@evenicanpm/storefront-core/src/components/product-card
|
|
|
6
6
|
import { Section } from "@evenicanpm/storefront-core/src/components/section";
|
|
7
7
|
import type { SimpleProduct } from "@msdyn365-commerce/retail-proxy";
|
|
8
8
|
import { Box } from "@mui/system";
|
|
9
|
-
import React from "react";
|
|
10
9
|
import { Light } from "@/cms/blocks/icons/index";
|
|
11
10
|
import type { Product, ProductCarouselBlock } from "@/cms/blocks/interfaces";
|
|
12
11
|
import { getImageUrl } from "@/cms/endpoints";
|
|
@@ -13,7 +13,6 @@ import type { SimpleProduct } from "@msdyn365-commerce/retail-proxy";
|
|
|
13
13
|
import Grid from "@mui/material/Grid2";
|
|
14
14
|
import Image from "next/image";
|
|
15
15
|
import NextLink from "next/link";
|
|
16
|
-
import React from "react";
|
|
17
16
|
// Icons
|
|
18
17
|
import { getIcon } from "@/cms/blocks/icons/index";
|
|
19
18
|
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import React from "react";
|
|
2
1
|
import { Helmet } from "react-helmet-async";
|
|
3
2
|
import type { MetaItem, SeoPageData } from "@/cms/blocks/interfaces";
|
|
4
3
|
import cmsEndPoints from "@/cms/endpoints";
|
|
@@ -35,7 +34,7 @@ const Seo = (pageData: SeoPageData) => {
|
|
|
35
34
|
<meta name="googlebot" content="noindex"></meta>
|
|
36
35
|
</>
|
|
37
36
|
)}
|
|
38
|
-
{pageData?.seo?.meta?.map((metaItem: MetaItem,
|
|
37
|
+
{pageData?.seo?.meta?.map((metaItem: MetaItem, _i: number) => (
|
|
39
38
|
<meta
|
|
40
39
|
name={metaItem.name}
|
|
41
40
|
key={metaItem.id}
|
|
@@ -9,7 +9,6 @@ import Card from "@mui/material/Card";
|
|
|
9
9
|
import Fab from "@mui/material/Fab";
|
|
10
10
|
import Grid from "@mui/material/Grid2";
|
|
11
11
|
import styled from "@mui/material/styles/styled";
|
|
12
|
-
import React from "react";
|
|
13
12
|
// CUSTOM ICON COMPONENTS
|
|
14
13
|
import { getIcon } from "@/cms/blocks/icons/index";
|
|
15
14
|
|
|
@@ -2,7 +2,6 @@
|
|
|
2
2
|
import HoverBox from "@evenicanpm/storefront-core/src/components/HoverBox";
|
|
3
3
|
import Image from "@evenicanpm/storefront-core/src/components/Image";
|
|
4
4
|
import { H4 } from "@evenicanpm/storefront-core/src/components/Typography";
|
|
5
|
-
import React from "react";
|
|
6
5
|
|
|
7
6
|
// ==========================================================
|
|
8
7
|
type Props = { title: string; imgUrl: string };
|
|
@@ -3,7 +3,7 @@ import BazaarImage from "@evenicanpm/storefront-core/src/components/BazaarImage"
|
|
|
3
3
|
// GLOBAL CUSTOM COMPONENTS
|
|
4
4
|
import { H4 } from "@evenicanpm/storefront-core/src/components/Typography";
|
|
5
5
|
import { type SxProps, styled, type Theme } from "@mui/material/styles";
|
|
6
|
-
import
|
|
6
|
+
import type HtmlHTMLAttributes from "react";
|
|
7
7
|
|
|
8
8
|
// STYLED COMPONENT
|
|
9
9
|
const StyledBazaarCard = styled(BazaarCard)(({ theme }) => ({
|
|
@@ -3,7 +3,6 @@ import ProductCard from "@evenicanpm/storefront-core/src/components/product-card
|
|
|
3
3
|
import { Section } from "@evenicanpm/storefront-core/src/components/section";
|
|
4
4
|
import Box from "@mui/material/Box";
|
|
5
5
|
import Grid from "@mui/material/Grid2";
|
|
6
|
-
import React from "react";
|
|
7
6
|
|
|
8
7
|
// CUSTOM DATA MODEL
|
|
9
8
|
|
|
@@ -6,7 +6,6 @@ import Card from "@mui/material/Card";
|
|
|
6
6
|
import Chip from "@mui/material/Chip";
|
|
7
7
|
import { useTheme } from "@mui/material/styles";
|
|
8
8
|
import styled from "@mui/material/styles/styled";
|
|
9
|
-
import React from "react";
|
|
10
9
|
|
|
11
10
|
// STYLED COMPONENT
|
|
12
11
|
const StyledChip = styled(Chip)({
|
|
@@ -9,7 +9,6 @@ import {
|
|
|
9
9
|
// CUSTOM UTILS LIBRARY FUNCTION
|
|
10
10
|
import { currency } from "@evenicanpm/storefront-core/src/lib/lib";
|
|
11
11
|
import Rating from "@mui/material/Rating";
|
|
12
|
-
import React from "react";
|
|
13
12
|
|
|
14
13
|
// ======================================================
|
|
15
14
|
interface Props {
|
|
@@ -2,7 +2,6 @@
|
|
|
2
2
|
import type { OverridableComponent } from "@mui/material/OverridableComponent";
|
|
3
3
|
import type { SvgIconTypeMap } from "@mui/material/SvgIcon";
|
|
4
4
|
import createSvgIcon from "@mui/material/utils/createSvgIcon";
|
|
5
|
-
import React from "react";
|
|
6
5
|
|
|
7
6
|
const Category: OverridableComponent<SvgIconTypeMap> = createSvgIcon(
|
|
8
7
|
<svg fill="currentColor" viewBox="0 0 64 64">
|
|
@@ -12,20 +12,20 @@ export default function BazaarTextField({
|
|
|
12
12
|
InputProps,
|
|
13
13
|
...props
|
|
14
14
|
}: Props) {
|
|
15
|
-
const boxProps:
|
|
16
|
-
const textFieldProps:
|
|
15
|
+
const boxProps: Record<string, unknown> = {};
|
|
16
|
+
const textFieldProps: Record<string, unknown> = {};
|
|
17
17
|
|
|
18
18
|
// Splits props into Box and TextField props. Bracket notation allows dynamic names like "mt" or "mb".
|
|
19
|
-
for (const key
|
|
19
|
+
for (const [key, value] of Object.entries(props)) {
|
|
20
20
|
if (SPACE_PROPS_LIST.has(key)) {
|
|
21
|
-
|
|
21
|
+
boxProps[key] = value;
|
|
22
22
|
} else {
|
|
23
|
-
|
|
23
|
+
textFieldProps[key] = value;
|
|
24
24
|
}
|
|
25
25
|
}
|
|
26
26
|
|
|
27
27
|
return (
|
|
28
|
-
<Box {...boxProps}>
|
|
28
|
+
<Box {...(boxProps as BoxProps)}>
|
|
29
29
|
{/* INPUT LEVEL TEXT */}
|
|
30
30
|
{label ? (
|
|
31
31
|
<H6 mb={1} fontSize={13} color="grey.700">
|
|
@@ -39,7 +39,7 @@ export default function BazaarTextField({
|
|
|
39
39
|
...InputProps,
|
|
40
40
|
style: { ...InputProps?.style, height: 44 },
|
|
41
41
|
}}
|
|
42
|
-
{...textFieldProps}
|
|
42
|
+
{...(textFieldProps as TextFieldProps)}
|
|
43
43
|
/>
|
|
44
44
|
</Box>
|
|
45
45
|
);
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { CountryRegionInfo } from "@msdyn365-commerce/retail-proxy";
|
|
1
2
|
import type { Meta, StoryObj } from "@storybook/react";
|
|
2
3
|
import { useState } from "react";
|
|
3
4
|
import { countries } from "../../__mocks__/countries";
|
|
@@ -12,8 +13,9 @@ const meta = {
|
|
|
12
13
|
export default meta;
|
|
13
14
|
type Story = StoryObj<typeof CountryInput>;
|
|
14
15
|
|
|
15
|
-
const Template = (args:
|
|
16
|
-
const [selectedCountry, setSelectedCountry] =
|
|
16
|
+
const Template = (args: React.ComponentProps<typeof CountryInput>) => {
|
|
17
|
+
const [selectedCountry, setSelectedCountry] =
|
|
18
|
+
useState<CountryRegionInfo | null>(null);
|
|
17
19
|
console.log(selectedCountry);
|
|
18
20
|
|
|
19
21
|
return (
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { render, screen } from "@testing-library/react";
|
|
2
|
-
import { vi } from "vitest";
|
|
2
|
+
import { describe, expect, it, vi } from "vitest";
|
|
3
3
|
import T from "../index";
|
|
4
4
|
|
|
5
5
|
vi.mock("next-intl", () => ({
|
|
@@ -19,7 +19,7 @@ vi.mock("next-intl", () => ({
|
|
|
19
19
|
describe("T (Translation Component)", () => {
|
|
20
20
|
it("renders translation for given path", () => {
|
|
21
21
|
render(<T path="HomePage.welcome" />);
|
|
22
|
-
expect(screen.getByText("Welcome to our store")).
|
|
22
|
+
expect(screen.getByText("Welcome to our store")).toBeTruthy();
|
|
23
23
|
});
|
|
24
24
|
|
|
25
25
|
it("renders multiple translations", () => {
|
|
@@ -36,17 +36,17 @@ describe("T (Translation Component)", () => {
|
|
|
36
36
|
|
|
37
37
|
it("renders fallback path when translation not found", () => {
|
|
38
38
|
render(<T path="Unknown.path" />);
|
|
39
|
-
expect(screen.getByText("Unknown.path")).
|
|
39
|
+
expect(screen.getByText("Unknown.path")).toBeTruthy();
|
|
40
40
|
});
|
|
41
41
|
|
|
42
42
|
it("handles nested translation paths", () => {
|
|
43
43
|
render(<T path="Navigation.home" />);
|
|
44
|
-
expect(screen.getByText("Home")).
|
|
44
|
+
expect(screen.getByText("Home")).toBeTruthy();
|
|
45
45
|
});
|
|
46
46
|
|
|
47
47
|
it("renders common translations", () => {
|
|
48
48
|
render(<T path="Common.loading" />);
|
|
49
|
-
expect(screen.getByText("Loading...")).
|
|
49
|
+
expect(screen.getByText("Loading...")).toBeTruthy();
|
|
50
50
|
});
|
|
51
51
|
|
|
52
52
|
it("renders multiple different paths together", () => {
|
|
@@ -63,17 +63,13 @@ describe("T (Translation Component)", () => {
|
|
|
63
63
|
|
|
64
64
|
it("renders translation with special characters", () => {
|
|
65
65
|
render(<T path="Common.error" />);
|
|
66
|
-
expect(screen.getByText("An error occurred")).
|
|
66
|
+
expect(screen.getByText("An error occurred")).toBeTruthy();
|
|
67
67
|
});
|
|
68
68
|
|
|
69
69
|
it("accepts dynamic paths", () => {
|
|
70
70
|
const paths = ["HomePage.welcome", "Navigation.home", "Common.loading"];
|
|
71
71
|
const { container } = render(
|
|
72
|
-
|
|
73
|
-
{paths.map((path) => (
|
|
74
|
-
<T key={path} path={path} />
|
|
75
|
-
))}
|
|
76
|
-
</>,
|
|
72
|
+
paths.map((path) => <T key={path} path={path} />),
|
|
77
73
|
);
|
|
78
74
|
const text = container.textContent || "";
|
|
79
75
|
expect(text).toContain("Welcome to our store");
|
|
@@ -83,9 +79,9 @@ describe("T (Translation Component)", () => {
|
|
|
83
79
|
|
|
84
80
|
it("re-renders when path changes", () => {
|
|
85
81
|
const { rerender } = render(<T path="HomePage.welcome" />);
|
|
86
|
-
expect(screen.getByText("Welcome to our store")).
|
|
82
|
+
expect(screen.getByText("Welcome to our store")).toBeTruthy();
|
|
87
83
|
|
|
88
84
|
rerender(<T path="Navigation.home" />);
|
|
89
|
-
expect(screen.getByText("Home")).
|
|
85
|
+
expect(screen.getByText("Home")).toBeTruthy();
|
|
90
86
|
});
|
|
91
87
|
});
|
|
@@ -3,7 +3,6 @@
|
|
|
3
3
|
import Box, { type BoxProps } from "@mui/material/Box";
|
|
4
4
|
import styled from "@mui/material/styles/styled";
|
|
5
5
|
import clsx from "clsx";
|
|
6
|
-
import React from "react";
|
|
7
6
|
|
|
8
7
|
// ==============================================================
|
|
9
8
|
type Ellipsis = { ellipsis: number };
|
|
@@ -15,11 +15,10 @@ vi.mock("next/link", () => ({
|
|
|
15
15
|
describe("SiteLogo", () => {
|
|
16
16
|
it("renders logo image", () => {
|
|
17
17
|
render(<SiteLogo />);
|
|
18
|
-
|
|
19
|
-
expect(
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
);
|
|
18
|
+
const logo = screen.getByAltText("E4 Logo");
|
|
19
|
+
expect(logo).toBeInTheDocument();
|
|
20
|
+
// next/image rewrites src to an optimized URL (e.g. /_next/image?url=...)
|
|
21
|
+
expect(logo.getAttribute("src")).toMatch(/logo-blue\.png/);
|
|
23
22
|
});
|
|
24
23
|
|
|
25
24
|
it("wraps logo in home link", () => {
|
|
@@ -9,7 +9,7 @@ import CategoryListItem from "@evenicanpm/storefront-core/src/components/categor
|
|
|
9
9
|
import MegaMenu1 from "@evenicanpm/storefront-core/src/components/categories/mega-menu/mega-menu-1";
|
|
10
10
|
import MegaMenu2 from "@evenicanpm/storefront-core/src/components/categories/mega-menu/mega-menu-2";
|
|
11
11
|
import type { CategoryHierarchy } from "@evenicanpm/storefront-core/src/lib/category-helpers";
|
|
12
|
-
import
|
|
12
|
+
import { createContext, type ReactNode, useContext } from "react";
|
|
13
13
|
|
|
14
14
|
type MegaMenuType = "default" | "mega-menu-1" | "mega-menu-2";
|
|
15
15
|
|
|
@@ -46,14 +46,8 @@ export default function NavLink({
|
|
|
46
46
|
pathname,
|
|
47
47
|
...props
|
|
48
48
|
}: Readonly<NavLinkProps>) {
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
try {
|
|
52
|
-
resolvedPathname = usePathname() ?? "";
|
|
53
|
-
} catch {
|
|
54
|
-
resolvedPathname = "";
|
|
55
|
-
}
|
|
56
|
-
}
|
|
49
|
+
const pathFromHook = usePathname();
|
|
50
|
+
const resolvedPathname = pathname ?? pathFromHook ?? "";
|
|
57
51
|
|
|
58
52
|
return (
|
|
59
53
|
<StyledLink
|
|
@@ -26,7 +26,13 @@ type MegaMenuContextType = {
|
|
|
26
26
|
checkOverflow: () => void;
|
|
27
27
|
};
|
|
28
28
|
const MegaMenuContext = createContext<MegaMenuContextType | null>(null);
|
|
29
|
-
const useMegaMenu = () =>
|
|
29
|
+
const useMegaMenu = () => {
|
|
30
|
+
const context = useContext(MegaMenuContext);
|
|
31
|
+
if (!context) {
|
|
32
|
+
throw new Error("useMegaMenu must be used within MegaMenu");
|
|
33
|
+
}
|
|
34
|
+
return context;
|
|
35
|
+
};
|
|
30
36
|
|
|
31
37
|
const Grid2Size = (length: number) => {
|
|
32
38
|
if (length === 1) return 12;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import MobileMenu from "@evenicanpm/storefront-core/src/components/navbar/mobile-menu/mobile-menu";
|
|
2
2
|
import { transformCmsNav } from "@evenicanpm/storefront-core/src/components/navbar/utils/transform-nav";
|
|
3
3
|
import { fireEvent, render, screen } from "@testing-library/react";
|
|
4
|
+
import type React from "react";
|
|
4
5
|
import { beforeEach, describe, it, vi } from "vitest";
|
|
5
6
|
import type { CmsNavItem } from "@/cms/interfaces/navigation";
|
|
6
7
|
|
|
@@ -11,7 +12,7 @@ vi.mock("@evenicanpm/storefront-core/src/providers/nav-provider", () => {
|
|
|
11
12
|
return {
|
|
12
13
|
NavContext: {
|
|
13
14
|
// We'll replace these in beforeEach per test
|
|
14
|
-
Provider: ({
|
|
15
|
+
Provider: ({ children }: { children: React.ReactNode }) => (
|
|
15
16
|
<div data-testid="nav-context-provider">{children}</div>
|
|
16
17
|
),
|
|
17
18
|
},
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import NavCms from "@evenicanpm/storefront-core/src/components/navbar/nav-list/index";
|
|
2
2
|
import { NavContext } from "@evenicanpm/storefront-core/src/providers/nav-provider";
|
|
3
3
|
import { render, screen } from "@testing-library/react";
|
|
4
|
-
import React from "react";
|
|
5
4
|
import { describe, expect, it } from "vitest";
|
|
6
5
|
|
|
7
6
|
describe("NavCms", () => {
|
|
@@ -3,7 +3,6 @@
|
|
|
3
3
|
import Favorite from "@mui/icons-material/Favorite";
|
|
4
4
|
import FavoriteBorder from "@mui/icons-material/FavoriteBorder";
|
|
5
5
|
import IconButton, { type IconButtonProps } from "@mui/material/IconButton";
|
|
6
|
-
import React from "react";
|
|
7
6
|
|
|
8
7
|
export interface FavoriteButtonProps extends Omit<IconButtonProps, "onClick"> {
|
|
9
8
|
isFavorite: boolean;
|
|
@@ -46,7 +46,7 @@ export const ContentWrapper = styled("div")({
|
|
|
46
46
|
},
|
|
47
47
|
});
|
|
48
48
|
|
|
49
|
-
const StyledBazaarCardType: StyledComponent<typeof BazaarCard,
|
|
50
|
-
StyledBazaarCard as StyledComponent<typeof BazaarCard,
|
|
49
|
+
const StyledBazaarCardType: StyledComponent<typeof BazaarCard, object, "div"> =
|
|
50
|
+
StyledBazaarCard as StyledComponent<typeof BazaarCard, object, "div">;
|
|
51
51
|
|
|
52
52
|
export default StyledBazaarCardType;
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
// Replace your-framework with the framework you are using, e.g. react-vite, nextjs, nextjs-vite, etc.
|
|
2
2
|
|
|
3
|
-
import type { Meta
|
|
4
|
-
import React from "react";
|
|
3
|
+
import type { Meta } from "@storybook/react";
|
|
5
4
|
import useVariants from "../../hooks/use-variants";
|
|
6
5
|
import { data, product } from "./__mocks__/data";
|
|
7
6
|
import { Dimensions } from "./compound/dimensions";
|
|
@@ -13,7 +12,6 @@ const meta = {
|
|
|
13
12
|
} satisfies Meta<typeof Dimensions>;
|
|
14
13
|
|
|
15
14
|
export default meta;
|
|
16
|
-
type Story = StoryObj<typeof meta>;
|
|
17
15
|
|
|
18
16
|
export const Interactive = () => {
|
|
19
17
|
const { handleChangeVariant, selectDimensions } = useVariants(product);
|
|
@@ -24,7 +22,7 @@ export const Interactive = () => {
|
|
|
24
22
|
handleChangeVariant={handleChangeVariant}
|
|
25
23
|
showDimensionError={true}
|
|
26
24
|
>
|
|
27
|
-
{data.dimensionGroups.map((group,
|
|
25
|
+
{data.dimensionGroups.map((group, _i) => (
|
|
28
26
|
<Dimensions.Group dimensions={group}>
|
|
29
27
|
<Dimensions.Group.Label />
|
|
30
28
|
<Dimensions.Group.List />
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import { DimensionGroup } from "@evenicanpm/storefront-core/src/components/product-dimensions/compound/dimensions-group";
|
|
3
3
|
import type { ProductDimensionValueInventoryAvailability } from "@msdyn365-commerce/retail-proxy";
|
|
4
|
-
import
|
|
4
|
+
import {
|
|
5
5
|
createContext,
|
|
6
6
|
type PropsWithChildren,
|
|
7
7
|
type ReactElement,
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
// Replace your-framework with the framework you are using, e.g. react-vite, nextjs, nextjs-vite, etc.
|
|
2
2
|
|
|
3
|
-
import type { Meta
|
|
4
|
-
import React from "react";
|
|
3
|
+
import type { Meta } from "@storybook/react";
|
|
5
4
|
import { QuantityButtons } from "./compound/quantity-buttons-root";
|
|
6
5
|
|
|
7
6
|
const meta = {
|
|
@@ -11,7 +10,6 @@ const meta = {
|
|
|
11
10
|
} satisfies Meta<typeof QuantityButtons>;
|
|
12
11
|
|
|
13
12
|
export default meta;
|
|
14
|
-
type Story = StoryObj<typeof meta>;
|
|
15
13
|
|
|
16
14
|
export const Interactive = () => {
|
|
17
15
|
return (
|