@nativescript/payments
为 NativeScript 提供的应用内购买和订阅服务
npm i --save @nativescript/payments

@nativescript/payments

一个插件,允许您的应用使用 Apple AppStore 和 Google PlayStore 购买系统进行应用内购买和订阅。

此插件使用 RxJS 可观察对象 来发出处理购买流程的事件。为了避免与平台购买流程的线程错误,您可以在可观察对象上使用 toMainThread() 作为管道,以便购买逻辑在主线程上执行。paymentEvents.pipe(toMainThread()).subscribe((event: PaymentEvent.Type) => {...

应用内购买示例 应该提供了一个如何使用可观察对象和设置购买机制的良好起点。

iOS 上的支付示例

示例项目列表 购买确认 购买完成 购买成功
Purchase Item List Example Purchase Flow Confirmation Purchase Flow Done Purchase Flow Success

Android 上的支付示例

示例项目列表 购买确认 购买成功
Item List Example Purchase Flow Confirmation Purchase Flow Successful

内容

安装

ns plugin add @nativescript/payments

先决条件

在开始之前,请查看以下先决条件

iOS 先决条件

要为您的 iOS 应用提供应用内购买,您需要在 AppStoreConnect.Apple.Com 上为应用创建项目。

In App Purchase Step One

在创建应用内购买项目的表单中,产品 ID 是您将在应用中用于获取用户购买项目的值。Apple 产品 ID 表单

创建项目完成后,您将看到在 AppStore Connect 上列出应用的全部项目列表。应用内购买项目列表

要完全测试 iOS 购买,您需要一台真实的 iOS 设备。您还需要在您的应用商店帐户中的沙盒环境中拥有一个 测试用户

Sandbox Testers

Android 先决条件

  1. 要为您的 Android 应用提供应用内购买,您需要至少上传一个 apk/aab 到 Google Play Console

  2. 在控制台中创建应用内产品。创建新的应用内产品

在创建产品的表单中,产品 ID 是您将用于获取用户购买产品的值。

关于 Google 项目的注意事项

  • Google 不喜欢 ID 字段中的数字值。它似乎在查询您的项目时会忽略 Sku,如果 ID 包含数字值,则只返回一个项目而不是多个值。产品 ID 表单

  • 在Google审核应用之前,Google应用内产品将无法使用。它们将显示在产品列表中,但在尝试购买时API将报错。当调用`fetchItems(['your.product.id'])`时,返回的项目标题应附加(待审核)或类似字样。只有当审核期过后,您才能完成购买流程。

Active, in review

为了完全测试Android购买,您应该使用带有Google Play设置并已登录账户的真实设备。您可以使用Google Play计费测试账户进行工作流程测试。这将允许您正确地测试开发中的应用程序。更多信息:https://support.google.com/googleplay/android-developer/answer/6062777

使用 @nativescript/payments

标准使用流程

以下是该插件方法调用标准流程

// This sets up the internal system of the plugin
init();
// Connect the RxJS Observable
paymentEvents.connect();
// Establish the Subscription with your event handling
paymentEvents.pipe(toMainThread()).subscribe((event: PaymentEvent.Type) => {...

// fetchItems(['item.id', ...]) will query the store for the items requested.
// Handle these items inside the PaymentEvent.Context.RETRIEVING_ITEMS event.
fetchItems(['item.id']);

// buyItem('item.id') will start the purchase flow on Android & iOS.
// Next handle the PaymentEvent.Context.PROCESSING_ORDER for SUCCESS or FAILURE.
// If SUCCESS then you can call the last method to the `finalizeOrder(payload)` method.
buyItem('item.id');

// finalizeOrder(payload) will complete the purchase flow.
// The payload argument here is provided in the PaymentEvent.Context.PROCESSING_ORDER - SUCCESS event (see below example for detailed usage).
finalizeOrder(payload)

// at this point you would process the order with your backend given the receiptToken from the purchase flow

应用内购买示例

import { buyItem, BuyItemOptions, canMakePayments, fetchItems, finalizeOrder, init as initPayments, Item, PaymentEvent, paymentEvents, toMainThread } from '@nativescript/payments';

export class SomeViewModel {
private item: Item;

pageLoaded() {
// Connect to the RxJS Observable
paymentEvents.connect();

// Subscribe to the RxJS Observable
// You do not have to handle all of the events
// RETRIEVING_ITEMS && PROCESSING_ORDER are the ones you'll want to use to handle the purchase flow
const subscription = paymentEvents.pipe(toMainThread()).subscribe((event: PaymentEvent.Type) => {
switch (event.context) {
case PaymentEvent.Context.CONNECTING_STORE:
console.log('
Store Status: ' + event.result);
if (event.result === PaymentEvent.Result.SUCCESS) {
const canPay = canMakePayments();
if (canPay) {
// pass in your product IDs here that you want to query for
fetchItems(['
io.nstudio.iapdemo.coinsfive', 'io.nstudio.iapdemo.coinsone', 'io.nstudio.iapdemo.coinsonethousand']);
}
}
break;
case PaymentEvent.Context.RETRIEVING_ITEMS:
if (event.result === PaymentEvent.Result.SUCCESS) {
// if you passed multiple items you will need to handle accordingly for your app
this.item = event.payload;
}
break;
case PaymentEvent.Context.PROCESSING_ORDER:
if (event.result === PaymentEvent.Result.FAILURE) {
console.log(`🛑 Payment Failure - ${event.payload.description} 🛑`);
// handle the failure of the purchase
} else if (event.result === PaymentEvent.Result.SUCCESS) {
// handle the successful purchase
console.log('
🟢 Payment Success 🟢');
console.log(`Order Date: ${event.payload.orderDate}`);
console.log(`Receipt Token: ${event.payload.receiptToken}`);
finalizeOrder(event.payload);
}
break;
case PaymentEvent.Context.FINALIZING_ORDER:
if (event.result === PaymentEvent.Result.SUCCESS) {
console.log('
Order Finalized');
}
break;
case PaymentEvent.Context.RESTORING_ORDERS:
console.log(event);
break;
default:
console.log(`Invalid EventContext: ${event}`);
break;
}
});

// This initializes the internal payment system for the plugin
initPayments();
}

buttonTap() {
const opts: BuyItemOptions = {
accountUserName: '
[email protected]',
android: {
vrPurchase: true,
},
ios: {
quantity: 1,
simulatesAskToBuyInSandbox: true,
},
};

// This method will kick off the platform purchase flow
// We are passing the item and an optional object with some configuration
buyItem(this.item, opts);
}
}

API

  • init() 设置插件内部系统。
  • paymentEvents 是RxJS Observable,用于发出处理购买流程的事件。

以下方法在响应由paymentEvents发出的事件时被调用。

方法 描述
fetchItems(itemIds: Array) 查询商店中请求的项目。您应该在PaymentEvent.Context.RETRIEVING_ITEMS事件中处理这些项目。
buyItem(item: Item, options?: BuyItemOptions) 在Android和iOS上启动购买流程,并发出带有SUCCESSFAILUREPaymentEvent.Context.PROCESSING_ORDER。如果成功,则可以调用最后一个方法调用finalizeOrder(payload)
fetchSubscriptions(itemIds: Array) 查询应用提供的订阅。您应该在PaymentEvent.Context.RETRIEVING_ITEMS事件中处理这些订阅。
startSubscription(item: Item, userData?: string) 仅限Android。通过展示Google商店订阅UI界面来启动计费流程。
restoreOrders(skuType?: string) 返回用户为每个产品所做的购买。您可以通过调用此方法在额外设备上安装购买或在用户删除并重新安装的应用程序中恢复购买。
canMakePayments() 返回truefalse,表示计费服务是否可用以及是否设置成功。
tearDown() 关闭与计费服务的连接以释放资源。

许可证

Apache许可证版本2.0