支付宝支付 /微信支付(iOS)  

支付宝流程


06FB153E-E539-4589-B7C7-2F9DA5923AC4.png


F511C2F7-2EC1-44C2-92E5-1BF3785E20CE.png

2ABA3F53-0820-4E89-920F-254465EDC742.png

77C28A67-B4E8-481B-A258-2471021B5980.png

模拟订单模拟支付行为


10C8BF8A-66F8-4EC7-8ABC-161866D972EF.png

557CC65F-4253-4CB7-8089-81A5C468974C.png

E279A377-33FF-494D-810A-6506815D3E58.png

下图中:支付类型----移动端只负责 "1.支付" 就行,其余后台管


B3E557A5-F312-409E-BC4C-7BFD6B1FB4A3.png
7A961896-ABBC-4F4B-BEB8-80B524BB3A1E.png

FFDA9D60-6589-4912-879E-8919684FAC3F.png

其中处理订单号代码如下

E96A92E9-17CA-4999-AB03-7C22636F03F1.png

通过各种算法生成随机订单号

EFF8DB1D-B063-4B3C-95C5-168203F6718A.png

二级商户

720A8BC3-4E5C-4730-8365-D186CAA32FE5.png



微信支付流程

#import "AppDelegate.h"
#import "WXApi.h"

@interface AppDelegate ()<WXApiDelegate>

@end

@implementation AppDelegate

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {

    //开启AFN框架内网路指示器(小菊花)
    [AFNetworkActivityIndicatorManager sharedManager].enabled = YES;
    
    //定义顶部20高的状态栏属性
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent animated:YES];
    
    //设置图片缓存策略
    [SDImageCache sharedImageCache].maxCacheAge = 1024*1024*10;

    //向微信注册
    [WXApi registerApp:@"wx1a851bd5c91204b3"];
    
    self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
    LoginController *loginController = [[LoginController alloc] init];
    ZYNavigationController *nav = [[ZYNavigationController alloc] initWithRootViewController:loginController];
    self.window.rootViewController = nav;
    
    [self.window makeKeyAndVisible];
    
    return YES;
    
}

- (BOOL)application:(UIApplication *)application handleOpenURL:(NSURL *)url {
    return  [WXApi handleOpenURL:url delegate:self];
}

- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation {
    return [WXApi handleOpenURL:url delegate:self];
}

- (void)onResp:(BaseResp *)resp
{
    [[NSNotificationCenter defaultCenter] postNotificationName:@"PAY_FINISH_NOTIF" object:nil]
    
    //如果支付成功则去后台查询支付结果再展示用户实际支付结果。注意    一定不能以客户端返回作为用户支付的结果,应以服务器端的接收的支付通知或查询API返回的结果为准。
    NSString *strMsg = [NSString stringWithFormat:@"支付结果"];
    switch (resp.errCode) {
        case WXSuccess:
            strMsg = @"支付结果:成功!";
            NSLog(@"支付成功-PaySuccess,retcode = %d", resp.errCode);
            
            //从服务器端再次确认支付是否成功
            [self makeSureChargeStatus];
 
            
            break;
        default:
            strMsg = [NSString stringWithFormat:@"支付结果:失败!retcode = %d, retstr = %@", resp.errCode,resp.errStr];
            NSLog(@"错误,retcode = %d, retstr = %@", resp.errCode,resp.errStr);
            break;
    }
}

