Skip to main content

Vue Themes

Vue works out of the box as a Shoppex theme framework — same Vite build pipeline, same SDK, just Vue components instead of React. The platform contract stays the same:
  • bun install
  • bun run build
  • build output in dist/index.html

Minimal Scripts

Your package.json must have scripts like:
  • dev
  • build
Example (conceptual):
{
  "scripts": {
    "dev": "vite",
    "build": "vite build"
  }
}

Minimal SDK Wiring (Framework-Agnostic)

This is the important part: initialize the SDK, then fetch storefront data.
// @validate
import shoppex from '@shoppexio/storefront';

shoppex.init('my-shop', { apiBaseUrl: 'https://api.shoppex.io' });

const res = await shoppex.getStorefront();
if (res.success && res.data) {
  console.log(res.data.shop.name);
}
Then in Vue you render the shop, products, and groups in your components.

Initial Data Injection (Optional)

If you want Shoppex to inject window.__SHOPPEX_INITIAL__, add the placeholder:
<!--initial-data-->
This works regardless of framework.

useStore() Composable (Composition API)

A reusable composable for loading storefront data:
// composables/useStore.ts
// In a real Vue app:
// import { ref, onMounted } from 'vue'

type Ref<T> = { value: T };
declare function ref<T>(value: T): Ref<T>;
declare function onMounted(fn: () => void | Promise<void>): void;

// assumes shoppex is available (via SDK import in your app entry)
declare const shoppex: any

export function useStore() {
  const store = ref(null)
  const products = ref([])
  const isLoading = ref(true)
  const error = ref(null)

  onMounted(async () => {
    const res = await shoppex.getStorefront()
    if (res.success && res.data) {
      store.value = res.data.shop
      products.value = res.data.products
    } else {
      error.value = res.message
    }
    isLoading.value = false
  })

  return { store, products, isLoading, error }
}

Cart Reactivity

Use the shoppex:cart-changed custom event to keep cart state in sync across components:
// composables/useCart.ts
// In a real Vue app:
// import { ref, onMounted, onUnmounted } from 'vue'

type Ref<T> = { value: T };
declare function ref<T>(value: T): Ref<T>;
declare function onMounted(fn: () => void | Promise<void>): void;
declare function onUnmounted(fn: () => void): void;

// assumes shoppex is available (via SDK import in your app entry)
declare const shoppex: any

export function useCart() {
  const items = ref(shoppex.getCart())
  const itemCount = ref(shoppex.getCartItemCount())

  function refresh() {
    items.value = shoppex.getCart()
    itemCount.value = shoppex.getCartItemCount()
  }

  onMounted(() => {
    window.addEventListener('shoppex:cart-changed', refresh)
    window.addEventListener('storage', refresh)
  })
  onUnmounted(() => {
    window.removeEventListener('shoppex:cart-changed', refresh)
    window.removeEventListener('storage', refresh)
  })

  return { items, itemCount }
}

// After modifying cart:
function addItem(productId: string, variantId: string) {
  shoppex.addToCart(productId, variantId)
  window.dispatchEvent(new CustomEvent('shoppex:cart-changed'))
}

Next Steps

Cart & Checkout

Add to cart, coupons, and the full checkout flow.

Theme Settings

Load published settings and apply them via CSS variables.

Theme Config

Define sections and settings in theme.config.ts.

SDK Reference

Complete SDK method reference for themes.