Null checks
Add null checks to product, category, and content page
Previously, category and product pages were always guaranteed to render with a category
or product
prop respectively, even if the data for that page had not yet been fetched. If the data was not available, the pages would render with a mock category or product object, with just a few fields on it.
Whilst this made the category and product page templates simpler in some ways, it meant that we needed checks elsewhere to determine whether a product or category was mocked or not, which added a lot of overhead. It also led to the requirement of a cacheHit
prop on category, product, and content pages in order to render a loading state when there was no real category or product data to load.
In 5.0, product and category pages will no longer have a mocked product/category object passed to them, which will require some small changes to the template.
Also, content pages will receive a page
prop, which makes it a little easier to work with.
Category
Previously you may have used the cacheHit
prop to determine whether or not to show a loading state. Instead, use the existence of the category
:
const Category = ({ category, result }) => {
// if there is no category data, render a loading state
if (!category) {
return <CategoryLoadingState />;
}
// otherwise render the category
return (
<CategoryWrapper>
<CategoryHeader category={category} />
// etc
</CategoryWrapper>
);
};
Product
As with categories, cacheHit
was used to determine whether the product was ready for render. Instead, use the existence of the product.
For example:
const Product = ({ product }) => {
const initialVariant = useVariantFromUrl();
const variantHandler = useProductVariants(product, { initialVariant });
// Return loading state early if there is no product
if (!product)
return (
<ProductContainer>
<ProductPageLoadingState />
</ProductContainer>
);
const { selectedVariant, getMissingOptions } = variantHandler;
const images = product.images || [];
const parents = getParentOrCanonicalRoute(data?.route?.parents, product);
const relatedProducts = product.relatedProducts;
return <ProductContainer>// etc</ProductContainer>;
};
Content Page
Content pages also previously received a cacheHit
prop. In 5.0, they will instead receive a page
prop, which contains the data for the page.
// before
function ContentPage(props) {
const { result, cacheHit } = props;
return (
<>
<Header>
<MaxWidth>
{cacheHit ? (
result.data.route.object.name
) : (
<LoadingLine heightPx={27} widthRem={15} />
)}
</MaxWidth>
</Header>
// etc
</>
);
}
// after
/// ꜜ ꜜ ꜜ ꜜ ꜜ ꜜ ꜜ ꜜ ꜜ ꜜ ꜜ
function ContentPage(props) {
const { page } = props;
return (
<>
<Header>
<MaxWidth>
{page ? page.name : <LoadingLine heightPx={27} widthRem={15} />}
</MaxWidth>
</Header>
// etc
</>
);
}