JAVA、PHP、前端、APP、网站开发 - 开发技术学习

开发技术学习 » APP开发 » uniapp苹果ios内购,ios支付,苹果支付内购

uniapp苹果ios内购,ios支付,苹果支付内购

此文被围观800 日期: 2023-04-21 分类 : APP开发  标签:  ······

首页使用uniapp提供的iap.js文件

// uni iap

const ProviderType = {
  IAP: 'iap'
}

const IapTransactionState = {
  purchasing: "0", // A transaction that is being processed by the App Store.
  purchased: "1", // A successfully processed transaction.
  failed: "2", // A failed transaction.
  restored: "3", // A transaction that restores content previously purchased by the user.
  deferred: "4" // A transaction that is in the queue, but its final status is pending external action such as Ask to Buy.
};

class Iap {

  _channel = null;
  _channelError = null;
  _productIds = [];

  _ready = false;

  constructor({
    products
  }) {
    this._productIds = products;
  }

  init() {
    return new Promise((resolve, reject) => {
      this.getChannels((channel) => {
        this._ready = true;
		uni.showToast({
			title:channel,
			icon:'none'
		})
        resolve(channel);
      }, (err) => {
        reject(err);
      })
    })
  }

  getProduct(productIds) {
    return new Promise((resolve, reject) => {
      this._channel.requestProduct(productIds || this._productIds, (res) => {
        resolve(res);
      }, (err) => {
        reject(err);
      })
    });
  }
  // 注意这里是新加的,必须要有,不然支付不起
  requestOrder(productIds) {
	  if (this._productIds.length == 0) this._productIds = productIds;
	  return new Promise((resolve, reject) => {
	    this._channel.requestOrder(productIds || this._productIds, (res) => {
	      resolve(res);
	    }, (err) => {
	      reject(err);
	    })
	  });
  }

  requestPayment(orderInfo) {
    return new Promise((resolve, reject) => {
		uni.requestPayment({
		  provider: 'appleiap',
		  orderInfo: orderInfo,
		  success: (res) => {
			resolve(res);
		  },
		  fail: (err) => {
			reject(err);
		  }
		});
    });
  }

  restoreCompletedTransactions(username) {
    return new Promise((resolve, reject) => {
      this._channel.restoreCompletedTransactions({
        manualFinishTransaction: true,
        username
      }, (res) => {
        resolve(res);
      }, (err) => {
        reject(err);
      })
    });
  }

  finishTransaction(transaction) {
    return new Promise((resolve, reject) => {
      this._channel.finishTransaction(transaction, (res) => {
        resolve(res);
      }, (err) => {
        reject(err);
      });
    });
  }

  getChannels(success, fail) {
    if (this._channel !== null) {
      success(this._channel)
      return
    }

    if (this._channelError !== null) {
      fail(this._channelError)
      return
    }

    uni.getProvider({
      service: 'payment',
      success: (res) => {
        this._channel = res.providers.find((channel) => {
          return (channel.id === 'appleiap')
        })

        if (this._channel) {
			
          success(this._channel)
        } else {
          this._channelError = {
            errMsg: 'paymentContext:fail iap service not found'
          }
          fail(this._channelError)
        }
      }
    });
  }

  get channel() {
    return this._channel;
  }
}

export {
  Iap,
  IapTransactionState
}


