一、介绍
支付宝的集成还是比较简单的,按照文档来一步步操作,基本上很顺利。不过,仍然有两个地方会是坑。这里我集成成功了,在此整理一下。说先说一下我遇到的坑如下:
第一个坑:下载的SDK文件AliPay.bundle和AliPay.framework一直报错,找不到库,没法使用。什么原因,我暂时还不知道。
解决办法:将官方提供的demo中SDK文件拖入项目中,替换掉自己下载的SDK即可
第二个坑:拖入的openssl目录下的所有#include <openssl/xxx.h>找不到路径。原因是在demo中openssl目录直接被放到了项目根目录下,而我们拖入是被放到了工程目录下,路径不一致,需要更改路径。
解决办法:在Build setting下设置Header Search Path路径。
例如我的路经设置图为,是根据下面图显示的openssl设置的:
二、看看我的项目图
三、准备
(1)在支付宝开发者平台注册登录账号创建应用获取appid,蚂蚁金服开放平台(open.alipay.com)
(2)配置密钥,开发者调用接口前需要先生成RSA密钥,RSA密钥包含应用私钥(APP_PRIVATE_KEY)、应用公钥(APP_PUBLIC_KEY)。生成密钥后在开放平台管理中心进行密钥配置,配置完成后可以获取支付宝公钥(ALIPAY_PUBLIC_KEY)。详细步骤请参考《配置应用环境》。
(3)集成并配置sdk,要将库添加完整(下面有一个libPods-xxx这个是使用cocopods开发项目自动生成的,没有使用cocoPods开发的不用管)
注意:在xcode8.0后,需要再多添加一个依赖库SystemConfiguration.framework,不然要报错了。
(4)设置URL Schemes,这个必须保证唯一性,因为支付完成后会根据这个调回到我们自己的app,我将这个在pch中做了定义,值必须保持一样
四、使用
在pch设置宏定义并导入头文件
// Prefix header
// 夏远全
// The contents of this file are implicitly included at the beginning of every source file.
// #import <Availability.h> #ifndef __IPHONE_5_0
#warning "This project uses features only available in iOS SDK 5.0 and later."
#endif #ifdef __OBJC__
#import <UIKit/UIKit.h>
#import <Foundation/Foundation.h>
#import <AlipaySDK/AlipaySDK.h> //支付宝SDK
#import "PayManager.h" //支付宝调起支付类
#import "DataSigner.h" //支付宝签名类
#import "Order.h" //订单模型
#import "APAuthV2Info.h" //授权模型 /**
-----------------------------------
支付宝支付需要配置的参数
-----------------------------------
*/ //开放平台登录https://openhome.alipay.com/platform/appManage.htm //管理中心获取APPID
#define AlipayAPPID @"xxxxxxxxx" //管理中心获取PIDID
#define PIDID @"xxxxxxxxx" //支付宝私钥(用户自主生成,使用pkcs8格式的私钥,文档上提供了两种生成方式,自己去选择吧)
#define AlipayPrivateKey @"xxxxxxxxx" //应用注册scheme,在AliSDKDemo-Info.plist定义URL types
#define URLScheme @"AliPayKit" //支付宝支付接口
#define AlipayUrl @"alipay.trade.app.pay" #endif
在AppDelegate.m中回调
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication
annotation:(id)annotation
{
if ([url.host isEqualToString:@"safepay"]) {
//支付跳转支付宝钱包进行支付,处理支付结果
[[AlipaySDK defaultService] processOrderWithPaymentResult:url standbyCallback:^(NSDictionary *resultDic) {
NSLog(@"result = %@",resultDic);
}]; // 授权跳转支付宝钱包进行支付,处理支付结果
[[AlipaySDK defaultService] processAuth_V2Result:url standbyCallback:^(NSDictionary *resultDic) {
NSLog(@"result = %@",resultDic);
//解析 auth code
NSString *result = resultDic[@"result"];
NSString *authCode = nil;
if (result.length>) {
NSArray *resultArr = [result componentsSeparatedByString:@"&"];
for (NSString *subResult in resultArr) {
if (subResult.length > && [subResult hasPrefix:@"auth_code="]) {
authCode = [subResult substringFromIndex:];
break;
}
}
}
NSLog(@"授权结果 authCode = %@", authCode?:@"");
}];
}
return YES;
} // NOTE: 9.0以后使用新API接口
- (BOOL)application:(UIApplication *)app openURL:(NSURL *)url options:(NSDictionary<NSString*, id> *)options
{
if ([url.host isEqualToString:@"safepay"]) {
// 支付跳转支付宝钱包进行支付,处理支付结果
[[AlipaySDK defaultService] processOrderWithPaymentResult:url standbyCallback:^(NSDictionary *resultDic) {
NSLog(@"result = %@",resultDic);
}]; // 授权跳转支付宝钱包进行支付,处理支付结果
[[AlipaySDK defaultService] processAuth_V2Result:url standbyCallback:^(NSDictionary *resultDic) {
NSLog(@"result = %@",resultDic);
// 解析 auth code
NSString *result = resultDic[@"result"];
NSString *authCode = nil;
if (result.length>) {
NSArray *resultArr = [result componentsSeparatedByString:@"&"];
for (NSString *subResult in resultArr) {
if (subResult.length > && [subResult hasPrefix:@"auth_code="]) {
authCode = [subResult substringFromIndex:];
break;
}
}
}
NSLog(@"授权结果 authCode = %@", authCode?:@"");
}];
}
return YES;
}
在工具类PayManager.m中实现支付
// PayManager.m
// AliPayKit
//
// Created by 夏远全 on 16/12/20.
// Copyright © 2016年 广州市东德网络科技有限公司. All rights reserved.
// #import "PayManager.h" @implementation PayManager #pragma mark - 进行支付 +(void)openAliPayForPaying{ /*=========================================================*/
/*====客户端调用支付宝支付(实际操作请放到服务端)=================*/
/*=========================================================*/ //AppId和PrivateKey没有配置下的提示
if ([AlipayAPPID length] == || [AlipayPrivateKey length] == )
{
[self alertShow];
return;
} //将商品信息赋予AlixPayOrder的成员变量
Order* order = [Order new];
order.app_id = AlipayAPPID; // NOTE: app_id设置
order.method = AlipayUrl; // NOTE: 支付接口名称
order.charset = @"utf-8"; // NOTE: 参数编码格式 NSDateFormatter* formatter = [NSDateFormatter new];
[formatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
order.timestamp = [formatter stringFromDate:[NSDate date]];// NOTE: 当前时间点 order.version = @"1.0"; // NOTE: 支付版本
order.sign_type = @"RSA"; // NOTE: sign_type设置 // NOTE: 商品数据
order.biz_content = [BizContent new];
order.biz_content.body = @"我是测试数据";
order.biz_content.subject = @"";
order.biz_content.out_trade_no = [self generateTradeNO]; //订单ID(由商家自行制定)
order.biz_content.timeout_express = @"30m"; //超时时间设置
order.biz_content.total_amount = [NSString stringWithFormat:@"%.2f", 0.01];//商品价格 //将商品信息拼接成字符串
NSString *orderInfo = [order orderInfoEncoded:NO];
NSString *orderInfoEncoded = [order orderInfoEncoded:YES];
NSLog(@"orderSpec = %@",orderInfo); // NOTE: 获取私钥并将商户信息签名,外部商户的加签过程请务必放在服务端,防止公私钥数据泄露;
// 需要遵循RSA签名规范,并将签名字符串base64编码和UrlEncode
id<DataSigner> signer = CreateRSADataSigner(AlipayPrivateKey);
NSString *signedString = [signer signString:orderInfo]; // NOTE: 如果加签成功,则继续执行支付
if (signedString != nil) {
//应用注册scheme,在AliSDKDemo-Info.plist定义URL types
NSString *appScheme = URLScheme; // NOTE: 将签名成功字符串格式化为订单字符串,请严格按照该格式
NSString *orderString = [NSString stringWithFormat:@"%@&sign=%@",
orderInfoEncoded, signedString]; // NOTE: 调用支付结果开始支付
[[AlipaySDK defaultService] payOrder:orderString fromScheme:appScheme callback:^(NSDictionary *resultDic) {
NSLog(@"reslut = %@",resultDic);
}];
}
} #pragma mark - 随机字符串
//==============产生随机订单号==============
+ (NSString *)generateTradeNO
{
static int kNumber = ;
NSString *sourceStr = @"0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
NSMutableString *resultStr = [[NSMutableString alloc] init];
srand((unsigned)time());
for (int i = ; i < kNumber; i++)
{
unsigned index = rand() % [sourceStr length];
NSString *oneStr = [sourceStr substringWithRange:NSMakeRange(index, )];
[resultStr appendString:oneStr];
}
return resultStr;
} #pragma mark - 提示信息
+(void)alertShow{ //去除警告
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wdeprecated-declarations" //AppId和PrivateKey没有配置下的提示
if ([AlipayAPPID length] == || [AlipayPrivateKey length] == )
{
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"提示"
message:@"缺少appId或者私钥。"
delegate:self
cancelButtonTitle:@"确定"
otherButtonTitles:nil];
[alert show];
}
#pragma clang diagnostic pop
} @end
五、模拟器和真机演示的截图如下:
首先我生成的私钥如下:
支付截图:
完成的demo地址,github:https://github.com/xiayuanquan/AliPaykit,希望有帮助