App Bridge
Overview
The module uses Shopify's CDN-based App Bridge (not the deprecated npm package). The CDN script and API key meta tag are automatically injected via SSR head — no manual setup required.
@shopify/app-bridge npm package — it is deprecated. The module uses the CDN approach exclusively.useAppBridge()
Access the App Bridge instance (typed as ShopifyGlobal) in your Vue components:
<script setup>
// Access the App Bridge instance
const shopify = useAppBridge()
// Get the current shop
const shop = shopify.config.shop
</script>
useAppBridge() is safe to call anywhere — it returns a lazy proxy that only throws when a property is accessed in an unavailable context (e.g., server-side or outside the Shopify admin iframe).
Common App Bridge APIs
<script setup>
const shopify = useAppBridge()
// Show a toast notification
shopify.toast.show('Product saved!')
// Open a resource picker
const selection = await shopify.resourcePicker({ type: 'product' })
// Get a session token
const token = await shopify.idToken()
</script>
useShopifyFetch()
Use useShopifyFetch() for API calls that automatically include the Shopify session token:
- Client: Fetches a session token via App Bridge and sets the
Authorizationheader - Server: Forwards the
Authorizationheader from the incoming request (when one is already present)
useShopifyFetch() inside useAsyncData, you must pass { server: false } so the fetch runs in the browser where App Bridge can provide a token.Basic usage
<script setup>
const { data: shop } = await useAsyncData(
'shop',
() => useShopifyFetch('/api/shop'),
{ server: false }
)
</script>
With TypeScript generics
<script setup lang="ts">
interface ShopData {
shop: { name: string; currencyCode: string }
}
const { data } = await useAsyncData(
'shop',
() => useShopifyFetch<ShopData>('/api/shop'),
{ server: false }
)
// data.value.shop.name is fully typed
</script>
With query parameters
<script setup>
const { data } = await useAsyncData(
'products',
() =>
useShopifyFetch('/api/products', {
query: { limit: 10, status: 'active' }
}),
{ server: false }
)
</script>
With mutations
<script setup>
async function createProduct() {
const result = await useShopifyFetch('/api/products', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ title: 'New Product' })
})
}
</script>
Loading Indicator
<ShLoadingIndicator> hooks into Nuxt's useLoadingIndicator() and calls shopify.loading() to show/hide the Shopify Admin's native top loading bar during page navigations:
<template>
<ShLoadingIndicator />
<NuxtPage />
</template>
This replaces <NuxtLoadingIndicator> with the native Shopify loading bar for a more integrated experience.