• 支付宝web支付


    过程

    1. 用户下单

    2. 商户后台产生订单

    3. 请求支付宝web支付页面(将订单信息返回给用户---放在form里面---隐藏起来-----并通过脚本自动提交此form到支付宝web支付页)

    4. 用户在支付宝官方支付web页上进行支付,完成后,支付宝跳转(redirect)到form里面的参数return_url指定的地址。同时异步方式通知商户后台(form里面的参数notify_url指定接收通知的地址)

    5. 在return_url指定的页面里显示支付结果(在notify_url指定的页面里面处理发货逻辑)

    技术要点

    1. 组装form返回给客户端,demo如下:

    <html><head></head><body>
     <form id='alipaysubmit' name='alipaysubmit' enctype='multipart/form-data'  
            action='https://mapi.alipay.com/gateway.do?_input_charset=utf-8' method='POST'>
      <input type="hidden" name="seller_email" value="xxx@163.com"/>
      <input type="hidden" name="_input_charset" value="utf-8"/>
      <input type="hidden" name="sign"  value="31e0dce2c291cfac59401019e3dfe4da"/>
      <input type="hidden" name="notify_url" value="http://www.xxx.com/alipay_notify"/>
      <input type="hidden" name="partner" value="20888xxxxxxxx302"/>
      <input type="hidden" name="subject" value="test"/>
      <input type="hidden" name="service" value="create_direct_pay_by_user"/>
      <input type="hidden" name="out_trade_no" value="1470xxxx28068"/>
      <input type="hidden" name="payment_type" value="1"/>
      <input type="hidden" name="total_fee" value="0.01"/>
      <input type="hidden" name="sign_type" value="MD5"/>
      <input type="hidden" name="return_url" value="http://www.xxx.com/alipay_return"/>
    
      <input type="submit" value="submit" style="display:none"/>
     </form></body>
            <script>document.forms['alipaysubmit'].submit();</script></html>
    </html>

    注意,基本每个有name属性的input的name对应参数都是必填。

    官方文档看这里:https://doc.open.alipay.com/doc2/detail.htm?spm=a219a.7629140.0.0.YRtzUV&treeId=58&articleId=103584&docType=1

    2. 签名

    md5.加密(排序拼接串+密钥)

    所谓“排序拼接串”即为:将参数按照名称排序,然后拼接成a=1&b=2的形式(不要加入sign和sign_type参数),本例demo为:

    _input_charset=utf-8&notify_url=http://www.xxx.com/alipay_notify&out_trade_no=1470xxxx28068&partner=20888xxxxxxxx302&payment_type=1&return_url=http://www.xxx.com/alipay_return&seller_email=xxx@163.com&service=create_direct_pay_by_user&subject=test&total_fee=0.01

    python版本实现

    for过程步骤3

    import md5
    def
    get_alipay_web_html(order_number, goods_name, total_price): """ DEMO演示:返回自动提交支付宝的form的html代码
      args in:
        order_number, 商户订单号
    goods_name, 货物名称(购买内容描述)
        total_price, 总价
    """ url_root = request.url_root web_alipay_data={ "service": "create_direct_pay_by_user", "partner": "2088xxxxxxxx11302", "_input_charset": "utf-8", "payment_type": "1", "notify_url": '%s%s'%(url_root, 'alipay_notify') , "return_url": '%s%s'%(url_root, 'alipay_return') ,# url_for('alipay_return'), "seller_email": "xxx@163.com", "out_trade_no": order_number, "subject": goods_name, "total_fee": total_price, "sign": "test", "sign_type": "MD5" } t="" for k,v in sorted(web_alipay_data.items(), key = lambda x:x[0]): if k not in ('sign', 'sign_type'): t+="%s=%s&"%(k,v) t=t[:-1] key = 'xxxx4mk9ms6rxxxxghlvyrd2sfdxxxx' #print t+key web_alipay_data.update({'sign':md5.new((t+key).encode('utf-8')).hexdigest()}) response_form_html ="""<html><head></head><body> <form id='alipaysubmit' name='alipaysubmit' enctype='multipart/form-data' action='https://mapi.alipay.com/gateway.do?_input_charset=utf-8' method='POST'> %s <input type="submit" value="submit" style="display:none"/> </form></body> <script>document.forms['alipaysubmit'].submit();</script></html> </html> """ html_inputs="" for k,v in web_alipay_data.items(): html_inputs +='<input type="hidden" name="%s" value="%s"/> '%(k,v) return response_form_html%html_inputs

    在用户提交订单(通常post方式)到服务器后, 生成订单,并将订单信息包裹到form里面(以上函数只包裹了订单号),返回form给客户端浏览器, 由于脚本

    <script>document.forms['alipaysubmit'].submit();</script>

    的存在,此form会自动提交给支付宝。

    注意变更 partner参数(商户id)和 key参数(md5加密用密钥,不知道看这里),以及商家的邮箱(seller_email);

    回调地址(notify_url)和返回地址(return_url)根据实际情况修改。

    支付通知回调

    支付宝会将支付结果异步的方式post/get给商户服务器。

    在post方式中,有一个问题需要注意:

    如果notifiy_url对应的url里面有参数(例如: notify_url?xxx_field=xxx_value), 支付宝会将此参数截取出来,放到post的body中,收到的body段会多一个( &xxx_field=xxx_value), 此字段不能参与签名验证! 否则签名不匹配!

    即自定义的url参数,会在异步通知的body中post回来, 签名时要把他们排除出去!!!这一点官方文档没有说明。

    后记

    支付宝/微信支付麻烦的不是技术,而是各种配置,“平台”入口太多, 一不小心就掉坑里了。

    转载请注明来自:http://www.cnblogs.com/Tommy-Yu/p/5739971.html,谢谢!

  • 相关阅读:
    projecthashing
    Windows 环境 gRPC环境搭建
    gitlab 适配性问题
    对 Golang 简洁架构实战的理解,以及 Golang 开源项目包定义的解惑
    Golang 关于百分比,小数点为数的问题
    Golang net/http 库日常 http 请求操作
    解决mysql建立事件时出现 “Cannot proceed because system tables used by Event Scheduler were found damaged at server start” 的错误
    如何在Linux安装Wine
    Public key for *.rpm is not installed
    从 IClassFactory 为 CLSID 为 {AA40D1D6CAEF4A56B9BBD0D3DC976BA2} 的 COM 组件创建实例失败,原因是出现以下错误: c001f011。
  • 原文地址:https://www.cnblogs.com/Tommy-Yu/p/5739971.html
Copyright © 2020-2023  润新知