页面上的调用

	import {
		Iap,
		IapTransactionState
	} from "./iap.js"
	export default {
		data() {
			return {
				constants: {},
				selected: 0, // 选择的套餐
				productList: [], // 套餐列表
				token: '',
				userInfo: {}, // 用户信息
				loading: false,
				paytype: 1, // 支付方式
				meal_id: 1, // 套餐ID与苹果那边添加的规则要对应上
				osType: '', // 判断客户端类型ios android
				disabled: true,
				productId: '', // 选择的产品id
				productIds: [] // 内购产品productid列表
			}
		},
		onLoad() {
			this.userInfo = uni.getStorageSync('userInfo');
			this.getUser();
			this.getMeal(); // 套餐列表
		},
		onShow() {
			if (this.osType == 'ios') {
				if (this._iap.ready) {
					this.restore();
				}
			}
		},
		methods: {
		// 获取登录用户信息
			getUser() {
				uni.$u.http.post('/user/index', {})
					.then(({
						data
					}) => {
						this.userInfo = data
						uni.setStorageSync('userInfo', this.userInfo)
					});
			},
			// 获取套餐列表
			getMeal() {

				uni.$u.http.post('/msg/meal', {})
					.then(({
						data
					}) => {
						this.meal_id = data[0].id; // 默认第一个选中
						this.productList = data;
						var productIds = [];
						data.forEach(item => {
							productIds.push('p'+item.id);
						})
						this.productIds = productIds;
						this.disabled = false;
						
						uni.getSystemInfo({
							success: (e) => {
								if (e.platform == 'ios') {
									// 创建示例
									this._iap = new Iap({
										products: [] // 苹果开发者中心创建
									})
									this.init();
								}
						}})
					})
			},
			submit() {
				if (this.loading) return;
				var that = this;
				var params = {}
				params.meal_id = this.meal_id;
				if (this.osType == 'ios') {
					params.paytype = 3;
				} else {
					params.paytype = this.paytype;
				}
				this.loading = true;
				// 后端生成订单
				uni.$u.http.post('/msg/order', params)
					.then(({data}) => {
						if (this.osType == 'ios') {
							this.payment(data.orderId)
						} else {
							// 其他支付
						}
						this.loading = false;
					})
					.catch(err => {
						this.loading = false;
					})
			},
			selectItem(index) {
				this.selected = index
				this.meal_id = this.productList[index].id;
			},
			selectPay(index) {
				this.payList[0].checked = false;
				this.payList[1].checked = false;
				this.payList[index].checked = true;
				this.paytype = this.payList[index].value;
			},
			async init() {
				uni.showLoading({
					title: '检测支付环境...'
				});

				try {
					// 初始化,获取iap支付通道
					await this._iap.init();
					this.requestOrder(); // 这步必须

					// 从苹果服务器获取产品列表
					// this.productList = await this._iap.getProduct(this.productIds);
					// this.selected = 0;
					// this.productId = this.productList[0].productid;

					// 填充产品列表,启用界面
					this.disabled = false;
				} catch (e) {
					uni.showModal({
						title: "提示",
						content: e.errMsg ? e.errMsg : (e.message ? e.message : '请求失败'),
						showCancel: false
					});
				} finally {
					uni.hideLoading();
				}

				if (this._iap.ready) {
					this.restore();
				}
			},
			// 必须请求
			requestOrder() {
			    this._iap.requestOrder(this.productIds, (orderList) => { //必须调用此方法才能进行 iap 支付
			        uni.hideLoading();
			    }, (e) => {
			        uni.hideLoading();
					uni.showToast({
						title:'初始化订单失败',
						icon:'none'
					})
			    });
			},
			async restore() {
				// 检查上次用户已支付且未关闭的订单,可能出现原因:首次绑卡,网络中断等异常

				// 在此处检查用户是否登陆

				uni.showLoading({
					title: '正在检测已支付且未关闭的订单...'
				});

				try {
					// 从苹果服务器检查未关闭的订单,可选根据 username 过滤,和调用支付时透传的值一致
					const transactions = await this._iap.restoreCompletedTransactions({
						username: this.userInfo.username
					});

					if (!transactions.length) {
						return;
					}

					// 开发者业务逻辑,从服务器获取当前用户未完成的订单列表,和本地的比较
					// 此处省略

					switch (transaction.transactionState) {
						case IapTransactionState.purchased:
							// 用户已付款,在此处请求开发者服务器,在服务器端请求苹果服务器验证票据
							let result = await this.validatePaymentResult();

							// 验证通过,交易结束,关闭订单
							if (result) {
							  await this._iap.finishTransaction(transaction);
							}
							break;
						case IapTransactionState.failed:
							// 关闭未支付的订单
							await this._iap.finishTransaction(transaction);
							break;
						default:
							break;
					}
				} catch (e) {
					uni.showModal({
						content: e.message,
						showCancel: false
					});
				} finally {
					uni.hideLoading();
				}
			},
			// 支付
			async payment(orderId) {
				// if (this.loading == true) {
				// 	return;
				// }
				// this.loading = true;

				uni.showLoading({
					title: '支付处理中...'
				});

				try {
					// 请求苹果支付
					const transaction = await this._iap.requestPayment({
						productid: 'prod'+this.meal_id, // 与苹果添加的id对应
						// manualFinishTransaction: true,
						username: this.userInfo.username+'-'+orderId //根据业务需求透传参数,关联用户和订单关系
					});

					// 在此处请求开发者服务器,在服务器端请求苹果服务器验证票据
					await this.validatePaymentResult({
					  orderId: orderId,
					  receipt: {
						  username: this.userInfo.username,
						  transactionReceipt: transaction.transactionReceipt, // 不可作为订单唯一标识
						  transactionIdentifier: transaction.transactionIdentifier
					  }
					});

					// 验证成功后关闭订单
					await this._iap.finishTransaction(transaction);

					this.loading = false;
					uni.hideLoading();
					// 支付成功
				} catch (e) {
					this.loading = false;
					uni.hideLoading();
					uni.showModal({
						content: e.message ? e.message : '支付失败',
						showCancel: false
					});
				} finally {
					this.loading = false;
					uni.hideLoading();
				}
			},
			// 能过后台验证支付
			validatePaymentResult(data) {
				return new Promise((resolve, reject) => {
					if (data) {
						uni.$u.http.post('/msg/checkorder', data)
						.then(({data}) => {
							uni.showToast({
								title:'支付成功',
								icon:'none'
							})
							resolve(data)
						})
						.catch(err => {
							reject(err)
						})
					} else {
						resolve()
					}
				});
			}
		},
	};


uniapp,苹果,ios内购,ios支付,苹果支付,内购


站点声明:部分内容源自互联网,为传播信息之用,如有侵权,请联系我们删除。

© Copyright 2011-2024 www.kfju.com. All Rights Reserved.
超级字帖 版权所有。 蜀ICP备12031064号      川公网安备51162302000234