diff --git a/CLAUDE.md b/CLAUDE.md index 04599a64..69737463 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -14,6 +14,7 @@ This document provides an overview for AI agents working across the OpenIAP mono | Platform Packages | [`knowledge/internal/04-platform-packages.md`](knowledge/internal/04-platform-packages.md) | | Docs Patterns | [`knowledge/internal/05-docs-patterns.md`](knowledge/internal/05-docs-patterns.md) | | Git & Deployment | [`knowledge/internal/06-git-deployment.md`](knowledge/internal/06-git-deployment.md) | +| Docs Consistency / SSOT | [`knowledge/internal/07-docs-consistency.md`](knowledge/internal/07-docs-consistency.md) (run `bun audit:docs` before pushing API/Type doc edits) | ## Monorepo Structure diff --git a/bun.lock b/bun.lock index ee54ca7c..fc22625a 100644 --- a/bun.lock +++ b/bun.lock @@ -38,6 +38,7 @@ "@typescript-eslint/parser": "^8.39.1", "@vitejs/plugin-react": "^4.3.1", "babel-plugin-react-compiler": "^19.1.0-rc.2", + "baseline-browser-mapping": "^2.10.22", "eslint": "^9.21.0", "eslint-plugin-react-hooks": "^5.1.0", "eslint-plugin-react-refresh": "^0.4.7", @@ -528,7 +529,7 @@ "balanced-match": ["balanced-match@1.0.2", "", {}, "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="], - "baseline-browser-mapping": ["baseline-browser-mapping@2.8.16", "", { "bin": { "baseline-browser-mapping": "dist/cli.js" } }, "sha512-OMu3BGQ4E7P1ErFsIPpbJh0qvDudM/UuJeHgkAvfWe+0HFJCXh+t/l8L6fVLR55RI/UbKrVLnAXZSVwd9ysWYw=="], + "baseline-browser-mapping": ["baseline-browser-mapping@2.10.22", "", { "bin": { "baseline-browser-mapping": "dist/cli.cjs" } }, "sha512-6qruVrb5rse6WylFkU0FhBKKGuecWseqdpQfhkawn6ztyk2QlfwSRjsDxMCLJrkfmfN21qvhl9ABgaMeRkuwww=="], "brace-expansion": ["brace-expansion@1.1.12", "", { "dependencies": { "balanced-match": "^1.0.0", "concat-map": "0.0.1" } }, "sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg=="], @@ -1224,6 +1225,8 @@ "@whatwg-node/promise-helpers/tslib": ["tslib@2.8.1", "", {}, "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w=="], + "browserslist/baseline-browser-mapping": ["baseline-browser-mapping@2.8.16", "", { "bin": { "baseline-browser-mapping": "dist/cli.js" } }, "sha512-OMu3BGQ4E7P1ErFsIPpbJh0qvDudM/UuJeHgkAvfWe+0HFJCXh+t/l8L6fVLR55RI/UbKrVLnAXZSVwd9ysWYw=="], + "camel-case/tslib": ["tslib@2.8.1", "", {}, "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w=="], "capital-case/tslib": ["tslib@2.8.1", "", {}, "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w=="], diff --git a/knowledge/internal/07-docs-consistency.md b/knowledge/internal/07-docs-consistency.md new file mode 100644 index 00000000..b999202f --- /dev/null +++ b/knowledge/internal/07-docs-consistency.md @@ -0,0 +1,190 @@ +# Docs Consistency Rules — Single Source of Truth (SSOT) + +This document captures the consistency rules for OpenIAP documentation, code +comments, and generated types. PR #107 (and earlier rounds) repeatedly +surfaced the same class of drift — the docs claimed one field/default/type, +but the SDK code actually used another. These rules + the companion audit +script (`scripts/audit-docs.ts`) catch those before review. + +## Sources of truth + +When two places disagree, the upstream wins: + +``` +GraphQL schema → generated Types → hand-written wrapper SDK → docs page +(packages/gql (libraries/*/src (Swift / Kotlin / (packages/docs/ + /src/*.graphql) /types.{ts,kt,...}) Dart / TS / GDScript) src/pages/...) +``` + +- `packages/gql/src/*.graphql` — schema descriptions ARE the canonical doc + string. Edits propagate via `bun run generate` to every generated + `Types.{ts,kt,swift,dart,gd}`. +- `libraries/*/src/types.ts` (or equivalent) — generated; never hand-edit. + When a docs page mentions a field name, that field MUST exist in the + generated TS type. The audit script enforces this. +- Wrapper SDK source (e.g. `libraries/expo-iap/src/index.ts`) — JSDoc + parameter names MUST match the actual function-signature parameter + names. ESLint rule `tsdoc/syntax` + the audit script catch drift. +- Doc pages — the surface visible to users. Must reflect what each upstream + layer actually exposes. + +## Rules + +### R1 — JSDoc / KDoc / Dartdoc / Swift `@param` names match the signature + +If the function declares `(args) =>`, the JSDoc tag is `@param args …`. +If it declares `(request) =>`, the tag is `@param request …`. Don't carry +over the schema field name (`props`, `params`) when the wrapper destructured +or renamed. + +```ts +// ✅ wrapper destructures from `args` +/** @param args Purchase request. … */ +export const requestPurchase = async (args) => { … }; + +// ❌ JSDoc says `props`; signature says `args` +/** @param props … */ +export const requestPurchase = async (args) => { … }; +``` + +### R2 — Defaults match across SDKs + +If `fetchProducts.type` defaults to `'in-app'` in Flutter / expo-iap / +react-native-iap / godot-iap, then the Apple wrapper must also default to +`.inApp` — and the Apple doc comment must say `.inApp`. The schema +description is the canonical statement. + +When changing a default, update: +1. The GraphQL schema description. +2. Re-run `bun run generate`. +3. Every wrapper SDK's `?? ` expression and JSDoc / KDoc / etc. +4. Every API doc page (`packages/docs/src/pages/docs/apis/.tsx`). + +### R3 — Doc pages reference real fields only + +When a Type doc page lists fields in a `` or ` diff --git a/packages/docs/src/pages/docs/apis/init-connection.tsx b/packages/docs/src/pages/docs/apis/init-connection.tsx index 7c17a415..1b1f7f84 100644 --- a/packages/docs/src/pages/docs/apis/init-connection.tsx +++ b/packages/docs/src/pages/docs/apis/init-connection.tsx @@ -1,4 +1,5 @@ import { Link } from 'react-router-dom'; +import AnchorLink from '../../../components/AnchorLink'; import CodeBlock from '../../../components/CodeBlock'; import LanguageTabs from '../../../components/LanguageTabs'; import SEO from '../../../components/SEO'; @@ -20,6 +21,30 @@ function InitConnection() { Initialize connection to the store service. Must be called before any other IAP operations.

+

+ iOS: Verifies AppStore.canMakePayments, + registers the SKPaymentQueue observer for promoted IAPs, + and starts a Transaction.updates listener that drives the + purchase event stream. Safe to call repeatedly.{' '} + + Apple docs + + . Android: Starts BillingClient and waits + for onBillingSetupFinished. Required before any other Play + Billing call.{' '} + + Google docs + + . +

Signature

@@ -45,6 +70,58 @@ function InitConnection() { }} + + Parameters + +

+ Pass an optional{' '} + + InitConnectionConfig + {' '} + — Android billing program flags. iOS ignores Android-specific fields. +

+ + + + Returns + +

+ Promise<boolean>true once the + platform billing client is connected. +

+ + + Throws + +

When the platform billing client fails to initialize.

+

Example

