iOS开发支付篇——内购(IAP)详解

栏目: IOS · 发布时间: 6年前

内容简介:先看gif图具体步骤:

先看gif图

iOS开发支付篇——内购(IAP)详解

具体步骤:

协议、税务和银行业务 信息填写

内购商品的添加

添加沙盒测试账号

内购代码的具体实现

内购的注意事项

流程

1.注册app,填写协议、税务和银行业务

注册app,需要唯一设置Bundle identifier,然后详细填写协议、税务和银行业务,此个步骤这里就不在写了

(【官方地址】(https://developer.apple.com/library/archive/technotes/tn2259/_index.html#//apple_ref/doc/uid/DTS40009578))。

2.内购商品的添加

我的App—>准提交的项目—>功能—>App内购买项目:添加内购商品信息

3.添加沙盒测试账号

iTunes Connect —>用户和职能 —>沙盒测试技术员:添加沙盒测试账号

4.代码实现过程

写了一个购买的单例

//
// VistaInAppPurchaseManager.h
// vista.homework
//
// Created by htkj on 2018/9/17.
// Copyright © 2018年 vista. All rights reserved.
#import
#import
@protocol VistaInAppPurchaseManagerDelegate <NSObject>
//接收到商品信息
-(void)receiveProductInfo:(SKProduct *)product;
//购买成功反馈
-(void)successfulPurchaseOfId:(NSString *)productID andReceipt:(NSData *)transactionReceipt;
//购买失败反馈
-(void)failedPurchaseWithError:(NSString *)errorDescripiton;
@end

@interface VistaInAppPurchaseManager : NSObject
@property (nonatomic, weak)id delegate;
//单例
+( instancetype)sharedInstance;
/*
* 请求商品信息,productID 商品ID
*/

-( void)requestProductWithID:( NSString *)productID;
/*
* 购买商品
*/

-( BOOL)purchaseProudct:( SKProduct *)skProduct;
@end
//
// VistaInAppPurchaseManager.m
// vista.homework
//
// Created by htkj on 2018/9/17.
// Copyright © 2018年 vista. All rights reserved.
//

#import "VistaInAppPurchaseManager.h"

@interface VistaInAppPurchaseManager ()<SKProductsRequestDelegate, SKPaymentTransactionObserver>


@end

@implementation VistaInAppPurchaseManager
{
SKProduct *myProduct;

}


static VistaInAppPurchaseManager *manager = nil;

+( instancetype)sharedInstance{
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
if (manager == nil) {
manager = [[VistaInAppPurchaseManager alloc]init];
}

});
return manager;
}

#pragma mark ------ public Methods
-( void)requestProductWithID:( NSString *)productID{
if (productID.length > 0) {
SKProductsRequest *productRequest = [[ SKProductsRequest alloc]initWithProductIdentifiers:[ NSSet setWithObject:productID]];
productRequest.delegate = self;
[productRequest start];

} else{

NSLog( @"productID为空");
}


}

-( BOOL)purchaseProudct:( SKProduct *)skProduct{

if (skProduct != nil) {
if ([ SKPaymentQueue canMakePayments]) {
SKPayment *payment = [ SKPayment paymentWithProduct:skProduct];
[[ SKPaymentQueue defaultQueue] addTransactionObserver: self];
[[ SKPaymentQueue defaultQueue] addPayment:payment];
return YES;
} else{
NSLog( @"失败,用户禁止应用内付费购买.");
}
}
return NO;
}

#pragma mark ------ SKProductsRequestDelegate

-( void)productsRequest:( SKProductsRequest *)request didReceiveResponse:( SKProductsResponse *)response{
NSArray *productArr = response.products;
if (productArr.count > 0) {
myProduct = [productArr objectAtIndex: 0];
[_delegate receiveProductInfo:myProduct];
} else{
NSLog( @"无法购买商品信息,购买失败");
[_delegate receiveProductInfo:myProduct];
}
}

#pragma mark ------ SKPaymentTransactionObserver

-( void)paymentQueue:( SKPaymentQueue *)queue updatedTransactions:( NSArray< SKPaymentTransaction *> *)transactions{
for ( SKPaymentTransaction *transaction in transactions) {
switch (transaction.transactionState) {
case SKPaymentTransactionStatePurchasing: //商品添加进列表
NSLog( @"商品:%@被添加进购买列表",myProduct.localizedTitle);
break;
case SKPaymentTransactionStatePurchased: //交易成功
[ self completeTransaction:transaction];
break;
case SKPaymentTransactionStateFailed: //交易失败
[ self failedTransaction:transaction];
NSLog( @"交易失败");
//发送通知
[[ NSNotificationCenter defaultCenter] postNotificationName: @"failNotification" object: self userInfo: nil];
break;
case SKPaymentTransactionStateRestored: //已购买过该商品
break;

case SKPaymentTransactionStateDeferred: //交易延迟
default:
break;
}
}
}


#pragma mark ---- private Methods

-( void)completeTransaction:( SKPaymentTransaction *)transaction{
NSURL *receiptUrl = [[ NSBundle mainBundle] appStoreReceiptURL];
NSData *receiptData = [ NSData dataWithContentsOfURL:receiptUrl];
[_delegate successfulPurchaseOfId:transaction.payment.productIdentifier andReceipt:receiptData];
// [[NSUserDefaults standardUserDefaults] setObject:receiptData forKey:@"receiptData"];
// [[NSUserDefaults standardUserDefaults] synchronize];
[[ SKPaymentQueue defaultQueue]finishTransaction:transaction];
}

