ios支付,帶本地伺服器驗證
.h檔案:
- #import <StoreKit/StoreKit.h>
- @interface SDKApplePay : NSObject <SKProductsRequestDelegate,SKPaymentTransactionObserver>{
- SKProductsRequest* _curProductRequest;
- NSMutableDictionary* _curActualProducts; //實際可購買列表
- NSString* _curAppId;
- bool receiptValid;
- #if __IPHONE_OS_VERSION_MAX_ALLOWED < __IPHONE_8_0
- UIAlertView *alertViewTest;
- #else
- UIAlertController *alertController;
- #endif
- }
- + (SDKApplePay*) getInstance;
- - (void) initSDK:(UIViewController *)viewController sdkName:(NSString *)sdkName;
- - (void)requestProductsValidate:(NSDictionary*)productsDict;
- - (void)requestProductsPay:(NSString*)productsDict;
- @end
.mm檔案:
- #import "SDKApplePay.h"
- #import "Util.h"
- #import "JSCallObjectCBridge.h"
- #define MyServerURL @"你的伺服器網址"//伺服器請求的地址
- #define DebugModel @"0" //@"sandbox" 沙盒測試 @"0" 正常購買
- @implementation SDKApplePay
- static NSString* const SDK_IAP_PREFIX_PRODUCT=@"com.xxxx.xxxx.";
- static SDKApplePay* curInstance=
- + (SDKApplePay*) getInstance
- {
- if(nil==curInstance)
- {
- curInstance = [[SDKApplePay alloc] init];
- }
- return curInstance;
- }
- - (void)requestProductsValidate:(NSDictionary*)productsDict
- {
- NSMutableSet* productsSet = [NSMutableSet set];
- for(NSString* key in productsDict)
- {
- [productsSet addObject:[NSString stringWithFormat:@"%@%@",SDK_IAP_PREFIX_PRODUCT,key]];
- }
- _curProductRequest=[[SKProductsRequest alloc] initWithProductIdentifiers:productsSet];
- _curProductRequest.delegate=self;
- [_curProductRequest start];
- }
- //購買時的呼叫方法
- - (void)requestProductsPay:(NSString*)productsDict
- {
- if(nil==productsDict){
- //引數為空,呼叫違法
- return;
- }
- if([SKPaymentQueue canMakePayments])
- {
- NSString* curProductIdentifier = nil;
- if(nil!=productsDict){
- curProductIdentifier = productsDict;
- }
- SKProduct* actualProduct = [_curActualProducts objectForKey:curProductIdentifier];
- SKPayment* payment = [SKPayment paymentWithProduct:actualProduct];
- [[SKPaymentQueue defaultQueue] addPayment:payment];
- }else
- {
- //TODO 通知使用者無法進行購買
- }
- }
- //-----------------override---------------
- - (void) initSDK:(UIViewController *)viewController sdkName:(NSString *)sdkName
- {
- _curActualProducts=[[NSMutableDictionary alloc] init];
- NSMutableDictionary* mm = [[NSMutableDictionary alloc] init];
- [mm setObject:@"buy01" forKey:@"buy01"];
- [mm setObject:@"buy02" forKey:@"buy02"];
- [mm setObject:@"buy13" forKey:@"buy13"];
- [mm setObject:@"buy04" forKey:@"buy04"];
- [self requestProductsValidate:mm];
- [[SKPaymentQueue defaultQueue] addTransactionObserver:self];
- }
- //-----------------implements--------------
- - (void) productsRequest:(SKProductsRequest *)request didReceiveResponse:(SKProductsResponse *)response
- {
- NSArray<SKProduct*>* productList=response.products;
- long count = productList.count;
- [_curActualProducts removeAllObjects];
- for(int i=0;i-count<0;i++)
- {
- SKProduct* curProduct = [productList objectAtIndex:i];
- [_curActualProducts setObject:curProduct forKey:curProduct.productIdentifier];
- }
- [_curProductRequest release];
- //======!!!!!購買時的呼叫方法
- //[self requestProductsPay:nil];
- }
- - (void) paymentQueue:(SKPaymentQueue *)queue removedTransactions:(NSArray<SKPaymentTransaction *> *)transactions
- {
- NSLog(@"removedTransactions");
- }
- - (void) paymentQueue:(SKPaymentQueue *)queue restoreCompletedTransactionsFailedWithError:(NSError *)error
- {
- NSLog(@"restoreCompletedTransactionsFailedWithError");
- //[self processRestoreFailed:queue error:error];
- }
- - (void) paymentQueue:(SKPaymentQueue *)queue updatedDownloads:(NSArray<SKDownload *> *)downloads
- {
- NSLog(@"updatedDownloads");
- }
- //購買結果發的回撥
- - (void) paymentQueue:(SKPaymentQueue *)queue updatedTransactions:(NSArray<SKPaymentTransaction *> *)transactions
- {
- NSLog(@"==[開始處理使用者交易操作]");
- for (SKPaymentTransaction *transaction in transactions)
- {
- NSLog(@"======[獲得使用者操作碼]:%d",(int)transaction.transactionState);
- switch (transaction.transactionState)
- {
- case SKPaymentTransactionStatePurchasing:
- NSLog(@"SKPaymentTransactionStatePurchasing");
- break;
- case SKPaymentTransactionStatePurchased:
- //購買成功
- NSLog(@"SKPaymentTransactionStatePurchased:%@",transaction.payment.productIdentifier);
- //進行回撥處理
- [self completeTransaction:transaction];
- break;
- case SKPaymentTransactionStateFailed:
- //購買失敗
- NSLog(@"SKPaymentTransactionStateFailed");
- [self failedTransaction:transaction];
- break;
- case SKPaymentTransactionStateRestored:
- //已經購買過該商品
- NSLog(@"SKPaymentTransactionStateRestored");
- [self restoreTransaction:transaction];
- break;
- case SKPaymentTransactionStateDeferred:
- NSLog(@"SKPaymentTransactionStateDeferred");
- break;
- default:
- break;
- }
- }
- NSLog(@"==[結束處理使用者交易操作!]");
- }
- - (void) paymentQueueRestoreCompletedTransactionsFinished:(SKPaymentQueue *)queue
- {
- NSLog(@"removedTransactions");
- }
- //向伺服器請求驗證
- - (void) verifyReceiptFromMyServer:(SKPaymentTransaction *)transaction
- {
- //初始化為合法
- if (transaction.payment.productIdentifier !=nil) {
- //base64 encode the receipt data for sending
- if ([transaction.transactionReceipt base64Encoding] != nil) {
- //將資料http post請求傳送到我的伺服器
- NSURL* url = [NSURL URLWithString:MyServerURL];
- NSMutableURLRequest* theRequest = [NSMutableURLRequest requestWithURL:url];
- [theRequest setHTTPMethod:@"POST"];
- //修改通訊方式
- NSString * productIdentifier = transaction.payment.productIdentifier;
- NSString *transactionReceiptString= nil;
- //系統IOS7.0以上獲取支付驗證憑證的方式應該改變,切驗證返回的資料結構也不一樣了。
- // if([[UIDevice currentDevice].systemVersion floatValue]>=7.0){
- // NSURLRequest*appstoreRequest = [NSURLRequest requestWithURL:[[NSBundle mainBundle]appStoreReceiptURL]];
- // NSError *error = nil;
- // NSData * receiptData = [NSURLConnection sendSynchronousRequest:appstoreRequest returningResponse:nil error:&error];
- // NSLog(@"+++apple_receipt:\n%@+++",receiptData);
- // //transactionReceiptString = [receiptData base64EncodedStringWithOptions:NSDataBase64EncodingEndLineWithLineFeed];
- // //transactionReceiptString = [receiptData base64EncodedStringWithOptions:0];
- // transactionReceiptString = [self base64Encode:receiptData];
- // }
- // else{
- NSData * receiptData = transaction.transactionReceipt;
- NSLog(@"+++apple_receipt:\n%@+++",receiptData);
- //transactionReceiptString = [receiptData base64EncodedString];
- transactionReceiptString = [self base64Encode:receiptData];
- // }
- NSLog(@"+++apple_receipt-base64:\n%@+++",transactionReceiptString);
- NSString *sendString = [NSString stringWithFormat:@"package_name=%@&product_id=%@&apple_receipt=\n%@&env=%@", @"com.tjyzy.dd2",productIdentifier,transactionReceiptString,DebugModel];
- NSLog(@"+++sendString:%@+++",sendString);
- [theRequest setHTTPBody:[sendString dataUsingEncoding:NSUTF8StringEncoding]];
- //傳送同步請求 因為你將使用自己的伺服器返回的資料來判斷是否成功
- NSURLResponse* response = [[NSURLResponse alloc] init];
- NSError* myerror = [[NSError alloc] init];
- NSMutableData* receiveData = (NSMutableData *)[NSURLConnection sendSynchronousRequest:theRequest returningResponse:&response error:&myerror];
- //NSURLConnection* theConnection = [[NSURLConnection alloc] initWithRequest:theRequest delegate:self];
- //接收到伺服器返回的資料
- NSString *receiptStatus = [[NSString alloc] initWithBytes: [receiveData mutableBytes] length:[receiveData length] encoding:NSUTF8StringEncoding];
- NSLog(@"\nreceiptStatus=%@",receiptStatus);
- NSString* str = @"\"errno\":0";
- if ([receiptStatus length]==0 || [receiptStatus isEqualToString:@""]) {
- receiptValid = false;
- }else{
- //轉換成二進位制資料
- NSData * data = [receiptStatus dataUsingEncoding:NSUTF8StringEncoding];
- //解析JSON檔案 OC中自帶的方法
- NSDictionary *dict = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
- int receivCode = [[dict objectForKey:@"errno"] intValue];
- if(receivCode==0){
- NSLog(@"++++伺服器通訊成功++++");
- receiptValid = true;
- }else{
- NSLog(@"++++伺服器通訊失敗++++錯誤碼為:%d",receivCode);
- receiptValid = false;
- }
- }
- // [receiptStatus release];
- // [myerror release];
- // [response release];
- } else {
- NSLog(@"當向伺服器傳送驗證資料時出錯!!!");
- receiptValid = false;
- }
- }
- else
- {
- NSLog(@"無效的商品ID");
- receiptValid = false;
- }
- }
- //將NSData64位編碼
- - (NSString*) base64Encode:(NSData *)theData
- {
- const uint8_t* input = (const uint8_t*)[theData bytes];
- NSInteger length = [theData length];
- staticchar table[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";
- NSMutableData* data = [NSMutableData dataWithLength:((length + 2) / 3) * 4];
- uint8_t* output = (uint8_t*)data.mutableBytes;
- NSInteger i;
- for (i=0; i < length; i += 3) {
- NSInteger value = 0;
- NSInteger j;
- for (j = i; j < (i + 3); j++) {
- value <<= 8;
- if (j < length) {
- value |= (0xFF & input[j]);
- }
- }
- NSInteger theIndex = (i / 3) * 4;
- output[theIndex + 0] = table[(value >> 18) & 0x3F];
- output[theIndex + 1] = table[(value >> 12) & 0x3F];
- output[theIndex + 2] = (i + 1) < length ? table[(value >> 6) & 0x3F] : '=';
- output[theIndex + 3] = (i + 2) < length ? table[(value >> 0) & 0x3F] : '=';
- }
- //return [[[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding] autorelease];
- return [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding];
- }
- //購買成功
- - (void) completeTransaction: (SKPaymentTransaction *)transaction
- {
- receiptValid = false;
- //進行伺服器驗證
- [self verifyReceiptFromMyServer:transaction];//這個方法是內支付最重要的方法
- if (receiptValid) {
- //給物品
- [[JSCallObjectCBridge getInstance] applePaySuccess:transaction.payment.productIdentifier];
- } else {
- //[self failedTransaction:transaction];
- }
- [[SKPaymentQueue defaultQueue] finishTransaction:transaction];
- }
- //購買恢復交易
- - (void) restoreTransaction: (SKPaymentTransaction *)transaction
- {
- NSLog(@" 交易恢復處理");
- //給物品
- [[JSCallObjectCBridge getInstance] applePaySuccess:transaction.payment.productIdentifier];
- [[SKPaymentQueue defaultQueue] finishTransaction:transaction];
- }
- //購買失敗
- - (void) failedTransaction: (SKPaymentTransaction *)transaction{
- NSLog(@"失敗");
- if (transaction.error.code != SKErrorPaymentCancelled)
- {
- //提示購買失敗
- UIAlertView *alerView2 = [[UIAlertView alloc] initWithTitle:@"Pay Result"
- message:@"Payment failed, Please try again!"
- delegate:nil cancelButtonTitle:NSLocalizedString(@"Close",nil) otherButtonTitles:nil];
- [alerView2 show];
- [alerView2 release];
- }
- [[SKPaymentQueue defaultQueue] finishTransaction: transaction];
- }
- -(void)dealloc
- {
- [[SKPaymentQueue defaultQueue] removeTransactionObserver:self];//解除監聽
- [super dealloc];
- }
- @end
PS:上面的程式碼部分,再檢視某些文章時,發現“系統IOS7.0以上獲取支付驗證憑證的方式應該改變,切驗證返回的資料結構也不一樣了”,最後通過實際專案發現支付驗證憑證採用原來的方式“transaction.transactionReceipt”即可。
使用方法:
1 在AppController.mm中進行初始化:
在函式“- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions”中
呼叫“[[SDKApplePay getInstance] initSDK:viewController sdkName:@"applepay"];“進行初始化;
2 在需要呼叫支付的部分呼叫支付程式碼:
[[SDKApplePay getInstance] requestProductsPay:appleProductId]; 支付道具的id(appleProductId的值)例:com.xxxx.xxxx.buy01
這個id是你在蘋果後臺申請的id。
相關推薦
ios支付,帶本地伺服器驗證
直接上程式碼..... .h檔案: #import <StoreKit/StoreKit.h>@interface SDKApplePay : NSObject <SKProductsRequestDelegate,SKPaymentTransacti
最近在做支付寶支付,在本地測試一切正常,上傳到服務器就遇到報錯:
-1 tail 服務 war tar nbsp 百度 nature function 最近在做支付寶支付,在本地測試一切正常,上傳到服務器就遇到報錯: Warning: openssl_sign() [function.openssl-sign]: Unknown sign
xcode 7.0後,網路載入失敗,以及本地伺服器資源載入失敗解決
在專案的info.plist 中新新增一項為NSAppTransportSecurity 型別為Dictionary 點選這一項,注意該項箭頭向下時新新增子項 NSAllowsArbitraryLoads ,型別為BOOL 型別, 值為YES
微信小程序支付,帶java源碼
項目 event fine 監聽 java源碼 ide otto area 也有 先說下這個的背景吧。。。 本人是做java後端的,自認為還有很大的發展空間(嘻嘻,你懂的),看過一段時間的小程序可是沒有支付成功。。。最近公司要做小程序項目,老大讓我看
Unity內IAP支付二次驗證/伺服器驗證————最白話,手把手教你做系列。
之前的一篇寫了Unity支付的IAP支付接入。 後來就出現了一些問題,資料統計的時候出現大量購買訂單。但是實際上賬戶的錢卻沒有增加。@¥……&¥……*@¥&@初步判定可能存在部分使用者通過其他渠道刷單的現象,然後才有以下操作,驗證使用者的訂單是
iOS啟動圖-從網絡獲取的gif圖,在本地一直是沒有動畫,還模糊的
ads dad microsoft view text isequal sof nload conn 背景介紹:APP啟動頁,常有靜態圖加鏈接,gif加鏈接,短視頻等幾種形式。我們APP前期只有靜態圖這一種,功能已經實現。之後,有了添加gif的需求,按理說,只要添加一個類型
【支付寶支付】掃碼付和app支付,回調驗證簽名失敗問題
界面 排序 div nbsp 參數 解碼 app支付 bsp api 在檢查了參數排序,編碼解碼,文件編碼等問題後,發現還是簽名失敗,最後找出原因: 掃碼付和app支付采用的支付寶公鑰不一樣 Pid和公鑰管理裏面: 開放平臺密鑰界面和開放平臺應用界面的密鑰應該一致,
nginx功能之一可以啟動一個本地伺服器,通過配置server_name和root目錄等來訪問目標檔案
一. 下載 http://nginx.org/ 下載後解壓 二. 修改配置檔案 nginx配置檔案在 nginx-1.8.0\conf\nginx.conf http { #壓縮html
利用github和git命令,將本地專案共享到伺服器上
一、步驟 1. 建立專案根目錄 mkdir 資料夾名 2. 初始化資料夾 git init 3. 配置使用者名稱和郵箱(第一次配置後,不需要再登入) git config user.name 名字 git config user.email 郵箱
html檔案直接可以瀏覽器開啟,為什麼很多人選擇本地伺服器localhost開啟?有什麼不一樣嗎?
最直接的區別,很容易注意到,一個是file協議,另一個是http協議。 --file協議更多的是將該請求視為一個本地資源訪問請求,和你使用資源管理器開啟是一樣的,是純粹的請求本地檔案。 --http請求方式則是通過假架設一個web伺服器,解析http協議的請求然後向瀏覽器返回資源資訊。我
微信支付非同步回撥,帶你解決微信支付的深坑
1.首先我們先下載微信支付的伺服器端demo 2.個檔案作用介紹 index.jsp 下單 payRequest.jsp 獲取微信支付prepay_id等。 重點我說說這個payNotifyUrl.jsp
iOS上傳影象到伺服器,以及伺服器PHP接收的幾種方法
iOS上傳影象到伺服器,以及伺服器PHP接收的幾種方法 1. 將圖片轉換為Base64編碼,POST上傳。PHP將Base64解碼為二進位制,再寫出檔案。缺點:不能上傳較大的圖片 // iOS(Swift) func upload(image: UIImage, url: S
關於專案本地執行未亂碼,上傳伺服器專案亂碼
如果是直接用其他編輯器(如visualCode、sublime等)寫的前端頁面。可能匯入myeclipse時,未在jsp頭部加上jsp頭部。 <%@ page language="java" import="java.util.*" pageEncoding="utf8"%> <
用nodejs搭建一個本地伺服器,以供本地介面獲取服務端資料
1、首先下載安裝好nodejs 64位的nodejs5.6.0下載地址: 5.6.0 nodejs,根據提示安裝在自己的電腦上即可 2、安裝好了,開啟cmd視窗,輸入命令:npm -v 檢驗nodejs是否安裝成功,如果出現以下介面則說明安裝成功了 3、輸入命令
python程式碼本地執行不報錯,上傳伺服器後報錯???
本地執行是成功的,程式碼也更新了,但在伺服器上執行程式碼就報錯了,500 Internal Server ErrorThe server encountered an internal error and was unable to complete your request. Either t
資料庫部署到linux伺服器,供本地訪問。
1. 將本地的sql檔案上傳至伺服器 scp /Users/fangke/Documents/article.sql [email protected]:/usr/local 2. 登陸伺服器的mysql 3. 建立資料庫 4. 執行
spring boot 讀取本地伺服器/本地硬碟上的圖片,避免圖片放在tomcat等伺服器下,windows系統為例
圖片放在主體專案所在伺服器以外的好處不言而喻,這裡以windows系統的E盤為例,E盤根目錄下放一張圖片,"test.jpg". 在後臺放置這樣一個類: import org.springframework.context.annotation.Configuration
【已解決】iphone 登出賬號的時候報錯:驗證失敗,連線到伺服器時出現問題
iphone 登出賬號的時候報錯:驗證失敗,連線到伺服器時出現問題,如下 在網上查了半天一點都沒有用 最後撥打的蘋果熱線,原來是蘋果的網路許可權的問題,預設的是把“設定”應用的網路關閉的,只需要把網路裡面“設定”這個應用的網路允許“WLAN與蜂窩行動網路”。 第
IP地址正則表示式,帶*驗證
IP地址正則表示式,在網上找了很多,但是沒有看到帶 ‘ * ’ 的正則表示式,通常我們在設定IP時,會設定IP段(0-255)或者用 ‘ * ’ 代替。 1、下為不帶 ‘ * ’ 的正則表示式 var checkName = /^(?:(?:1[0-9][0-9]\.)|
【微信小程式控制硬體②】 開始微信小程式之旅,匯入小程式Mqtt客戶端原始碼,實現簡單的驗證和通訊於伺服器!(附帶原始碼)
本博文由熱愛分享熱愛技術的半顆心臟原創,非官方人員、非組織名義編寫,博文如有不對或侵犯您的權益,請及時留言,第一時間糾正! 一、前言; 繼續我們的小程式控制智慧硬體(包括esp8266)學