{{ diff --git a/packages/docs/src/pages/docs/apis/ios/begin-refund-request-ios.tsx b/packages/docs/src/pages/docs/apis/ios/begin-refund-request-ios.tsx index fa812d6f..5b718d27 100644 --- a/packages/docs/src/pages/docs/apis/ios/begin-refund-request-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/begin-refund-request-ios.tsx @@ -1,4 +1,5 @@ import { Link } from 'react-router-dom'; +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -23,6 +24,18 @@ function BeginRefundRequestIOS() { Initiate a refund request for a product (iOS 15+). Presents the StoreKit refund sheet.

+

+ Wraps Transaction.beginRefundRequest(in:) — presents the + refund-request sheet. iOS 15+. See the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -30,6 +43,72 @@ function BeginRefundRequestIOS() { swift: ( {`func beginRefundRequestIOS(sku: String) async throws -> String?`} ), + kotlin: ( + {`suspend fun beginRefundRequestIOS(sku: String): String?`} + ), + typescript: ( + {`beginRefundRequestIOS(sku: string): Promise`} + ), + dart: ( + {`Future beginRefundRequestIOS(String sku);`} + ), + gdscript: ( + {`func begin_refund_request_ios(product_id: String) -> Types.RefundResultIOS`} + ), + }} + + + + Parameters + +
    +
  • + sku{' '} + + (required, string) + {' '} + — Product identifier to refund. +
  • +
+ + + Returns + +

+ Promise<string | null> — Refund request status + string, or null if the user dismissed the sheet. +

+ +

Example

+ + {{ + swift: ( + {`let status = try await OpenIapModule.shared.beginRefundRequestIOS(sku: "com.app.premium")`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +val status = kmpIAP.beginRefundRequestIOS(sku = "com.app.premium")`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { Platform } from 'react-native'; +import { beginRefundRequestIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + const status = await beginRefundRequestIOS('com.app.premium'); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + final status = await FlutterInappPurchase.instance + .beginRefundRequestIOS('com.app.premium'); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + # Synchronous — no await; returns Types.RefundResultIOS directly. + var result = iap.begin_refund_request_ios("com.app.premium")`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/can-present-external-purchase-notice-ios.tsx b/packages/docs/src/pages/docs/apis/ios/can-present-external-purchase-notice-ios.tsx index 4f62def5..f66326a7 100644 --- a/packages/docs/src/pages/docs/apis/ios/can-present-external-purchase-notice-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/can-present-external-purchase-notice-ios.tsx @@ -1,3 +1,4 @@ +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -21,6 +22,18 @@ function CanPresentExternalPurchaseNoticeIOS() {

Check if external purchase notice sheet can be presented (iOS 17.4+).

+

+ Wraps ExternalPurchase.canPresent — gate before calling{' '} + presentExternalPurchaseNoticeSheetIOS. iOS 17.4+. See the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -28,6 +41,57 @@ function CanPresentExternalPurchaseNoticeIOS() { swift: ( {`func canPresentExternalPurchaseNoticeIOS() async throws -> Bool`} ), + kotlin: ( + {`suspend fun canPresentExternalPurchaseNoticeIOS(): Boolean`} + ), + typescript: ( + {`canPresentExternalPurchaseNoticeIOS(): Promise`} + ), + dart: ( + {`Future canPresentExternalPurchaseNoticeIOS();`} + ), + gdscript: ( + {`func can_present_external_purchase_notice_ios() -> bool`} + ), + }} + + + + Returns + +

+ Promise<boolean>true if the + external-purchase notice sheet can be presented (iOS 17.4+). +

+ +

Example

+ + {{ + swift: ( + {`let can = try await OpenIapModule.shared.canPresentExternalPurchaseNoticeIOS()`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +val can = kmpIAP.canPresentExternalPurchaseNoticeIOS()`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { canPresentExternalPurchaseNoticeIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + const can = await canPresentExternalPurchaseNoticeIOS(); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + final can = await FlutterInappPurchase.instance + .canPresentExternalPurchaseNoticeIOS(); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + var can = await iap.can_present_external_purchase_notice_ios()`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/clear-transaction-ios.tsx b/packages/docs/src/pages/docs/apis/ios/clear-transaction-ios.tsx index 632179e3..d52d293a 100644 --- a/packages/docs/src/pages/docs/apis/ios/clear-transaction-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/clear-transaction-ios.tsx @@ -1,3 +1,4 @@ +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -19,6 +20,19 @@ function ClearTransactionIOS() { clearTransactionIOS

Clear pending transactions from the StoreKit payment queue.

+

+ Iterates Transaction.unfinished and calls{' '} + .finish() on each — sandbox/dev helper, do NOT ship in + production paths. See the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -26,6 +40,56 @@ function ClearTransactionIOS() { swift: ( {`func clearTransactionIOS() async throws -> Bool`} ), + kotlin: ( + {`suspend fun clearTransactionIOS(): Boolean`} + ), + typescript: ( + {`clearTransactionIOS(): Promise`} + ), + dart: ( + {`Future clearTransactionIOS();`} + ), + gdscript: ( + {`func clear_transaction_ios() -> Variant`} + ), + }} + + + + Returns + +

+ Promise<boolean>true once unfinished + transactions in the queue have been cleared. +

+ +

Example

+ + {{ + swift: ( + {`try await OpenIapModule.shared.clearTransactionIOS()`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +kmpIAP.clearTransactionIOS()`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { clearTransactionIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + await clearTransactionIOS(); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + await FlutterInappPurchase.instance.clearTransactionIOS(); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + var result = await iap.clear_transaction_ios()`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/current-entitlement-ios.tsx b/packages/docs/src/pages/docs/apis/ios/current-entitlement-ios.tsx index 7d0834a7..4d1f49e2 100644 --- a/packages/docs/src/pages/docs/apis/ios/current-entitlement-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/current-entitlement-ios.tsx @@ -1,3 +1,5 @@ +import { Link } from 'react-router-dom'; +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -19,6 +21,18 @@ function CurrentEntitlementIOS() { currentEntitlementIOS

Get current StoreKit 2 entitlement for a product (iOS 15+).

+

+ Wraps Transaction.currentEntitlement(for:) — single-product + convenience over currentEntitlements. See the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -26,6 +40,73 @@ function CurrentEntitlementIOS() { swift: ( {`func currentEntitlementIOS(sku: String) async throws -> Purchase?`} ), + kotlin: ( + {`suspend fun currentEntitlementIOS(sku: String): PurchaseIOS?`} + ), + typescript: ( + {`currentEntitlementIOS(sku: string): Promise`} + ), + dart: ( + {`Future currentEntitlementIOS(String sku);`} + ), + gdscript: ( + {`func current_entitlement_ios(sku: String) -> Variant`} + ), + }} + + + + Parameters + +
    +
  • + sku{' '} + + (required, string) + {' '} + — Product identifier. +
  • +
+ + + Returns + +

+ + Promise<PurchaseIOS | null> + {' '} + — iOS purchase shape, or null if the SKU has no matching + transaction. +

+ +

Example

+ + {{ + swift: ( + {`let entitlement = try await OpenIapModule.shared.currentEntitlementIOS(sku: "com.app.premium")`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +val entitlement = kmpIAP.currentEntitlementIOS(sku = "com.app.premium")`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { currentEntitlementIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + const entitlement = await currentEntitlementIOS('com.app.premium'); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + final entitlement = await FlutterInappPurchase.instance + .currentEntitlementIOS('com.app.premium'); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + var entitlement = await iap.current_entitlement_ios("com.app.premium")`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/get-all-transactions-ios.tsx b/packages/docs/src/pages/docs/apis/ios/get-all-transactions-ios.tsx index b236cd20..1a5cb9a0 100644 --- a/packages/docs/src/pages/docs/apis/ios/get-all-transactions-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/get-all-transactions-ios.tsx @@ -1,3 +1,5 @@ +import { Link } from 'react-router-dom'; +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -23,6 +25,19 @@ function GetAllTransactionsIOS() { Requires the SK2ConsumableTransactionHistory Info.plist key for finished consumables to be included (iOS 18+).

+

+ Iterates Transaction.all. iOS 18+ requires{' '} + SK2ConsumableTransactionHistory Info.plist key for finished + consumables to appear. See the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -30,6 +45,62 @@ function GetAllTransactionsIOS() { swift: ( {`func getAllTransactionsIOS() async throws -> [PurchaseIOS]`} ), + kotlin: ( + {`suspend fun getAllTransactionsIOS(): List`} + ), + typescript: ( + {`getAllTransactionsIOS(): Promise`} + ), + dart: ( + {`Future> getAllTransactionsIOS();`} + ), + gdscript: ( + {`func get_all_transactions_ios() -> Variant`} + ), + }} + + + + Returns + +

+ + Promise<PurchaseIOS[]> + {' '} + — array of StoreKit transactions in the iOS-specific shape. See{' '} + + Purchase + {' '} + for the full field reference. +

+ +

Example

+ + {{ + swift: ( + {`let txs = try await OpenIapModule.shared.getAllTransactionsIOS()`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +val txs = kmpIAP.getAllTransactionsIOS()`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { getAllTransactionsIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + const txs = await getAllTransactionsIOS(); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + final txs = await FlutterInappPurchase.instance.getAllTransactionsIOS(); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + var txs = await iap.get_all_transactions_ios()`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/get-app-transaction-ios.tsx b/packages/docs/src/pages/docs/apis/ios/get-app-transaction-ios.tsx index 91d8c97b..f565763e 100644 --- a/packages/docs/src/pages/docs/apis/ios/get-app-transaction-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/get-app-transaction-ios.tsx @@ -1,4 +1,5 @@ import { Link } from 'react-router-dom'; +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -20,6 +21,18 @@ function GetAppTransactionIOS() { getAppTransactionIOS

Fetch the current app transaction (iOS 16+).

+

+ Wraps AppTransaction.shared — the JWS-verified record of + how the app was acquired. iOS 16+. See the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -27,6 +40,59 @@ function GetAppTransactionIOS() { swift: ( {`func getAppTransactionIOS() async throws -> AppTransactionIOS?`} ), + kotlin: ( + {`suspend fun getAppTransactionIOS(): AppTransaction?`} + ), + typescript: ( + {`getAppTransactionIOS(): Promise`} + ), + dart: ( + {`Future getAppTransactionIOS();`} + ), + gdscript: ( + {`func get_app_transaction_ios() -> Variant`} + ), + }} + + + + Returns + +

+ + Promise<AppTransaction | null> + {' '} + — JWS-verified record of how the app was acquired. Returns{' '} + null on iOS < 16 or when no transaction is available. +

+ +

Example

+ + {{ + swift: ( + {`let appTx = try await OpenIapModule.shared.getAppTransactionIOS()`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +val appTx = kmpIAP.getAppTransactionIOS()`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { getAppTransactionIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + const appTx = await getAppTransactionIOS(); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + final appTx = await FlutterInappPurchase.instance.getAppTransactionIOS(); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + var app_tx = await iap.get_app_transaction_ios()`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/get-external-purchase-custom-link-token-ios.tsx b/packages/docs/src/pages/docs/apis/ios/get-external-purchase-custom-link-token-ios.tsx index 51124119..676aa434 100644 --- a/packages/docs/src/pages/docs/apis/ios/get-external-purchase-custom-link-token-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/get-external-purchase-custom-link-token-ios.tsx @@ -1,3 +1,5 @@ +import { Link } from 'react-router-dom'; +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -30,6 +32,19 @@ function GetExternalPurchaseCustomLinkTokenIOS() { API (iOS 18.1+). Pair the returned token with Apple's External Purchase Server API to report acquisition or services transactions.

+

+ Wraps ExternalPurchaseCustomLink.token(for:) — token to + report transactions to Apple's External Purchase Server. iOS 18.1+. See + the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -39,6 +54,88 @@ function GetExternalPurchaseCustomLinkTokenIOS() { tokenType: ExternalPurchaseCustomLinkTokenTypeIOS ) async throws -> ExternalPurchaseCustomLinkTokenResultIOS`} ), + kotlin: ( + {`suspend fun getExternalPurchaseCustomLinkTokenIOS( + tokenType: ExternalPurchaseCustomLinkTokenTypeIOS +): ExternalPurchaseCustomLinkTokenResultIOS`} + ), + typescript: ( + {`getExternalPurchaseCustomLinkTokenIOS( + tokenType: ExternalPurchaseCustomLinkTokenTypeIOS, +): Promise`} + ), + dart: ( + {`Future + getExternalPurchaseCustomLinkTokenIOS( + ExternalPurchaseCustomLinkTokenTypeIOS tokenType, +);`} + ), + gdscript: ( + {`func get_external_purchase_custom_link_token_ios(token_type: String) -> Variant`} + ), + }} + + + + Parameters + +
    +
  • + tokenType{' '} + + (required, ExternalPurchaseCustomLinkTokenTypeIOS) + {' '} + — acquisition (new customers) or services{' '} + (existing customers). +
  • +
+ + + Returns + +

+ + Promise<ExternalPurchaseCustomLinkTokenResultIOS> + {' '} + — token plus its acquired/expiry metadata. Send the token{' '} + field to Apple's External Purchase Server within the documented validity + window. +

+ +

Example

+ + {{ + swift: ( + {`let token = try await OpenIapModule.shared.getExternalPurchaseCustomLinkTokenIOS( + tokenType: .acquisition +)`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +val token = kmpIAP.getExternalPurchaseCustomLinkTokenIOS( + tokenType = ExternalPurchaseCustomLinkTokenTypeIOS.ACQUISITION +)`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { getExternalPurchaseCustomLinkTokenIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + const token = await getExternalPurchaseCustomLinkTokenIOS('acquisition'); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + final token = await FlutterInappPurchase.instance + .getExternalPurchaseCustomLinkTokenIOS( + ExternalPurchaseCustomLinkTokenTypeIOS.acquisition, + ); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + var token = await iap.get_external_purchase_custom_link_token_ios("acquisition")`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/get-pending-transactions-ios.tsx b/packages/docs/src/pages/docs/apis/ios/get-pending-transactions-ios.tsx index 25cc0898..3c3b11c7 100644 --- a/packages/docs/src/pages/docs/apis/ios/get-pending-transactions-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/get-pending-transactions-ios.tsx @@ -1,3 +1,5 @@ +import { Link } from 'react-router-dom'; +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -19,6 +21,18 @@ function GetPendingTransactionsIOS() { getPendingTransactionsIOS

Retrieve all pending transactions in the StoreKit queue.

+

+ Iterates Transaction.unfinished to surface transactions + still awaiting finish(). See the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -26,6 +40,62 @@ function GetPendingTransactionsIOS() { swift: ( {`func getPendingTransactionsIOS() async throws -> [Purchase]`} ), + kotlin: ( + {`suspend fun getPendingTransactionsIOS(): List`} + ), + typescript: ( + {`getPendingTransactionsIOS(): Promise`} + ), + dart: ( + {`Future> getPendingTransactionsIOS();`} + ), + gdscript: ( + {`func get_pending_transactions_ios() -> Variant`} + ), + }} + + + + Returns + +

+ + Promise<PurchaseIOS[]> + {' '} + — array of StoreKit transactions in the iOS-specific shape. See{' '} + + Purchase + {' '} + for the full field reference. +

+ +

Example

+ + {{ + swift: ( + {`let txs = try await OpenIapModule.shared.getPendingTransactionsIOS()`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +val txs = kmpIAP.getPendingTransactionsIOS()`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { getPendingTransactionsIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + const txs = await getPendingTransactionsIOS(); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + final txs = await FlutterInappPurchase.instance.getPendingTransactionsIOS(); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + var txs = await iap.get_pending_transactions_ios()`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/get-promoted-product-ios.tsx b/packages/docs/src/pages/docs/apis/ios/get-promoted-product-ios.tsx index 38a8070a..f067f458 100644 --- a/packages/docs/src/pages/docs/apis/ios/get-promoted-product-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/get-promoted-product-ios.tsx @@ -1,3 +1,5 @@ +import { Link } from 'react-router-dom'; +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -19,6 +21,19 @@ function GetPromotedProductIOS() { getPromotedProductIOS

Get the currently promoted product from App Store (iOS 11+).

+

+ Reads the product surfaced via App Store promoted IAP campaigns ( + SKPaymentTransactionObserver.shouldAddStorePayment). iOS + 11+. See the{' '} + + Apple StoreKit reference + + . +

Signature

@@ -26,6 +41,59 @@ function GetPromotedProductIOS() { swift: ( {`func getPromotedProductIOS() async throws -> Product?`} ), + kotlin: ( + {`suspend fun getPromotedProductIOS(): ProductIOS?`} + ), + typescript: ( + {`getPromotedProductIOS(): Promise`} + ), + dart: ( + {`Future getPromotedProductIOS();`} + ), + gdscript: ( + {`func get_promoted_product_ios() -> Variant`} + ), + }} + + + + Returns + +

+ + Promise<ProductIOS | null> + {' '} + — the App Store-promoted product, or null if no campaign is + currently queued. +

+ +

Example

+ + {{ + swift: ( + {`let product = try await OpenIapModule.shared.getPromotedProductIOS()`} + ), + kotlin: ( + {`// kmp-iap (iOS targets only — no-op on Android) +val product = kmpIAP.getPromotedProductIOS()`} + ), + typescript: ( + {`// expo-iap (also exported from react-native-iap) +import { getPromotedProductIOS } from 'expo-iap'; + +if (Platform.OS === 'ios') { + const product = await getPromotedProductIOS(); +}`} + ), + dart: ( + {`if (Platform.isIOS) { + final product = await FlutterInappPurchase.instance.getPromotedProductIOS(); +}`} + ), + gdscript: ( + {`if iap.get_platform() == "iOS": + var product = await iap.get_promoted_product_ios()`} + ), }} diff --git a/packages/docs/src/pages/docs/apis/ios/get-receipt-data-ios.tsx b/packages/docs/src/pages/docs/apis/ios/get-receipt-data-ios.tsx index 05b39119..501cbd6e 100644 --- a/packages/docs/src/pages/docs/apis/ios/get-receipt-data-ios.tsx +++ b/packages/docs/src/pages/docs/apis/ios/get-receipt-data-ios.tsx @@ -1,4 +1,5 @@ import { Link } from 'react-router-dom'; +import AnchorLink from '../../../../components/AnchorLink'; import CodeBlock from '../../../../components/CodeBlock'; import LanguageTabs from '../../../../components/LanguageTabs'; import SEO from '../../../../components/SEO'; @@ -20,74 +21,75 @@ function GetReceiptDataIOS() { getReceiptDataIOS

Get base64-encoded receipt data for legacy validation.

+

+ Reads Bundle.main.appStoreReceiptURL and base64-encodes the + file. Legacy StoreKit 1 flow — prefer JWS / verifyPurchase. + See the{' '} + + Apple StoreKit reference + + . +

Signature

{{ - typescript: ( - {`getReceiptDataIOS(): Promise`} - ), swift: ( {`func getReceiptDataIOS() async throws -> String?`} ), kotlin: ( {`suspend fun getReceiptDataIOS(): String?`} ), - kmp: ( - {`suspend fun getReceiptDataIOS(): String?`} + typescript: ( + {`getReceiptDataIOS(): Promise`} ), dart: ( {`Future getReceiptDataIOS();`} ), + gdscript: ( + {`func get_receipt_data_ios() -> String`} + ), }} + + Returns + +

+ Promise<string | null> — Base64-encoded receipt data + (legacy StoreKit 1 path). +

+

Example

{{ - typescript: ( - {`// expo-iap -import { getReceiptDataIOS } from 'expo-iap'; -// Same API in react-native-iap: -// import { getReceiptDataIOS } from 'react-native-iap'; - -const receipt = await getReceiptDataIOS(); -// Send the base64-encoded receipt to your server for legacy verifyReceipt. -console.log(receipt?.length ?? 0, 'bytes'); - -// --- Or alongside the useIAP() hook (also exported from react-native-iap) --- -// getReceiptDataIOS is a module-level helper; useIAP doesn't expose it on the -// hook return, so call the module function from inside your component once -// the hook reports the connection is ready. -import { useIAP } from 'expo-iap'; - -function ReceiptUploader() { - const { connected } = useIAP(); - - const upload = async () => { - if (!connected) return; - const receipt = await getReceiptDataIOS(); - if (!receipt) return; - await fetch('/api/validate-receipt', { - method: 'POST', - body: JSON.stringify({ receipt }), - }); - }; - - return , + document.body + ); + return (
- + {sidebarToggle} {isSidebarOpen && (
diff --git a/packages/docs/src/pages/docs/types/active-subscription.tsx b/packages/docs/src/pages/docs/types/active-subscription.tsx index 32706103..2acfb880 100644 --- a/packages/docs/src/pages/docs/types/active-subscription.tsx +++ b/packages/docs/src/pages/docs/types/active-subscription.tsx @@ -29,6 +29,29 @@ function ActiveSubscription() { . Provides a unified view of subscription status across platforms.

+

+ Cross-platform shape returned by getActiveSubscriptions.{' '} + iOS: derived from{' '} + Transaction.currentEntitlements filtered to subscription + products ( + + Apple docs + + ). Android: derived from{' '} + BillingClient.queryPurchasesAsync(SUBS) ( + + Google docs + + ). +

Native references:{' '} +

+ Modes for opting into Google's alternative-billing programs.{' '} + Android only — passed via{' '} + InitConnectionConfig.alternativeBillingModeAndroid{' '} + (deprecated; prefer enableBillingProgramAndroid) ( + + Google docs + + ). +

Native references:{' '} Discounts feature guide.

+

+ Android only. Mirrors{' '} + ProductDetails.OneTimePurchaseOfferDetails ( + + Google docs + + ). +

Native reference:{' '} {' '} one-to-one.

+

+ Android only. Mirrors{' '} + ProductDetails.PricingPhase — one billing-cycle phase of + a subscription's pricing schedule ( + + Google docs + + ). +

- Verify via a managed provider (IAPKit, Apple, Google, Horizon) - without standing up your own server. + Verify via a managed provider without standing up your own + server. The PurchaseVerificationProvider enum + currently exposes only IAPKit.
diff --git a/packages/docs/src/pages/docs/types/android/subscription-offer-android.tsx b/packages/docs/src/pages/docs/types/android/subscription-offer-android.tsx index 777a97be..36981b88 100644 --- a/packages/docs/src/pages/docs/types/android/subscription-offer-android.tsx +++ b/packages/docs/src/pages/docs/types/android/subscription-offer-android.tsx @@ -28,6 +28,20 @@ function SubscriptionOfferAndroid() { (cross-platform) instead.

Offer details for subscription purchases:

+

+ Android only. Mirrors{' '} + ProductDetails.SubscriptionOfferDetails — the + offerToken-bearing offer payload required for subscription{' '} + requestPurchase ( + + Google docs + + ). +

Native reference:{' '} +

+ Identifiers for Play Billing 8.2.0+ programs (External Payments, + etc.). Android only ( + + Google docs + + ). +

Native references:{' '} Introductory, Promotional) and one-time product offers (OneTime, Android only on Google Play Billing Library 7.0+). For iOS-specific WinBack offers see{' '} - - SubscriptionOfferTypeIOS - - ; iOS does not support one-time product discounts. + DiscountOfferIOS; + iOS does not support one-time product discounts. +

+

+ Cross-platform discount-offer envelope. iOS: maps to + a signed Product.SubscriptionOffer ( + + Apple docs + + ). Android: maps to a Play{' '} + SubscriptionOfferDetails entry ( + + Google docs + + ).

Native references:{' '} diff --git a/packages/docs/src/pages/docs/types/external-purchase-link.tsx b/packages/docs/src/pages/docs/types/external-purchase-link.tsx index 317f3872..a9470e1a 100644 --- a/packages/docs/src/pages/docs/types/external-purchase-link.tsx +++ b/packages/docs/src/pages/docs/types/external-purchase-link.tsx @@ -26,6 +26,19 @@ function ExternalPurchaseLink() { payment using Apple's StoreKit ExternalPurchase API. Available from iOS 17.4+ (notice sheet) and iOS 18.2+ (custom links).

+

+ Result of presentExternalPurchaseLinkIOS.{' '} + iOS only — wraps{' '} + ExternalPurchaseLink.open(url:) ( + + Apple docs + + ). +

Native references:{' '}

+ + ExternalPurchaseCustomLinkTokenResultIOS + +

+ Returned by{' '} + + getExternalPurchaseCustomLinkTokenIOS + {' '} + (iOS 18.1+). +

+ + + + + + + + + + + + + + + + + + + + + + + + + +
NameTypeSummary
+ token + + string + + Token to send to Apple's External Purchase Server reporting API. +
+ tokenType + + 'acquisition' | 'services' + + Echoes the requested token type (new customers vs. existing + customers). +
+ error + + string? + Populated when token creation fails.
+ + + ExternalPurchaseCustomLinkNoticeResultIOS + +

+ Returned by{' '} + + showExternalPurchaseCustomLinkNoticeIOS + {' '} + (iOS 18.1+). +

+ + + + + + + + + + + + + + + + + + + + +
NameTypeSummary
+ continued + + boolean + + Whether the user chose to continue to the external purchase. +
+ error + + string? + Populated when the sheet failed to present.
+ {{ typescript: ( diff --git a/packages/docs/src/pages/docs/types/ios/app-transaction-ios.tsx b/packages/docs/src/pages/docs/types/ios/app-transaction-ios.tsx index 1fe29e47..e351cd64 100644 --- a/packages/docs/src/pages/docs/types/ios/app-transaction-ios.tsx +++ b/packages/docs/src/pages/docs/types/ios/app-transaction-ios.tsx @@ -28,6 +28,18 @@ function AppTransactionIos() { . Contains metadata about the app's purchase and installation.

+

+ iOS only. Mirrors AppTransaction (iOS + 16+) — the JWS-verified record of how the app was acquired ( + + Apple docs + + ). +

Native reference:{' '}

Discount info returned as part of product details:

+

+ iOS only. Mirrors{' '} + Product.SubscriptionOffer for promotional/intro discounts + ( + + Apple docs + + ). +

Native reference:{' '} +

+ iOS only. Signed-discount payload for{' '} + Product.purchase(options:) ( + + Apple docs + + ). +

Native reference:{' '}

Payment mode for offers:

+

+ iOS only. Mirrors{' '} + Product.SubscriptionOffer.PaymentMode ( + payAsYouGo, payUpFront,{' '} + freeTrial) ( + + Apple docs + + ). +

Native reference:{' '} +

+ iOS only. Mirrors{' '} + Product.SubscriptionInfo.RenewalInfo — autoRenewStatus, + renewalDate, expirationReason ( + + Apple docs + + ). +

diff --git a/packages/docs/src/pages/docs/types/ios/subscription-period-ios.tsx b/packages/docs/src/pages/docs/types/ios/subscription-period-ios.tsx index 5997494d..2367807b 100644 --- a/packages/docs/src/pages/docs/types/ios/subscription-period-ios.tsx +++ b/packages/docs/src/pages/docs/types/ios/subscription-period-ios.tsx @@ -19,6 +19,19 @@ function SubscriptionPeriodIos() { SubscriptionPeriodIOS

Subscription period units:

+

+ iOS only. Mirrors{' '} + Product.SubscriptionPeriodunit and{' '} + value ( + + Apple docs + + ). +

Native reference:{' '} subscriptionStatusIOS(sku) to get detailed subscription state.

+

+ iOS only. A trimmed projection of Apple's{' '} + Product.SubscriptionInfo.Status — the OpenIAP wrapper + exposes renewalInfo and state only;{' '} + transaction from the Apple type is not surfaced ( + + Apple docs + + ). +

Native reference:{' '} .

+

+ Input to fetchProducts. iOS: passed to{' '} + Product.products(for:) ( + + Apple docs + + ). Android: passed to{' '} + BillingClient.queryProductDetailsAsync ( + + Google docs + + ). +

Native references:{' '} , discriminated by the platform field.

+

+ Cross-platform one-time product shape returned by{' '} + fetchProducts. iOS: derived from{' '} + Product ( + + Apple docs + + ). Android: derived from ProductDetails{' '} + ( + + Google docs + + ). +

Native references:{' '} , discriminated by the platform field.

+

+ Normalized purchase / transaction record. iOS:{' '} + derived from Transaction ( + + Apple docs + + ). Android: derived from Purchase ( + + Google docs + + ). +

Native references:{' '}

+ +
+ + PurchaseOptions + +

+ Optional input to{' '} + + getAvailablePurchases + + . PurchaseOptions does not have its own dedicated page — it lives here + next to Purchase because every field is platform- + specific and changes which subset of purchases the query returns. +

+

+ All fields are optional; pass null / omit the argument + entirely to use defaults. iOS-only fields are ignored on Android (and + vice-versa). +

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
NamePlatformDefaultSummary
+ alsoPublishToEventListenerIOS + iOS + false + + When true, every purchase returned by the query is + also re-emitted on{' '} + + purchaseUpdatedListener + {' '} + so existing listeners can process them with the same code path + used for live purchases. +
+ onlyIncludeActiveItemsIOS + iOS + false + + Switches the query from Transaction.all (full + StoreKit 2 history, including refunded / revoked entries) to{' '} + Transaction.currentEntitlements, which narrows the + result to active non-consumables and live subscriptions. +
+ includeSuspendedAndroid + Android + false + + When true, includes subscriptions in a paused or + grace-period state in the returned list. Suspended subscriptions + should not grant entitlements — see{' '} + isSuspendedAndroid on the Purchase fields above. +
+
); } diff --git a/packages/docs/src/pages/docs/types/request-purchase-props.tsx b/packages/docs/src/pages/docs/types/request-purchase-props.tsx index 28eb347d..f186143c 100644 --- a/packages/docs/src/pages/docs/types/request-purchase-props.tsx +++ b/packages/docs/src/pages/docs/types/request-purchase-props.tsx @@ -29,6 +29,29 @@ function RequestPurchaseProps() { .

+

+ Discriminated input to requestPurchase ( + type: 'in-app' | 'subs').{' '} + iOS: maps to Product.purchase(options:){' '} + ( + + Apple docs + + ). Android: maps to{' '} + BillingClient.launchBillingFlow ( + + Google docs + + ). +

Native references:{' '} .

+

+ Country-code shape returned by getStorefront.{' '} + iOS: Storefront.current ( + + Apple docs + + ). Android: BillingConfig.countryCode ( + + Google docs + + ). +

Native references:{' '} +

+ Cross-platform subscription-offer envelope. iOS: maps + to Product.SubscriptionOffer ( + + Apple docs + + ). Android: maps to{' '} + SubscriptionOfferDetails ( + + Google docs + + ). +

Native references:{' '} +

+ Cross-platform subscription product shape. iOS:{' '} + derived from Product with subscription{' '} + populated ( + + Apple docs + + ). Android: derived from ProductDetails{' '} + with subscriptionOfferDetails ( + + Google docs + + ). +

Native references:{' '} .

+

+ Input to verifyPurchaseWithProvider — pick a managed + validator. The PurchaseVerificationProvider enum + currently exposes only IAPKit. See{' '} + + Validation docs + + . +

diff --git a/packages/docs/src/pages/docs/types/verify-purchase-with-provider-result.tsx b/packages/docs/src/pages/docs/types/verify-purchase-with-provider-result.tsx index d1d94d03..79e1dfcf 100644 --- a/packages/docs/src/pages/docs/types/verify-purchase-with-provider-result.tsx +++ b/packages/docs/src/pages/docs/types/verify-purchase-with-provider-result.tsx @@ -24,6 +24,18 @@ function VerifyPurchaseWithProviderResult() {

Result type returned by verifyPurchaseWithProvider().

+

+ Result envelope from verifyPurchaseWithProvider. Carries{' '} + isValid plus the underlying provider response. See{' '} + + Validation docs + + . +

diff --git a/packages/docs/src/pages/docs/types/verify-purchase.tsx b/packages/docs/src/pages/docs/types/verify-purchase.tsx index 36d4b3a1..b9a77d69 100644 --- a/packages/docs/src/pages/docs/types/verify-purchase.tsx +++ b/packages/docs/src/pages/docs/types/verify-purchase.tsx @@ -23,6 +23,28 @@ function VerifyPurchase() { Types used with verifyPurchase() for server-side purchase verification.

+

+ Input/output shape for verifyPurchase.{' '} + iOS: validates the JWS from{' '} + Transaction.jsonRepresentation ( + + Apple docs + + ). Android: validates the purchaseToken{' '} + against Google Play Developer API ( + + Google docs + + ). +

Native references:{' '} --max-width + (calc is negative). Below --max-width the calc flips positive and would + visually shove the sidebar to the right of the viewport (the + tablet-range bug); clamp to 0 so it stays put. */ + margin-left: min(0px, calc((var(--max-width) - 100vw) / 2)); box-sizing: content-box; } @@ -559,16 +563,21 @@ opacity: 1; } -/* Tables — full-width table layout. Non-last columns shrink to fit their - nowrap content; the last column absorbs remaining width and wraps. */ +/* Tables — full-width layout, but allow horizontal scrolling when the + minimum content width exceeds the available space (rare, but + prevents catastrophic squeeze on phones). The `display: block` + trick + `overflow-x: auto` is the most portable way to scope the + scroll to the table without needing a wrapper element. */ .error-table, .doc-page table { + display: block; width: 100%; + max-width: 100%; + overflow-x: auto; border-collapse: collapse; margin: 1.5rem 0; background: var(--bg-primary); border-radius: 0.5rem; - overflow: hidden; box-shadow: 0 1px 3px rgba(0, 0, 0, 0.1); } @@ -596,24 +605,27 @@ border-bottom: 1px solid var(--border-color); } -/* Non-last columns (Name, Type, etc.) shrink to fit their content and - keep identifiers on one line. */ -.error-table th:not(:last-child), -.error-table td:not(:last-child), -.doc-page table th:not(:last-child), -.doc-page table td:not(:last-child) { +/* Only the FIRST column (identifier name) stays on one line — applying + `nowrap; width:1%` to every non-last column also forced middle + columns like Description to refuse to wrap, which then squeezed the + last column (e.g. Availability `iOS 17.4+`) to per-character width + on narrow viewports. */ +.error-table th:first-child, +.error-table td:first-child, +.doc-page table th:first-child, +.doc-page table td:first-child { width: 1%; white-space: nowrap; vertical-align: top; } -/* Last column (Summary/Description) absorbs remaining width and wraps at - word boundaries only — never breaks single characters per line. */ -.error-table th:last-child, -.error-table td:last-child, -.doc-page table th:last-child, -.doc-page table td:last-child { - width: auto; +/* All other columns wrap at word boundaries; long fields like + identifiers stay readable thanks to overflow-wrap: anywhere as a + safety net (no per-character wrap unless absolutely necessary). */ +.error-table th:not(:first-child), +.error-table td:not(:first-child), +.doc-page table th:not(:first-child), +.doc-page table td:not(:first-child) { white-space: normal; vertical-align: top; overflow-wrap: anywhere; @@ -859,13 +871,15 @@ scrollbar-color: var(--border-color) transparent; } -/* Docs Sidebar Toggle - Mobile Only */ +/* Docs Sidebar Toggle - Mobile Only. + z-index pushed well above the top nav (which is z-index: 100) so it + stays clickable even if the nav's mobile dropdown is mid-transition. */ .docs-sidebar-toggle { display: none; position: fixed; top: 100px; left: 1.5rem; - z-index: 1001; + z-index: 9001; background: var(--primary-color); color: white; border: none; @@ -882,8 +896,14 @@ pointer-events: auto; } +/* When the user scrolls, keep the toggle clear of the sticky top nav + (56px tall) instead of jumping it up to `top: 1rem` which lands the + button INSIDE the nav's bounding box. Even with z-index 9001 vs the + nav's 100, taps in the overlap zone were flaky on mobile WebKit — + keeping the toggle below the nav avoids the geometry collision + entirely. */ .docs-sidebar-toggle.scrolled { - top: 1rem; + top: 64px; } .docs-sidebar-toggle svg { @@ -906,16 +926,21 @@ pointer-events: none; } -/* Sidebar Overlay (mobile only) */ +/* Sidebar Overlay (mobile only). Starts below the top nav (56px) so the + nav stays visible/interactive — but the backdrop swallows every other + tap on the page so menu items behind don't fire by accident. The + alpha is high enough that page content doesn't read THROUGH the + overlay, which previously made the drawer look like it had a z-index + bug on long pages with code blocks behind it. */ .sidebar-overlay { display: none; position: fixed; - top: 0; + top: 56px; left: 0; right: 0; bottom: 0; - background: rgba(0, 0, 0, 0.5); - z-index: 999; + background: rgba(0, 0, 0, 0.78); + z-index: 8999; } /* Mobile Responsive Styles */ @@ -933,12 +958,16 @@ .sidebar-overlay { display: block; - backdrop-filter: blur(2px); + backdrop-filter: blur(6px); + -webkit-backdrop-filter: blur(6px); } .docs-sidebar { position: fixed !important; - top: 0 !important; + /* Start the drawer BELOW the sticky top nav (which is 56px tall) so + the two never overlap geometrically — taps at the very top of the + drawer can't bleed into the nav's hamburger menu and vice versa. */ + top: 56px !important; left: 0; bottom: 0; /* Reset desktop centering offset — at viewports below --max-width, @@ -948,18 +977,27 @@ --sidebar-edge-fill: 0px; width: 280px; max-width: 85vw; - height: 100vh !important; - max-height: 100vh !important; + height: calc(100vh - 56px) !important; + max-height: calc(100vh - 56px) !important; background: var(--bg-secondary); - z-index: 1000; + z-index: 9000; transition: + transform 0.25s ease, opacity 0.2s ease, visibility 0.2s ease; border-right: 1px solid var(--border-color); padding: var(--spacing-xl) 0; box-shadow: 4px 0 24px rgba(0, 0, 0, 0.15); + /* Closed state: slide fully off-screen, hide visually, AND disable + pointer events. iOS Safari has been observed to still deliver taps + to children of a `visibility: hidden; opacity: 0` fixed element, + so we belt-and-braces it: translateX moves the geometry out of the + hit-test area, and pointer-events: none turns off hit-testing for + this entire subtree even if the transform isn't honored. */ + transform: translateX(-100%); opacity: 0; visibility: hidden; + pointer-events: none; overflow-y: auto; box-sizing: border-box; } @@ -971,8 +1009,10 @@ } .docs-sidebar.open { + transform: translateX(0); opacity: 1; visibility: visible; + pointer-events: auto; } .docs-content { diff --git a/packages/docs/src/styles/responsive.css b/packages/docs/src/styles/responsive.css index bdfd8981..f1fc3d5e 100644 --- a/packages/docs/src/styles/responsive.css +++ b/packages/docs/src/styles/responsive.css @@ -48,14 +48,10 @@ flex-direction: column; } - .docs-sidebar { - width: 100%; - margin-bottom: 2rem; - } - - .docs-nav { - position: static; - } + /* Sidebar drawer styling lives in documentation.css's mobile block — + don't redefine width/position here (the older inline-sidebar layout + leaked `width: 100%` and `position: static` rules that would override + the drawer and let taps fall through to the top nav). */ .features-container, .benefit-grid, diff --git a/packages/google/openiap/src/main/java/dev/hyo/openiap/Types.kt b/packages/google/openiap/src/main/java/dev/hyo/openiap/Types.kt index bc6306db..9697826f 100644 --- a/packages/google/openiap/src/main/java/dev/hyo/openiap/Types.kt +++ b/packages/google/openiap/src/main/java/dev/hyo/openiap/Types.kt @@ -4744,146 +4744,172 @@ public sealed interface VerifyPurchaseResult { */ public interface MutationResolver { /** - * Acknowledge a non-consumable purchase or subscription + * Acknowledge a non-consumable purchase. Required within 3 days or Google auto-refunds. + * See: https://www.openiap.dev/docs/apis/android/acknowledge-purchase-android */ suspend fun acknowledgePurchaseAndroid(purchaseToken: String): Boolean /** - * Initiate a refund request for a product (iOS 15+) + * Present the refund request sheet (iOS 15+). See also Features → Refund. + * See: https://www.openiap.dev/docs/apis/ios/begin-refund-request-ios */ suspend fun beginRefundRequestIOS(sku: String): String? /** - * Check if alternative billing is available for this user/device - * Step 1 of alternative billing flow + * Check whether alternative billing is available for the user. Step 1 of the alternative billing flow. * - * Returns true if available, false otherwise - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns true if available, false otherwise. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/check-alternative-billing-availability-android */ suspend fun checkAlternativeBillingAvailabilityAndroid(): Boolean /** - * Clear pending transactions from the StoreKit payment queue + * Clear pending transactions in the queue (sandbox helper). + * See: https://www.openiap.dev/docs/apis/ios/clear-transaction-ios */ suspend fun clearTransactionIOS(): Boolean /** - * Consume a purchase token so it can be repurchased + * Consume a consumable purchase so it can be re-bought. + * See: https://www.openiap.dev/docs/apis/android/consume-purchase-android */ suspend fun consumePurchaseAndroid(purchaseToken: String): Boolean /** - * Create external transaction token for Google Play reporting - * Step 3 of alternative billing flow - * Must be called AFTER successful payment in your payment system - * Token must be reported to Google Play backend within 24 hours + * Create a reporting token for an alternative billing flow. Step 3 of the alternative billing flow. + * Must be called AFTER successful payment in your payment system. + * Token must be reported to Google Play backend within 24 hours. * - * Returns token string, or null if creation failed - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns token string, or null if creation failed. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/create-alternative-billing-token-android */ suspend fun createAlternativeBillingTokenAndroid(): String? /** - * Create reporting details for a billing program - * Replaces the deprecated createExternalOfferReportingDetailsAsync API + * Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). + * Replaces the deprecated createExternalOfferReportingDetailsAsync API. * - * Available in Google Play Billing Library 8.2.0+ - * Returns external transaction token needed for reporting external transactions - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns external transaction token needed for reporting external transactions. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/create-billing-program-reporting-details-android */ suspend fun createBillingProgramReportingDetailsAndroid(program: BillingProgramAndroid): BillingProgramReportingDetailsAndroid /** - * Open the native subscription management surface + * Open the platform's subscription management UI. + * See: https://www.openiap.dev/docs/apis/deep-link-to-subscriptions */ suspend fun deepLinkToSubscriptions(options: DeepLinkOptions? = null): Unit /** - * Close the platform billing connection + * Close the store connection and release resources. + * See: https://www.openiap.dev/docs/apis/end-connection */ suspend fun endConnection(): Boolean /** - * Finish a transaction after validating receipts + * Complete a transaction after server-side verification. Required on Android within 3 days. + * See: https://www.openiap.dev/docs/apis/finish-transaction */ suspend fun finishTransaction(purchase: PurchaseInput, isConsumable: Boolean? = null): Unit /** - * Establish the platform billing connection + * Initialize the store connection. Call before any IAP API. + * See: https://www.openiap.dev/docs/apis/init-connection */ suspend fun initConnection(config: InitConnectionConfig? = null): Boolean /** - * Check if a billing program is available for the current user - * Replaces the deprecated isExternalOfferAvailableAsync API + * Check whether a billing program (e.g., External Payments) is available for the current user. + * Replaces the deprecated isExternalOfferAvailableAsync API. * - * Available in Google Play Billing Library 8.2.0+ - * Returns availability result with isAvailable flag - * Throws OpenIapError.NotPrepared if billing client not ready + * Available in Google Play Billing Library 8.2.0+. + * Returns availability result with isAvailable flag. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/is-billing-program-available-android */ suspend fun isBillingProgramAvailableAndroid(program: BillingProgramAndroid): BillingProgramAvailabilityResultAndroid /** - * Launch external link flow for external billing programs - * Replaces the deprecated showExternalOfferInformationDialog API + * Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). + * Replaces the deprecated showExternalOfferInformationDialog API. * - * Available in Google Play Billing Library 8.2.0+ - * Shows Play Store dialog and optionally launches external URL - * Throws OpenIapError.NotPrepared if billing client not ready + * Shows Play Store dialog and optionally launches external URL. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/launch-external-link-android */ suspend fun launchExternalLinkAndroid(params: LaunchExternalLinkParamsAndroid): Boolean /** - * Present the App Store code redemption sheet + * Show the App Store offer code redemption sheet. + * See: https://www.openiap.dev/docs/apis/ios/present-code-redemption-sheet-ios */ suspend fun presentCodeRedemptionSheetIOS(): Boolean /** - * Present external purchase custom link with StoreKit UI + * Present an external purchase link, StoreKit External (iOS 16+). + * See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-link-ios */ suspend fun presentExternalPurchaseLinkIOS(url: String): ExternalPurchaseLinkResultIOS /** - * Present external purchase notice sheet (iOS 17.4+). - * Uses ExternalPurchase.presentNoticeSheet() which returns a token when user continues. + * Present the external purchase notice sheet (iOS 17.4+). + * Uses ExternalPurchase.presentNoticeSheet() which returns a token when the user continues. * Reference: https://developer.apple.com/documentation/storekit/externalpurchase/presentnoticesheet() + * See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-notice-sheet-ios */ suspend fun presentExternalPurchaseNoticeSheetIOS(): ExternalPurchaseNoticeResultIOS /** - * Initiate a purchase flow; rely on events for final state + * Initiate a purchase or subscription flow; rely on events for final state. + * See: https://www.openiap.dev/docs/apis/request-purchase */ suspend fun requestPurchase(params: RequestPurchaseProps): RequestPurchaseResult? /** - * Purchase the promoted product surfaced by the App Store. + * Buy the currently promoted product. * * @deprecated Use promotedProductListenerIOS to receive the productId, * then call requestPurchase with that SKU instead. In StoreKit 2, * promoted products can be purchased directly via the standard purchase flow. + * See: https://www.openiap.dev/docs/apis/ios/request-purchase-on-promoted-product-ios */ suspend fun requestPurchaseOnPromotedProductIOS(): Boolean /** - * Restore completed purchases across platforms + * Restore non-consumable and active subscription purchases. + * See: https://www.openiap.dev/docs/apis/restore-purchases */ suspend fun restorePurchases(): Unit /** - * Show alternative billing information dialog to user - * Step 2 of alternative billing flow - * Must be called BEFORE processing payment in your payment system + * Display Google's alternative billing information dialog. Step 2 of the alternative billing flow. + * Must be called BEFORE processing payment in your payment system. * - * Returns true if user accepted, false if user canceled - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns true if user accepted, false if user canceled. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/show-alternative-billing-dialog-android */ suspend fun showAlternativeBillingDialogAndroid(): Boolean /** - * Show ExternalPurchaseCustomLink notice sheet (iOS 18.1+). - * Displays the system disclosure notice sheet for custom external purchase links. + * Present the disclosure sheet required before linking out via ExternalPurchaseCustomLink (iOS 18.1+). * Call this after a deliberate customer interaction before linking out to external purchases. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/shownotice(type:) + * See: https://www.openiap.dev/docs/apis/ios/show-external-purchase-custom-link-notice-ios */ suspend fun showExternalPurchaseCustomLinkNoticeIOS(noticeType: ExternalPurchaseCustomLinkNoticeTypeIOS): ExternalPurchaseCustomLinkNoticeResultIOS /** - * Open subscription management UI and return changed purchases (iOS 15+) + * Present the manage-subscriptions sheet and return changed purchases (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/show-manage-subscriptions-ios */ suspend fun showManageSubscriptionsIOS(): List /** - * Force a StoreKit sync for transactions (iOS 15+) + * Force sync transactions with the App Store (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/sync-ios */ suspend fun syncIOS(): Boolean /** - * Validate purchase receipts with the configured providers + * Deprecated. Validate purchase receipts with the configured providers — use verifyPurchase instead. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase */ suspend fun validateReceipt(options: VerifyPurchaseProps): VerifyPurchaseResult /** - * Verify purchases with the configured providers + * Verify a purchase against your own backend. Returns a platform-specific + * variant of VerifyPurchaseResult — VerifyPurchaseResultIOS exposes isValid + * + receipt/JWS metadata, VerifyPurchaseResultAndroid carries Play Store + * receipt fields (no isValid), and VerifyPurchaseResultHorizon uses success. + * Inspect the concrete variant before reading fields. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase */ suspend fun verifyPurchase(options: VerifyPurchaseProps): VerifyPurchaseResult /** - * Verify purchases with a specific provider (e.g., IAPKit) + * Verify via a managed provider without standing up your own server. The + * PurchaseVerificationProvider enum currently exposes only IAPKit; platform + * availability may differ by implementation. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase-with-provider */ suspend fun verifyPurchaseWithProvider(options: VerifyPurchaseWithProviderProps): VerifyPurchaseWithProviderResult } @@ -4893,95 +4919,116 @@ public interface MutationResolver { */ public interface QueryResolver { /** - * Check if external purchase notice sheet can be presented (iOS 17.4+) - * Uses ExternalPurchase.canPresent + * Check eligibility for the external purchase notice sheet (iOS 17.4+). + * Uses ExternalPurchase.canPresent. + * See: https://www.openiap.dev/docs/apis/ios/can-present-external-purchase-notice-ios */ suspend fun canPresentExternalPurchaseNoticeIOS(): Boolean /** - * Get current StoreKit 2 entitlements (iOS 15+) + * Get the user's current entitlement for a product, using StoreKit 2 (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/current-entitlement-ios */ suspend fun currentEntitlementIOS(sku: String): PurchaseIOS? /** - * Retrieve products or subscriptions from the store + * Fetch products or subscriptions from the store. + * See: https://www.openiap.dev/docs/apis/fetch-products */ suspend fun fetchProducts(params: ProductRequest): FetchProductsResult /** - * Get active subscriptions (filters by subscriptionIds when provided) + * Get details of all currently active subscriptions (filters by subscriptionIds when provided). + * See: https://www.openiap.dev/docs/apis/get-active-subscriptions */ suspend fun getActiveSubscriptions(subscriptionIds: List? = null): List /** - * Get the full StoreKit 2 transaction history as PurchaseIOS values. + * List every StoreKit transaction (finished + unfinished) for the current user. * Requires the SK2ConsumableTransactionHistory Info.plist key in the host app * for finished consumables to be included (iOS 18+). * Unlike getAvailablePurchases, always returns the iOS-specific PurchaseIOS shape. + * See: https://www.openiap.dev/docs/apis/ios/get-all-transactions-ios */ suspend fun getAllTransactionsIOS(): List /** - * Fetch the current app transaction (iOS 16+) + * Fetch the app transaction (iOS 16+). + * See: https://www.openiap.dev/docs/apis/ios/get-app-transaction-ios */ suspend fun getAppTransactionIOS(): AppTransaction? /** - * Get all available purchases for the current user + * List active purchases for the current user. + * See: https://www.openiap.dev/docs/apis/get-available-purchases */ suspend fun getAvailablePurchases(options: PurchaseOptions? = null): List /** - * Get external purchase token for reporting to Apple (iOS 18.1+). - * Use this token with Apple's External Purchase Server API to report transactions. + * Fetch a token for Apple's External Purchase Server reporting API (iOS 18.1+). + * Use this token to report transactions made through ExternalPurchaseCustomLink. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/token(for:) + * See: https://www.openiap.dev/docs/apis/ios/get-external-purchase-custom-link-token-ios */ suspend fun getExternalPurchaseCustomLinkTokenIOS(tokenType: ExternalPurchaseCustomLinkTokenTypeIOS): ExternalPurchaseCustomLinkTokenResultIOS /** - * Retrieve all pending transactions in the StoreKit queue + * List unfinished StoreKit transactions in the queue. + * See: https://www.openiap.dev/docs/apis/ios/get-pending-transactions-ios */ suspend fun getPendingTransactionsIOS(): List /** - * Get the currently promoted product (iOS 11+) + * Read the App Store-promoted product, if any (iOS 11+). + * See: https://www.openiap.dev/docs/apis/ios/get-promoted-product-ios */ suspend fun getPromotedProductIOS(): ProductIOS? /** - * Get base64-encoded receipt data for validation + * Get base64-encoded receipt data (legacy validation). + * See: https://www.openiap.dev/docs/apis/ios/get-receipt-data-ios */ suspend fun getReceiptDataIOS(): String? /** - * Get the current storefront country code + * Return the user's storefront country code. + * See: https://www.openiap.dev/docs/apis/get-storefront */ suspend fun getStorefront(): String /** - * Get the current App Store storefront country code + * Deprecated. Get the current App Store storefront country code — use cross-platform getStorefront instead. + * See: https://www.openiap.dev/docs/apis/ios/get-storefront-ios */ suspend fun getStorefrontIOS(): String /** - * Get the transaction JWS (StoreKit 2) + * Return the JWS string for a transaction (StoreKit 2). + * See: https://www.openiap.dev/docs/apis/ios/get-transaction-jws-ios */ suspend fun getTransactionJwsIOS(sku: String): String? /** - * Check whether the user has active subscriptions + * Check whether the user has any active subscription. + * See: https://www.openiap.dev/docs/apis/has-active-subscriptions */ suspend fun hasActiveSubscriptions(subscriptionIds: List? = null): Boolean /** - * Check if app is eligible for ExternalPurchaseCustomLink API (iOS 18.1+). + * Check eligibility for the custom-link variant of external purchase (iOS 18.1+). * Returns true if the app can use custom external purchase links. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/iseligible + * See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-external-purchase-custom-link-ios */ suspend fun isEligibleForExternalPurchaseCustomLinkIOS(): Boolean /** - * Check introductory offer eligibility for a subscription group + * Check intro-offer eligibility for a subscription group. + * See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-intro-offer-ios */ suspend fun isEligibleForIntroOfferIOS(groupID: String): Boolean /** - * Verify a StoreKit 2 transaction signature + * Check whether a transaction's JWS verification passed (StoreKit 2). + * See: https://www.openiap.dev/docs/apis/ios/is-transaction-verified-ios */ suspend fun isTransactionVerifiedIOS(sku: String): Boolean /** - * Get the latest transaction for a product using StoreKit 2 + * Get the latest verified transaction for a product, using StoreKit 2. + * See: https://www.openiap.dev/docs/apis/ios/latest-transaction-ios */ suspend fun latestTransactionIOS(sku: String): PurchaseIOS? /** - * Get StoreKit 2 subscription status details (iOS 15+) + * Get subscription status objects from StoreKit 2 (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/subscription-status-ios */ suspend fun subscriptionStatusIOS(sku: String): List /** - * Validate a receipt for a specific product + * Deprecated. Legacy App Store receipt validation — use verifyPurchase instead. + * See: https://www.openiap.dev/docs/apis/ios/validate-receipt-ios */ suspend fun validateReceiptIOS(options: VerifyPurchaseProps): VerifyPurchaseResultIOS } diff --git a/packages/google/openiap/src/main/java/dev/hyo/openiap/store/OpenIapStore.kt b/packages/google/openiap/src/main/java/dev/hyo/openiap/store/OpenIapStore.kt index 4484cf9f..4cddc759 100644 --- a/packages/google/openiap/src/main/java/dev/hyo/openiap/store/OpenIapStore.kt +++ b/packages/google/openiap/src/main/java/dev/hyo/openiap/store/OpenIapStore.kt @@ -219,6 +219,17 @@ class OpenIapStore(private val module: OpenIapProtocol) { // Connection Management - Using GraphQL handler pattern // ------------------------------------------------------------------------- + /** + * Initialize the store connection. Must be called before any other IAP API. + * + * @param config Optional [InitConnectionConfig]. Use `enableBillingProgramAndroid` to + * opt in to External Payments / similar Play Billing programs. Pass `null` for default. + * @return `true` once the Play Billing client is connected. + * @throws OpenIapError.InitConnection when the billing client fails to initialize + * (e.g. Play Store missing, version too old). + * + * @see init-connection + */ val initConnection: MutationInitConnectionHandler = { config -> setLoading { it.initConnection = true } try { @@ -237,13 +248,26 @@ class OpenIapStore(private val module: OpenIapProtocol) { } /** - * Convenience overload that calls initConnection with null config + * Initialize the store connection. Must be called before any other IAP API. + * + * Convenience overload — calls the config-accepting variant with `null`. + * + * @return `true` once the Play Billing client is connected. + * @throws OpenIapError.InitConnection when the billing client fails to initialize + * (e.g. Play Store missing, version too old). + * + * @see init-connection */ suspend fun initConnection(): Boolean { OpenIapLog.i("OpenIapStore.initConnection(): Calling initConnection(null)...", "OpenIapStore") return initConnection(null) } + /** + * Close the store connection and release resources. + * + * @see https://www.openiap.dev/docs/apis/end-connection + */ val endConnection: MutationEndConnectionHandler = { removePurchaseUpdateListener(purchaseUpdateListener) removePurchaseErrorListener(purchaseErrorListener) @@ -262,6 +286,18 @@ class OpenIapStore(private val module: OpenIapProtocol) { // ------------------------------------------------------------------------- // Product Management - Using GraphQL handler pattern // ------------------------------------------------------------------------- + /** + * Retrieve products or subscriptions from Google Play by SKU. + * + * @param params [ProductRequest] with `skus` and an optional `type` + * ([ProductQueryType.InApp], [ProductQueryType.Subs], or [ProductQueryType.All]; + * defaults to InApp). + * @return A [FetchProductsResult] sealed variant — `Products` for InApp, + * `Subscriptions` for Subs, mixed list for All. + * @throws OpenIapError on store rejection (unknown SKU, network failure, not connected). + * + * @see fetch-products + */ val fetchProducts: QueryFetchProductsHandler = { request -> android.util.Log.i("OpenIapStore", "fetchProducts called with SKUs: ${request.skus}, type: ${request.type}") setLoading { it.fetchProducts = true } @@ -341,6 +377,21 @@ class OpenIapStore(private val module: OpenIapProtocol) { // ------------------------------------------------------------------------- // Purchases / Restore - Using GraphQL handler pattern // ------------------------------------------------------------------------- + /** + * List the owned/available purchases held by Play Billing — non-consumables, + * active subscriptions, and any pending transactions returned by + * `BillingClient.queryPurchasesAsync` for INAPP + SUBS. Use this to restore + * purchases or to recover anything not finished previously. (iOS uses + * `Transaction.unfinished` / `Transaction.all` semantics; on Android the + * concept is "owned by the user", not strictly "unfinished".) + * + * @param options Optional [PurchaseOptions]. Most fields are iOS-only and ignored + * on Android. + * @return List of [Purchase] currently owned according to Play Billing. + * @throws OpenIapError when the Play Billing query fails. + * + * @see get-available-purchases + */ val getAvailablePurchases: QueryGetAvailablePurchasesHandler = { options -> android.util.Log.i("OpenIapStore", "getAvailablePurchases called, module type: ${module.javaClass.simpleName}") setLoading { it.restorePurchases = true } @@ -363,6 +414,22 @@ class OpenIapStore(private val module: OpenIapProtocol) { // ------------------------------------------------------------------------- // Purchase Flow - Using GraphQL handler pattern // ------------------------------------------------------------------------- + /** + * Initiate a purchase flow. The result is delivered via the purchase update listener, + * NOT through the return value. + * + * @param props [RequestPurchaseProps]. Use `request.google.skus` and pass + * `subscriptionOffers = [{sku, offerToken}]` for subscriptions. + * @return The dispatched purchase payload (do not rely on this for the actual outcome). + * @throws OpenIapError on synchronous rejection (e.g. billing client not ready, + * developer error such as missing offerToken on subs). + * + * Warning: Event-based. Collect from `purchaseUpdatedListener` / `purchaseErrorListener` + * (or `OpenIapStore.currentPurchase` and `OpenIapStore.status.lastError` flows) for the + * final state — there is no `currentError` field; errors live on `status.lastError`. + * + * @see request-purchase + */ val requestPurchase: MutationRequestPurchaseHandler = { props -> val skuForStatus = when (val request = props.request) { is RequestPurchaseProps.Request.Purchase -> request.value.android?.skus?.firstOrNull() @@ -383,7 +450,18 @@ class OpenIapStore(private val module: OpenIapProtocol) { } - // Using GraphQL handler pattern + /** + * Complete a purchase transaction. Call after server-side verification. + * + * @param purchase The [PurchaseInput] to finalize. + * @param isConsumable Pass `true` for consumables (consumes the token so the SKU can be + * bought again), `false` for non-consumables and subscriptions (acknowledges only). + * @throws OpenIapError when the Play Billing finalize call fails. + * + * Important: Google auto-refunds Android purchases NOT acknowledged/consumed within 3 days. + * + * @see finish-transaction + */ val finishTransaction: MutationFinishTransactionHandler = { purchaseInput, isConsumable -> val token = purchaseInput.purchaseToken // Check if already processed - but we can't check isAcknowledgedAndroid on PurchaseInput @@ -402,32 +480,45 @@ class OpenIapStore(private val module: OpenIapProtocol) { // ------------------------------------------------------------------------- // Subscriptions // ------------------------------------------------------------------------- + /** + * Get details of all currently active subscriptions. + * + * @see https://www.openiap.dev/docs/apis/get-active-subscriptions + */ suspend fun getActiveSubscriptions(subscriptionIds: List? = null): List = module.queryHandlers.getActiveSubscriptions?.invoke(subscriptionIds) ?: emptyList() + /** + * Check whether the user has any active subscription. + * + * @see https://www.openiap.dev/docs/apis/has-active-subscriptions + */ suspend fun hasActiveSubscriptions(subscriptionIds: List? = null): Boolean = module.queryHandlers.hasActiveSubscriptions?.invoke(subscriptionIds) ?: false + /** + * Open the platform's subscription management UI. + * + * @see https://www.openiap.dev/docs/apis/deep-link-to-subscriptions + */ suspend fun deepLinkToSubscriptions(options: DeepLinkOptions) = module.mutationHandlers.deepLinkToSubscriptions?.invoke(options) // ------------------------------------------------------------------------- // Alternative Billing (Step-by-Step API) // ------------------------------------------------------------------------- /** - * Step 1: Check if alternative billing is available for this user/device - * @return true if available, false otherwise - * @deprecated Use isBillingProgramAvailable with BillingProgramAndroid.ExternalOffer instead + * Check whether alternative billing is available for the user. + * + * @see https://www.openiap.dev/docs/apis/android/check-alternative-billing-availability-android */ @Deprecated("Use isBillingProgramAvailable with BillingProgramAndroid.ExternalOffer instead") @Suppress("DEPRECATION") suspend fun checkAlternativeBillingAvailability(): Boolean = module.checkAlternativeBillingAvailability() /** - * Step 2: Show alternative billing information dialog to user - * Must be called BEFORE processing payment - * @param activity Current activity context - * @return true if user accepted, false if canceled - * @deprecated Use launchExternalLink instead + * Display Google's alternative billing information dialog. + * + * @see https://www.openiap.dev/docs/apis/android/show-alternative-billing-dialog-android */ @Deprecated("Use launchExternalLink instead") @Suppress("DEPRECATION") @@ -435,11 +526,9 @@ class OpenIapStore(private val module: OpenIapProtocol) { module.showAlternativeBillingInformationDialog(activity) /** - * Step 3: Create external transaction token for alternative billing - * Must be called AFTER successful payment in your payment system - * Token must be reported to Google Play backend within 24 hours - * @return External transaction token, or null if failed - * @deprecated Use createBillingProgramReportingDetails with BillingProgramAndroid.ExternalOffer instead + * Create a reporting token for an alternative billing flow. + * + * @see https://www.openiap.dev/docs/apis/android/create-alternative-billing-token-android */ @Deprecated("Use createBillingProgramReportingDetails with BillingProgramAndroid.ExternalOffer instead") @Suppress("DEPRECATION") @@ -450,32 +539,25 @@ class OpenIapStore(private val module: OpenIapProtocol) { // Billing Programs (Google Play Billing Library 8.2.0+) // ------------------------------------------------------------------------- /** - * Check if a billing program is available for this user/device. - * This is the new API that replaces checkAlternativeBillingAvailability for external offers. + * Check whether a billing program (e.g., External Payments) is available. * - * @param program The billing program to check (EXTERNAL_CONTENT_LINK or EXTERNAL_OFFER) - * @return Result containing availability information + * @see https://www.openiap.dev/docs/apis/android/is-billing-program-available-android */ suspend fun isBillingProgramAvailable(program: BillingProgramAndroid): BillingProgramAvailabilityResultAndroid = module.isBillingProgramAvailable(program) /** - * Create reporting details for transactions made outside of Google Play Billing. - * This is the new API that replaces createAlternativeBillingReportingToken for external offers. + * Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). * - * @param program The billing program (EXTERNAL_CONTENT_LINK or EXTERNAL_OFFER) - * @return Reporting details containing the external transaction token + * @see https://www.openiap.dev/docs/apis/android/create-billing-program-reporting-details-android */ suspend fun createBillingProgramReportingDetails(program: BillingProgramAndroid): BillingProgramReportingDetailsAndroid = module.createBillingProgramReportingDetails(program) /** - * Launch an external link for external offer or app download. - * This is the new API that replaces showAlternativeBillingInformationDialog for external offers. + * Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). * - * @param activity Current activity context - * @param params Parameters for the external link - * @return true if launch was successful, false otherwise + * @see https://www.openiap.dev/docs/apis/android/launch-external-link-android */ suspend fun launchExternalLink(activity: Activity, params: LaunchExternalLinkParamsAndroid): Boolean = module.launchExternalLink(activity, params) diff --git a/packages/gql/src/api-android.graphql b/packages/gql/src/api-android.graphql index d6baf87a..2530e2d2 100644 --- a/packages/gql/src/api-android.graphql +++ b/packages/gql/src/api-android.graphql @@ -2,78 +2,81 @@ extend type Mutation { """ - Acknowledge a non-consumable purchase or subscription + Acknowledge a non-consumable purchase. Required within 3 days or Google auto-refunds. + See: https://www.openiap.dev/docs/apis/android/acknowledge-purchase-android """ # Future acknowledgePurchaseAndroid(purchaseToken: String!): Boolean! """ - Consume a purchase token so it can be repurchased + Consume a consumable purchase so it can be re-bought. + See: https://www.openiap.dev/docs/apis/android/consume-purchase-android """ # Future consumePurchaseAndroid(purchaseToken: String!): Boolean! # Alternative Billing APIs """ - Check if alternative billing is available for this user/device - Step 1 of alternative billing flow + Check whether alternative billing is available for the user. Step 1 of the alternative billing flow. - Returns true if available, false otherwise - Throws OpenIapError.NotPrepared if billing client not ready + Returns true if available, false otherwise. + Throws OpenIapError.NotPrepared if billing client not ready. + See: https://www.openiap.dev/docs/apis/android/check-alternative-billing-availability-android """ # Future checkAlternativeBillingAvailabilityAndroid: Boolean! """ - Show alternative billing information dialog to user - Step 2 of alternative billing flow - Must be called BEFORE processing payment in your payment system + Display Google's alternative billing information dialog. Step 2 of the alternative billing flow. + Must be called BEFORE processing payment in your payment system. - Returns true if user accepted, false if user canceled - Throws OpenIapError.NotPrepared if billing client not ready + Returns true if user accepted, false if user canceled. + Throws OpenIapError.NotPrepared if billing client not ready. + See: https://www.openiap.dev/docs/apis/android/show-alternative-billing-dialog-android """ # Future showAlternativeBillingDialogAndroid: Boolean! """ - Create external transaction token for Google Play reporting - Step 3 of alternative billing flow - Must be called AFTER successful payment in your payment system - Token must be reported to Google Play backend within 24 hours + Create a reporting token for an alternative billing flow. Step 3 of the alternative billing flow. + Must be called AFTER successful payment in your payment system. + Token must be reported to Google Play backend within 24 hours. - Returns token string, or null if creation failed - Throws OpenIapError.NotPrepared if billing client not ready + Returns token string, or null if creation failed. + Throws OpenIapError.NotPrepared if billing client not ready. + See: https://www.openiap.dev/docs/apis/android/create-alternative-billing-token-android """ # Future createAlternativeBillingTokenAndroid: String # Billing Programs API (Google Play Billing Library 8.2.0+) """ - Check if a billing program is available for the current user - Replaces the deprecated isExternalOfferAvailableAsync API + Check whether a billing program (e.g., External Payments) is available for the current user. + Replaces the deprecated isExternalOfferAvailableAsync API. - Available in Google Play Billing Library 8.2.0+ - Returns availability result with isAvailable flag - Throws OpenIapError.NotPrepared if billing client not ready + Available in Google Play Billing Library 8.2.0+. + Returns availability result with isAvailable flag. + Throws OpenIapError.NotPrepared if billing client not ready. + See: https://www.openiap.dev/docs/apis/android/is-billing-program-available-android """ # Future isBillingProgramAvailableAndroid(program: BillingProgramAndroid!): BillingProgramAvailabilityResultAndroid! """ - Create reporting details for a billing program - Replaces the deprecated createExternalOfferReportingDetailsAsync API + Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). + Replaces the deprecated createExternalOfferReportingDetailsAsync API. - Available in Google Play Billing Library 8.2.0+ - Returns external transaction token needed for reporting external transactions - Throws OpenIapError.NotPrepared if billing client not ready + Returns external transaction token needed for reporting external transactions. + Throws OpenIapError.NotPrepared if billing client not ready. + See: https://www.openiap.dev/docs/apis/android/create-billing-program-reporting-details-android """ # Future createBillingProgramReportingDetailsAndroid(program: BillingProgramAndroid!): BillingProgramReportingDetailsAndroid! """ - Launch external link flow for external billing programs - Replaces the deprecated showExternalOfferInformationDialog API + Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). + Replaces the deprecated showExternalOfferInformationDialog API. - Available in Google Play Billing Library 8.2.0+ - Shows Play Store dialog and optionally launches external URL - Throws OpenIapError.NotPrepared if billing client not ready + Shows Play Store dialog and optionally launches external URL. + Throws OpenIapError.NotPrepared if billing client not ready. + See: https://www.openiap.dev/docs/apis/android/launch-external-link-android """ # Future launchExternalLinkAndroid(params: LaunchExternalLinkParamsAndroid!): Boolean! diff --git a/packages/gql/src/api-ios.graphql b/packages/gql/src/api-ios.graphql index ba7802c0..a9494f2e 100644 --- a/packages/gql/src/api-ios.graphql +++ b/packages/gql/src/api-ios.graphql @@ -2,32 +2,37 @@ extend type Query { """ - Get the current App Store storefront country code + Deprecated. Get the current App Store storefront country code — use cross-platform getStorefront instead. + See: https://www.openiap.dev/docs/apis/ios/get-storefront-ios """ # Future getStorefrontIOS: String! @deprecated(reason: "Use getStorefront") """ - Get the currently promoted product (iOS 11+) + Read the App Store-promoted product, if any (iOS 11+). + See: https://www.openiap.dev/docs/apis/ios/get-promoted-product-ios """ # Future getPromotedProductIOS: ProductIOS """ - Check if external purchase notice sheet can be presented (iOS 17.4+) - Uses ExternalPurchase.canPresent + Check eligibility for the external purchase notice sheet (iOS 17.4+). + Uses ExternalPurchase.canPresent. + See: https://www.openiap.dev/docs/apis/ios/can-present-external-purchase-notice-ios """ # Future canPresentExternalPurchaseNoticeIOS: Boolean! """ - Check if app is eligible for ExternalPurchaseCustomLink API (iOS 18.1+). + Check eligibility for the custom-link variant of external purchase (iOS 18.1+). Returns true if the app can use custom external purchase links. Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/iseligible + See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-external-purchase-custom-link-ios """ # Future isEligibleForExternalPurchaseCustomLinkIOS: Boolean! """ - Get external purchase token for reporting to Apple (iOS 18.1+). - Use this token with Apple's External Purchase Server API to report transactions. + Fetch a token for Apple's External Purchase Server reporting API (iOS 18.1+). + Use this token to report transactions made through ExternalPurchaseCustomLink. Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/token(for:) + See: https://www.openiap.dev/docs/apis/ios/get-external-purchase-custom-link-token-ios """ # Future getExternalPurchaseCustomLinkTokenIOS( @@ -37,60 +42,71 @@ extend type Query { tokenType: ExternalPurchaseCustomLinkTokenTypeIOS! ): ExternalPurchaseCustomLinkTokenResultIOS! """ - Retrieve all pending transactions in the StoreKit queue + List unfinished StoreKit transactions in the queue. + See: https://www.openiap.dev/docs/apis/ios/get-pending-transactions-ios """ # Future getPendingTransactionsIOS: [PurchaseIOS!]! """ - Check introductory offer eligibility for a subscription group + Check intro-offer eligibility for a subscription group. + See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-intro-offer-ios """ # Future isEligibleForIntroOfferIOS(groupID: String!): Boolean! """ - Get StoreKit 2 subscription status details (iOS 15+) + Get subscription status objects from StoreKit 2 (iOS 15+). + See: https://www.openiap.dev/docs/apis/ios/subscription-status-ios """ # Future subscriptionStatusIOS(sku: String!): [SubscriptionStatusIOS!]! """ - Get current StoreKit 2 entitlements (iOS 15+) + Get the user's current entitlement for a product, using StoreKit 2 (iOS 15+). + See: https://www.openiap.dev/docs/apis/ios/current-entitlement-ios """ # Future currentEntitlementIOS(sku: String!): PurchaseIOS """ - Get the latest transaction for a product using StoreKit 2 + Get the latest verified transaction for a product, using StoreKit 2. + See: https://www.openiap.dev/docs/apis/ios/latest-transaction-ios """ # Future latestTransactionIOS(sku: String!): PurchaseIOS """ - Verify a StoreKit 2 transaction signature + Check whether a transaction's JWS verification passed (StoreKit 2). + See: https://www.openiap.dev/docs/apis/ios/is-transaction-verified-ios """ # Future isTransactionVerifiedIOS(sku: String!): Boolean! """ - Get the transaction JWS (StoreKit 2) + Return the JWS string for a transaction (StoreKit 2). + See: https://www.openiap.dev/docs/apis/ios/get-transaction-jws-ios """ # Future getTransactionJwsIOS(sku: String!): String """ - Get base64-encoded receipt data for validation + Get base64-encoded receipt data (legacy validation). + See: https://www.openiap.dev/docs/apis/ios/get-receipt-data-ios """ # Future getReceiptDataIOS: String """ - Fetch the current app transaction (iOS 16+) + Fetch the app transaction (iOS 16+). + See: https://www.openiap.dev/docs/apis/ios/get-app-transaction-ios """ # Future getAppTransactionIOS: AppTransaction """ - Get the full StoreKit 2 transaction history as PurchaseIOS values. + List every StoreKit transaction (finished + unfinished) for the current user. Requires the SK2ConsumableTransactionHistory Info.plist key in the host app for finished consumables to be included (iOS 18+). Unlike getAvailablePurchases, always returns the iOS-specific PurchaseIOS shape. + See: https://www.openiap.dev/docs/apis/ios/get-all-transactions-ios """ # Future getAllTransactionsIOS: [PurchaseIOS!]! """ - Validate a receipt for a specific product + Deprecated. Legacy App Store receipt validation — use verifyPurchase instead. + See: https://www.openiap.dev/docs/apis/ios/validate-receipt-ios """ # Future validateReceiptIOS(options: VerifyPurchaseProps!): VerifyPurchaseResultIOS! @deprecated(reason: "Use verifyPurchase") @@ -98,56 +114,64 @@ extend type Query { extend type Mutation { """ - Clear pending transactions from the StoreKit payment queue + Clear pending transactions in the queue (sandbox helper). + See: https://www.openiap.dev/docs/apis/ios/clear-transaction-ios """ # Future clearTransactionIOS: Boolean! """ - Purchase the promoted product surfaced by the App Store. + Buy the currently promoted product. @deprecated Use promotedProductListenerIOS to receive the productId, then call requestPurchase with that SKU instead. In StoreKit 2, promoted products can be purchased directly via the standard purchase flow. + See: https://www.openiap.dev/docs/apis/ios/request-purchase-on-promoted-product-ios """ # Future requestPurchaseOnPromotedProductIOS: Boolean! @deprecated(reason: "Use promotedProductListenerIOS + requestPurchase instead") """ - Open subscription management UI and return changed purchases (iOS 15+) + Present the manage-subscriptions sheet and return changed purchases (iOS 15+). + See: https://www.openiap.dev/docs/apis/ios/show-manage-subscriptions-ios """ # Future showManageSubscriptionsIOS: [PurchaseIOS!]! """ - Initiate a refund request for a product (iOS 15+) + Present the refund request sheet (iOS 15+). See also Features → Refund. + See: https://www.openiap.dev/docs/apis/ios/begin-refund-request-ios """ # Future beginRefundRequestIOS(sku: String!): String """ - Force a StoreKit sync for transactions (iOS 15+) + Force sync transactions with the App Store (iOS 15+). + See: https://www.openiap.dev/docs/apis/ios/sync-ios """ # Future syncIOS: Boolean! """ - Present the App Store code redemption sheet + Show the App Store offer code redemption sheet. + See: https://www.openiap.dev/docs/apis/ios/present-code-redemption-sheet-ios """ # Future presentCodeRedemptionSheetIOS: Boolean! """ - Present external purchase notice sheet (iOS 17.4+). - Uses ExternalPurchase.presentNoticeSheet() which returns a token when user continues. + Present the external purchase notice sheet (iOS 17.4+). + Uses ExternalPurchase.presentNoticeSheet() which returns a token when the user continues. Reference: https://developer.apple.com/documentation/storekit/externalpurchase/presentnoticesheet() + See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-notice-sheet-ios """ # Future presentExternalPurchaseNoticeSheetIOS: ExternalPurchaseNoticeResultIOS! """ - Present external purchase custom link with StoreKit UI + Present an external purchase link, StoreKit External (iOS 16+). + See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-link-ios """ # Future presentExternalPurchaseLinkIOS(url: String!): ExternalPurchaseLinkResultIOS! """ - Show ExternalPurchaseCustomLink notice sheet (iOS 18.1+). - Displays the system disclosure notice sheet for custom external purchase links. + Present the disclosure sheet required before linking out via ExternalPurchaseCustomLink (iOS 18.1+). Call this after a deliberate customer interaction before linking out to external purchases. Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/shownotice(type:) + See: https://www.openiap.dev/docs/apis/ios/show-external-purchase-custom-link-notice-ios """ # Future showExternalPurchaseCustomLinkNoticeIOS( diff --git a/packages/gql/src/api.graphql b/packages/gql/src/api.graphql index a4e56824..8c7e357b 100644 --- a/packages/gql/src/api.graphql +++ b/packages/gql/src/api.graphql @@ -3,27 +3,32 @@ # Product management extend type Query { """ - Retrieve products or subscriptions from the store + Fetch products or subscriptions from the store. + See: https://www.openiap.dev/docs/apis/fetch-products """ # Future fetchProducts(params: ProductRequest!): FetchProductsResult! """ - Get all available purchases for the current user + List active purchases for the current user. + See: https://www.openiap.dev/docs/apis/get-available-purchases """ # Future getAvailablePurchases(options: PurchaseOptions): [Purchase!]! """ - Get active subscriptions (filters by subscriptionIds when provided) + Get details of all currently active subscriptions (filters by subscriptionIds when provided). + See: https://www.openiap.dev/docs/apis/get-active-subscriptions """ # Future getActiveSubscriptions(subscriptionIds: [String!]): [ActiveSubscription!]! """ - Check whether the user has active subscriptions + Check whether the user has any active subscription. + See: https://www.openiap.dev/docs/apis/has-active-subscriptions """ # Future hasActiveSubscriptions(subscriptionIds: [String!]): Boolean! """ - Get the current storefront country code + Return the user's storefront country code. + See: https://www.openiap.dev/docs/apis/get-storefront """ # Future getStorefront: String! @@ -32,22 +37,26 @@ extend type Query { # Request APIs (event driven) extend type Mutation { """ - Establish the platform billing connection + Initialize the store connection. Call before any IAP API. + See: https://www.openiap.dev/docs/apis/init-connection """ # Future initConnection(config: InitConnectionConfig): Boolean! """ - Close the platform billing connection + Close the store connection and release resources. + See: https://www.openiap.dev/docs/apis/end-connection """ # Future endConnection: Boolean! """ - Initiate a purchase flow; rely on events for final state + Initiate a purchase or subscription flow; rely on events for final state. + See: https://www.openiap.dev/docs/apis/request-purchase """ # Future requestPurchase(params: RequestPurchaseProps!): RequestPurchaseResult """ - Finish a transaction after validating receipts + Complete a transaction after server-side verification. Required on Android within 3 days. + See: https://www.openiap.dev/docs/apis/finish-transaction """ # Future finishTransaction( @@ -55,27 +64,38 @@ extend type Mutation { isConsumable: Boolean ): VoidResult! """ - Restore completed purchases across platforms + Restore non-consumable and active subscription purchases. + See: https://www.openiap.dev/docs/apis/restore-purchases """ # Future restorePurchases: VoidResult! """ - Open the native subscription management surface + Open the platform's subscription management UI. + See: https://www.openiap.dev/docs/apis/deep-link-to-subscriptions """ # Future deepLinkToSubscriptions(options: DeepLinkOptions): VoidResult! """ - Validate purchase receipts with the configured providers + Deprecated. Validate purchase receipts with the configured providers — use verifyPurchase instead. + See: https://www.openiap.dev/docs/features/validation#verify-purchase """ # Future validateReceipt(options: VerifyPurchaseProps!): VerifyPurchaseResult! @deprecated(reason: "Use verifyPurchase") """ - Verify purchases with the configured providers + Verify a purchase against your own backend. Returns a platform-specific + variant of VerifyPurchaseResult — VerifyPurchaseResultIOS exposes isValid + + receipt/JWS metadata, VerifyPurchaseResultAndroid carries Play Store + receipt fields (no isValid), and VerifyPurchaseResultHorizon uses success. + Inspect the concrete variant before reading fields. + See: https://www.openiap.dev/docs/features/validation#verify-purchase """ # Future verifyPurchase(options: VerifyPurchaseProps!): VerifyPurchaseResult! """ - Verify purchases with a specific provider (e.g., IAPKit) + Verify via a managed provider without standing up your own server. The + PurchaseVerificationProvider enum currently exposes only IAPKit; platform + availability may differ by implementation. + See: https://www.openiap.dev/docs/features/validation#verify-purchase-with-provider """ # Future verifyPurchaseWithProvider( diff --git a/packages/gql/src/generated/Types.kt b/packages/gql/src/generated/Types.kt index d5151235..75ffa755 100644 --- a/packages/gql/src/generated/Types.kt +++ b/packages/gql/src/generated/Types.kt @@ -4833,146 +4833,172 @@ public sealed interface VerifyPurchaseResult { */ public interface MutationResolver { /** - * Acknowledge a non-consumable purchase or subscription + * Acknowledge a non-consumable purchase. Required within 3 days or Google auto-refunds. + * See: https://www.openiap.dev/docs/apis/android/acknowledge-purchase-android */ suspend fun acknowledgePurchaseAndroid(purchaseToken: String): Boolean /** - * Initiate a refund request for a product (iOS 15+) + * Present the refund request sheet (iOS 15+). See also Features → Refund. + * See: https://www.openiap.dev/docs/apis/ios/begin-refund-request-ios */ suspend fun beginRefundRequestIOS(sku: String): String? /** - * Check if alternative billing is available for this user/device - * Step 1 of alternative billing flow + * Check whether alternative billing is available for the user. Step 1 of the alternative billing flow. * - * Returns true if available, false otherwise - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns true if available, false otherwise. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/check-alternative-billing-availability-android */ suspend fun checkAlternativeBillingAvailabilityAndroid(): Boolean /** - * Clear pending transactions from the StoreKit payment queue + * Clear pending transactions in the queue (sandbox helper). + * See: https://www.openiap.dev/docs/apis/ios/clear-transaction-ios */ suspend fun clearTransactionIOS(): Boolean /** - * Consume a purchase token so it can be repurchased + * Consume a consumable purchase so it can be re-bought. + * See: https://www.openiap.dev/docs/apis/android/consume-purchase-android */ suspend fun consumePurchaseAndroid(purchaseToken: String): Boolean /** - * Create external transaction token for Google Play reporting - * Step 3 of alternative billing flow - * Must be called AFTER successful payment in your payment system - * Token must be reported to Google Play backend within 24 hours + * Create a reporting token for an alternative billing flow. Step 3 of the alternative billing flow. + * Must be called AFTER successful payment in your payment system. + * Token must be reported to Google Play backend within 24 hours. * - * Returns token string, or null if creation failed - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns token string, or null if creation failed. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/create-alternative-billing-token-android */ suspend fun createAlternativeBillingTokenAndroid(): String? /** - * Create reporting details for a billing program - * Replaces the deprecated createExternalOfferReportingDetailsAsync API + * Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). + * Replaces the deprecated createExternalOfferReportingDetailsAsync API. * - * Available in Google Play Billing Library 8.2.0+ - * Returns external transaction token needed for reporting external transactions - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns external transaction token needed for reporting external transactions. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/create-billing-program-reporting-details-android */ suspend fun createBillingProgramReportingDetailsAndroid(program: BillingProgramAndroid): BillingProgramReportingDetailsAndroid /** - * Open the native subscription management surface + * Open the platform's subscription management UI. + * See: https://www.openiap.dev/docs/apis/deep-link-to-subscriptions */ suspend fun deepLinkToSubscriptions(options: DeepLinkOptions? = null): Unit /** - * Close the platform billing connection + * Close the store connection and release resources. + * See: https://www.openiap.dev/docs/apis/end-connection */ suspend fun endConnection(): Boolean /** - * Finish a transaction after validating receipts + * Complete a transaction after server-side verification. Required on Android within 3 days. + * See: https://www.openiap.dev/docs/apis/finish-transaction */ suspend fun finishTransaction(purchase: PurchaseInput, isConsumable: Boolean? = null): Unit /** - * Establish the platform billing connection + * Initialize the store connection. Call before any IAP API. + * See: https://www.openiap.dev/docs/apis/init-connection */ suspend fun initConnection(config: InitConnectionConfig? = null): Boolean /** - * Check if a billing program is available for the current user - * Replaces the deprecated isExternalOfferAvailableAsync API + * Check whether a billing program (e.g., External Payments) is available for the current user. + * Replaces the deprecated isExternalOfferAvailableAsync API. * - * Available in Google Play Billing Library 8.2.0+ - * Returns availability result with isAvailable flag - * Throws OpenIapError.NotPrepared if billing client not ready + * Available in Google Play Billing Library 8.2.0+. + * Returns availability result with isAvailable flag. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/is-billing-program-available-android */ suspend fun isBillingProgramAvailableAndroid(program: BillingProgramAndroid): BillingProgramAvailabilityResultAndroid /** - * Launch external link flow for external billing programs - * Replaces the deprecated showExternalOfferInformationDialog API + * Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). + * Replaces the deprecated showExternalOfferInformationDialog API. * - * Available in Google Play Billing Library 8.2.0+ - * Shows Play Store dialog and optionally launches external URL - * Throws OpenIapError.NotPrepared if billing client not ready + * Shows Play Store dialog and optionally launches external URL. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/launch-external-link-android */ suspend fun launchExternalLinkAndroid(params: LaunchExternalLinkParamsAndroid): Boolean /** - * Present the App Store code redemption sheet + * Show the App Store offer code redemption sheet. + * See: https://www.openiap.dev/docs/apis/ios/present-code-redemption-sheet-ios */ suspend fun presentCodeRedemptionSheetIOS(): Boolean /** - * Present external purchase custom link with StoreKit UI + * Present an external purchase link, StoreKit External (iOS 16+). + * See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-link-ios */ suspend fun presentExternalPurchaseLinkIOS(url: String): ExternalPurchaseLinkResultIOS /** - * Present external purchase notice sheet (iOS 17.4+). - * Uses ExternalPurchase.presentNoticeSheet() which returns a token when user continues. + * Present the external purchase notice sheet (iOS 17.4+). + * Uses ExternalPurchase.presentNoticeSheet() which returns a token when the user continues. * Reference: https://developer.apple.com/documentation/storekit/externalpurchase/presentnoticesheet() + * See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-notice-sheet-ios */ suspend fun presentExternalPurchaseNoticeSheetIOS(): ExternalPurchaseNoticeResultIOS /** - * Initiate a purchase flow; rely on events for final state + * Initiate a purchase or subscription flow; rely on events for final state. + * See: https://www.openiap.dev/docs/apis/request-purchase */ suspend fun requestPurchase(params: RequestPurchaseProps): RequestPurchaseResult? /** - * Purchase the promoted product surfaced by the App Store. + * Buy the currently promoted product. * * @deprecated Use promotedProductListenerIOS to receive the productId, * then call requestPurchase with that SKU instead. In StoreKit 2, * promoted products can be purchased directly via the standard purchase flow. + * See: https://www.openiap.dev/docs/apis/ios/request-purchase-on-promoted-product-ios */ suspend fun requestPurchaseOnPromotedProductIOS(): Boolean /** - * Restore completed purchases across platforms + * Restore non-consumable and active subscription purchases. + * See: https://www.openiap.dev/docs/apis/restore-purchases */ suspend fun restorePurchases(): Unit /** - * Show alternative billing information dialog to user - * Step 2 of alternative billing flow - * Must be called BEFORE processing payment in your payment system + * Display Google's alternative billing information dialog. Step 2 of the alternative billing flow. + * Must be called BEFORE processing payment in your payment system. * - * Returns true if user accepted, false if user canceled - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns true if user accepted, false if user canceled. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/show-alternative-billing-dialog-android */ suspend fun showAlternativeBillingDialogAndroid(): Boolean /** - * Show ExternalPurchaseCustomLink notice sheet (iOS 18.1+). - * Displays the system disclosure notice sheet for custom external purchase links. + * Present the disclosure sheet required before linking out via ExternalPurchaseCustomLink (iOS 18.1+). * Call this after a deliberate customer interaction before linking out to external purchases. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/shownotice(type:) + * See: https://www.openiap.dev/docs/apis/ios/show-external-purchase-custom-link-notice-ios */ suspend fun showExternalPurchaseCustomLinkNoticeIOS(noticeType: ExternalPurchaseCustomLinkNoticeTypeIOS): ExternalPurchaseCustomLinkNoticeResultIOS /** - * Open subscription management UI and return changed purchases (iOS 15+) + * Present the manage-subscriptions sheet and return changed purchases (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/show-manage-subscriptions-ios */ suspend fun showManageSubscriptionsIOS(): List /** - * Force a StoreKit sync for transactions (iOS 15+) + * Force sync transactions with the App Store (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/sync-ios */ suspend fun syncIOS(): Boolean /** - * Validate purchase receipts with the configured providers + * Deprecated. Validate purchase receipts with the configured providers — use verifyPurchase instead. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase */ suspend fun validateReceipt(options: VerifyPurchaseProps): VerifyPurchaseResult /** - * Verify purchases with the configured providers + * Verify a purchase against your own backend. Returns a platform-specific + * variant of VerifyPurchaseResult — VerifyPurchaseResultIOS exposes isValid + * + receipt/JWS metadata, VerifyPurchaseResultAndroid carries Play Store + * receipt fields (no isValid), and VerifyPurchaseResultHorizon uses success. + * Inspect the concrete variant before reading fields. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase */ suspend fun verifyPurchase(options: VerifyPurchaseProps): VerifyPurchaseResult /** - * Verify purchases with a specific provider (e.g., IAPKit) + * Verify via a managed provider without standing up your own server. The + * PurchaseVerificationProvider enum currently exposes only IAPKit; platform + * availability may differ by implementation. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase-with-provider */ suspend fun verifyPurchaseWithProvider(options: VerifyPurchaseWithProviderProps): VerifyPurchaseWithProviderResult } @@ -4982,95 +5008,116 @@ public interface MutationResolver { */ public interface QueryResolver { /** - * Check if external purchase notice sheet can be presented (iOS 17.4+) - * Uses ExternalPurchase.canPresent + * Check eligibility for the external purchase notice sheet (iOS 17.4+). + * Uses ExternalPurchase.canPresent. + * See: https://www.openiap.dev/docs/apis/ios/can-present-external-purchase-notice-ios */ suspend fun canPresentExternalPurchaseNoticeIOS(): Boolean /** - * Get current StoreKit 2 entitlements (iOS 15+) + * Get the user's current entitlement for a product, using StoreKit 2 (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/current-entitlement-ios */ suspend fun currentEntitlementIOS(sku: String): PurchaseIOS? /** - * Retrieve products or subscriptions from the store + * Fetch products or subscriptions from the store. + * See: https://www.openiap.dev/docs/apis/fetch-products */ suspend fun fetchProducts(params: ProductRequest): FetchProductsResult /** - * Get active subscriptions (filters by subscriptionIds when provided) + * Get details of all currently active subscriptions (filters by subscriptionIds when provided). + * See: https://www.openiap.dev/docs/apis/get-active-subscriptions */ suspend fun getActiveSubscriptions(subscriptionIds: List? = null): List /** - * Get the full StoreKit 2 transaction history as PurchaseIOS values. + * List every StoreKit transaction (finished + unfinished) for the current user. * Requires the SK2ConsumableTransactionHistory Info.plist key in the host app * for finished consumables to be included (iOS 18+). * Unlike getAvailablePurchases, always returns the iOS-specific PurchaseIOS shape. + * See: https://www.openiap.dev/docs/apis/ios/get-all-transactions-ios */ suspend fun getAllTransactionsIOS(): List /** - * Fetch the current app transaction (iOS 16+) + * Fetch the app transaction (iOS 16+). + * See: https://www.openiap.dev/docs/apis/ios/get-app-transaction-ios */ suspend fun getAppTransactionIOS(): AppTransaction? /** - * Get all available purchases for the current user + * List active purchases for the current user. + * See: https://www.openiap.dev/docs/apis/get-available-purchases */ suspend fun getAvailablePurchases(options: PurchaseOptions? = null): List /** - * Get external purchase token for reporting to Apple (iOS 18.1+). - * Use this token with Apple's External Purchase Server API to report transactions. + * Fetch a token for Apple's External Purchase Server reporting API (iOS 18.1+). + * Use this token to report transactions made through ExternalPurchaseCustomLink. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/token(for:) + * See: https://www.openiap.dev/docs/apis/ios/get-external-purchase-custom-link-token-ios */ suspend fun getExternalPurchaseCustomLinkTokenIOS(tokenType: ExternalPurchaseCustomLinkTokenTypeIOS): ExternalPurchaseCustomLinkTokenResultIOS /** - * Retrieve all pending transactions in the StoreKit queue + * List unfinished StoreKit transactions in the queue. + * See: https://www.openiap.dev/docs/apis/ios/get-pending-transactions-ios */ suspend fun getPendingTransactionsIOS(): List /** - * Get the currently promoted product (iOS 11+) + * Read the App Store-promoted product, if any (iOS 11+). + * See: https://www.openiap.dev/docs/apis/ios/get-promoted-product-ios */ suspend fun getPromotedProductIOS(): ProductIOS? /** - * Get base64-encoded receipt data for validation + * Get base64-encoded receipt data (legacy validation). + * See: https://www.openiap.dev/docs/apis/ios/get-receipt-data-ios */ suspend fun getReceiptDataIOS(): String? /** - * Get the current storefront country code + * Return the user's storefront country code. + * See: https://www.openiap.dev/docs/apis/get-storefront */ suspend fun getStorefront(): String /** - * Get the current App Store storefront country code + * Deprecated. Get the current App Store storefront country code — use cross-platform getStorefront instead. + * See: https://www.openiap.dev/docs/apis/ios/get-storefront-ios */ suspend fun getStorefrontIOS(): String /** - * Get the transaction JWS (StoreKit 2) + * Return the JWS string for a transaction (StoreKit 2). + * See: https://www.openiap.dev/docs/apis/ios/get-transaction-jws-ios */ suspend fun getTransactionJwsIOS(sku: String): String? /** - * Check whether the user has active subscriptions + * Check whether the user has any active subscription. + * See: https://www.openiap.dev/docs/apis/has-active-subscriptions */ suspend fun hasActiveSubscriptions(subscriptionIds: List? = null): Boolean /** - * Check if app is eligible for ExternalPurchaseCustomLink API (iOS 18.1+). + * Check eligibility for the custom-link variant of external purchase (iOS 18.1+). * Returns true if the app can use custom external purchase links. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/iseligible + * See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-external-purchase-custom-link-ios */ suspend fun isEligibleForExternalPurchaseCustomLinkIOS(): Boolean /** - * Check introductory offer eligibility for a subscription group + * Check intro-offer eligibility for a subscription group. + * See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-intro-offer-ios */ suspend fun isEligibleForIntroOfferIOS(groupID: String): Boolean /** - * Verify a StoreKit 2 transaction signature + * Check whether a transaction's JWS verification passed (StoreKit 2). + * See: https://www.openiap.dev/docs/apis/ios/is-transaction-verified-ios */ suspend fun isTransactionVerifiedIOS(sku: String): Boolean /** - * Get the latest transaction for a product using StoreKit 2 + * Get the latest verified transaction for a product, using StoreKit 2. + * See: https://www.openiap.dev/docs/apis/ios/latest-transaction-ios */ suspend fun latestTransactionIOS(sku: String): PurchaseIOS? /** - * Get StoreKit 2 subscription status details (iOS 15+) + * Get subscription status objects from StoreKit 2 (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/subscription-status-ios */ suspend fun subscriptionStatusIOS(sku: String): List /** - * Validate a receipt for a specific product + * Deprecated. Legacy App Store receipt validation — use verifyPurchase instead. + * See: https://www.openiap.dev/docs/apis/ios/validate-receipt-ios */ suspend fun validateReceiptIOS(options: VerifyPurchaseProps): VerifyPurchaseResultIOS } diff --git a/packages/gql/src/generated/Types.swift b/packages/gql/src/generated/Types.swift index a3547e12..efacb85c 100644 --- a/packages/gql/src/generated/Types.swift +++ b/packages/gql/src/generated/Types.swift @@ -2334,150 +2334,197 @@ public enum VerifyPurchaseResult: Codable { /// GraphQL root mutation operations. public protocol MutationResolver { - /// Acknowledge a non-consumable purchase or subscription + /// Acknowledge a non-consumable purchase. Required within 3 days or Google auto-refunds. + /// See: https://www.openiap.dev/docs/apis/android/acknowledge-purchase-android func acknowledgePurchaseAndroid(_ purchaseToken: String) async throws -> Bool - /// Initiate a refund request for a product (iOS 15+) + /// Present the refund request sheet (iOS 15+). See also Features → Refund. + /// See: https://www.openiap.dev/docs/apis/ios/begin-refund-request-ios func beginRefundRequestIOS(_ sku: String) async throws -> String? - /// Check if alternative billing is available for this user/device - /// Step 1 of alternative billing flow + /// Check whether alternative billing is available for the user. Step 1 of the alternative billing flow. /// - /// Returns true if available, false otherwise - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Returns true if available, false otherwise. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/check-alternative-billing-availability-android func checkAlternativeBillingAvailabilityAndroid() async throws -> Bool - /// Clear pending transactions from the StoreKit payment queue + /// Clear pending transactions in the queue (sandbox helper). + /// See: https://www.openiap.dev/docs/apis/ios/clear-transaction-ios func clearTransactionIOS() async throws -> Bool - /// Consume a purchase token so it can be repurchased + /// Consume a consumable purchase so it can be re-bought. + /// See: https://www.openiap.dev/docs/apis/android/consume-purchase-android func consumePurchaseAndroid(_ purchaseToken: String) async throws -> Bool - /// Create external transaction token for Google Play reporting - /// Step 3 of alternative billing flow - /// Must be called AFTER successful payment in your payment system - /// Token must be reported to Google Play backend within 24 hours + /// Create a reporting token for an alternative billing flow. Step 3 of the alternative billing flow. + /// Must be called AFTER successful payment in your payment system. + /// Token must be reported to Google Play backend within 24 hours. /// - /// Returns token string, or null if creation failed - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Returns token string, or null if creation failed. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/create-alternative-billing-token-android func createAlternativeBillingTokenAndroid() async throws -> String? - /// Create reporting details for a billing program - /// Replaces the deprecated createExternalOfferReportingDetailsAsync API + /// Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). + /// Replaces the deprecated createExternalOfferReportingDetailsAsync API. /// - /// Available in Google Play Billing Library 8.2.0+ - /// Returns external transaction token needed for reporting external transactions - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Returns external transaction token needed for reporting external transactions. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/create-billing-program-reporting-details-android func createBillingProgramReportingDetailsAndroid(_ program: BillingProgramAndroid) async throws -> BillingProgramReportingDetailsAndroid - /// Open the native subscription management surface + /// Open the platform's subscription management UI. + /// See: https://www.openiap.dev/docs/apis/deep-link-to-subscriptions func deepLinkToSubscriptions(_ options: DeepLinkOptions?) async throws -> Void - /// Close the platform billing connection + /// Close the store connection and release resources. + /// See: https://www.openiap.dev/docs/apis/end-connection func endConnection() async throws -> Bool - /// Finish a transaction after validating receipts + /// Complete a transaction after server-side verification. Required on Android within 3 days. + /// See: https://www.openiap.dev/docs/apis/finish-transaction func finishTransaction(purchase: PurchaseInput, isConsumable: Bool?) async throws -> Void - /// Establish the platform billing connection + /// Initialize the store connection. Call before any IAP API. + /// See: https://www.openiap.dev/docs/apis/init-connection func initConnection(_ config: InitConnectionConfig?) async throws -> Bool - /// Check if a billing program is available for the current user - /// Replaces the deprecated isExternalOfferAvailableAsync API + /// Check whether a billing program (e.g., External Payments) is available for the current user. + /// Replaces the deprecated isExternalOfferAvailableAsync API. /// - /// Available in Google Play Billing Library 8.2.0+ - /// Returns availability result with isAvailable flag - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Available in Google Play Billing Library 8.2.0+. + /// Returns availability result with isAvailable flag. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/is-billing-program-available-android func isBillingProgramAvailableAndroid(_ program: BillingProgramAndroid) async throws -> BillingProgramAvailabilityResultAndroid - /// Launch external link flow for external billing programs - /// Replaces the deprecated showExternalOfferInformationDialog API + /// Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). + /// Replaces the deprecated showExternalOfferInformationDialog API. /// - /// Available in Google Play Billing Library 8.2.0+ - /// Shows Play Store dialog and optionally launches external URL - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Shows Play Store dialog and optionally launches external URL. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/launch-external-link-android func launchExternalLinkAndroid(_ params: LaunchExternalLinkParamsAndroid) async throws -> Bool - /// Present the App Store code redemption sheet + /// Show the App Store offer code redemption sheet. + /// See: https://www.openiap.dev/docs/apis/ios/present-code-redemption-sheet-ios func presentCodeRedemptionSheetIOS() async throws -> Bool - /// Present external purchase custom link with StoreKit UI + /// Present an external purchase link, StoreKit External (iOS 16+). + /// See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-link-ios func presentExternalPurchaseLinkIOS(_ url: String) async throws -> ExternalPurchaseLinkResultIOS - /// Present external purchase notice sheet (iOS 17.4+). - /// Uses ExternalPurchase.presentNoticeSheet() which returns a token when user continues. + /// Present the external purchase notice sheet (iOS 17.4+). + /// Uses ExternalPurchase.presentNoticeSheet() which returns a token when the user continues. /// Reference: https://developer.apple.com/documentation/storekit/externalpurchase/presentnoticesheet() + /// See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-notice-sheet-ios func presentExternalPurchaseNoticeSheetIOS() async throws -> ExternalPurchaseNoticeResultIOS - /// Initiate a purchase flow; rely on events for final state + /// Initiate a purchase or subscription flow; rely on events for final state. + /// See: https://www.openiap.dev/docs/apis/request-purchase func requestPurchase(_ params: RequestPurchaseProps) async throws -> RequestPurchaseResult? - /// Purchase the promoted product surfaced by the App Store. + /// Buy the currently promoted product. /// /// @deprecated Use promotedProductListenerIOS to receive the productId, /// then call requestPurchase with that SKU instead. In StoreKit 2, /// promoted products can be purchased directly via the standard purchase flow. + /// See: https://www.openiap.dev/docs/apis/ios/request-purchase-on-promoted-product-ios func requestPurchaseOnPromotedProductIOS() async throws -> Bool - /// Restore completed purchases across platforms + /// Restore non-consumable and active subscription purchases. + /// See: https://www.openiap.dev/docs/apis/restore-purchases func restorePurchases() async throws -> Void - /// Show alternative billing information dialog to user - /// Step 2 of alternative billing flow - /// Must be called BEFORE processing payment in your payment system + /// Display Google's alternative billing information dialog. Step 2 of the alternative billing flow. + /// Must be called BEFORE processing payment in your payment system. /// - /// Returns true if user accepted, false if user canceled - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Returns true if user accepted, false if user canceled. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/show-alternative-billing-dialog-android func showAlternativeBillingDialogAndroid() async throws -> Bool - /// Show ExternalPurchaseCustomLink notice sheet (iOS 18.1+). - /// Displays the system disclosure notice sheet for custom external purchase links. + /// Present the disclosure sheet required before linking out via ExternalPurchaseCustomLink (iOS 18.1+). /// Call this after a deliberate customer interaction before linking out to external purchases. /// Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/shownotice(type:) + /// See: https://www.openiap.dev/docs/apis/ios/show-external-purchase-custom-link-notice-ios func showExternalPurchaseCustomLinkNoticeIOS(_ noticeType: ExternalPurchaseCustomLinkNoticeTypeIOS) async throws -> ExternalPurchaseCustomLinkNoticeResultIOS - /// Open subscription management UI and return changed purchases (iOS 15+) + /// Present the manage-subscriptions sheet and return changed purchases (iOS 15+). + /// See: https://www.openiap.dev/docs/apis/ios/show-manage-subscriptions-ios func showManageSubscriptionsIOS() async throws -> [PurchaseIOS] - /// Force a StoreKit sync for transactions (iOS 15+) + /// Force sync transactions with the App Store (iOS 15+). + /// See: https://www.openiap.dev/docs/apis/ios/sync-ios func syncIOS() async throws -> Bool - /// Validate purchase receipts with the configured providers + /// Deprecated. Validate purchase receipts with the configured providers — use verifyPurchase instead. + /// See: https://www.openiap.dev/docs/features/validation#verify-purchase func validateReceipt(_ options: VerifyPurchaseProps) async throws -> VerifyPurchaseResult - /// Verify purchases with the configured providers + /// Verify a purchase against your own backend. Returns a platform-specific + /// variant of VerifyPurchaseResult — VerifyPurchaseResultIOS exposes isValid + /// + receipt/JWS metadata, VerifyPurchaseResultAndroid carries Play Store + /// receipt fields (no isValid), and VerifyPurchaseResultHorizon uses success. + /// Inspect the concrete variant before reading fields. + /// See: https://www.openiap.dev/docs/features/validation#verify-purchase func verifyPurchase(_ options: VerifyPurchaseProps) async throws -> VerifyPurchaseResult - /// Verify purchases with a specific provider (e.g., IAPKit) + /// Verify via a managed provider without standing up your own server. The + /// PurchaseVerificationProvider enum currently exposes only IAPKit; platform + /// availability may differ by implementation. + /// See: https://www.openiap.dev/docs/features/validation#verify-purchase-with-provider func verifyPurchaseWithProvider(_ options: VerifyPurchaseWithProviderProps) async throws -> VerifyPurchaseWithProviderResult } /// GraphQL root query operations. public protocol QueryResolver { - /// Check if external purchase notice sheet can be presented (iOS 17.4+) - /// Uses ExternalPurchase.canPresent + /// Check eligibility for the external purchase notice sheet (iOS 17.4+). + /// Uses ExternalPurchase.canPresent. + /// See: https://www.openiap.dev/docs/apis/ios/can-present-external-purchase-notice-ios func canPresentExternalPurchaseNoticeIOS() async throws -> Bool - /// Get current StoreKit 2 entitlements (iOS 15+) + /// Get the user's current entitlement for a product, using StoreKit 2 (iOS 15+). + /// See: https://www.openiap.dev/docs/apis/ios/current-entitlement-ios func currentEntitlementIOS(_ sku: String) async throws -> PurchaseIOS? - /// Retrieve products or subscriptions from the store + /// Fetch products or subscriptions from the store. + /// See: https://www.openiap.dev/docs/apis/fetch-products func fetchProducts(_ params: ProductRequest) async throws -> FetchProductsResult - /// Get active subscriptions (filters by subscriptionIds when provided) + /// Get details of all currently active subscriptions (filters by subscriptionIds when provided). + /// See: https://www.openiap.dev/docs/apis/get-active-subscriptions func getActiveSubscriptions(_ subscriptionIds: [String]?) async throws -> [ActiveSubscription] - /// Get the full StoreKit 2 transaction history as PurchaseIOS values. + /// List every StoreKit transaction (finished + unfinished) for the current user. /// Requires the SK2ConsumableTransactionHistory Info.plist key in the host app /// for finished consumables to be included (iOS 18+). /// Unlike getAvailablePurchases, always returns the iOS-specific PurchaseIOS shape. + /// See: https://www.openiap.dev/docs/apis/ios/get-all-transactions-ios func getAllTransactionsIOS() async throws -> [PurchaseIOS] - /// Fetch the current app transaction (iOS 16+) + /// Fetch the app transaction (iOS 16+). + /// See: https://www.openiap.dev/docs/apis/ios/get-app-transaction-ios func getAppTransactionIOS() async throws -> AppTransaction? - /// Get all available purchases for the current user + /// List active purchases for the current user. + /// See: https://www.openiap.dev/docs/apis/get-available-purchases func getAvailablePurchases(_ options: PurchaseOptions?) async throws -> [Purchase] - /// Get external purchase token for reporting to Apple (iOS 18.1+). - /// Use this token with Apple's External Purchase Server API to report transactions. + /// Fetch a token for Apple's External Purchase Server reporting API (iOS 18.1+). + /// Use this token to report transactions made through ExternalPurchaseCustomLink. /// Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/token(for:) + /// See: https://www.openiap.dev/docs/apis/ios/get-external-purchase-custom-link-token-ios func getExternalPurchaseCustomLinkTokenIOS(_ tokenType: ExternalPurchaseCustomLinkTokenTypeIOS) async throws -> ExternalPurchaseCustomLinkTokenResultIOS - /// Retrieve all pending transactions in the StoreKit queue + /// List unfinished StoreKit transactions in the queue. + /// See: https://www.openiap.dev/docs/apis/ios/get-pending-transactions-ios func getPendingTransactionsIOS() async throws -> [PurchaseIOS] - /// Get the currently promoted product (iOS 11+) + /// Read the App Store-promoted product, if any (iOS 11+). + /// See: https://www.openiap.dev/docs/apis/ios/get-promoted-product-ios func getPromotedProductIOS() async throws -> ProductIOS? - /// Get base64-encoded receipt data for validation + /// Get base64-encoded receipt data (legacy validation). + /// See: https://www.openiap.dev/docs/apis/ios/get-receipt-data-ios func getReceiptDataIOS() async throws -> String? - /// Get the current storefront country code + /// Return the user's storefront country code. + /// See: https://www.openiap.dev/docs/apis/get-storefront func getStorefront() async throws -> String - /// Get the current App Store storefront country code + /// Deprecated. Get the current App Store storefront country code — use cross-platform getStorefront instead. + /// See: https://www.openiap.dev/docs/apis/ios/get-storefront-ios func getStorefrontIOS() async throws -> String - /// Get the transaction JWS (StoreKit 2) + /// Return the JWS string for a transaction (StoreKit 2). + /// See: https://www.openiap.dev/docs/apis/ios/get-transaction-jws-ios func getTransactionJwsIOS(_ sku: String) async throws -> String? - /// Check whether the user has active subscriptions + /// Check whether the user has any active subscription. + /// See: https://www.openiap.dev/docs/apis/has-active-subscriptions func hasActiveSubscriptions(_ subscriptionIds: [String]?) async throws -> Bool - /// Check if app is eligible for ExternalPurchaseCustomLink API (iOS 18.1+). + /// Check eligibility for the custom-link variant of external purchase (iOS 18.1+). /// Returns true if the app can use custom external purchase links. /// Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/iseligible + /// See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-external-purchase-custom-link-ios func isEligibleForExternalPurchaseCustomLinkIOS() async throws -> Bool - /// Check introductory offer eligibility for a subscription group + /// Check intro-offer eligibility for a subscription group. + /// See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-intro-offer-ios func isEligibleForIntroOfferIOS(_ groupID: String) async throws -> Bool - /// Verify a StoreKit 2 transaction signature + /// Check whether a transaction's JWS verification passed (StoreKit 2). + /// See: https://www.openiap.dev/docs/apis/ios/is-transaction-verified-ios func isTransactionVerifiedIOS(_ sku: String) async throws -> Bool - /// Get the latest transaction for a product using StoreKit 2 + /// Get the latest verified transaction for a product, using StoreKit 2. + /// See: https://www.openiap.dev/docs/apis/ios/latest-transaction-ios func latestTransactionIOS(_ sku: String) async throws -> PurchaseIOS? - /// Get StoreKit 2 subscription status details (iOS 15+) + /// Get subscription status objects from StoreKit 2 (iOS 15+). + /// See: https://www.openiap.dev/docs/apis/ios/subscription-status-ios func subscriptionStatusIOS(_ sku: String) async throws -> [SubscriptionStatusIOS] - /// Validate a receipt for a specific product + /// Deprecated. Legacy App Store receipt validation — use verifyPurchase instead. + /// See: https://www.openiap.dev/docs/apis/ios/validate-receipt-ios func validateReceiptIOS(_ options: VerifyPurchaseProps) async throws -> VerifyPurchaseResultIOS } diff --git a/packages/gql/src/generated/types.dart b/packages/gql/src/generated/types.dart index ea75b5b3..1645922e 100644 --- a/packages/gql/src/generated/types.dart +++ b/packages/gql/src/generated/types.dart @@ -4846,118 +4846,144 @@ sealed class VerifyPurchaseResult { /// GraphQL root mutation operations. abstract class MutationResolver { - /// Acknowledge a non-consumable purchase or subscription + /// Acknowledge a non-consumable purchase. Required within 3 days or Google auto-refunds. + /// See: https://www.openiap.dev/docs/apis/android/acknowledge-purchase-android Future acknowledgePurchaseAndroid(String purchaseToken); - /// Initiate a refund request for a product (iOS 15+) + /// Present the refund request sheet (iOS 15+). See also Features → Refund. + /// See: https://www.openiap.dev/docs/apis/ios/begin-refund-request-ios Future beginRefundRequestIOS(String sku); - /// Check if alternative billing is available for this user/device - /// Step 1 of alternative billing flow + /// Check whether alternative billing is available for the user. Step 1 of the alternative billing flow. /// - /// Returns true if available, false otherwise - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Returns true if available, false otherwise. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/check-alternative-billing-availability-android Future checkAlternativeBillingAvailabilityAndroid(); - /// Clear pending transactions from the StoreKit payment queue + /// Clear pending transactions in the queue (sandbox helper). + /// See: https://www.openiap.dev/docs/apis/ios/clear-transaction-ios Future clearTransactionIOS(); - /// Consume a purchase token so it can be repurchased + /// Consume a consumable purchase so it can be re-bought. + /// See: https://www.openiap.dev/docs/apis/android/consume-purchase-android Future consumePurchaseAndroid(String purchaseToken); - /// Create external transaction token for Google Play reporting - /// Step 3 of alternative billing flow - /// Must be called AFTER successful payment in your payment system - /// Token must be reported to Google Play backend within 24 hours + /// Create a reporting token for an alternative billing flow. Step 3 of the alternative billing flow. + /// Must be called AFTER successful payment in your payment system. + /// Token must be reported to Google Play backend within 24 hours. /// - /// Returns token string, or null if creation failed - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Returns token string, or null if creation failed. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/create-alternative-billing-token-android Future createAlternativeBillingTokenAndroid(); - /// Create reporting details for a billing program - /// Replaces the deprecated createExternalOfferReportingDetailsAsync API + /// Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). + /// Replaces the deprecated createExternalOfferReportingDetailsAsync API. /// - /// Available in Google Play Billing Library 8.2.0+ - /// Returns external transaction token needed for reporting external transactions - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Returns external transaction token needed for reporting external transactions. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/create-billing-program-reporting-details-android Future createBillingProgramReportingDetailsAndroid(BillingProgramAndroid program); - /// Open the native subscription management surface + /// Open the platform's subscription management UI. + /// See: https://www.openiap.dev/docs/apis/deep-link-to-subscriptions Future deepLinkToSubscriptions({ String? packageNameAndroid, String? skuAndroid, }); - /// Close the platform billing connection + /// Close the store connection and release resources. + /// See: https://www.openiap.dev/docs/apis/end-connection Future endConnection(); - /// Finish a transaction after validating receipts + /// Complete a transaction after server-side verification. Required on Android within 3 days. + /// See: https://www.openiap.dev/docs/apis/finish-transaction Future finishTransaction({ required PurchaseInput purchase, bool? isConsumable, }); - /// Establish the platform billing connection + /// Initialize the store connection. Call before any IAP API. + /// See: https://www.openiap.dev/docs/apis/init-connection Future initConnection({ AlternativeBillingModeAndroid? alternativeBillingModeAndroid, BillingProgramAndroid? enableBillingProgramAndroid, }); - /// Check if a billing program is available for the current user - /// Replaces the deprecated isExternalOfferAvailableAsync API + /// Check whether a billing program (e.g., External Payments) is available for the current user. + /// Replaces the deprecated isExternalOfferAvailableAsync API. /// - /// Available in Google Play Billing Library 8.2.0+ - /// Returns availability result with isAvailable flag - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Available in Google Play Billing Library 8.2.0+. + /// Returns availability result with isAvailable flag. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/is-billing-program-available-android Future isBillingProgramAvailableAndroid(BillingProgramAndroid program); - /// Launch external link flow for external billing programs - /// Replaces the deprecated showExternalOfferInformationDialog API + /// Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). + /// Replaces the deprecated showExternalOfferInformationDialog API. /// - /// Available in Google Play Billing Library 8.2.0+ - /// Shows Play Store dialog and optionally launches external URL - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Shows Play Store dialog and optionally launches external URL. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/launch-external-link-android Future launchExternalLinkAndroid({ required BillingProgramAndroid billingProgram, required ExternalLinkLaunchModeAndroid launchMode, required ExternalLinkTypeAndroid linkType, required String linkUri, }); - /// Present the App Store code redemption sheet + /// Show the App Store offer code redemption sheet. + /// See: https://www.openiap.dev/docs/apis/ios/present-code-redemption-sheet-ios Future presentCodeRedemptionSheetIOS(); - /// Present external purchase custom link with StoreKit UI + /// Present an external purchase link, StoreKit External (iOS 16+). + /// See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-link-ios Future presentExternalPurchaseLinkIOS(String url); - /// Present external purchase notice sheet (iOS 17.4+). - /// Uses ExternalPurchase.presentNoticeSheet() which returns a token when user continues. + /// Present the external purchase notice sheet (iOS 17.4+). + /// Uses ExternalPurchase.presentNoticeSheet() which returns a token when the user continues. /// Reference: https://developer.apple.com/documentation/storekit/externalpurchase/presentnoticesheet() + /// See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-notice-sheet-ios Future presentExternalPurchaseNoticeSheetIOS(); - /// Initiate a purchase flow; rely on events for final state + /// Initiate a purchase or subscription flow; rely on events for final state. + /// See: https://www.openiap.dev/docs/apis/request-purchase Future requestPurchase(RequestPurchaseProps params); - /// Purchase the promoted product surfaced by the App Store. + /// Buy the currently promoted product. /// /// @deprecated Use promotedProductListenerIOS to receive the productId, /// then call requestPurchase with that SKU instead. In StoreKit 2, /// promoted products can be purchased directly via the standard purchase flow. + /// See: https://www.openiap.dev/docs/apis/ios/request-purchase-on-promoted-product-ios Future requestPurchaseOnPromotedProductIOS(); - /// Restore completed purchases across platforms + /// Restore non-consumable and active subscription purchases. + /// See: https://www.openiap.dev/docs/apis/restore-purchases Future restorePurchases(); - /// Show alternative billing information dialog to user - /// Step 2 of alternative billing flow - /// Must be called BEFORE processing payment in your payment system + /// Display Google's alternative billing information dialog. Step 2 of the alternative billing flow. + /// Must be called BEFORE processing payment in your payment system. /// - /// Returns true if user accepted, false if user canceled - /// Throws OpenIapError.NotPrepared if billing client not ready + /// Returns true if user accepted, false if user canceled. + /// Throws OpenIapError.NotPrepared if billing client not ready. + /// See: https://www.openiap.dev/docs/apis/android/show-alternative-billing-dialog-android Future showAlternativeBillingDialogAndroid(); - /// Show ExternalPurchaseCustomLink notice sheet (iOS 18.1+). - /// Displays the system disclosure notice sheet for custom external purchase links. + /// Present the disclosure sheet required before linking out via ExternalPurchaseCustomLink (iOS 18.1+). /// Call this after a deliberate customer interaction before linking out to external purchases. /// Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/shownotice(type:) + /// See: https://www.openiap.dev/docs/apis/ios/show-external-purchase-custom-link-notice-ios Future showExternalPurchaseCustomLinkNoticeIOS(ExternalPurchaseCustomLinkNoticeTypeIOS noticeType); - /// Open subscription management UI and return changed purchases (iOS 15+) + /// Present the manage-subscriptions sheet and return changed purchases (iOS 15+). + /// See: https://www.openiap.dev/docs/apis/ios/show-manage-subscriptions-ios Future> showManageSubscriptionsIOS(); - /// Force a StoreKit sync for transactions (iOS 15+) + /// Force sync transactions with the App Store (iOS 15+). + /// See: https://www.openiap.dev/docs/apis/ios/sync-ios Future syncIOS(); - /// Validate purchase receipts with the configured providers + /// Deprecated. Validate purchase receipts with the configured providers — use verifyPurchase instead. + /// See: https://www.openiap.dev/docs/features/validation#verify-purchase Future validateReceipt({ VerifyPurchaseAppleOptions? apple, VerifyPurchaseGoogleOptions? google, VerifyPurchaseHorizonOptions? horizon, }); - /// Verify purchases with the configured providers + /// Verify a purchase against your own backend. Returns a platform-specific + /// variant of VerifyPurchaseResult — VerifyPurchaseResultIOS exposes isValid + /// + receipt/JWS metadata, VerifyPurchaseResultAndroid carries Play Store + /// receipt fields (no isValid), and VerifyPurchaseResultHorizon uses success. + /// Inspect the concrete variant before reading fields. + /// See: https://www.openiap.dev/docs/features/validation#verify-purchase Future verifyPurchase({ VerifyPurchaseAppleOptions? apple, VerifyPurchaseGoogleOptions? google, VerifyPurchaseHorizonOptions? horizon, }); - /// Verify purchases with a specific provider (e.g., IAPKit) + /// Verify via a managed provider without standing up your own server. The + /// PurchaseVerificationProvider enum currently exposes only IAPKit; platform + /// availability may differ by implementation. + /// See: https://www.openiap.dev/docs/features/validation#verify-purchase-with-provider Future verifyPurchaseWithProvider({ RequestVerifyPurchaseWithIapkitProps? iapkit, required PurchaseVerificationProvider provider, @@ -4966,62 +4992,83 @@ abstract class MutationResolver { /// GraphQL root query operations. abstract class QueryResolver { - /// Check if external purchase notice sheet can be presented (iOS 17.4+) - /// Uses ExternalPurchase.canPresent + /// Check eligibility for the external purchase notice sheet (iOS 17.4+). + /// Uses ExternalPurchase.canPresent. + /// See: https://www.openiap.dev/docs/apis/ios/can-present-external-purchase-notice-ios Future canPresentExternalPurchaseNoticeIOS(); - /// Get current StoreKit 2 entitlements (iOS 15+) + /// Get the user's current entitlement for a product, using StoreKit 2 (iOS 15+). + /// See: https://www.openiap.dev/docs/apis/ios/current-entitlement-ios Future currentEntitlementIOS(String sku); - /// Retrieve products or subscriptions from the store + /// Fetch products or subscriptions from the store. + /// See: https://www.openiap.dev/docs/apis/fetch-products Future fetchProducts({ required List skus, ProductQueryType? type, }); - /// Get active subscriptions (filters by subscriptionIds when provided) + /// Get details of all currently active subscriptions (filters by subscriptionIds when provided). + /// See: https://www.openiap.dev/docs/apis/get-active-subscriptions Future> getActiveSubscriptions([List? subscriptionIds]); - /// Get the full StoreKit 2 transaction history as PurchaseIOS values. + /// List every StoreKit transaction (finished + unfinished) for the current user. /// Requires the SK2ConsumableTransactionHistory Info.plist key in the host app /// for finished consumables to be included (iOS 18+). /// Unlike getAvailablePurchases, always returns the iOS-specific PurchaseIOS shape. + /// See: https://www.openiap.dev/docs/apis/ios/get-all-transactions-ios Future> getAllTransactionsIOS(); - /// Fetch the current app transaction (iOS 16+) + /// Fetch the app transaction (iOS 16+). + /// See: https://www.openiap.dev/docs/apis/ios/get-app-transaction-ios Future getAppTransactionIOS(); - /// Get all available purchases for the current user + /// List active purchases for the current user. + /// See: https://www.openiap.dev/docs/apis/get-available-purchases Future> getAvailablePurchases({ bool? alsoPublishToEventListenerIOS, bool? includeSuspendedAndroid, bool? onlyIncludeActiveItemsIOS, }); - /// Get external purchase token for reporting to Apple (iOS 18.1+). - /// Use this token with Apple's External Purchase Server API to report transactions. + /// Fetch a token for Apple's External Purchase Server reporting API (iOS 18.1+). + /// Use this token to report transactions made through ExternalPurchaseCustomLink. /// Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/token(for:) + /// See: https://www.openiap.dev/docs/apis/ios/get-external-purchase-custom-link-token-ios Future getExternalPurchaseCustomLinkTokenIOS(ExternalPurchaseCustomLinkTokenTypeIOS tokenType); - /// Retrieve all pending transactions in the StoreKit queue + /// List unfinished StoreKit transactions in the queue. + /// See: https://www.openiap.dev/docs/apis/ios/get-pending-transactions-ios Future> getPendingTransactionsIOS(); - /// Get the currently promoted product (iOS 11+) + /// Read the App Store-promoted product, if any (iOS 11+). + /// See: https://www.openiap.dev/docs/apis/ios/get-promoted-product-ios Future getPromotedProductIOS(); - /// Get base64-encoded receipt data for validation + /// Get base64-encoded receipt data (legacy validation). + /// See: https://www.openiap.dev/docs/apis/ios/get-receipt-data-ios Future getReceiptDataIOS(); - /// Get the current storefront country code + /// Return the user's storefront country code. + /// See: https://www.openiap.dev/docs/apis/get-storefront Future getStorefront(); - /// Get the current App Store storefront country code + /// Deprecated. Get the current App Store storefront country code — use cross-platform getStorefront instead. + /// See: https://www.openiap.dev/docs/apis/ios/get-storefront-ios Future getStorefrontIOS(); - /// Get the transaction JWS (StoreKit 2) + /// Return the JWS string for a transaction (StoreKit 2). + /// See: https://www.openiap.dev/docs/apis/ios/get-transaction-jws-ios Future getTransactionJwsIOS(String sku); - /// Check whether the user has active subscriptions + /// Check whether the user has any active subscription. + /// See: https://www.openiap.dev/docs/apis/has-active-subscriptions Future hasActiveSubscriptions([List? subscriptionIds]); - /// Check if app is eligible for ExternalPurchaseCustomLink API (iOS 18.1+). + /// Check eligibility for the custom-link variant of external purchase (iOS 18.1+). /// Returns true if the app can use custom external purchase links. /// Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/iseligible + /// See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-external-purchase-custom-link-ios Future isEligibleForExternalPurchaseCustomLinkIOS(); - /// Check introductory offer eligibility for a subscription group + /// Check intro-offer eligibility for a subscription group. + /// See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-intro-offer-ios Future isEligibleForIntroOfferIOS(String groupID); - /// Verify a StoreKit 2 transaction signature + /// Check whether a transaction's JWS verification passed (StoreKit 2). + /// See: https://www.openiap.dev/docs/apis/ios/is-transaction-verified-ios Future isTransactionVerifiedIOS(String sku); - /// Get the latest transaction for a product using StoreKit 2 + /// Get the latest verified transaction for a product, using StoreKit 2. + /// See: https://www.openiap.dev/docs/apis/ios/latest-transaction-ios Future latestTransactionIOS(String sku); - /// Get StoreKit 2 subscription status details (iOS 15+) + /// Get subscription status objects from StoreKit 2 (iOS 15+). + /// See: https://www.openiap.dev/docs/apis/ios/subscription-status-ios Future> subscriptionStatusIOS(String sku); - /// Validate a receipt for a specific product + /// Deprecated. Legacy App Store receipt validation — use verifyPurchase instead. + /// See: https://www.openiap.dev/docs/apis/ios/validate-receipt-ios Future validateReceiptIOS({ VerifyPurchaseAppleOptions? apple, VerifyPurchaseGoogleOptions? google, diff --git a/packages/gql/src/generated/types.gd b/packages/gql/src/generated/types.gd index f1b51f5a..bc96928f 100644 --- a/packages/gql/src/generated/types.gd +++ b/packages/gql/src/generated/types.gd @@ -4800,7 +4800,7 @@ class Query: const return_type = "Boolean" const is_array = false - ## Retrieve products or subscriptions from the store + ## Fetch products or subscriptions from the store. class fetchProductsField: const name = "fetchProducts" const snake_name = "fetch_products" @@ -4820,7 +4820,7 @@ class Query: const return_type = "FetchProductsResult" const is_array = false - ## Get all available purchases for the current user + ## List active purchases for the current user. class getAvailablePurchasesField: const name = "getAvailablePurchases" const snake_name = "get_available_purchases" @@ -4840,7 +4840,7 @@ class Query: const return_type = "Purchase" const is_array = true - ## Get active subscriptions (filters by subscriptionIds when provided) + ## Get details of all currently active subscriptions (filters by subscriptionIds when provided). class getActiveSubscriptionsField: const name = "getActiveSubscriptions" const snake_name = "get_active_subscriptions" @@ -4860,7 +4860,7 @@ class Query: const return_type = "ActiveSubscription" const is_array = true - ## Check whether the user has active subscriptions + ## Check whether the user has any active subscription. class hasActiveSubscriptionsField: const name = "hasActiveSubscriptions" const snake_name = "has_active_subscriptions" @@ -4880,7 +4880,7 @@ class Query: const return_type = "Boolean" const is_array = false - ## Get the current storefront country code + ## Return the user's storefront country code. class getStorefrontField: const name = "getStorefront" const snake_name = "get_storefront" @@ -4889,7 +4889,7 @@ class Query: const return_type = "String" const is_array = false - ## Get the current App Store storefront country code + ## Deprecated. Get the current App Store storefront country code — use cross-platform getStorefront instead. class getStorefrontIOSField: const name = "getStorefrontIOS" const snake_name = "get_storefront_ios" @@ -4898,7 +4898,7 @@ class Query: const return_type = "String" const is_array = false - ## Get the currently promoted product (iOS 11+) + ## Read the App Store-promoted product, if any (iOS 11+). class getPromotedProductIOSField: const name = "getPromotedProductIOS" const snake_name = "get_promoted_product_ios" @@ -4907,7 +4907,7 @@ class Query: const return_type = "ProductIOS" const is_array = false - ## Check if external purchase notice sheet can be presented (iOS 17.4+) + ## Check eligibility for the external purchase notice sheet (iOS 17.4+). class canPresentExternalPurchaseNoticeIOSField: const name = "canPresentExternalPurchaseNoticeIOS" const snake_name = "can_present_external_purchase_notice_ios" @@ -4916,7 +4916,7 @@ class Query: const return_type = "Boolean" const is_array = false - ## Check if app is eligible for ExternalPurchaseCustomLink API (iOS 18.1+). + ## Check eligibility for the custom-link variant of external purchase (iOS 18.1+). class isEligibleForExternalPurchaseCustomLinkIOSField: const name = "isEligibleForExternalPurchaseCustomLinkIOS" const snake_name = "is_eligible_for_external_purchase_custom_link_ios" @@ -4925,7 +4925,7 @@ class Query: const return_type = "Boolean" const is_array = false - ## Get external purchase token for reporting to Apple (iOS 18.1+). + ## Fetch a token for Apple's External Purchase Server reporting API (iOS 18.1+). class getExternalPurchaseCustomLinkTokenIOSField: const name = "getExternalPurchaseCustomLinkTokenIOS" const snake_name = "get_external_purchase_custom_link_token_ios" @@ -4953,7 +4953,7 @@ class Query: const return_type = "ExternalPurchaseCustomLinkTokenResultIOS" const is_array = false - ## Retrieve all pending transactions in the StoreKit queue + ## List unfinished StoreKit transactions in the queue. class getPendingTransactionsIOSField: const name = "getPendingTransactionsIOS" const snake_name = "get_pending_transactions_ios" @@ -4962,7 +4962,7 @@ class Query: const return_type = "PurchaseIOS" const is_array = true - ## Check introductory offer eligibility for a subscription group + ## Check intro-offer eligibility for a subscription group. class isEligibleForIntroOfferIOSField: const name = "isEligibleForIntroOfferIOS" const snake_name = "is_eligible_for_intro_offer_ios" @@ -4982,7 +4982,7 @@ class Query: const return_type = "Boolean" const is_array = false - ## Get StoreKit 2 subscription status details (iOS 15+) + ## Get subscription status objects from StoreKit 2 (iOS 15+). class subscriptionStatusIOSField: const name = "subscriptionStatusIOS" const snake_name = "subscription_status_ios" @@ -5002,7 +5002,7 @@ class Query: const return_type = "SubscriptionStatusIOS" const is_array = true - ## Get current StoreKit 2 entitlements (iOS 15+) + ## Get the user's current entitlement for a product, using StoreKit 2 (iOS 15+). class currentEntitlementIOSField: const name = "currentEntitlementIOS" const snake_name = "current_entitlement_ios" @@ -5022,7 +5022,7 @@ class Query: const return_type = "PurchaseIOS" const is_array = false - ## Get the latest transaction for a product using StoreKit 2 + ## Get the latest verified transaction for a product, using StoreKit 2. class latestTransactionIOSField: const name = "latestTransactionIOS" const snake_name = "latest_transaction_ios" @@ -5042,7 +5042,7 @@ class Query: const return_type = "PurchaseIOS" const is_array = false - ## Verify a StoreKit 2 transaction signature + ## Check whether a transaction's JWS verification passed (StoreKit 2). class isTransactionVerifiedIOSField: const name = "isTransactionVerifiedIOS" const snake_name = "is_transaction_verified_ios" @@ -5062,7 +5062,7 @@ class Query: const return_type = "Boolean" const is_array = false - ## Get the transaction JWS (StoreKit 2) + ## Return the JWS string for a transaction (StoreKit 2). class getTransactionJwsIOSField: const name = "getTransactionJwsIOS" const snake_name = "get_transaction_jws_ios" @@ -5082,7 +5082,7 @@ class Query: const return_type = "String" const is_array = false - ## Get base64-encoded receipt data for validation + ## Get base64-encoded receipt data (legacy validation). class getReceiptDataIOSField: const name = "getReceiptDataIOS" const snake_name = "get_receipt_data_ios" @@ -5091,7 +5091,7 @@ class Query: const return_type = "String" const is_array = false - ## Fetch the current app transaction (iOS 16+) + ## Fetch the app transaction (iOS 16+). class getAppTransactionIOSField: const name = "getAppTransactionIOS" const snake_name = "get_app_transaction_ios" @@ -5100,7 +5100,7 @@ class Query: const return_type = "AppTransaction" const is_array = false - ## Get the full StoreKit 2 transaction history as PurchaseIOS values. + ## List every StoreKit transaction (finished + unfinished) for the current user. class getAllTransactionsIOSField: const name = "getAllTransactionsIOS" const snake_name = "get_all_transactions_ios" @@ -5109,7 +5109,7 @@ class Query: const return_type = "PurchaseIOS" const is_array = true - ## Validate a receipt for a specific product + ## Deprecated. Legacy App Store receipt validation — use verifyPurchase instead. class validateReceiptIOSField: const name = "validateReceiptIOS" const snake_name = "validate_receipt_ios" @@ -5143,7 +5143,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Establish the platform billing connection + ## Initialize the store connection. Call before any IAP API. class initConnectionField: const name = "initConnection" const snake_name = "init_connection" @@ -5163,7 +5163,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Close the platform billing connection + ## Close the store connection and release resources. class endConnectionField: const name = "endConnection" const snake_name = "end_connection" @@ -5172,7 +5172,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Initiate a purchase flow; rely on events for final state + ## Initiate a purchase or subscription flow; rely on events for final state. class requestPurchaseField: const name = "requestPurchase" const snake_name = "request_purchase" @@ -5192,7 +5192,7 @@ class Mutation: const return_type = "RequestPurchaseResult" const is_array = false - ## Finish a transaction after validating receipts + ## Complete a transaction after server-side verification. Required on Android within 3 days. class finishTransactionField: const name = "finishTransaction" const snake_name = "finish_transaction" @@ -5216,7 +5216,7 @@ class Mutation: const return_type = "VoidResult" const is_array = false - ## Restore completed purchases across platforms + ## Restore non-consumable and active subscription purchases. class restorePurchasesField: const name = "restorePurchases" const snake_name = "restore_purchases" @@ -5225,7 +5225,7 @@ class Mutation: const return_type = "VoidResult" const is_array = false - ## Open the native subscription management surface + ## Open the platform's subscription management UI. class deepLinkToSubscriptionsField: const name = "deepLinkToSubscriptions" const snake_name = "deep_link_to_subscriptions" @@ -5245,7 +5245,7 @@ class Mutation: const return_type = "VoidResult" const is_array = false - ## Validate purchase receipts with the configured providers + ## Deprecated. Validate purchase receipts with the configured providers — use verifyPurchase instead. class validateReceiptField: const name = "validateReceipt" const snake_name = "validate_receipt" @@ -5265,7 +5265,7 @@ class Mutation: const return_type = "VerifyPurchaseResult" const is_array = false - ## Verify purchases with the configured providers + ## Verify a purchase against your own backend. Returns a platform-specific class verifyPurchaseField: const name = "verifyPurchase" const snake_name = "verify_purchase" @@ -5285,7 +5285,7 @@ class Mutation: const return_type = "VerifyPurchaseResult" const is_array = false - ## Verify purchases with a specific provider (e.g., IAPKit) + ## Verify via a managed provider without standing up your own server. The class verifyPurchaseWithProviderField: const name = "verifyPurchaseWithProvider" const snake_name = "verify_purchase_with_provider" @@ -5305,7 +5305,7 @@ class Mutation: const return_type = "VerifyPurchaseWithProviderResult" const is_array = false - ## Clear pending transactions from the StoreKit payment queue + ## Clear pending transactions in the queue (sandbox helper). class clearTransactionIOSField: const name = "clearTransactionIOS" const snake_name = "clear_transaction_ios" @@ -5314,7 +5314,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Purchase the promoted product surfaced by the App Store. + ## Buy the currently promoted product. class requestPurchaseOnPromotedProductIOSField: const name = "requestPurchaseOnPromotedProductIOS" const snake_name = "request_purchase_on_promoted_product_ios" @@ -5323,7 +5323,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Open subscription management UI and return changed purchases (iOS 15+) + ## Present the manage-subscriptions sheet and return changed purchases (iOS 15+). class showManageSubscriptionsIOSField: const name = "showManageSubscriptionsIOS" const snake_name = "show_manage_subscriptions_ios" @@ -5332,7 +5332,7 @@ class Mutation: const return_type = "PurchaseIOS" const is_array = true - ## Initiate a refund request for a product (iOS 15+) + ## Present the refund request sheet (iOS 15+). See also Features → Refund. class beginRefundRequestIOSField: const name = "beginRefundRequestIOS" const snake_name = "begin_refund_request_ios" @@ -5352,7 +5352,7 @@ class Mutation: const return_type = "String" const is_array = false - ## Force a StoreKit sync for transactions (iOS 15+) + ## Force sync transactions with the App Store (iOS 15+). class syncIOSField: const name = "syncIOS" const snake_name = "sync_ios" @@ -5361,7 +5361,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Present the App Store code redemption sheet + ## Show the App Store offer code redemption sheet. class presentCodeRedemptionSheetIOSField: const name = "presentCodeRedemptionSheetIOS" const snake_name = "present_code_redemption_sheet_ios" @@ -5370,7 +5370,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Present external purchase notice sheet (iOS 17.4+). + ## Present the external purchase notice sheet (iOS 17.4+). class presentExternalPurchaseNoticeSheetIOSField: const name = "presentExternalPurchaseNoticeSheetIOS" const snake_name = "present_external_purchase_notice_sheet_ios" @@ -5379,7 +5379,7 @@ class Mutation: const return_type = "ExternalPurchaseNoticeResultIOS" const is_array = false - ## Present external purchase custom link with StoreKit UI + ## Present an external purchase link, StoreKit External (iOS 16+). class presentExternalPurchaseLinkIOSField: const name = "presentExternalPurchaseLinkIOS" const snake_name = "present_external_purchase_link_ios" @@ -5399,7 +5399,7 @@ class Mutation: const return_type = "ExternalPurchaseLinkResultIOS" const is_array = false - ## Show ExternalPurchaseCustomLink notice sheet (iOS 18.1+). + ## Present the disclosure sheet required before linking out via ExternalPurchaseCustomLink (iOS 18.1+). class showExternalPurchaseCustomLinkNoticeIOSField: const name = "showExternalPurchaseCustomLinkNoticeIOS" const snake_name = "show_external_purchase_custom_link_notice_ios" @@ -5427,7 +5427,7 @@ class Mutation: const return_type = "ExternalPurchaseCustomLinkNoticeResultIOS" const is_array = false - ## Acknowledge a non-consumable purchase or subscription + ## Acknowledge a non-consumable purchase. Required within 3 days or Google auto-refunds. class acknowledgePurchaseAndroidField: const name = "acknowledgePurchaseAndroid" const snake_name = "acknowledge_purchase_android" @@ -5447,7 +5447,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Consume a purchase token so it can be repurchased + ## Consume a consumable purchase so it can be re-bought. class consumePurchaseAndroidField: const name = "consumePurchaseAndroid" const snake_name = "consume_purchase_android" @@ -5467,7 +5467,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Check if alternative billing is available for this user/device + ## Check whether alternative billing is available for the user. Step 1 of the alternative billing flow. class checkAlternativeBillingAvailabilityAndroidField: const name = "checkAlternativeBillingAvailabilityAndroid" const snake_name = "check_alternative_billing_availability_android" @@ -5476,7 +5476,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Show alternative billing information dialog to user + ## Display Google's alternative billing information dialog. Step 2 of the alternative billing flow. class showAlternativeBillingDialogAndroidField: const name = "showAlternativeBillingDialogAndroid" const snake_name = "show_alternative_billing_dialog_android" @@ -5485,7 +5485,7 @@ class Mutation: const return_type = "Boolean" const is_array = false - ## Create external transaction token for Google Play reporting + ## Create a reporting token for an alternative billing flow. Step 3 of the alternative billing flow. class createAlternativeBillingTokenAndroidField: const name = "createAlternativeBillingTokenAndroid" const snake_name = "create_alternative_billing_token_android" @@ -5494,7 +5494,7 @@ class Mutation: const return_type = "String" const is_array = false - ## Check if a billing program is available for the current user + ## Check whether a billing program (e.g., External Payments) is available for the current user. class isBillingProgramAvailableAndroidField: const name = "isBillingProgramAvailableAndroid" const snake_name = "is_billing_program_available_android" @@ -5521,7 +5521,7 @@ class Mutation: const return_type = "BillingProgramAvailabilityResultAndroid" const is_array = false - ## Create reporting details for a billing program + ## Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). class createBillingProgramReportingDetailsAndroidField: const name = "createBillingProgramReportingDetailsAndroid" const snake_name = "create_billing_program_reporting_details_android" @@ -5548,7 +5548,7 @@ class Mutation: const return_type = "BillingProgramReportingDetailsAndroid" const is_array = false - ## Launch external link flow for external billing programs + ## Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). class launchExternalLinkAndroidField: const name = "launchExternalLinkAndroid" const snake_name = "launch_external_link_android" @@ -5576,7 +5576,7 @@ class Mutation: # Query API helpers -## Retrieve products or subscriptions from the store +## Fetch products or subscriptions from the store. static func fetch_products_args(params: ProductRequest) -> Dictionary: var args = {} if params != null: @@ -5586,7 +5586,7 @@ static func fetch_products_args(params: ProductRequest) -> Dictionary: args["params"] = params return args -## Get all available purchases for the current user +## List active purchases for the current user. static func get_available_purchases_args(options: PurchaseOptions) -> Dictionary: var args = {} if options != null: @@ -5596,97 +5596,97 @@ static func get_available_purchases_args(options: PurchaseOptions) -> Dictionary args["options"] = options return args -## Get active subscriptions (filters by subscriptionIds when provided) +## Get details of all currently active subscriptions (filters by subscriptionIds when provided). static func get_active_subscriptions_args(subscription_ids: Array[String]) -> Dictionary: var args = {} args["subscriptionIds"] = subscription_ids return args -## Check whether the user has active subscriptions +## Check whether the user has any active subscription. static func has_active_subscriptions_args(subscription_ids: Array[String]) -> Dictionary: var args = {} args["subscriptionIds"] = subscription_ids return args -## Get the current storefront country code +## Return the user's storefront country code. static func get_storefront_args() -> Dictionary: return {} -## Get the current App Store storefront country code +## Deprecated. Get the current App Store storefront country code — use cross-platform getStorefront instead. static func get_storefront_ios_args() -> Dictionary: return {} -## Get the currently promoted product (iOS 11+) +## Read the App Store-promoted product, if any (iOS 11+). static func get_promoted_product_ios_args() -> Dictionary: return {} -## Check if external purchase notice sheet can be presented (iOS 17.4+) +## Check eligibility for the external purchase notice sheet (iOS 17.4+). static func can_present_external_purchase_notice_ios_args() -> Dictionary: return {} -## Check if app is eligible for ExternalPurchaseCustomLink API (iOS 18.1+). +## Check eligibility for the custom-link variant of external purchase (iOS 18.1+). static func is_eligible_for_external_purchase_custom_link_ios_args() -> Dictionary: return {} -## Get external purchase token for reporting to Apple (iOS 18.1+). +## Fetch a token for Apple's External Purchase Server reporting API (iOS 18.1+). static func get_external_purchase_custom_link_token_ios_args(token_type: ExternalPurchaseCustomLinkTokenTypeIOS) -> Dictionary: var args = {} args["tokenType"] = token_type return args -## Retrieve all pending transactions in the StoreKit queue +## List unfinished StoreKit transactions in the queue. static func get_pending_transactions_ios_args() -> Dictionary: return {} -## Check introductory offer eligibility for a subscription group +## Check intro-offer eligibility for a subscription group. static func is_eligible_for_intro_offer_ios_args(group_id: String) -> Dictionary: var args = {} args["groupID"] = group_id return args -## Get StoreKit 2 subscription status details (iOS 15+) +## Get subscription status objects from StoreKit 2 (iOS 15+). static func subscription_status_ios_args(sku: String) -> Dictionary: var args = {} args["sku"] = sku return args -## Get current StoreKit 2 entitlements (iOS 15+) +## Get the user's current entitlement for a product, using StoreKit 2 (iOS 15+). static func current_entitlement_ios_args(sku: String) -> Dictionary: var args = {} args["sku"] = sku return args -## Get the latest transaction for a product using StoreKit 2 +## Get the latest verified transaction for a product, using StoreKit 2. static func latest_transaction_ios_args(sku: String) -> Dictionary: var args = {} args["sku"] = sku return args -## Verify a StoreKit 2 transaction signature +## Check whether a transaction's JWS verification passed (StoreKit 2). static func is_transaction_verified_ios_args(sku: String) -> Dictionary: var args = {} args["sku"] = sku return args -## Get the transaction JWS (StoreKit 2) +## Return the JWS string for a transaction (StoreKit 2). static func get_transaction_jws_ios_args(sku: String) -> Dictionary: var args = {} args["sku"] = sku return args -## Get base64-encoded receipt data for validation +## Get base64-encoded receipt data (legacy validation). static func get_receipt_data_ios_args() -> Dictionary: return {} -## Fetch the current app transaction (iOS 16+) +## Fetch the app transaction (iOS 16+). static func get_app_transaction_ios_args() -> Dictionary: return {} -## Get the full StoreKit 2 transaction history as PurchaseIOS values. +## List every StoreKit transaction (finished + unfinished) for the current user. static func get_all_transactions_ios_args() -> Dictionary: return {} -## Validate a receipt for a specific product +## Deprecated. Legacy App Store receipt validation — use verifyPurchase instead. static func validate_receipt_ios_args(options: VerifyPurchaseProps) -> Dictionary: var args = {} if options != null: @@ -5698,7 +5698,7 @@ static func validate_receipt_ios_args(options: VerifyPurchaseProps) -> Dictionar # Mutation API helpers -## Establish the platform billing connection +## Initialize the store connection. Call before any IAP API. static func init_connection_args(config: InitConnectionConfig) -> Dictionary: var args = {} if config != null: @@ -5708,11 +5708,11 @@ static func init_connection_args(config: InitConnectionConfig) -> Dictionary: args["config"] = config return args -## Close the platform billing connection +## Close the store connection and release resources. static func end_connection_args() -> Dictionary: return {} -## Initiate a purchase flow; rely on events for final state +## Initiate a purchase or subscription flow; rely on events for final state. static func request_purchase_args(params: RequestPurchaseProps) -> Dictionary: var args = {} if params != null: @@ -5722,7 +5722,7 @@ static func request_purchase_args(params: RequestPurchaseProps) -> Dictionary: args["params"] = params return args -## Finish a transaction after validating receipts +## Complete a transaction after server-side verification. Required on Android within 3 days. static func finish_transaction_args(purchase: PurchaseInput, is_consumable: bool) -> Dictionary: var args = {} if purchase != null: @@ -5733,11 +5733,11 @@ static func finish_transaction_args(purchase: PurchaseInput, is_consumable: bool args["isConsumable"] = is_consumable return args -## Restore completed purchases across platforms +## Restore non-consumable and active subscription purchases. static func restore_purchases_args() -> Dictionary: return {} -## Open the native subscription management surface +## Open the platform's subscription management UI. static func deep_link_to_subscriptions_args(options: DeepLinkOptions) -> Dictionary: var args = {} if options != null: @@ -5747,7 +5747,7 @@ static func deep_link_to_subscriptions_args(options: DeepLinkOptions) -> Diction args["options"] = options return args -## Validate purchase receipts with the configured providers +## Deprecated. Validate purchase receipts with the configured providers — use verifyPurchase instead. static func validate_receipt_args(options: VerifyPurchaseProps) -> Dictionary: var args = {} if options != null: @@ -5757,7 +5757,7 @@ static func validate_receipt_args(options: VerifyPurchaseProps) -> Dictionary: args["options"] = options return args -## Verify purchases with the configured providers +## Verify a purchase against your own backend. Returns a platform-specific static func verify_purchase_args(options: VerifyPurchaseProps) -> Dictionary: var args = {} if options != null: @@ -5767,7 +5767,7 @@ static func verify_purchase_args(options: VerifyPurchaseProps) -> Dictionary: args["options"] = options return args -## Verify purchases with a specific provider (e.g., IAPKit) +## Verify via a managed provider without standing up your own server. The static func verify_purchase_with_provider_args(options: VerifyPurchaseWithProviderProps) -> Dictionary: var args = {} if options != null: @@ -5777,85 +5777,85 @@ static func verify_purchase_with_provider_args(options: VerifyPurchaseWithProvid args["options"] = options return args -## Clear pending transactions from the StoreKit payment queue +## Clear pending transactions in the queue (sandbox helper). static func clear_transaction_ios_args() -> Dictionary: return {} -## Purchase the promoted product surfaced by the App Store. +## Buy the currently promoted product. static func request_purchase_on_promoted_product_ios_args() -> Dictionary: return {} -## Open subscription management UI and return changed purchases (iOS 15+) +## Present the manage-subscriptions sheet and return changed purchases (iOS 15+). static func show_manage_subscriptions_ios_args() -> Dictionary: return {} -## Initiate a refund request for a product (iOS 15+) +## Present the refund request sheet (iOS 15+). See also Features → Refund. static func begin_refund_request_ios_args(sku: String) -> Dictionary: var args = {} args["sku"] = sku return args -## Force a StoreKit sync for transactions (iOS 15+) +## Force sync transactions with the App Store (iOS 15+). static func sync_ios_args() -> Dictionary: return {} -## Present the App Store code redemption sheet +## Show the App Store offer code redemption sheet. static func present_code_redemption_sheet_ios_args() -> Dictionary: return {} -## Present external purchase notice sheet (iOS 17.4+). +## Present the external purchase notice sheet (iOS 17.4+). static func present_external_purchase_notice_sheet_ios_args() -> Dictionary: return {} -## Present external purchase custom link with StoreKit UI +## Present an external purchase link, StoreKit External (iOS 16+). static func present_external_purchase_link_ios_args(url: String) -> Dictionary: var args = {} args["url"] = url return args -## Show ExternalPurchaseCustomLink notice sheet (iOS 18.1+). +## Present the disclosure sheet required before linking out via ExternalPurchaseCustomLink (iOS 18.1+). static func show_external_purchase_custom_link_notice_ios_args(notice_type: ExternalPurchaseCustomLinkNoticeTypeIOS) -> Dictionary: var args = {} args["noticeType"] = notice_type return args -## Acknowledge a non-consumable purchase or subscription +## Acknowledge a non-consumable purchase. Required within 3 days or Google auto-refunds. static func acknowledge_purchase_android_args(purchase_token: String) -> Dictionary: var args = {} args["purchaseToken"] = purchase_token return args -## Consume a purchase token so it can be repurchased +## Consume a consumable purchase so it can be re-bought. static func consume_purchase_android_args(purchase_token: String) -> Dictionary: var args = {} args["purchaseToken"] = purchase_token return args -## Check if alternative billing is available for this user/device +## Check whether alternative billing is available for the user. Step 1 of the alternative billing flow. static func check_alternative_billing_availability_android_args() -> Dictionary: return {} -## Show alternative billing information dialog to user +## Display Google's alternative billing information dialog. Step 2 of the alternative billing flow. static func show_alternative_billing_dialog_android_args() -> Dictionary: return {} -## Create external transaction token for Google Play reporting +## Create a reporting token for an alternative billing flow. Step 3 of the alternative billing flow. static func create_alternative_billing_token_android_args() -> Dictionary: return {} -## Check if a billing program is available for the current user +## Check whether a billing program (e.g., External Payments) is available for the current user. static func is_billing_program_available_android_args(program: BillingProgramAndroid) -> Dictionary: var args = {} args["program"] = program return args -## Create reporting details for a billing program +## Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). static func create_billing_program_reporting_details_android_args(program: BillingProgramAndroid) -> Dictionary: var args = {} args["program"] = program return args -## Launch external link flow for external billing programs +## Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). static func launch_external_link_android_args(params: LaunchExternalLinkParamsAndroid) -> Dictionary: var args = {} if params != null: diff --git a/packages/gql/src/generated/types.ts b/packages/gql/src/generated/types.ts index 4afb30b7..48f0103b 100644 --- a/packages/gql/src/generated/types.ts +++ b/packages/gql/src/generated/types.ts @@ -585,118 +585,176 @@ export interface LimitedQuantityInfoAndroid { } export interface Mutation { - /** Acknowledge a non-consumable purchase or subscription */ + /** + * Acknowledge a non-consumable purchase. Required within 3 days or Google auto-refunds. + * See: https://www.openiap.dev/docs/apis/android/acknowledge-purchase-android + */ acknowledgePurchaseAndroid: Promise; - /** Initiate a refund request for a product (iOS 15+) */ + /** + * Present the refund request sheet (iOS 15+). See also Features → Refund. + * See: https://www.openiap.dev/docs/apis/ios/begin-refund-request-ios + */ beginRefundRequestIOS?: Promise<(string | null)>; /** - * Check if alternative billing is available for this user/device - * Step 1 of alternative billing flow + * Check whether alternative billing is available for the user. Step 1 of the alternative billing flow. * - * Returns true if available, false otherwise - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns true if available, false otherwise. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/check-alternative-billing-availability-android */ checkAlternativeBillingAvailabilityAndroid: Promise; - /** Clear pending transactions from the StoreKit payment queue */ + /** + * Clear pending transactions in the queue (sandbox helper). + * See: https://www.openiap.dev/docs/apis/ios/clear-transaction-ios + */ clearTransactionIOS: Promise; - /** Consume a purchase token so it can be repurchased */ + /** + * Consume a consumable purchase so it can be re-bought. + * See: https://www.openiap.dev/docs/apis/android/consume-purchase-android + */ consumePurchaseAndroid: Promise; /** - * Create external transaction token for Google Play reporting - * Step 3 of alternative billing flow - * Must be called AFTER successful payment in your payment system - * Token must be reported to Google Play backend within 24 hours + * Create a reporting token for an alternative billing flow. Step 3 of the alternative billing flow. + * Must be called AFTER successful payment in your payment system. + * Token must be reported to Google Play backend within 24 hours. * - * Returns token string, or null if creation failed - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns token string, or null if creation failed. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/create-alternative-billing-token-android */ createAlternativeBillingTokenAndroid?: Promise<(string | null)>; /** - * Create reporting details for a billing program - * Replaces the deprecated createExternalOfferReportingDetailsAsync API + * Create the reporting payload Google requires after a Developer-Provided Billing transaction (Play Billing 8.3.0+). + * Replaces the deprecated createExternalOfferReportingDetailsAsync API. * - * Available in Google Play Billing Library 8.2.0+ - * Returns external transaction token needed for reporting external transactions - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns external transaction token needed for reporting external transactions. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/create-billing-program-reporting-details-android */ createBillingProgramReportingDetailsAndroid: Promise; - /** Open the native subscription management surface */ + /** + * Open the platform's subscription management UI. + * See: https://www.openiap.dev/docs/apis/deep-link-to-subscriptions + */ deepLinkToSubscriptions: Promise; - /** Close the platform billing connection */ + /** + * Close the store connection and release resources. + * See: https://www.openiap.dev/docs/apis/end-connection + */ endConnection: Promise; - /** Finish a transaction after validating receipts */ + /** + * Complete a transaction after server-side verification. Required on Android within 3 days. + * See: https://www.openiap.dev/docs/apis/finish-transaction + */ finishTransaction: Promise; - /** Establish the platform billing connection */ + /** + * Initialize the store connection. Call before any IAP API. + * See: https://www.openiap.dev/docs/apis/init-connection + */ initConnection: Promise; /** - * Check if a billing program is available for the current user - * Replaces the deprecated isExternalOfferAvailableAsync API + * Check whether a billing program (e.g., External Payments) is available for the current user. + * Replaces the deprecated isExternalOfferAvailableAsync API. * - * Available in Google Play Billing Library 8.2.0+ - * Returns availability result with isAvailable flag - * Throws OpenIapError.NotPrepared if billing client not ready + * Available in Google Play Billing Library 8.2.0+. + * Returns availability result with isAvailable flag. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/is-billing-program-available-android */ isBillingProgramAvailableAndroid: Promise; /** - * Launch external link flow for external billing programs - * Replaces the deprecated showExternalOfferInformationDialog API + * Launch an external content/offer link from inside the Billing Programs flow (Play Billing 8.2.0+). + * Replaces the deprecated showExternalOfferInformationDialog API. * - * Available in Google Play Billing Library 8.2.0+ - * Shows Play Store dialog and optionally launches external URL - * Throws OpenIapError.NotPrepared if billing client not ready + * Shows Play Store dialog and optionally launches external URL. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/launch-external-link-android */ launchExternalLinkAndroid: Promise; - /** Present the App Store code redemption sheet */ + /** + * Show the App Store offer code redemption sheet. + * See: https://www.openiap.dev/docs/apis/ios/present-code-redemption-sheet-ios + */ presentCodeRedemptionSheetIOS: Promise; - /** Present external purchase custom link with StoreKit UI */ + /** + * Present an external purchase link, StoreKit External (iOS 16+). + * See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-link-ios + */ presentExternalPurchaseLinkIOS: Promise; /** - * Present external purchase notice sheet (iOS 17.4+). - * Uses ExternalPurchase.presentNoticeSheet() which returns a token when user continues. + * Present the external purchase notice sheet (iOS 17.4+). + * Uses ExternalPurchase.presentNoticeSheet() which returns a token when the user continues. * Reference: https://developer.apple.com/documentation/storekit/externalpurchase/presentnoticesheet() + * See: https://www.openiap.dev/docs/apis/ios/present-external-purchase-notice-sheet-ios */ presentExternalPurchaseNoticeSheetIOS: Promise; - /** Initiate a purchase flow; rely on events for final state */ + /** + * Initiate a purchase or subscription flow; rely on events for final state. + * See: https://www.openiap.dev/docs/apis/request-purchase + */ requestPurchase?: Promise<(Purchase | Purchase[] | null)>; /** - * Purchase the promoted product surfaced by the App Store. + * Buy the currently promoted product. * * @deprecated Use promotedProductListenerIOS to receive the productId, * then call requestPurchase with that SKU instead. In StoreKit 2, * promoted products can be purchased directly via the standard purchase flow. + * See: https://www.openiap.dev/docs/apis/ios/request-purchase-on-promoted-product-ios * @deprecated Use promotedProductListenerIOS + requestPurchase instead */ requestPurchaseOnPromotedProductIOS: Promise; - /** Restore completed purchases across platforms */ + /** + * Restore non-consumable and active subscription purchases. + * See: https://www.openiap.dev/docs/apis/restore-purchases + */ restorePurchases: Promise; /** - * Show alternative billing information dialog to user - * Step 2 of alternative billing flow - * Must be called BEFORE processing payment in your payment system + * Display Google's alternative billing information dialog. Step 2 of the alternative billing flow. + * Must be called BEFORE processing payment in your payment system. * - * Returns true if user accepted, false if user canceled - * Throws OpenIapError.NotPrepared if billing client not ready + * Returns true if user accepted, false if user canceled. + * Throws OpenIapError.NotPrepared if billing client not ready. + * See: https://www.openiap.dev/docs/apis/android/show-alternative-billing-dialog-android */ showAlternativeBillingDialogAndroid: Promise; /** - * Show ExternalPurchaseCustomLink notice sheet (iOS 18.1+). - * Displays the system disclosure notice sheet for custom external purchase links. + * Present the disclosure sheet required before linking out via ExternalPurchaseCustomLink (iOS 18.1+). * Call this after a deliberate customer interaction before linking out to external purchases. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/shownotice(type:) + * See: https://www.openiap.dev/docs/apis/ios/show-external-purchase-custom-link-notice-ios */ showExternalPurchaseCustomLinkNoticeIOS: Promise; - /** Open subscription management UI and return changed purchases (iOS 15+) */ + /** + * Present the manage-subscriptions sheet and return changed purchases (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/show-manage-subscriptions-ios + */ showManageSubscriptionsIOS: Promise; - /** Force a StoreKit sync for transactions (iOS 15+) */ + /** + * Force sync transactions with the App Store (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/sync-ios + */ syncIOS: Promise; /** - * Validate purchase receipts with the configured providers + * Deprecated. Validate purchase receipts with the configured providers — use verifyPurchase instead. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase * @deprecated Use verifyPurchase */ validateReceipt: Promise; - /** Verify purchases with the configured providers */ + /** + * Verify a purchase against your own backend. Returns a platform-specific + * variant of VerifyPurchaseResult — VerifyPurchaseResultIOS exposes isValid + * + receipt/JWS metadata, VerifyPurchaseResultAndroid carries Play Store + * receipt fields (no isValid), and VerifyPurchaseResultHorizon uses success. + * Inspect the concrete variant before reading fields. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase + */ verifyPurchase: Promise; - /** Verify purchases with a specific provider (e.g., IAPKit) */ + /** + * Verify via a managed provider without standing up your own server. The + * PurchaseVerificationProvider enum currently exposes only IAPKit; platform + * availability may differ by implementation. + * See: https://www.openiap.dev/docs/features/validation#verify-purchase-with-provider + */ verifyPurchaseWithProvider: Promise; } @@ -1234,66 +1292,117 @@ export type PurchaseVerificationProvider = 'iapkit'; export interface Query { /** - * Check if external purchase notice sheet can be presented (iOS 17.4+) - * Uses ExternalPurchase.canPresent + * Check eligibility for the external purchase notice sheet (iOS 17.4+). + * Uses ExternalPurchase.canPresent. + * See: https://www.openiap.dev/docs/apis/ios/can-present-external-purchase-notice-ios */ canPresentExternalPurchaseNoticeIOS: Promise; - /** Get current StoreKit 2 entitlements (iOS 15+) */ + /** + * Get the user's current entitlement for a product, using StoreKit 2 (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/current-entitlement-ios + */ currentEntitlementIOS?: Promise<(PurchaseIOS | null)>; - /** Retrieve products or subscriptions from the store */ + /** + * Fetch products or subscriptions from the store. + * See: https://www.openiap.dev/docs/apis/fetch-products + */ fetchProducts: Promise<(ProductOrSubscription[] | Product[] | ProductSubscription[] | null)>; - /** Get active subscriptions (filters by subscriptionIds when provided) */ + /** + * Get details of all currently active subscriptions (filters by subscriptionIds when provided). + * See: https://www.openiap.dev/docs/apis/get-active-subscriptions + */ getActiveSubscriptions: Promise; /** - * Get the full StoreKit 2 transaction history as PurchaseIOS values. + * List every StoreKit transaction (finished + unfinished) for the current user. * Requires the SK2ConsumableTransactionHistory Info.plist key in the host app * for finished consumables to be included (iOS 18+). * Unlike getAvailablePurchases, always returns the iOS-specific PurchaseIOS shape. + * See: https://www.openiap.dev/docs/apis/ios/get-all-transactions-ios */ getAllTransactionsIOS: Promise; - /** Fetch the current app transaction (iOS 16+) */ + /** + * Fetch the app transaction (iOS 16+). + * See: https://www.openiap.dev/docs/apis/ios/get-app-transaction-ios + */ getAppTransactionIOS?: Promise<(AppTransaction | null)>; - /** Get all available purchases for the current user */ + /** + * List active purchases for the current user. + * See: https://www.openiap.dev/docs/apis/get-available-purchases + */ getAvailablePurchases: Promise; /** - * Get external purchase token for reporting to Apple (iOS 18.1+). - * Use this token with Apple's External Purchase Server API to report transactions. + * Fetch a token for Apple's External Purchase Server reporting API (iOS 18.1+). + * Use this token to report transactions made through ExternalPurchaseCustomLink. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/token(for:) + * See: https://www.openiap.dev/docs/apis/ios/get-external-purchase-custom-link-token-ios */ getExternalPurchaseCustomLinkTokenIOS: Promise; - /** Retrieve all pending transactions in the StoreKit queue */ + /** + * List unfinished StoreKit transactions in the queue. + * See: https://www.openiap.dev/docs/apis/ios/get-pending-transactions-ios + */ getPendingTransactionsIOS: Promise; - /** Get the currently promoted product (iOS 11+) */ + /** + * Read the App Store-promoted product, if any (iOS 11+). + * See: https://www.openiap.dev/docs/apis/ios/get-promoted-product-ios + */ getPromotedProductIOS?: Promise<(ProductIOS | null)>; - /** Get base64-encoded receipt data for validation */ + /** + * Get base64-encoded receipt data (legacy validation). + * See: https://www.openiap.dev/docs/apis/ios/get-receipt-data-ios + */ getReceiptDataIOS?: Promise<(string | null)>; - /** Get the current storefront country code */ + /** + * Return the user's storefront country code. + * See: https://www.openiap.dev/docs/apis/get-storefront + */ getStorefront: Promise; /** - * Get the current App Store storefront country code + * Deprecated. Get the current App Store storefront country code — use cross-platform getStorefront instead. + * See: https://www.openiap.dev/docs/apis/ios/get-storefront-ios * @deprecated Use getStorefront */ getStorefrontIOS: Promise; - /** Get the transaction JWS (StoreKit 2) */ + /** + * Return the JWS string for a transaction (StoreKit 2). + * See: https://www.openiap.dev/docs/apis/ios/get-transaction-jws-ios + */ getTransactionJwsIOS?: Promise<(string | null)>; - /** Check whether the user has active subscriptions */ + /** + * Check whether the user has any active subscription. + * See: https://www.openiap.dev/docs/apis/has-active-subscriptions + */ hasActiveSubscriptions: Promise; /** - * Check if app is eligible for ExternalPurchaseCustomLink API (iOS 18.1+). + * Check eligibility for the custom-link variant of external purchase (iOS 18.1+). * Returns true if the app can use custom external purchase links. * Reference: https://developer.apple.com/documentation/storekit/externalpurchasecustomlink/iseligible + * See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-external-purchase-custom-link-ios */ isEligibleForExternalPurchaseCustomLinkIOS: Promise; - /** Check introductory offer eligibility for a subscription group */ + /** + * Check intro-offer eligibility for a subscription group. + * See: https://www.openiap.dev/docs/apis/ios/is-eligible-for-intro-offer-ios + */ isEligibleForIntroOfferIOS: Promise; - /** Verify a StoreKit 2 transaction signature */ + /** + * Check whether a transaction's JWS verification passed (StoreKit 2). + * See: https://www.openiap.dev/docs/apis/ios/is-transaction-verified-ios + */ isTransactionVerifiedIOS: Promise; - /** Get the latest transaction for a product using StoreKit 2 */ + /** + * Get the latest verified transaction for a product, using StoreKit 2. + * See: https://www.openiap.dev/docs/apis/ios/latest-transaction-ios + */ latestTransactionIOS?: Promise<(PurchaseIOS | null)>; - /** Get StoreKit 2 subscription status details (iOS 15+) */ + /** + * Get subscription status objects from StoreKit 2 (iOS 15+). + * See: https://www.openiap.dev/docs/apis/ios/subscription-status-ios + */ subscriptionStatusIOS: Promise; /** - * Validate a receipt for a specific product + * Deprecated. Legacy App Store receipt validation — use verifyPurchase instead. + * See: https://www.openiap.dev/docs/apis/ios/validate-receipt-ios * @deprecated Use verifyPurchase */ validateReceiptIOS: Promise; diff --git a/scripts/audit-docs.ts b/scripts/audit-docs.ts new file mode 100644 index 00000000..d391541d --- /dev/null +++ b/scripts/audit-docs.ts @@ -0,0 +1,498 @@ +#!/usr/bin/env bun +/** + * audit-docs.ts — SSOT consistency check for /docs/apis and /docs/types pages. + * + * What it does + * 1. Walks every `packages/docs/src/pages/docs/apis/**\/*.tsx` and + * `packages/docs/src/pages/docs/types/**\/*.tsx` page. + * 2. Loads the generated TypeScript types from + * `libraries/expo-iap/src/types.ts` and indexes every `interface`, + * `type` alias, and `enum` / string-literal union shape. + * 3. For each doc page, extracts: + * - `` targets + * - `fieldName` mentions inside `

` rows or + * `