Vue Storefront is now Alokai! Learn More
GetProductDetails

GetProductDetails

Implements GetProductDetails Unified Method.

Source

import { defineApi } from "@vsf-enterprise/unified-api-sfcc";
import type { SFCCIntegrationContext } from "@vsf-enterprise/sfcc-api";
import type { Category, Product } from "@vsf-enterprise/sfcc-types";
import { getNormalizers } from "@vsf-enterprise/unified-api-sfcc/udl";
import { ProductGetParams } from "@vsf-enterprise/sfcc-types";


declare module "@vsf-enterprise/unified-api-sfcc" {
  interface GetProductDetailsExtendedArgs {
    /**
     * The additional fields to filter products.
     */
    product?: Omit<ProductGetParams, "perPricebook" | "id" | "currency" | "locale">;
  }
}


export const getProductDetails = defineApi.getProductDetails(async (context, args) => {
  const { id, sku } = args;
  const productId = sku || id;
  const product = await context.api.getProduct({ perPricebook: true, id: productId });

  const rootCategoryId = await getPrimaryCategoryId(context, product);
  const productCategory = rootCategoryId
    ? await context.api.getCategory({ id: rootCategoryId })
    : undefined;

  const { normalizeProduct, normalizeCategory } = getNormalizers(context);

  return {
    product: normalizeProduct(product),
    categoryHierarchy:
      productCategory?.parentCategoryTree?.map((category) =>
        normalizeCategory(category as Category),
      ) ?? [],
  };
});

async function getPrimaryCategoryId(context: SFCCIntegrationContext, product: Product) {
  if (product?.primaryCategoryId) {
    return product.primaryCategoryId;
  }
  const masterId = product.master?.masterId;
  if (!masterId) {
    return;
  }
  const masterProduct = await context.api.getProduct({ id: masterId });
  return masterProduct?.primaryCategoryId;
}