@apptus/esales-api
Version:
Library for making requests to Elevate 4 API v3
1,370 lines (1,346 loc) • 59.3 kB
TypeScript
/** Used to determine server settings to use. */
type Touchpoint = 'desktop' | 'mobile';
/** Session is used to handle session information for a specific visitor. */
interface Session {
/**
* Method for retrieving session information, synchronously
* or asynchronously. Returns a `SessionMetadata` object that
* contains `customerKey` and `sessionKey`.
*
* @example
* ```ts
* declare const session: Session;
*
* const { customerKey, sessionKey } = await session();
* ```
*/
(): SessionMetadata | Promise<SessionMetadata>;
}
/** Metadata information regarding a visitor, used during requests to the Elevate Storefront API. */
interface SessionMetadata {
/**
* A key that uniquely identifies the current visitor. Using UUIDs as keys are recommended.
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/common/query-parameters/#mandatory-parameters
*/
customerKey: string;
/**
* A unique key, identifying the session. Using UUIDs as keys are recommended.
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/common/query-parameters/#mandatory-parameters
*/
sessionKey: string;
}
/**
* Configuration required during initialization for the Elevate Storefront API.
*
* @example
* ```ts
* const config: Config = { ... };
* const api = elevate(config);
* ```
*/
interface Config {
/**
* The ID for the Elevate cluster for all subsequent API requests.
* Production/Test/Development clusters each have their own unique ID.
* The value for `clusterId` can be found in credentials tab in
* the Voyado Elevate app,
*
* The value should be:
* - An identifier in a format similar to `'w00000000'`
* - A URL with the origin to the Elevate cluster, e.g.
* `'https://w00000000.api.esales.apptus.cloud/'`
*
* @example
* ```ts
* const api = elevate({ clusterId: 'w00000000' });
* ```
*/
clusterId: string;
/** Required for loading correct products and behavior data. */
market: string;
/** Required for loading localized product and facet data. */
locale: string;
/** Used to determine various server settings. */
touchpoint: Touchpoint;
/** Configures how session metadata (customerKey & sessionKey) is retrieved before requests to the API */
session: Session;
}
/**
* Subset of Config for interacting with the Notifications API.
* @see Config
*/
type NotificationConfig = Pick<Config, 'clusterId' | 'market' | 'session'>;
/**
* Created from a validated `Config`. Used internally.
* @internal
*/
interface BaseOptions extends Omit<NotificationConfig, 'clusterId'> {
clusterUrl: string;
}
/**
* Created from a validated `Config`. Used internally.
* @internal
*/
interface FullOptions extends Omit<Config, 'clusterId'> {
clusterUrl: string;
}
type ViewId = 'production' | 'preview';
type FacetValue = boolean | string[] | FacetRange;
type FacetRange = {
min: number;
max?: number;
} | {
min?: number;
max: number;
};
interface FacetParams {
[key: string]: FacetValue;
}
/** Parameters shared between all Storefront queries */
interface BaseParams {
/** Setting this parameter can change the returned content between "preview" and "production" (default) */
viewId?: ViewId;
/** Set this parameter to `false` to not generate any event data for this request */
notify?: boolean;
}
/** Parameters that change product data based on current context (price used, channels, etc) */
interface ProductContextParams {
/** Set this parameter to change to a custom price that exists in your product feed */
priceId?: string;
/**
* Selects what channels to use, ONLINE or STORE, affecting stock-related ranking and filtering.
* Defaults to ONLINE|STORE
*/
channels?: 'ONLINE' | 'STORE' | 'ONLINE|STORE' | 'STORE|ONLINE';
/** One or more store keys from the product feed, used with channels and presented in the result */
stores?: string;
}
/** Parameters used by queries that search for items */
interface SearchParams {
/** The search query for this request */
q: string;
}
/** Paramaters used by pagination of products or content items */
interface PaginationParams {
/** For implementing pagination, how many items to fetch in the result (defaults to 60) */
limit?: number;
/** For implementing pagination, how many items to skip in the result */
skip?: number;
}
/** Paramaters that are shared for endpoints returning products */
interface ProductParams extends BaseParams, ProductContextParams {
/** A list of custom attributes to include on products in listings */
presentCustom?: string[];
/**
* A list of custom price ID's to include for products.
*
* Each ID must match a supplied custom price ID in the data feed.
* @example
* ['VIP', 'member']
*/
presentPrices?: string[];
/**
* The ID of a response template to apply to all product lists returned.
*
* Templates can adjust which attributes are returned for products, and makes
* `presentCustom` unnecessary. Templates can be imported via the Admin API.
* @see https://docs.elevate.voyado.cloud/elevate/4/guides/product-list-response-templates/
*/
templateId?: string;
}
/** Paramaters used by pages that list products, for pagination, sorting, and facets */
interface ProductListParams extends PaginationParams {
/** The facets to be passed along e.g.
* @example
* {
* "price": { "min": 10, "max": 100 }, // range
* "custom.fit": [ "slim", "regular" ], // multiple values
* }
*/
facets?: FacetParams;
/** Changes how products are sorted in the response */
sort?: SortType;
}
type ContentAlgorithm = 'NEWEST_CONTENT' | 'TOP_CONTENT';
interface RecommendationListConfiguration extends Pick<RecommendationList, 'label' | 'showMoreLink'> {
/**
* The identifier to use for this list. Typically a short name describing
* where on the page it's used.
*/
id: string;
/**
* Which algorithm to use for the recommendationList. Some algorithms require
* additional parameters for some page types.
*
* - `CART` - Unless `CartPage` is used, requires `params.cart` to be specified
* - `UPSELL | ALTERNATIVES` - Unless `ProductPage` is used,
* requires `params.productKey` to be specified
*/
algorithm?: Algorithm;
/** How many products to fetch in the result */
limit?: number;
/** @deprecated Use productRules instead */
productFilter?: ProductFilter;
/**
* Product rules to apply to limit the product selection in accordance with Elevate product rules syntax
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/common/page-configuration/
*/
productRules?: string;
/** RecommendationList specific parameters */
params?: RecommendationListParams;
/** How the list should visaully be presented */
visualization?: Visualization;
}
interface RecommendationListParams {
/**
* The base product to use for `ALTERNATIVES`, `STYLE_WITH` and `UPSELL recommendations.
* Defaults to `productKey` for `ProductPage` requests.
*/
productKey?: string;
/** List of product and/or variant keys to be use in combination with the `CART` Algorithm */
cart?: string[];
}
interface ContentListConfig {
/**
* An identifier for the content listing area. The same ID cannot appear twice in
* the same request.
*
* Has a maximum length limit, as well as validation on character types.
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/common/page-configuration/#content-lists
*/
id: string;
/** The number of items to list. Must be a positive number */
limit?: number;
/** Configuration to filter available content items */
contentFilter?: ContentFilter;
/** Algorithm to apply for this listing. Defaults to 'NEWEST_CONTENT' */
algorithm?: ContentAlgorithm;
}
/**
* @deprecated Use the `productRules` property instead
*
* `ProductFilter`, used with primary- and recommendation-lists
*
* - `{ "attribute": "val1" }`
* - `{ "attribute": ["val2","val3"] }`
* - `{ "range_attribute": { "min": 1, "max": 20 } }`
*
* Custom attributes can be used as a filter, but the name must be prefixed with `custom.`
*
* @example
* ```json
* {
* "size": "Women;NO_FORMAT;M",
* "brand": ["some_brand", "another_brand"],
* "custom.season": "fall",
* "discount": 50,
* "stock_number": [1, 2],
* "price": { "max": 200 },
* "rating": { "min": 3.5 }
* }
* ```
*/
interface ProductFilter {
[key: string]: string | string[] | number | number[] | FacetRange;
}
/**
* Allows filtering of content lists based on built-in or custom properties.
* For an item to be included, it must match all specified properties. If multiple
* values for a property is specified (e.g. `"custom.season": ["Winter", "Spring"]`),
* it's enough if one value matches.
*
* @example
* ```ts
* const contentFilter = {
* type: 'article',
* 'custom.season': ['Winter', 'Spring']
* };
* ```
*/
interface ContentFilter {
/** Content item type (as provided in the data-feed) */
type?: string | string[];
/** Content item key (as provided in the data-feed) */
content_key?: string | string[];
/** Any custom properties added in the data-feed. */
[customProperty: `custom.${string}`]: string | string[];
}
interface PrimaryListPageBody {
/** Settings for the primary list */
primaryList?: {
/**
* Include primary listing in result, defaults to `false` for landing-page,
* but will always be `true` for search-page
*/
include: boolean;
/** @deprecated Use productRules instead */
productFilter?: ProductFilter;
/**
* Product rules to apply to limit the product selection in accordance with the Elevate product rules syntax
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/common/page-configuration/
*/
productRules?: string;
};
}
interface NavigationPageBody {
/** Settings for navigation */
navigation?: {
/** Include navigation in result, defaults to `false` */
include: boolean;
};
}
interface RecommendationListPageBody {
/** Recommendation list settings, specify to include additional recommendations on a page */
recommendationLists?: RecommendationListConfiguration[];
}
interface ContentListPageBody {
/** Content list settings, for retrieving non-products together with the request */
contentLists?: ContentListConfig[];
}
type Flavor<T, N extends string> = T & {
/** Don't use this. Added by `Flavor` to support Nominal typing */
readonly __brand?: N;
};
/** ISO-8601 timestamp. E.g. '2021-10-10T15:30:00Z' */
type Timestamp = Flavor<string, 'ISO'>;
interface CustomAttributes {
[attribute: string]: CustomAttribute[];
}
interface CustomAttribute {
/** The id of the attribute */
id: string;
/**
* The label of the attribute (name in the feed).
* *Note*: Currently not available for content items
*/
label: string;
}
interface Image {
/**
* The alt text for the image for A11y. Should describe the image.
* Will be `undefined` if omitted during import
*/
alt?: string;
/**
* The caption for the image. Only available for ProductPage and ContentInformation
* requests. Will be `undefined` if omitted during import
*/
caption?: string;
/** Custom attributes added to this image during import. Will be `undefined` if omitted during import */
custom?: Record<string, string>;
/** Multiple sources for each image, use with `<img srcset={VALUES} />` */
sources: ImageSource[];
}
interface ImageSource {
/** Url to the image source. */
url: string;
/**
* The width of the image. Will be `undefined` if not expicitly specified or if
* image hasn't yet been assessed by image service.
*/
width?: number;
/** The height of the image. Will be `undefined` if not specified. */
height?: number;
}
interface AutoCorrect {
/** The original search phrase */
q: string;
/** The number of hits for the original search phrase */
originalTotalHits: number;
}
interface DidYouMean {
/** A suggested correction phrase */
q: string;
}
interface RelatedSearch {
/** A suggested query related to the original query */
q: string;
}
interface ContentItem {
/** Identifier for this `ContentItem` */
key: string;
/** Type for this `ContentItem`. An example could be: "article" or "faq" */
type: string;
/** Title for this `ContentItem` */
title: string;
/** Link to the page representing this content item */
link: string;
/** Use with notifications to identify interaction */
ticket: string;
/** Item description. Undefined if omitted during import */
description?: string;
/** Item release date. Undefined if omitted during import */
releaseDate?: Timestamp;
/** Item image information. Undefined if omitted during import */
image?: Image;
/** Custom attributes for the content item. */
custom: CustomAttributes;
}
type Facet = TextFacet | ColorFacet | RangeFacet | SizeFacet | CheckboxFacet;
type FacetType = Facet['type'];
type FacetTextSort = 'ALPHABETICAL' | 'RELEVANCE' | 'NATURAL';
interface FacetData {
/**
* Identifier for this facet. Should be used to select this facet,
* e.g. when creating a facet query parameters or product rules.
*
* @example
* ```ts
* api.query.landingPage({
* facets: {
* [facet.id]: [facet.values[0].id]
* }
* });
* ```
*/
id: string;
/** Presentation text for facet */
label: string;
}
interface TextFacet extends FacetData {
/** Type of facet */
type: 'TEXT';
/** How the values are sorted */
sort: FacetTextSort;
/** Number of selected facet values */
selectedCount: number;
/** Values of facet */
values: TextFacetValue[];
}
interface ColorFacet extends FacetData {
/** Type of facet */
type: 'COLOR';
/** Number of selected facet values */
selectedCount: number;
/** Values of facet */
values: ColorFacetValue[];
}
interface RangeFacet extends FacetData {
/** Type of facet */
type: 'RANGE';
/** The unit of the value. Only applicable for measurements */
unit?: string;
/** Minimum value of range, inclusive. Undefined if there are no products in the selection */
min?: number;
/** Maximum value of range, inclusive. Undefined if there are no products in the selection */
max?: number;
/** Selected min value, undefined if not selected */
minSelected?: number;
/** Selected max value, undefined if not selected */
maxSelected?: number;
}
interface SizeFacet extends FacetData {
/** Type of facet */
type: 'SIZE';
/** Number of selected facet values */
selectedCount: number;
/** The defined sizeTypes */
sizeTypes: SizeType[];
}
interface CheckboxFacet extends FacetData {
/** Type of facet */
type: 'CHECKBOX';
/** Identifies the checkbox as selected */
selected: boolean;
/** The number of products that match the criteria. Only available when `selected` is `true` */
count?: number;
}
interface TextFacetValue {
/**
* Identifier for this facet value. Use this value when refining queries with
* selected facet values.
*/
id: string;
/** Presentation text */
label: string;
/** Identifies the value as selected */
selected: boolean;
/** The number of products that match the criteria */
count: number;
}
interface ColorFacetValue extends TextFacetValue {
/** A CSS-color code for this color facet */
color: string;
}
interface SizeType {
/** Type of size, e.g. cloth or shoe sizes */
label: string;
/** Size formats for type */
formats: SizeFormat[];
}
interface SizeFormat {
/** The identifier for this size format */
format: string;
/** Size values for format */
values: TextFacetValue[];
}
type ImageEffect = 'NONE' | 'SWAP' | 'GALLERY';
type BadgeType = 'NONE' | 'SALE' | 'DISCOUNT' | 'NEW' | 'THEME_1' | 'THEME_2' | 'THEME_3';
type SwatchType = 'MISSING_COLORS' | 'COLORS' | 'SILVER' | 'GOLD' | 'MULTI';
interface ProductGroup {
/** Identifier for this `ProductGroup` */
key: string;
/**
* The number of products within this group not included in the response. E.g. if Elevate has been set to
* include the first five products in the response and this group has seven, there will be two remaining.
*/
remaining: number;
/**
* Products in the Product group. The first element corresponds to the main product.
* The remaining elements are the other products in the group, to be shown as thumbnails or color swatches, etc.
*/
products: Product[];
}
interface Product {
/** Product identifier */
key: string;
/** Title of the product */
title: string;
/** Name of the product */
name?: string;
/** Brand of the product */
brand: string;
/** Series that this product belongs to. */
series?: string;
/** Description of the product, undefined if omitted during import */
description?: string;
/** Link to product page */
link: string;
/** Use with notifications to identify interaction */
ticket: string;
/** Will be undefined when rating is disabled. Otherwise it will be the current rating value*/
rating?: number;
/** True if any variant is in stock */
inStock: boolean;
/** Min and max list price of variants */
listPrice: Price;
/** Min and max selling price of variants */
sellingPrice: Price;
/** Main width of product. */
width?: MeasurementResult;
/** Main height of product. */
height?: MeasurementResult;
/** Main depth of product. */
depth?: MeasurementResult;
/** Main length of product. */
length?: MeasurementResult;
/** Volume of product. */
volume?: MeasurementResult;
/** Weight of product. */
weight?: MeasurementResult;
/**
* Collection of variants
*
* Might be empty if all variants are out of stock and the setting
* `Display out of stock sizes in product card` is disabled
* */
variants: Variant[];
/** Product badges, split per area */
badges: {
/** Primary badges */
primary: Badge[];
/** Secondary badges */
secondary: Badge[];
};
/** Product images, their presentation and multiple sources */
imageInfo: {
/** Effect that should be used for switching images */
effect: ImageEffect;
/** Images to be displayed */
images: Image[];
/** Thumbnail of the product, will be undefined if no images are defined */
thumbnail?: string;
};
/** Color swatch for product */
swatch: {
/** Type of color swatch */
type: SwatchType;
/** Only populated if type === SwatchType.COLORS */
colors: string[];
};
/**
* Custom attributes of the product.
*
* Attributes included depends on the context. Primary product-group of
* `/product-page` requests includes all attributes. In listings, attributes
* included are controlled by:
* - Parameter `presentCustom`, which includes listed attributes
* - Parameter `templateId`, which includes all attributes in the target Template
*/
custom?: CustomAttributes;
/**
* Typed custom attributes of the product.
*
* Attributes included depends on the context. Primary product-group of
* `/product-page` requests includes all attributes. In listings, attributes
* included are controlled by:
* - Parameter `presentCustom`, which includes listed attributes
* - Parameter `templateId`, which includes all attributes in the target Template
*/
typedCustom?: TypedCustomAttributes;
/** If the product is a sponsored product placement. */
sponsored?: boolean;
}
interface Variant {
/** Variant identifier */
key: string;
/** Use with click notification to identify interaction */
ticket: string;
/** Size, will be undefined if omitted during import */
size?: string;
/** Label, will be undefined if omitted during import */
label?: string;
/** Stock number */
stockNumber: number;
/** True if variant stock number is greater than 0 */
inStock: boolean;
/** Direct link to variant or fallback to product if missing */
link: string;
/** List price */
listPrice: number;
/** Discounted price, same as listPrice if no discount */
sellingPrice: number;
/**
* Additional prices for presentation. Only available on the /product-page `ProductGroup`
* and when using the query parameter 'presentPrices'.
*/
prices: PriceResult[];
/** Availability of the product in different channels */
availability: Availability[];
/** Main width of variant. */
width?: MeasurementResult;
/** Main height of variant. */
height?: MeasurementResult;
/** Main depth of variant. */
depth?: MeasurementResult;
/** Main length of variant. */
length?: MeasurementResult;
/** Volume of variant. */
volume?: MeasurementResult;
/** Weight of variant. */
weight?: MeasurementResult;
/**
* Custom attributes of the product.
*
* Attributes included depends on the context. Primary product-group of
* `/product-page` requests includes all attributes. In listings, attributes
* included are controlled by:
* - Parameter `presentCustom`, which includes listed attributes
* - Parameter `templateId`, which includes all attributes in the target Template
*/
custom?: CustomAttributes;
/**
* Typed custom attributes of the product.
*
* Attributes included depends on the context. Primary product-group of
* `/product-page` requests includes all attributes. In listings, attributes
* included are controlled by:
* - Parameter `presentCustom`, which includes listed attributes
* - Parameter `templateId`, which includes all attributes in the target Template
*/
typedCustom?: TypedCustomAttributes;
}
interface Price {
/** The lowest variant price */
min: number;
/** The highest variant price */
max: number;
}
interface MeasurementResult {
/** The amount of the measurement */
amount: number;
/** The unit of the measurement, different measurements have different units */
unit: string;
}
interface TypedCustomAttributes {
/** Custom lengths of the Product/Variant (`custom.length.<attr_name>`) */
lengths: TypedCustomMeasurementAttribute;
/** Custom numbers of the Product/Variant (`custom.number.<attr_name>`) */
numbers: TypedCustomNumberAttribute;
/** Custom JSON data of the Product/Variant (`custom.json.<attr_name>`) */
json: TypedCustomJsonAttribute;
}
/**
* @deprecated Use the `TypedCustomMeasurementAttribute` type instead.
*/
type TypedCustomAttribute = TypedCustomMeasurementAttribute;
type TypedCustomMeasurementAttribute = Record<string, MeasurementResult>;
type TypedCustomNumberAttribute = Record<string, number>;
type TypedCustomJsonAttribute = Record<string, unknown>;
interface PriceResult {
/** The id identifying the custom price. */
id: string;
/** The price displayed in the shop as the standard price. */
listPrice: number;
/** The price that the customer pays. */
sellingPrice: number;
}
interface Badge {
/** Presentation text of badge */
label: string;
/** Identifier for the Badge styling */
theme: BadgeType;
/**
* The related product attribe, will be `undefined` when the `theme`
* property is `'DISCOUNT'`, `'NEW'` or `'SALE'`
*/
attribute?: string;
}
interface Availability {
/** Channel identifer */
channel: 'ONLINE' | 'STORE';
/** Stock number */
stockNumber: number;
/** Store identifer */
key?: string;
}
type SortType = 'RELEVANCE' | 'NEWEST_FIRST' | 'PRICE_ASCENDING' | 'PRICE_DESCENDING' | 'DISCOUNT' | 'RATING' | 'NAME' | 'LENGTH_INCREASING' | 'LENGTH_DECREASING' | 'WIDTH_INCREASING' | 'WIDTH_DECREASING' | 'HEIGHT_INCREASING' | 'HEIGHT_DECREASING' | 'DEPTH_INCREASING' | 'DEPTH_DECREASING' | 'VOLUME_INCREASING' | 'VOLUME_DECREASING' | 'WEIGHT_INCREASING' | 'WEIGHT_DECREASING' | 'TITLE';
type ContentSortType = 'RELEVANCE' | 'NEWEST_FIRST';
interface Sort<T = SortType> {
/** Which SortOption that is currently selected */
selected: T;
/** SortOptions to choose from */
options: SortOption<T>[];
}
interface SortOption<T = SortType> {
/** Identifier for SortOption */
id: T;
/** Presentation text for SortOption */
label: string;
}
type Visualization = 'CAROUSEL' | 'GRID';
type Algorithm = 'TOP_PRODUCTS' | 'PERSONAL' | 'CART' | 'STYLE_WITH' | 'ALTERNATIVES' | 'UPSELL' | 'NEWEST_PRODUCTS' | 'FAVORITES' | 'MORE_FROM_SERIES' | 'RECENTLY_VIEWED' | 'ADD_TO_CART_RECS';
interface RecommendationList {
/**
* The identifier for this list. Typically a short name describing
* where on the page it's used.
*/
id: string;
/**
* The algorithm type being used for this recommendationList. It's possible to change
* algorithm for pages in the Elevate app, so this value could be different from the algorithm
* used in the POST request.
*/
algorithm: Algorithm;
/** ProductGroups that matched the algorithm, limit of the input or saved setting */
productGroups: ProductGroup[];
/**
* Indicates whether this recommendation list has been hidden or not in the Elevate app.
* Hidden product lists are still returned, but their `productGroups` list is empty.
*/
visible: boolean;
/** The presentation text for list. Can be `undefined` if the list item label is left empty in the app. */
label?: string;
/** A URL to use to link to a full product listing for the recommendation selection */
showMoreLink?: string;
/** Indicator on how the list should be presented. */
visualization: Visualization;
}
interface SponsoredList extends RecommendationList {
/** Ticket used to track impressions of a list, i.e. if a list has been shown to a user.*/
impressionTicket?: string;
/** The winning brands in the bid for the sponsored list*/
winners: string[];
}
interface RecommendationListPage {
/** Collection of recommendation lists, defined either by POST body or PageSetting in apps */
recommendationLists: RecommendationList[];
}
interface ContentList {
/** List identifier */
id: string;
/** The total number of content items that matches filter and query (if applicable) */
totalHits: number;
/** List of matched content items */
items: ContentItem[];
}
interface ContentListPage {
/**
* A list of lists of requested content, as specified in request body. Will be
* empty unless specified in request body.
*/
contentLists: ContentList[];
}
interface PrimaryList {
/** How the ProductGrups are sorted */
sort: Sort;
/** Collection of ProductGroup */
productGroups: ProductGroup[];
/** Total number of ProductGroup hits */
totalHits: number;
/** Collection of Facet */
facets: Facet[];
}
type SecondaryList = Pick<PrimaryList, 'productGroups' | 'totalHits'>;
interface Breadcrumb {
/** Path to node */
path: string;
/** Presentation text for node */
label: string;
}
/** Contains all properties that are used by `NavigationTree` model. */
interface NavigationData<Type extends NavigationItemType, Child> {
/** Type of node */
type: Type;
/** Number of ProductGroups in node */
count: number;
/** Child navigation nodes */
children: Child[];
}
/** Contains all properties that are used by `NavigationTree` model. */
interface NavigationStateData<Type extends NavigationItemType, Child> extends NavigationData<Type, Child> {
/** Identifies the node as selected in the tree */
selected: boolean;
/**
* Indication that this node has children, even though they might not be present.
* They might be missing since only one level below a selected node is returned.
*/
expandable: boolean;
}
/** Contains all properties that are used by `NavigationTree` model. */
interface NavigationProductData {
/** Path to node */
path: string;
/**
* The path to the image used as this node's icon, if any.
* @example
* node.iconPath;
* > "/resources/images/navigation/spring_node.jpg"
*/
iconPath?: string;
}
/** Contains properties that are unique to the `'PAGE_LINK'` `type` for `Navigation` and `NavigationTree`. */
interface NavigationLinkData {
/** Link to page, will only by populated if type is `PAGE_LINK` */
link: string;
}
/** Contains label property that is common amongst Label, Product and Link nodes */
interface NavigationLabelData {
/** Presentation text for node */
label: string;
}
/** Available values for the `type` field for `Navigation` and `NavigationTree` models */
type NavigationItemType = 'PRODUCT' | 'LABEL' | 'PAGE_LINK' | 'SPACER';
type NavigationLabelNode = NavigationData<'LABEL', NavigationNode> & NavigationLabelData;
type NavigationProductNode = NavigationData<'PRODUCT', NavigationNode> & NavigationProductData & NavigationLabelData;
type NavigationLinkNode = NavigationData<'PAGE_LINK', NavigationNode> & NavigationLinkData & NavigationLabelData;
type NavigationSpacerNode = NavigationData<'SPACER', NavigationNode>;
type NavigationLabelStateNode = NavigationStateData<'LABEL', NavigationStateNode> & NavigationLabelData;
type NavigationProductStateNode = NavigationStateData<'PRODUCT', NavigationStateNode> & NavigationProductData & NavigationLabelData;
type NavigationLinkStateNode = NavigationStateData<'PAGE_LINK', NavigationStateNode> & NavigationLinkData & NavigationLabelData;
type NavigationSpacerStateNode = NavigationStateData<'SPACER', NavigationStateNode>;
type NavigationNode = NavigationLabelNode | NavigationProductNode | NavigationLinkNode | NavigationSpacerNode;
type NavigationStateNode = NavigationLabelStateNode | NavigationProductStateNode | NavigationLinkStateNode | NavigationSpacerStateNode;
interface Navigation {
breadcrumbs: Breadcrumb[];
tree: NavigationStateNode;
}
interface AddToCartPopupParams extends ProductParams {
/** A list of product keys for the products in the cart */
cart?: string[];
/** The key of the product variant added to cart. Must match a variant key from the data feed. */
variantKey: string;
}
type AddToCartPopupBody = RecommendationListConfiguration[];
interface AddToCartPopup extends RecommendationListPage {
}
interface AutocompleteParams extends ProductParams, SearchParams {
}
interface AutocompleteBody extends ContentListPageBody {
/** @deprecated Use productRules instead */
productFilter?: ProductFilter;
/**
* Product rules to apply for autocomplete in accordance with the Elevate product rules syntax
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/common/page-configuration/
*/
productRules?: string;
}
interface Autocomplete extends ContentListPage {
/** Collection of PhraseSuggestion, that matched query */
phraseSuggestions: PhraseSuggestion[];
/** Collection of ProductGroup, that matched query */
productSuggestions: ProductGroup[];
/** Collection of Content Suggestions, that matched query */
contentSuggestions: ContentSuggestion[];
/** Collection of recent searches by the current `customerKey` in the form of RecentSearch, when query is empty */
recentSearches: RecentSearch[];
/** Collection of ProductGroup, the recently viewed products */
recentlyViewed: ProductGroup[];
/** Total number of ProductGroup that matched query */
totalHits: number;
/** Redirect direct to product page */
redirectLink?: string;
}
interface PhraseSuggestion {
/** Matching phrase with highlight, e.g. {{jea}}ns */
highlighted: string;
/** Matching phrase */
q: string;
}
interface ContentSuggestion {
/** Matching title */
title: string;
/** Matching title with highlight, e.g. {{Return}}s */
highlightedTitle: string;
/** Link to content page */
link: string;
/** Use with click notification to identify interaction */
ticket: string;
}
interface RecentSearch {
/** Recent search phrase */
q: string;
}
interface CartPageParams extends ProductParams {
/** A list of product keys for the products in the cart */
cart: string[];
}
interface CartPageBody extends RecommendationListPageBody {
/** Settings for cart */
cart?: {
/** Include cart in result, defaults to `false` */
include: boolean;
};
}
interface CartPage extends RecommendationListPage {
/** Collection of ProductGroup that matched input parameters */
cart: ProductGroup[];
}
interface ContentInformationParams extends BaseParams {
/** The content keys to retrieve information from */
contentKeys: string[];
}
interface ContentInformation {
items: ContentItem[];
}
type ContentSearchOrigin = 'ORGANIC' | 'DID_YOU_MEAN' | 'UNDO_AUTO_CORRECT';
interface ContentSearchPageParams extends BaseParams, PaginationParams, SearchParams {
/** The origin of the content search request */
origin?: ContentSearchOrigin;
/** Changes how content items are sorted in the response */
sort?: ContentSortType;
}
interface ContentSearchPageBody {
/**
* Configure the search result by specifying contentFilter, to only
* include a subset of content items in the result.
*/
primaryList?: {
contentFilter: ContentFilter;
};
}
interface ContentSearchPage {
q: string;
primaryList: PrimaryContentList;
didYouMean: DidYouMean[];
autoCorrect?: AutoCorrect;
}
interface PrimaryContentList {
sort: Sort<ContentSortType>;
items: ContentItem[];
totalHits: number;
}
interface LandingPageParams extends ProductParams, ProductListParams {
/** A search phrase used to further refine the result */
q?: string;
/**
* Required if the `Referer` header is missing, used to identify the current page.
* Any string is accepted, but using URLs is a good practice to follow.
*/
pageReference?: string;
/**
* Whether or not the response should include a navigation object (including breadcrumbs),
* i.e. when navigation is handled through Elevate. Defaults to false if omitted.
*/
includeNavigation?: boolean;
}
interface LandingPageBody extends PrimaryListPageBody, NavigationPageBody, RecommendationListPageBody, ContentListPageBody {
}
interface LandingPage extends RecommendationListPage, ContentListPage {
/** A product list with facets, sort orders and hit count */
primaryList?: PrimaryList;
/** Navigation, can be `undefined` if disabled */
navigation?: Navigation;
/** String key/value map with custom data added via the Admin page import API */
customData: Record<string, string>;
/** Is `true` if the returned page's settings were overridden from the Elevate API or the Elevate app */
published: boolean;
/** SEO information */
seo: SearchEngineOptimization;
}
interface SearchEngineOptimization {
/** Preamble text for the current page */
preamble?: string;
/** Description for the current page, use with: `<meta type="description" content="{VALUE}">` */
metaDescription?: string;
/** Title for the current page, use with: `<title>{VALUE}</title>` */
pageTitle?: string;
/** Preferred URL for the current page, use with `<link rel="canonical" href="{VALUE}">` */
canonicalPath?: string;
/** Main heading for the current page */
pageHeading?: string;
}
interface RetailMediaParams extends BaseParams {
/**
* Required if the `Referer` header is missing, used to identify the current page.
* Any string is accepted, but using URLs is a good practice to follow.
*/
pageReference: string;
/**
* The ID of a response template to apply to all banners returned.
*
* Templates can adjust which attributes are returned for banners, and makes
* `presentCustom` unnecessary. Templates can be imported via the Admin API.
* @see https://docs.apptus.com/elevate/4/guides/product-list-response-templates/
*/
templateId?: string;
}
type SponsoredPageParams = RetailMediaParams;
interface SponsoredPage {
/** Lists with winners and sponsored, sort orders and hit count */
sponsoredLists: SponsoredList[];
}
type BannersParams = RetailMediaParams;
interface Banner {
/** Banner identifier */
id: string;
images: {
/** Image URL */
url: string;
/** Ticket used to track impressions of a banner */
ticket: string;
}[];
/** Banner width in pixels */
width: number;
/** Banner height in pixels */
height: number;
}
interface Banners {
/** Lists with banners */
banners: Banner[];
}
interface NavigationTreeParams extends BaseParams, ProductContextParams {
}
interface NavigationTree {
/** Root node for the entire navigation tree */
tree: NavigationNode;
}
interface ProductPageParams extends ProductParams {
/** Required parameter for product page, the product to return and show recommendations for */
productKey: string;
}
interface ProductPageBody extends RecommendationListPageBody {
/** Settings for product group */
productGroup?: {
/** Include product group in result, defaults to `false` */
include: boolean;
};
}
interface ProductPage extends RecommendationListPage {
/** ProductGroup for page, if enabled */
productGroup?: ProductGroup;
/**
* Tickets for each variant within the product group.
*
* Returned only if product details were NOT requested (otherwise, they are found on the product group).
* Use the corresponding ticket(s) for variants added in add-to-cart notifications from this page.
*/
tickets: Record<string, string>;
}
type SearchOrigin = 'ORGANIC' | 'PHRASE_SUGGEST' | 'DID_YOU_MEAN' | 'UNDO_AUTO_CORRECT' | 'RELATED_SEARCHES' | 'RECENT_SEARCH';
interface SearchPageParams extends ProductParams, ProductListParams, SearchParams {
/**
* Used to correctly track and analyze search behavior. For example, use `'UNDO_AUTO_CORRECT'`
* with a search query to avoid the query being autocorrected.
*/
origin?: SearchOrigin;
/** The selected category, will return all categories above and including */
selectedCategory?: string;
/** Show an expanded view of the secondary list instead of the primary list */
viewAllSecondary?: boolean;
}
interface SearchPageBody extends PrimaryListPageBody, NavigationPageBody, ContentListPageBody {
}
interface SearchPage extends ContentListPage {
/** Search query */
q: string;
/** Autocorrected the query. Information about search results */
autoCorrect?: AutoCorrect;
/** Did you mean suggestions */
didYouMean: DidYouMean[];
/** A product list with facets, sort orders and hit count */
primaryList: PrimaryList;
/** Navigation, can be `undefined` if disabled */
navigation?: Navigation;
/** An extension of the PrimaryList, that can show e.g. relaxed or related listing of products */
secondaryList?: SecondaryList;
/** A list of phrases related to the search phrase. */
relatedSearches?: RelatedSearch[];
}
declare class Query {
private readonly __config;
constructor(__config: FullOptions);
/**
* Retrieve recommendations for a product that has just been added to the cart.
*
* @param params query parameter options to submit
* @param body configuration options to submit
*
* @example
* ```ts
* const res = await api.query.addToCartPopup({ variantKey: 'variant-key-123' }, {
* recommendationLists: [{
* id: 'addons',
* algorithm: 'ADD_TO_CART_RECS'
* }]
* });
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/add-to-cart-popup/
*/
addToCartPopup(params: AddToCartPopupParams, recommendationLists: AddToCartPopupBody): Promise<AddToCartPopup>;
/**
* Autocomplete based on provided query parameter, for search suggestions,
* product suggestions, and more.
*
* @param params query parameter options to submit
* @param body configuration options to submit
*
* @example
* ```ts
* const res = await api.query.autocomplete({ q: 'shirt' });
* const sale = await api.query.autocomplete({ q: 'dress' }, {
* productFilter: { discount: 50 }
* p});
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/autocomplete/
*/
autocomplete(params: AutocompleteParams, body?: AutocompleteBody): Promise<Autocomplete>;
/**
* Retrieve the complete navigation tree, suitable for a top/mobile navigation of the site.
*
* @param params query parameter options to submit
*
* @example
* ```ts
* const tree = await api.query.navigationTree();
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/navigation-tree/
*/
navigationTree(params?: NavigationTreeParams): Promise<NavigationTree>;
/**
* Returns a product listing with facets based on provided query, optionally
* with related navigation included.
*
* @param params query parameter options to submit
* @param body configuration options to submit
*
* @example
* ```ts
* const res = await api.query.searchPage({ q: 'shirt' });
* const sale = await api.query.searchPage({ q: 'dress' }, {
* primaryList: {
* productFilter: { discount: 50 }
* },
* navigation: { include: true }
* });
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/search-page/
*/
searchPage(params: SearchPageParams, body?: SearchPageBody): Promise<SearchPage>;
/**
* Retrieves product information and related info suitable to show on a Product page.
* Can be configured to show various recommendation lists based on body configuration settings.
*
* @param params query parameter options to submit
* @param body configuration options to submit
*
* @example
* ```ts
* const res = await api.query.productPage({ productKey: 'p123' }, {
* recommendationLists: [{
* id: 'alts',
* algorithm: 'ALTERNATIVES'
* }]
* });
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/product-page/
*/
productPage(params: ProductPageParams, body?: ProductPageBody): Promise<ProductPage>;
/**
* Retrieve products - and possibly recommendation lists - suitable for display
* on a cart page.
*
* @param params query parameter options to submit
* @param body configuration options to submit
*
* @example
* ```ts
* const res = await api.query.cartPage({ cart: ['p123', 'p456'] }, {
* recommendationLists: [{
* id: 'addons',
* algorithm: 'CART'
* }]
* });
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/cart-page/
*/
cartPage(params: CartPageParams, body?: CartPageBody): Promise<CartPage>;
/**
* Request for generic landing pages, or category pages. Can return product listing with facets,
* recommendation lists, or both. Suitable for the start/home page, intermediate category pages,
* brand pages, and more.
*
* @param params query parameter options to submit
* @param body configuration options to submit
*
* @example
* ```ts
* const res = await api.query.landingPage();
* const sale = await api.query.landingPage({ limit: 30, skip: 0 }, {
* primaryList: {
* productFilter: { discount: 50 }
* },
* recommendationLists: [{
* id: 'personal',
* algorithm: 'PERSONAL'
* }]
* });
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/landing-page/
*/
landingPage(params?: LandingPageParams, body?: LandingPageBody): Promise<LandingPage>;
/**
* Request for retrieving a list of sponsored products for a Page.
*
* @beta ⚠️ This request is currently limited to a private beta and will fail otherwise.
*
* @param params query parameter options to submit
*
* @example
* ```ts
* const res = await api.query.sponsoredPage({
* pageReference: '/women/tops'
* });
* ```
* @see https://docs.apptus.com/elevate/4/integration/api/specifications/storefront/v3/queries/sponsored-page/
*/
sponsoredPage(params: SponsoredPageParams): Promise<SponsoredPage>;
/**
* Request for retrieving a list of banners for a Page.
*
* @beta ⚠️ This request is currently limited to a private beta and will fail otherwise.
*
* @param params query parameter options to submit
*
* @example
* ```ts
* const res = await api.query.banners({
* pageReference: '/women/tops'
* });
* ```
* @see https://docs.apptus.com/elevate/4/integration/api/specifications/storefront/v3/queries/banners/
*/
banners(params: BannersParams): Promise<Banners>;
/**
* Mirrors the Product Page, but for Content instead of Products. Retrieves content
* information for the provided `contentKeys` (required).
*
* @param params query parameter options to submit
*
* @example
* ```ts
* const res = await api.query.contentInformation({
* contentKeys: ['ck_123456', 'ck_234567']
* });
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/content-information/
*/
contentInformation(params: ContentInformationParams): Promise<ContentInformation>;
/**
* Mirrors the Search Page request, but for Content instead of Products. Returns content
* results matching the provided query. Suiteable for searching in e.g. FAQ or customer service,
* where no product results are required.
*
* @param params query parameter options to submit
* @param body configuration options to submit
*
* @example
* ```ts
* const res = await this.contentSearchPage({ q: 'returns' });
* ```
* @example
* ```ts
* const res = await this.contentSearchPage({ q: 'shipping', skip: 20 }, {
* primaryList: {
* contentFilter: {
* type: 'faq'
* }
* }
* });
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/queries/content-search-page/
*/
contentSearchPage(params: ContentSearchPageParams, body?: ContentSearchPageBody): Promise<ContentSearchPage>;
private __query;
}
type FavoritePayload = {
productKey: string;
} | {
variantKey: string;
};
declare class Notification {
private readonly __config;
constructor(__config: BaseOptions);
/**
* Send click notification with ticket. Tries to queue fetch
* request with `keepalive` option, with one retry if it fails.
*
* @param ticket is present on product and variant
*
* @example
* ```ts
* await api.notify.click('OzE7cHJ...yM7Mjg7');
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/notifications/click/
*/
click(ticket: string): Promise<void>;
/**
* Send impression notification. Tries to queue fetch
* request with `keepalive` option, with one retry if it fails.
*
* @beta ⚠️ This request is currently limited to a private beta and will fail otherwise.
*
* @param ticket attached to a sponsored product or list
*
* @example
* ```ts
* await api.notify.adImpression('OzE7cHJ...yM7Mjg7');
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/notifications/ad-impression/
*/
adImpression(ticket: string): Promise<void>;
/**
* Send add to cart notification with ticket. Tries to queue fetch
* request with `keepalive` option, with one retry if it fails.
*
* @param ticket is present on product and variant
*
* @example
* ```ts
* await api.notify.addToCart('OzE7cHJ...jOzI4Ow');
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefront/v3/notifications/add-to-cart/
*/
addToCart(ticket: string): Promise<void>;
/**
* Send add favorite notification with product-key. Tries to queue fetch
* request with `keepalive` option, with one retry if it fails.
*
* @param productKeyOrPayload a `Product.key` or object with variant or product key
*
* @example
* ```ts
* await api.notify.addFavorite('pk_123456');
* await api.notify.addFavorite({ variantKey: 'vk_234567' });
* ```
* @see https://docs.elevate.voyado.cloud/elevate/4/integration/api/specifications/storefr