Utilising SDK modules
Introduction
Alokai SDK is a framework-agnostic communication layer in Alokai Integrations. It communicates with Commerce Platforms and third-party services through the Server Middleware, which works as a proxy. Alokai SDK creates a contract between the storefront and the Server Middleware.
The middlewareModule is a module of the Alokai SDK that allows you to interact with the Storefront API. It is designed to work seamlessly with other Alokai SDK modules, such as those for various eCommerce platforms like SAP Commerce Cloud.
In this guide, we'll show you how to use the SDK modules in your Storefront application.
Installation
To use a new module, for instance the SAP Commerce Cloud, you'll need to follow the below steps:
Installing the middleware API module
Remember that each time you add an SDK module, it should have a relevant middleware API Client installed as well. In Storefront, the middleware API Client should be installed into the apps/storefront-middleware directory.
- Install the API Client (the server).
yarn workspace storefront-middleware add @vsf-enterprise/sapcc-api
- Update
apps/storefront-middleware/middleware.config.tsfile.
- Add new API-client integration to the config (more info here)
// apps/storefront-middleware/middleware.config.ts
const config = {
integrations: {
...,
sapcc: {
location: '@vsf-enterprise/sapcc-api/server',
configuration: {
OAuth: {
uri: process.env.SAPCC_OAUTH_URI,
clientId: process.env.SAPCC_OAUTH_CLIENT_ID,
clientSecret: process.env.SAPCC_OAUTH_CLIENT_SECRET,
tokenEndpoint: process.env.SAPCC_OAUTH_TOKEN_ENDPOINT,
tokenRevokeEndpoint: process.env.SAPCC_OAUTH_TOKEN_REVOKE_ENDPOINT,
cookieOptions: {
'vsf-sap-token': { secure: process.env.NODE_ENV !== 'development' }
}
},
api: {
uri: process.env.SAPCC_API_URI,
baseSiteId: 'apparel-uk',
catalogId: 'apparelProductCatalog',
catalogVersion: 'Online',
defaultLanguage: 'en',
defaultCurrency: 'GBP'
},
}
}
},
};
- Export the API Client
Endpointstype fromstorefront-middleware/types.tsfile.
export type { Endpoints as SapccEndpoints } from "@vsf-enterprise/sapcc-api";
- Update SDK config.
- Add the new module inside SDK configuration.
// apps/storefront-unified-nextjs/sdk/config.ts
import { SapccEndpoints } from "storefront-middleware/types"; import { defineSdkConfig } from '@vue-storefront/next';
export function getSdkConfig() {
return defineSdkConfig(({ buildModule, config, getRequestHeaders, middlewareModule }) => ({
// ...
sapcc: buildModule(middlewareModule<SapccEndpoints>, {
apiUrl: `${config.middlewareUrl}/sapcc`,
defaultRequestConfig: {
headers: getRequestHeaders(),
},
}),
}));
}
Now you can use both sdk.unified.<methodName>, which returns the Unified Data Model, and sdk.sapcc.<methodName> which returns the raw data.
Real World Examples
Adding Product Reviews with SAP SDK
In this example, we'll create a custom React hook that utilizes useQuery and sdk.sapcc.createProductReview to add product reviews. We'll also create a form component for adding reviews and update the existing ProductReviews component to include the form.
Creating the useAddProductReview Hook
- Create a new file
useAddProductReview.tsin ahooks/directory. - Import the necessary dependencies, including the
useQueryhook and the SAP SDK module. - Implement the
useAddProductReview()hook to utilize useQuery and thesdk.sapcc.createProductReviewmethod to add a product review. - Return the necessary variables and functions from the hook.
import { useMutation } from "@tanstack/react-query";
import { sdk } from "~/sdk";
export const useAddProductReview = (productCode: string) => {
return useMutation(["addProductReview", productCode], ({ review }) =>
sdk.sapcc.createProductReview({ productCode, review })
);
};
Update the index.ts in the hooks/ directory and export useAddProductReview module:
export * from "./useAddProductReview";
Creating the AddProductReviewForm Component
- Create a new client component
add-product-review-form.tsxin thecomponents/directory. - Import the necessary React components from the
@storefront-uilibrary (e.g.,SfInput,SfTextarea). - Import the
useAddProductReviewhook. - Define the
AddProductReviewFormcomponent as a client component. - Implement the form submission handler function that will utilize the
createProductReviewfunction from theuseAddProductReviewhook. - Render the form fields and UI components using SFUI library.
- Export the
AddProductReviewFormcomponent for use in other components.
"use client";
import {
SfButton,
SfInput,
SfTextarea,
SfRatingButton,
} from "@storefront-ui/react";
import { resolveFormData } from "@/helpers/form-data";
import useAddProductReview from "@/hooks";
interface AddProductReviewFormProps {
productId: string;
}
export function AddProductReviewForm({ productId }: AddProductReviewFormProps) {
const createProductReview = useAddProductReview(productId);
const handleSubmit: FormEventHandler<HTMLFormElement> = (event) => {
event.preventDefault();
createProductReview.mutate(
{ review: resolveFormData(event.currentTarget) },
{
onSuccess() {
// Handle success
console.log("Product review submitted successfully");
},
onError() {
// Handle error
console.error("Failed to submit product review:", error);
},
}
);
};
return (
<form onSubmit={handleSubmit} className="space-y-5 mx-3">
<h3 className="my-3">Write a Review</h3>
<div>
<p id="rating">Select Rating</p>
<SfRatingButton name="rating" aria-labelledby="rating" />
</div>
<div>
<label htmlFor="title">Title:</label>
<SfInput id="title" type="text" name="title" required />
</div>
<div>
<label htmlFor="review" className="block">
Review:
</label>
<SfTextarea id="review" name="review" required />
</div>
<SfButton type="submit">Submit Review</SfButton>
</form>
);
}
Updating the ProductReviews Component
- Import the
AddProductReviewFormcomponent into the existingProductReviewscomponent. - Add the
AddProductReviewFormcomponent to the JSX of theProductReviewscomponent.
"use client";
// Some of the imports was omitted for brevity
import { useTranslations } from "next-intl";
import { useQuery } from "@tanstack/react-query";
import { useSdk } from "@/sdk/sdk-context";
import Review from "./ui/review";
import AddProductReviewForm from "./add-product-review-form";
interface ProductReviewsProps {
productId: string;
}
export function ProductReviews({ productId }: ProductReviewsProps) {
// ... Some code was omitted for brevity
const t = useTranslations("ProductReviews");
const sdk = useSdk();
const reviews = useQuery({
queryFn: () => sdk.unified.getProductReviews({ productId }),
// ...
});
return (
<>
{/* Existing code for displaying product reviews */}
{reviewsList.map((review) => (
<Review
key={review.id}
content={review.text}
author={review.reviewer}
title={review.title}
rating={review.rating}
date={review.createdAt}
showLessText={t("readLess")}
showMoreText={t("readMore")}
/>
))}
{/* Add product review form */}
<AddProductReviewForm productId={productId} />
</>
);
}