//从服务器端再次确认支付是否成功
- (void)makeSureChargeStatus
{
    /*
     ### 查询充值结果
     * 地址
     http://dyt-win/greapost/rest/charge/status
     * 参数
     {"userId":"a0d8ec16f42b11e6b50ed279e40c8da1","chargeId":"a0d8ec16f42b11e6b50ed279e40c8da1"}
     * 返回值
     {"success":true,"state":"SUCCESS"}
     ps: state 可选值
     PAYSTATE_PREFAIL = "PREFAIL";
     PAYSTATE_NOTPAY = "NOTPAY";
     PAYSTATE_REFUND = "REFUND";
     PAYSTATE_SUCCESS = "SUCCESS";
     PAYSTATE_CLOSED = "CLOSED";
     PAYSTATE_USERPAYING = "REVOKED";
     PAYSTATE_PAYERROR = "REVOKED";
     PREFAIL-统一下单失败
     SUCCESS—支付成功
     REFUND—转入退款
     NOTPAY—未支付
     CLOSED—已关闭
     REVOKED—已撤销(刷卡支付)
     USERPAYING--用户支付中
     PAYERROR--支付失败(其他原因,如银行返回失败)
     */
    
    NSDictionary *parameters = @{
                                 @"userId": [Tool sharedTool].userID,
                                 @"chargeId": [Tool sharedTool].chargeId
                                 };
    
    [HttpRequest postWithURLString:@"greapost/rest/charge/status" parameters:parameters success:^(id responseObject) {
        
        NSLog(@"支付结果查询:%@",responseObject);
        if (responseObject[@"success"]) {
            [self showPayState:responseObject[@"state"]];
        } else {
            [Tool showErrorSVProgressHUDWithStatus:responseObject[@"msg"]];
        }
    } failure:^(NSError *error) {
        
        [Tool showErrorSVProgressHUDWithStatus:ServerNetworkError];
    }];
    
}

//获取支付状态
- (void)showPayState:(NSString *)state
{
    
    if ([state isEqualToString:@"NOTPAY"]) {
        [Tool showWarningSVProgressHUDWithStatus:@"未支付" time:2.0];
        return;
    }
    if ([state isEqualToString:@"SUCCESS"]) {
        [Tool showSuccessSVProgressHUDWithStatus:@"支付成功"];
        return;
    }
    if ([state isEqualToString:@"REFUND"]) {
        [Tool showWarningSVProgressHUDWithStatus:@"转入退款" time:2.0];
        return;
    }
    if ([state isEqualToString:@"REVOKED"]) {
        [Tool showWarningSVProgressHUDWithStatus:@"已撤销" time:2.0];
        return;
    }
    if ([state isEqualToString:@"CLOSED"]) {
        [Tool showWarningSVProgressHUDWithStatus:@"已关闭" time:2.0];
        return;
    }
    if ([state isEqualToString:@"PREFAIL"]) {
        [Tool showWarningSVProgressHUDWithStatus:@"统一下单失败" time:2.0];
        return;
    }
    if ([state isEqualToString:@"USERPAYING"]) {
        [Tool showWarningSVProgressHUDWithStatus:@"用户支付中" time:2.0];
        return;
    }
    if ([state isEqualToString:@"PAYERROR"]) {
        [Tool showWarningSVProgressHUDWithStatus:@"支付失败(其他原因,如银行返回失败)" time:2.0];
        return;
    }
    
}

- (void)applicationDidReceiveMemoryWarning:(UIApplication *)application
{
    [[SDImageCache sharedImageCache] clearMemory];
    [[SDWebImageManager sharedManager] cancelAll];
}

- (void)dealloc
{
    [[NSNotificationCenter defaultCenter] removeObserver:self];
}

@end


#import "ChargeController.h"
#import "WXApi.h"

@interface ChargeController ()<ChoosePayViewDelegate>

@property (nonatomic, weak) ChoosePayView *choosePayView;

@end

@implementation ChargeController

- (void)viewDidLoad {
    [super viewDidLoad];
    [self addSubViews];
}

- (void)addSubViews
{
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(popViewController) name:@"PAY_FINISH_NOTIF" object:nil];
    
    self.title = @"充值";    
    
}

- (void)popViewController
{
    [self.navigationController popViewControllerAnimated:YES];
}

- (void)choosePayView
{
            if(!_choosePayView){
              _choosePayView = [[ChoosePayView alloc] initWithFrame:CGRectMake(0, SCREEN_HEIGHT, SCREEN_WIDTH, SCREEN_HEIGHT)];
    choosePayView.delegate = self;
    choosePayView.money = money;//用户选中的充值面额
}
return  _choosePayView;
}

//点击充值按钮,动画弹出微信.支付宝方式选中框
- (void)clickChargeButton:(UIButton *)ban
{
    //懒加载添加,保证只添加一次
    UIApplication *ap = [UIApplication sharedApplication];
    [ap.keyWindow addSubview:self.choosePayView];  
    
    [UIView animateWithDuration:0.3 animations:^{
        self.choosePayView.top = 0;
    } completion:^(BOOL finished) {
        count = 0;
    }];
    
}

