Skip to main content

Overview

The Store API provides endpoints to retrieve store configuration, navigation structure, and product categorization tags. These operations help you build the structure and branding of your storefront.
Store operations do not require authentication. However, some information may be personalized when a customer token is provided.

Get Store

Retrieves store information including name, currency, branding, and configuration.
storefront.store.getStorefrontStore(config?)

Parameters

config
object
Configuration object for the request

Returns

Returns a StorefrontStoreDto object:
id
string
The store’s unique identifier
slug
string
The URL-friendly identifier for the store (e.g., “m0ukas-awesome-store”)
name
string
The display name of the store
platform
string
The platform or game of the store (e.g., “rust”, “minecraft”)
game
string
The game of the store (equivalent to platform for backwards compatibility)
currency
string
The three-letter ISO currency code used for pricing. If using Adaptive Currency, this reflects the customer’s local currency.
creator_currency
string
The main currency of the store (always the store’s base currency)
description
string
A detailed description of the store
website_url
string
The URL of the store’s main website
support_email
string
The email address customers can use to contact store support
support_url
string
The URL of the store’s support page
integration_type
string
The type of integration this store uses
live_mode
boolean
Indicates whether the store is in live mode (true) or test mode (false)
logo_url
string
The URL to the store’s main logo image
logo_square_url
string
The URL to the store’s square logo image
created_at
string
The date and time when the store was created (ISO 8601 format)
updated_at
string
The date and time when the store was last updated (ISO 8601 format)

Example

import { createStorefrontClient } from '@paynow-gg/sdk';

const storefront = createStorefrontClient('store-id');

// Get store information
const { data: store } = await storefront.store.getStorefrontStore();

console.log(`Store: ${store.name}`);
console.log(`Platform: ${store.platform}`);
console.log(`Currency: ${store.currency}`);
console.log(`Live Mode: ${store.live_mode}`);

// Get store with customer location for adaptive currency
const { data: storeAdaptive } = await storefront.store.getStorefrontStore({
  headers: {
    'x-paynow-customer-ip': '203.0.113.42',
    'x-paynow-customer-countrycode': 'GB'
  }
});

console.log(`Customer currency: ${storeAdaptive.currency}`);
console.log(`Store base currency: ${storeAdaptive.creator_currency}`);
Retrieves the store’s navigation link structure for building category menus.
storefront.navlinks.getStorefrontNavLinks(config?)

Parameters

config
object
Configuration object for the request (currently no parameters required)

Returns

Returns an array of StorefrontNavLinkDto objects representing the hierarchical navigation structure:
node_id
string
The unique identifier for this navigation node
parent_node_id
string
The identifier of the parent navigation node (null for root nodes)
tag_id
string
The unique identifier of the associated tag
tag_slug
string
The URL-friendly slug for the tag (e.g., “perks”)
tag_query
string[]
A list containing all parent tags and this node’s tag, representing the complete path in the tag hierarchy
name
string
The display name of the navigation link
order
number
The display order of this navigation link relative to its siblings
children
array
The collection of child navigation links beneath this link

Example

// Get navigation structure
const { data: navLinks } = await storefront.navlinks.getStorefrontNavLinks();

// Render navigation menu
function renderNavigation(links: typeof navLinks, level = 0) {
  return links.map(link => (
    <div key={link.node_id} style={{ marginLeft: level * 20 }}>
      <a href={`/products?tags=${link.tag_query.join(',')}`}>
        {link.name}
      </a>
      {link.children.length > 0 && renderNavigation(link.children, level + 1)}
    </div>
  ));
}

// Build breadcrumb from tag_query
function buildBreadcrumb(link: typeof navLinks[0]) {
  return link.tag_query.map((tag, index) => ({
    name: index === link.tag_query.length - 1 ? link.name : tag,
    url: `/products?tags=${link.tag_query.slice(0, index + 1).join(',')}`
  }));
}

Get Tags

Retrieves all product tags used for categorization and filtering.
storefront.tags.getStorefrontTags(config?)

Parameters

config
object
Configuration object for the request (currently no parameters required)

Returns

Returns an array of StorefrontTagDto objects:
id
string
The tag’s unique identifier
store_id
string
The store’s unique identifier
slug
string
The URL-friendly identifier for the tag
name
string
The display name of the tag
description
string
A detailed description of the tag’s purpose
image_url
string
The URL to the tag image
enabled
boolean
Indicates whether the tag is active
created_at
string
The date and time when the tag was created (ISO 8601 format)
updated_at
string
The date and time when the tag was last updated (ISO 8601 format)

Example

// Get all tags
const { data: tags } = await storefront.tags.getStorefrontTags();

// Display tag filters
const enabledTags = tags.filter(tag => tag.enabled);

enabbledTags.forEach(tag => {
  console.log(`${tag.name} (${tag.slug})`);
  if (tag.description) {
    console.log(`  ${tag.description}`);
  }
});

