Skip to main content

IAP.createSubscriptionPurchaseOrder

Navigates to the in-app purchase checkout page for a subscription product. The flow mirrors createOneTimePurchaseOrder, with the addition of a subscriptionId field in the processProductGrant callback.

Signature

createSubscriptionPurchaseOrder is a member of the IAP namespace object.

import { IAP } from '@apps-in-toss/web-framework';

declare const IAP: {
createSubscriptionPurchaseOrder(params: {
options: {
sku: string;
offerId?: string | null;
processProductGrant: (params: {
orderId: string;
subscriptionId?: string;
}) => boolean | Promise<boolean>;
};
onEvent: (event: { type: 'success'; data: IapCreateSubscriptionPurchaseOrderResult }) => void | Promise<void>;
onError: (error: unknown) => void | Promise<void>;
}): () => void;
// ...see overview
};

Parameters

NameTypeRequiredDescription
params.options.skustringUnique ID of the subscription product to purchase.
params.options.offerIdstring | nullOffer ID to apply. Defaults to base price when omitted.
params.options.processProductGrant(params: { orderId: string; subscriptionId?: string }) => boolean | Promise<boolean>Callback invoked to activate the subscription on your server. Return true on success, false on failure.
params.onEvent(event: SubscriptionSuccessEvent) => void | Promise<void>Called on payment success.
params.onError(error: unknown) => void | Promise<void>Called when an error occurs during payment.

Returns

  • () => void — app-bridge cleanup function. Must be called when the payment flow ends to release resources.

Permission

No permission required — the IAP namespace is not bound to a PermissionName.

Examples

Minimal

import { IAP } from '@apps-in-toss/web-framework';

const cleanup = IAP.createSubscriptionPurchaseOrder({
options: {
sku: 'sub_monthly',
processProductGrant: async ({ orderId, subscriptionId }) => {
// Activate subscription on server, then return true
return true;
},
},
onEvent: (event) => {
console.log('Subscription active', event.data);
cleanup();
},
onError: (error) => {
console.error('Subscription error', error);
cleanup();
},
});

Realistic — with offer ID

import { IAP } from '@apps-in-toss/web-framework';
import { useCallback, useRef } from 'react';

interface Props {
sku: string;
offerId?: string;
}

function SubscriptionButton({ sku, offerId }: Props) {
const cleanupRef = useRef<(() => void) | null>(null);

const handleClick = useCallback(() => {
cleanupRef.current = IAP.createSubscriptionPurchaseOrder({
options: {
sku,
offerId: offerId ?? null,
processProductGrant: async ({ orderId, subscriptionId }) => {
try {
await fetch('/api/subscribe', {
method: 'POST',
body: JSON.stringify({ orderId, subscriptionId }),
headers: { 'Content-Type': 'application/json' },
});
return true;
} catch {
return false;
}
},
},
onEvent: (event) => {
console.log('Subscription activated', event.data);
cleanupRef.current?.();
},
onError: (error) => {
console.error(error);
cleanupRef.current?.();
},
});
}, [sku, offerId]);

return (
<button type="button" onClick={handleClick}>
Subscribe
</button>
);
}

Try it live

Run the subscription purchase flow on the IAP page in sdk-example.

Open in sdk-example
  • Guides — IAP payment flowprocessProductGrant/completeProductGrant sequencing, server fulfillment, and recovery patterns in one place.

External references