zoukankan      html  css  js  c++  java
  • python-支付宝支付示例

    项目演示:

    1、输入金额

    2、扫码支付:

    3、支付完成:

    一、注册账号

    https://openhome.alipay.com/platform/appDaily.htm?tab=info

    二、设置应用公钥

    三、代码实现

    1、项目结构:

            

    2、把生成的     应用私钥     和    支付宝的公钥       放入keys目录下:

        注意:
    支付宝公钥

    商户私钥

     --- 配置商户应用私钥--copy到key目录下

                

                

    --- 配置支付宝公钥--进入网页-->查看支付宝公钥-->把公钥放到key目录下

                

    但是要做修改:

    1. alipay_public_2048.txt  
    2.     -----BEGIN PUBLIC KEY-----  # 加上这行  
    3.         支付宝的公钥  
    4.     -----END PUBLIC KEY-----   # 同上  
    5.   
    6. app_private_2048.txt  
    7.     -----BEGIN PUBLIC KEY-----  #同上  
    8.         应用的私钥  
    9.     -----END PUBLIC KEY-----   # 同上  

    3、pay.py 这是从git上找到的支付宝支付接口(PC端支付接口) 

                

    1. in pay.py  
    2.   
    3. from datetime import datetime  
    4. from Crypto.PublicKey import RSA  
    5. from Crypto.Signature import PKCS1_v1_5  
    6. from Crypto.Hash import SHA256  
    7. from urllib.parse import quote_plus  
    8. from urllib.parse import urlparse, parse_qs  
    9. from base64 import decodebytes, encodebytes  
    10. import json  
    11.   
    12. class AliPay(object):  
    13.     """ 
    14.     支付宝支付接口(PC端支付接口) 
    15.     """  
    16.   
    17.     def __init__(self, appid, app_notify_url, app_private_key_path,  
    18.                  alipay_public_key_path, return_url, debug=False):  
    19.         self.appid = appid  
    20.         self.app_notify_url = app_notify_url  
    21.         self.app_private_key_path = app_private_key_path  
    22.         self.app_private_key = None  
    23.         self.return_url = return_url  
    24.         with open(self.app_private_key_path) as fp:  
    25.             self.app_private_key = RSA.importKey(fp.read())  
    26.         self.alipay_public_key_path = alipay_public_key_path  
    27.         with open(self.alipay_public_key_path) as fp:  
    28.             self.alipay_public_key = RSA.importKey(fp.read())  
    29.   
    30.         if debug is True:  
    31.             self.__gateway = "https://openapi.alipaydev.com/gateway.do"  
    32.         else:  
    33.             self.__gateway = "https://openapi.alipay.com/gateway.do"  
    34.   
    35.     def direct_pay(self, subject, out_trade_no, total_amount, return_url=None, **kwargs):  
    36.         biz_content = {  
    37.             "subject": subject,  
    38.             "out_trade_no": out_trade_no,  
    39.             "total_amount": total_amount,  
    40.             "product_code""FAST_INSTANT_TRADE_PAY",  
    41.             # "qr_pay_mode":4  
    42.         }  
    43.   
    44.         biz_content.update(kwargs)  
    45.         data = self.build_body("alipay.trade.page.pay", biz_content, self.return_url)  
    46.         return self.sign_data(data)  
    47.   
    48.     def build_body(self, method, biz_content, return_url=None):  
    49.         data = {  
    50.             "app_id"self.appid,  
    51.             "method": method,  
    52.             "charset""utf-8",  
    53.             "sign_type""RSA2",  
    54.             "timestamp": datetime.now().strftime("%Y-%m-%d %H:%M:%S"),  
    55.             "version""1.0",  
    56.             "biz_content": biz_content  
    57.         }  
    58.   
    59.         if return_url is not None:  
    60.             data["notify_url"] = self.app_notify_url  
    61.             data["return_url"] = self.return_url  
    62.   
    63.         return data  
    64.   
    65.     def sign_data(self, data):  
    66.         data.pop("sign"None)  
    67.         # 排序后的字符串  
    68.         unsigned_items = self.ordered_data(data)  
    69.         unsigned_string = "&".join("{0}={1}".format(k, v) for k, v in unsigned_items)  
    70.         sign = self.sign(unsigned_string.encode("utf-8"))  
    71.         # ordered_items = self.ordered_data(data)  
    72.         quoted_string = "&".join("{0}={1}".format(k, quote_plus(v)) for k, v in unsigned_items)  
    73.   
    74.         # 获得最终的订单信息字符串  
    75.         signed_string = quoted_string + "&sign=" + quote_plus(sign)  
    76.         return signed_string  
    77.   
    78.     def ordered_data(self, data):  
    79.         complex_keys = []  
    80.         for key, value in data.items():  
    81.             if isinstance(value, dict):  
    82.                 complex_keys.append(key)  
    83.   
    84.         # 将字典类型的数据dump出来  
    85.         for key in complex_keys:  
    86.             data[key] = json.dumps(data[key], separators=(','':'))  
    87.   
    88.         return sorted([(k, v) for k, v in data.items()])  
    89.   
    90.     def sign(self, unsigned_string):  
    91.         # 开始计算签名  
    92.         key = self.app_private_key  
    93.         signer = PKCS1_v1_5.new(key)  
    94.         signature = signer.sign(SHA256.new(unsigned_string))  
    95.         # base64 编码,转换为unicode表示并移除回车  
    96.         sign = encodebytes(signature).decode("utf8").replace(" ", "")  
    97.         return sign  
    98.   
    99.     def _verify(self, raw_content, signature):  
    100.         # 开始计算签名  
    101.         key = self.alipay_public_key  
    102.         signer = PKCS1_v1_5.new(key)  
    103.         digest = SHA256.new()  
    104.         digest.update(raw_content.encode("utf8"))  
    105.         if signer.verify(digest, decodebytes(signature.encode("utf8"))):  
    106.             return True  
    107.         return False  
    108.   
    109.     def verify(self, data, signature):  
    110.         if "sign_type" in data:  
    111.             sign_type = data.pop("sign_type")  
    112.         # 排序后的字符串  
    113.         unsigned_items = self.ordered_data(data)  
    114.         message = "&".join(u"{}={}".format(k, v) for k, v in unsigned_items)  
    115.         return self._verify(message, signature)  
    3、路由设置
    1. in urls.py  
    2.     urlpatterns = [  
    3.         url(r'^admin/', admin.site.urls),  
    4.         url(r'^page1/', views.page1),  
    5.             url(r'^index/', views.index),  
    6.         url(r'^page2/', views.page2),  
    7.     ]  

    4、视图设置

    1. in  view.py  
    2.     from django.shortcuts import render, redirect, HttpResponse  
    3.     from utils.pay import AliPay  
    4.     import json  
    5.     import time  
    6.   
    7.   
    8.     def get_ali_object():  
    9.         # 沙箱环境地址:https://openhome.alipay.com/platform/appDaily.htm?tab=info  
    10.         app_id = "2016091100486897"  #  APPID (沙箱应用)  
    11.   
    12.         # 支付完成后,支付偷偷向这里地址发送一个post请求,识别公网IP,如果是 192.168.20.13局域网IP ,支付宝找不到,def page2()   
    13.             # 接收不到这个请求  
    14.         notify_url = "http://47.94.172.250:8804/page2/"  
    15.   
    16.         # 支付完成后,跳转的地址。  
    17.         return_url = "http://47.94.172.250:8804/page2/"  
    18.   
    19.         merchant_private_key_path = "keys/app_private_2048.txt" # 应用私钥  
    20.         alipay_public_key_path = "keys/alipay_public_2048.txt"  # 支付宝公钥  
    21.   
    22.         alipay = AliPay(  
    23.             appid=app_id,  
    24.             app_notify_url=notify_url,  
    25.             return_url=return_url,  
    26.             app_private_key_path=merchant_private_key_path,  
    27.             alipay_public_key_path=alipay_public_key_path,  # 支付宝的公钥,验证支付宝回传消息使用,不是你自己的公钥  
    28.             debug=True,  # 默认False,  
    29.         )  
    30.         return alipay  
    31.   
    32.   def index(request):  
    33.             return render(request,'index.html')  
    34.   
    35.     def page1(request):  
    36.         # 根据当前用户的配置,生成URL,并跳转。    
    37.         money = float(request.POST.get('money'))  
    38.   
    39.         alipay = get_ali_object()  
    40.   
    41.         # 生成支付的url  
    42.         query_params = alipay.direct_pay(  
    43.             subject="充气式赵俊明",  # 商品简单描述  
    44.             out_trade_no="x2" + str(time.time()),  # 用户购买的商品订单号(每次不一样) 20180301073422891  
    45.             total_amount=money,  # 交易金额(单位: 元 保留俩位小数)  
    46.         )  
    47.   
    48.         pay_url = "https://openapi.alipaydev.com/gateway.do?{0}".format(query_params)  # 支付宝网关地址(沙箱应用)  
    49.   
    50.         return redirect(pay_url)  
    51.   
    52.   
    53.     def page2(request):  
    54.         alipay = get_ali_object()  
    55.         if request.method == "POST":  
    56.             # 检测是否支付成功  
    57.             # 去请求体中获取所有返回的数据:状态/订单号  
    58.             from urllib.parse import parse_qs  
    59.             # name&age=123....  
    60.             body_str = request.body.decode('utf-8')  
    61.             post_data = parse_qs(body_str)  
    62.   
    63.             post_dict = {}  
    64.             for k, v in post_data.items():  
    65.                 post_dict[k] = v[0]  
    66.   
    67.             # post_dict有10key: 9 ,1  
    68.             sign = post_dict.pop('sign'None)  
    69.             status = alipay.verify(post_dict, sign)  
    70.             print('------------------开始------------------')  
    71.             print('POST验证', status)  
    72.             print(post_dict)  
    73.             out_trade_no = post_dict['out_trade_no']  
    74.   
    75.             # 修改订单状态  
    76.             # models.Order.objects.filter(trade_no=out_trade_no).update(status=2)  
    77.             print('------------------结束------------------')  
    78.             # 修改订单状态:获取订单号  
    79.             return HttpResponse('POST返回')  
    80.   
    81.         else:  
    82.             params = request.GET.dict()  
    83.             sign = params.pop('sign'None)  
    84.             status = alipay.verify(params, sign)  
    85.             print('==================开始==================')  
    86.             print('GET验证', status)  
    87.             print('==================结束==================')  
    88.             return HttpResponse('支付成功')  
    
    

    5、模板

    1. in index.html  
    2.   
    3. <!DOCTYPE html>  
    4. <html lang="en">  
    5. <head>  
    6.     <meta charset="UTF-8">  
    7.     <title>Title</title>  
    8.     <link rel="stylesheet" href="dist/css/bootstrap.css">  
    9. </head>  
    10. <body>  
    11.     <form action="/page1/" method="POST">  
    12.         {% csrf_token %}  
    13.         <input type="text" name="money">  
    14.         <input type="submit" value="去支付" />  
    15.     </form>  
    16. <script></script>  
    17. </body>  
    18. </html>  

    6、当你全部设置完,代码只需修改三个地方

    git项目地址:https://github.com/zhbittt/s5alipay.git

        (1)、修改APPID

            -- 这是你账号的APPID

             

           -- in  views.py

                       def  get_ali_object():

                            app_id = 'xxxxxxx' #你的账号APPID  

    ================================

        (2)、换上你的支付宝公钥

        (3)、换上你的应用私钥

  • 相关阅读:
    android 关于双卡设置
    android apk反编译和odex转dex
    Android中获取系统内存信息以及进程信息ActivityManager的使用(一)
    ubuntu banshee music
    linux 查看文件夹大小
    嵌入式Linux学习笔记之GPIO接口
    Android中MediaButtonReceiver广播监听器的机制分析
    在Ubuntu中VirtualBox下xp使用usb设备
    beyond compare 与git diff整合
    Linux学习笔记一 Linux基础知识认知以及初识Linux下C编程入门
  • 原文地址:https://www.cnblogs.com/zhangningyang/p/8550138.html
Copyright © 2011-2022 走看看