- ( void)failedTransaction:( SKPaymentTransaction *)transaction{
if (transaction.error.code != SKErrorPaymentCancelled && transaction.error.code != SKErrorUnknown) {
[_delegate failedPurchaseWithError:transaction.error.localizedDescription];
}
[[ SKPaymentQueue defaultQueue] finishTransaction:transaction];
}

-( void)dealloc{
[[ SKPaymentQueue defaultQueue] removeTransactionObserver: self];
}

@end

导入单例

#import “VistaInAppPurchaseManager.h”

设置代理

VistaInAppPurchaseManagerDelegate

点击充值按钮事件

-(void)commitBtnClick{
    [self createhui];
    [MBProgressHUD showLoadToView:self.view title:@"支付中,请勿关闭App"];
    NSString *productID = nil;
    switch (purchaseType) {
        case 0:
            productID = @"Vista_coin_1";
            break;
        case 1:
            productID = @"Vista_coin_6";
            break;
        case 2:
            productID = @"Vista_coin_18";
            break;
        case 3:
            productID = @"Vista_coin_30";
            break;
        case 4:
            productID = @"Vista_coin_68";
            break;
        case 5:
            productID = @"Vista_coin_108";
            break;
        case 6:
            productID = @"Vista_coin_208";
            break;
        case 7:
            productID = @"Vista_coin_388";
            break;
        case 8:
            productID = @"Vista_coin_698";
            break;
        default:
            break;
    }
    if (productID == nil) {
        Hidden
        return;
    }
    [self.payManager requestProductWithID:productID];
}

代理方法

#pragma mark -----   VistaInAppPurchaseManagerDelegate
//购买商品回调
-(void)receiveProductInfo:(SKProduct *)product{
    Hidden
    if (product != nil) {
        if (![self.payManager purchaseProudct:product]) {
            UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"失败" message:@"您禁止了应用内购买权限,请到设置中开启" delegate:self cancelButtonTitle:@"关闭" otherButtonTitles:nil, nil];
            [alert show];
        }
        NSLog(@"SKProduct 描述信息%@", [product description]);
        NSLog(@"产品标题 %@" , product.localizedTitle);
        NSLog(@"产品描述信息: %@" , product.localizedDescription);
        NSLog(@"价格: %@" , product.price);
        NSLog(@"Product id: %@" , product.productIdentifier);
    }else{
        UIAlertView *alert = [[UIAlertView alloc]initWithTitle:@"失败" message:@"无法连接App store!" delegate:self cancelButtonTitle:@"关闭" otherButtonTitles:nil, nil];
        [alert show];
    }
     [self hidden];
}
#pragma mark-VistaInAppPurchaseManagerDelegate
//成功回调
//附加:官方文档:向苹果校验支付结果https://developer.apple.com/library/content/releasenotes/General/ValidateAppStoreReceipt/Chapters/ValidateRemotely.html
-(void)successfulPurchaseOfId:(NSString *)productID andReceipt:(NSData *)transactionReceipt{
    NSString *transactionReceiptString = [transactionReceipt base64EncodedStringWithOptions:NSDataBase64EncodingEndLineWithLineFeed];
    NSDictionary *dict = @{@"receipt-data":transactionReceiptString};
    NSString *str=[self conData11:dict];
    //上传支付凭证到后台
        NSDictionary *json = @{@"receipt":str};
        NSDictionary *Json=@{@"code":@"5077",@"payload":[HHCommon convertToJsonData:json],@"token":personalToken};
        [HTTPRequestManager postNetworkRequestWithUrlString:Com parameters:Json succeed:^(id data) {
            if ([data[@"code"] integerValue]==0&&[data[@"payload"][@"status"] integerValue]==0) {
                 [PHAlertView showTitle:@"充值成功!" message:@"" surnBtnTitle:@"确定" result:nil];
                [self loadmoney];
                [[NSUserDefaults standardUserDefaults] removeObjectForKey:@"receiptData"];
            }else{
                NSLog(@"%@",data[@"message"]);
            }
        } fail:^(NSError *error) {

        }];
}
//失败回调
- (void)failedPurchaseWithError:(NSString *)errorDescripiton {
    NSLog(@"购买失败");
    UIAlertView *alert = [[UIAlertView alloc]initWithTitle:@"失败" message:errorDescripiton delegate:self cancelButtonTitle:@"关闭" otherButtonTitles:nil, nil];
    [alert show];

}

作者:静RJM

原文:https://blog.csdn.net/RJM758859182/article/details/83303380


以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

爱上Arduino

爱上Arduino

Massimo Banzi / 于欣龙、郭浩赟 / 人民邮电出版社 / 2012-10 / 38.00元

《硬件开源电子设计平台:爱上Arduino(第2版)》全面透彻地介绍了arduino的相关内容,它会给你带来许多项目的点子,并帮助你顺利地实现从开始策划直到完成安装的全过程。由于《硬件开源电子设计平台:爱上Arduino(第2版)》是arduino项目合作创始人massimobanzi所著,其中一定融入了创始人对开源硬件的独到见解。《硬件开源电子设计平台:爱上Arduino(第2版)》内容完全考虑......一起来看看 《爱上Arduino》 这本书的介绍吧!

在线进制转换器
在线进制转换器

各进制数互转换器

XML 在线格式化
XML 在线格式化

在线 XML 格式化压缩工具

正则表达式在线测试
正则表达式在线测试

正则表达式在线测试