#import "IAPManager.h" #import @interface IAPManager () @property (nonatomic, strong) NSArray *products; @property (nonatomic, strong) NetHttpsManager *httpsManager; @property (nonatomic, copy) IAPCompletionBlock completionBlock; @end @implementation IAPManager + (instancetype)sharedManager { static IAPManager *manager; static dispatch_once_t onceToken; dispatch_once(&onceToken, ^{ manager = [[self alloc] init]; [[SKPaymentQueue defaultQueue] addTransactionObserver:manager]; }); return manager; } #pragma mark - 获取商品信息 - (void)fetchProducts:(NSArray *)productIds { NSSet *productIDs = [NSSet setWithArray:productIds]; SKProductsRequest *request = [[SKProductsRequest alloc] initWithProductIdentifiers:productIDs]; request.delegate = self; [request start]; NSLog(@"fetchProducts: %@",productIDs); } - (void)productsRequest:(SKProductsRequest *)request didReceiveResponse:(SKProductsResponse *)response { self.products = response.products; SKProduct *p = response.products.firstObject; NSLog(@"商品: %@, 价格: %@", p.localizedTitle, p.price); if (!p) { [[BGHUDHelper sharedInstance] tipMessage:ASLocalizedString(@"无法获取产品信息,购买失败。")]; [SVProgressHUD dismiss]; if (self.completionBlock) self.completionBlock(NO, 0, nil); return; } SKPayment *payment = [SKPayment paymentWithProduct:p]; [[SKPaymentQueue defaultQueue] addPayment:payment]; } #pragma mark - 购买 - (void)buyProduct:(NSString *)productId completion:(IAPCompletionBlock)completion { _completionBlock = completion; if ([SKPaymentQueue canMakePayments]) { [SVProgressHUD setDefaultMaskType:SVProgressHUDMaskTypeClear]; [SVProgressHUD showWithStatus:ASLocalizedString(@"正在提交iTunes Store,请等待...")]; [self fetchProducts:@[productId]]; } else { [FanweMessage alert:ASLocalizedString(@"您已禁止应用内付费购买商品")]; } } #pragma mark - 交易回调 - (void)paymentQueue:(SKPaymentQueue *)queue updatedTransactions:(NSArray *)transactions { for (SKPaymentTransaction *transaction in transactions) { switch (transaction.transactionState) { case SKPaymentTransactionStatePurchased://交易完成 NSLog(@"transactionIdentifier = %@", transaction.transactionIdentifier); [self completeTransaction:transaction]; break; case SKPaymentTransactionStateFailed://交易失败 NSLog(@"%@", ASLocalizedString(@"交易失败")); [self failedTransaction:transaction]; break; case SKPaymentTransactionStateRestored://恢复已购买商品 NSLog(@"%@", ASLocalizedString(@"恢复已购买商品")); [self restoreTransaction:transaction]; [queue finishTransaction:transaction]; break; case SKPaymentTransactionStatePurchasing: break; case SKPaymentTransactionStateDeferred: break; } } } #pragma mark - 掉单检查 - (void)checkUnfinishedTransactions { NSArray *transactions = [SKPaymentQueue defaultQueue].transactions; for (SKPaymentTransaction *transaction in transactions) { if (transaction.transactionState == SKPaymentTransactionStatePurchased) { [self completeTransaction:transaction]; // 再次验证并发货 } } } - (void)completeTransaction:(SKPaymentTransaction *)transaction { NSURL *receiptURL = [[NSBundle mainBundle] appStoreReceiptURL]; NSData *receiptData = [NSData dataWithContentsOfURL:receiptURL]; NSString *receiptString = [receiptData base64EncodedStringWithOptions:0]; if ([receiptString length] > 0) { // 保存本地(掉单恢复使用) [[NSUserDefaults standardUserDefaults] setObject:receiptString forKey:@"lastReceipt"]; [[NSUserDefaults standardUserDefaults] synchronize]; // 向自己的服务器验证购买凭证 [self shoppingTransaction:transaction receiptString:receiptString retryCount:3]; } else { [SVProgressHUD dismiss]; [[SKPaymentQueue defaultQueue] finishTransaction: transaction]; if (self.completionBlock) self.completionBlock(NO, 0, nil); } } #pragma mark -- 向自己的服务器验证购买凭证 - (void)shoppingTransaction:(SKPaymentTransaction *)transaction receiptString:(NSString *)receiptString retryCount:(NSInteger)retryCount { retryCount--; if (retryCount <= 0) { [SVProgressHUD dismiss]; [FanweMessage alert:ASLocalizedString(@"支付失败")]; return; } NSMutableDictionary *dict = [NSMutableDictionary dictionaryWithCapacity:0]; // if (_is_vip) // { // [dict setObject:@"vip_pay" forKey:@"ctl"]; // } // else // { [dict setObject:@"pay" forKey:@"ctl"]; // } [dict setObject:@"iappay" forKey:@"act"]; NSString *userid = [IMAPlatform sharedInstance].host.imUserId; [dict setObject:userid forKey:@"user_id"]; [dict setObject:receiptString forKey:@"receipt-data"]; [self.httpsManager POSTWithParameters:dict SuccessBlock:^(NSDictionary *responseJson) { [SVProgressHUD dismiss]; NSInteger diamonds = [[responseJson objectForKey:@"total_diamonds"] integerValue]; if (self.completionBlock) self.completionBlock(YES, diamonds, nil); [FanweMessage alert:ASLocalizedString(@"充值成功")]; [[SKPaymentQueue defaultQueue] finishTransaction:transaction]; [[NSUserDefaults standardUserDefaults] removeObjectForKey:@"lastReceipt"]; } FailureBlock:^(NSError *error) { dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(2.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ [self shoppingTransaction:transaction receiptString:receiptString retryCount:retryCount]; }); }]; } - (void)failedTransaction:(SKPaymentTransaction *)transaction { [SVProgressHUD dismiss]; if(transaction.error.code == SKErrorPaymentCancelled) { [FanweMessage alert:ASLocalizedString(@"您已经取消交易")]; } else { [FanweMessage alert:ASLocalizedString(@"购买失败")]; } [[SKPaymentQueue defaultQueue] finishTransaction: transaction]; if (self.completionBlock) self.completionBlock(NO, 0, nil); } - (void)restoreTransaction:(SKPaymentTransaction *)transaction { // 对于已购商品,处理恢复购买的逻辑 //[[SKPaymentQueue defaultQueue] finishTransaction: transaction]; [[SKPaymentQueue defaultQueue] restoreCompletedTransactions]; } #pragma mark - 恢复购买 - (void)handleRestore:(SKPaymentTransaction *)transaction { NSLog(@"恢复购买: %@", transaction.payment.productIdentifier); } - (void)restorePurchases { [[SKPaymentQueue defaultQueue] restoreCompletedTransactions]; } - (NetHttpsManager *)httpsManager { if (!_httpsManager) { _httpsManager = [NetHttpsManager manager]; } return _httpsManager; } @end