#pragma mark - choosePayViewDelegate
//选择支付方式代理方法
- (void)chooseAlipayOrWeChatPay:(PayType)payType
{
    
     /*
     ### 充值
     * 地址
     http://dyt-win/greapost/rest/charge/unifiedorder
     * 参数
     {"userId":"a0d8ec16f42b11e6b50ed279e40c8da1","totalFee":"0.01"}
     * 返回值
     {"success":true,"package":"Sign=WXPay","appid":"wx1a851bd5c91204b3","sign":"773CC5445E6C38CF9D8B7BEDE2D5DC33","prepayid":"wx20170217141956a16afe8fb70522432780","partnerid":"1243435702","noncestr":"77qous9c45mceab6kuw86705igouz0m7","timestamp":"1487312412"}
     */
    
    [self.choosePayView removeFromSuperview];
    
    if (payType == kALiPayTYPE) {
        NSLog(@"选中了支付宝支付方式");
        [Tool showWarningSVProgressHUDWithStatus:@"暂时不支持支付宝支付" time:2.0];
    } else {
        NSLog(@"选中了微信支付方式");
        
        //调起支付: 商户服务器生成支付订单,先调用【统一下单API】生成预付单,获取到prepay_id后将参数再次签名传输给APP发起支付。以下是调起微信支付的关键代码:
        NSDictionary *parameters = @{
                                      //传入用户id
                                     @"userId": [Tool sharedTool].userID,
                                     //传入选中充值面额
                                     @"totalFee": self.choosePayView.money
                                     };
        
        [HttpRequest postWithURLString:@"greapost/rest/charge/unifiedorder" parameters:parameters success:^(id responseObject) {
            
            /*
             支付结果: {
             appid = wx1a851bd5c91204b3;
             noncestr = 8bv12duoidtoqo0pqpdz1z41wy9dxdse;
             package = "Sign=WXPay";
             partnerid = 1243435702;
             prepayid = wx201702171457555d8a431e470433379896;
             sign = B2DB5E26D59B19134EF3660AC6C2711F;
             success = 1;
             timestamp = 1487314687;
             
             chargeId = 3d626bc3f5e211e6bc070050563731d8;
             }
             */
            
            NSLog(@"支付结果: %@",responseObject);
            if ([responseObject[@"success"] boolValue]) {
                
                [[Tool sharedTool] setChargeId:responseObject[@"chargeId"]];
                
                //服务器返回订单成功后, 进行微信支付
                PayReq *request = [[PayReq alloc] init];
                request.partnerId = responseObject[@"partnerid"];
                request.prepayId= responseObject[@"prepayid"];
                request.package = @"Sign=WXPay";
                request.nonceStr= responseObject[@"noncestr"];
                request.timeStamp= [responseObject[@"timestamp"] intValue];
                request.sign= responseObject[@"sign"];
                
                if ([WXApi isWXAppInstalled]) {
                    [WXApi sendReq:request];
                } else {
                    [Tool showWarningSVProgressHUDWithStatus:@"未安装微信应用" time:2.0];
                }
                
            } else { 
                [Tool showErrorSVProgressHUDWithStatus:[NSString stringWithFormat: @"%@",responseObject[@"msg"]]];
            }
            
        } failure:^(NSError *error) {
            NSLog(@"服务器请求订单失败 error:%@",error.localizedDescription);
//            [Tool showErrorSVProgressHUDWithStatus:ServerNetworkError];
        }];
        
    }
}

- (void)dismissChoosePayView
{
    [self.choosePayView removeFromSuperview];
}

- (void)dealloc
{
    [[NSNotificationCenter defaultCenter] removeObserver:self];
}

@end
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 211,265评论 6 490
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,078评论 2 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 156,852评论 0 347
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,408评论 1 283
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,445评论 5 384
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,772评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,921评论 3 406
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,688评论 0 266
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,130评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,467评论 2 325
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,617评论 1 340
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,276评论 4 329
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,882评论 3 312
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,740评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,967评论 1 265
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,315评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,486评论 2 348

推荐阅读更多精彩内容