// Create tag-based navigation
function createTagFilters(tags: typeof tags) {
  return tags
    .filter(t => t.enabled)
    .map(tag => ({
      id: tag.id,
      slug: tag.slug,
      name: tag.name,
      image: tag.image_url,
      description: tag.description
    }));
}

Use Cases

Display store information in your header:
async function loadStoreHeader() {
  const { data: store } = await storefront.store.getStorefrontStore();
  
  return {
    name: store.name,
    logo: store.logo_url || store.logo_square_url,
    websiteUrl: store.website_url,
    supportEmail: store.support_email,
    isTestMode: !store.live_mode
  };
}
Build a navigation menu from navigation links:
async function buildCategoryMenu() {
  const { data: navLinks } = await storefront.navlinks.getStorefrontNavLinks();
  
  // Sort by order and build menu structure
  const sortedLinks = navLinks.sort((a, b) => a.order - b.order);
  
  return sortedLinks.map(link => ({
    id: link.node_id,
    name: link.name,
    slug: link.tag_slug,
    tagPath: link.tag_query,
    children: link.children.sort((a, b) => a.order - b.order)
  }));
}
Create a tag filter UI:
async function createTagFilter() {
  const { data: tags } = await storefront.tags.getStorefrontTags();
  
  const activeTags = tags.filter(t => t.enabled);
  
  return activeTags.map(tag => ({
    slug: tag.slug,
    name: tag.name,
    description: tag.description,
    image: tag.image_url,
    onClick: async () => {
      // Filter products by this tag
      const { data: products } = await storefront.products.getStorefrontProducts({
        params: { tag: [tag.slug] }
      });
      return products;
    }
  }));
}
Handle adaptive currency for international customers:
async function getStoreCurrency(customerIp?: string, countryCode?: string) {
  const { data: store } = await storefront.store.getStorefrontStore({
    headers: customerIp ? {
      'x-paynow-customer-ip': customerIp,
      'x-paynow-customer-countrycode': countryCode
    } : undefined
  });
  
  return {
    displayCurrency: store.currency,        // Customer's currency
    baseCurrency: store.creator_currency,   // Store's base currency
    isAdapted: store.currency !== store.creator_currency
  };
}
Display support options to customers:
async function getSupportInfo() {
  const { data: store } = await storefront.store.getStorefrontStore();
  
  return {
    email: store.support_email,
    url: store.support_url,
    hasSupport: !!(store.support_email || store.support_url)
  };
}

Best Practices

Store information doesn’t change frequently, so cache it to reduce API calls:
let storeCache: any = null;
let cacheTime = 0;
const CACHE_TTL = 5 * 60 * 1000; // 5 minutes

async function getStore() {
  const now = Date.now();
  
  if (storeCache && (now - cacheTime) < CACHE_TTL) {
    return storeCache;
  }
  
  const { data: store } = await storefront.store.getStorefrontStore();
  storeCache = store;
  cacheTime = now;
  
  return store;
}
Use the navigation links to create nested menus:
function buildNestedNav(links: any[], parentId: string | null = null) {
  return links
    .filter(link => link.parent_node_id === parentId)
    .sort((a, b) => a.order - b.order)
    .map(link => ({
      ...link,
      children: buildNestedNav(links, link.node_id)
    }));
}

const { data: navLinks } = await storefront.navlinks.getStorefrontNavLinks();
const navigation = buildNestedNav(navLinks);
Use the tag_query array for filtering:
async function getProductsByNavLink(navLink: any) {
  // navLink.tag_query contains the full tag path
  const { data: products } = await storefront.products.getStorefrontProducts({
    params: {
      tag: navLink.tag_query
    }
  });
  
  return products;
}
Alert users when the store is in test mode:
const { data: store } = await storefront.store.getStorefrontStore();

if (!store.live_mode) {
  // Show test mode banner
  return (
    <div className="test-mode-banner">
      This store is in test mode. Payments will not be processed.
    </div>
  );
}

Additional Operations

The Store API group also includes customer and delivery operations:

Customer Operations

// Authenticate a customer
const { data } = await storefront.customer.authenticateStorefrontCustomer({
  data: {
    platform: 'steam',
    id: '76561198152492642'
  }
});
const customerToken = data.customer_token;

// Get current customer
const { data: customer } = await storefront.customer.getStorefrontCustomer();

// Lookup a gift card
const { data: giftCard } = await storefront.customer.getStorefrontGiftCard({
  path: { code: 'GIFT-CARD-CODE' }
});

Delivery Operations

// Get customer's delivery items
const { data: deliveryItems } = await storefront.delivery.getStorefrontCustomerDeliveryItems({
  params: {
    limit: 50,
    asc: false // Most recent first
  }
});

// Paginate through delivery items
const { data: nextPage } = await storefront.delivery.getStorefrontCustomerDeliveryItems({
  params: {
    limit: 50,
    after: deliveryItems[deliveryItems.length - 1].id
  }
});
Customer and delivery operations require a customer token for authentication.

Build docs developers (and LLMs) love