前言
微信支付是由微信及财付通联合推出的移动支付创新产品。如今,随着微信支付的全面开放,相关需求也越来越多,很多开发人员进行微信支付开发及商家申请微信支付时,面临着诸多疑惑。
要想开发顺利进行,首先要对业务流程有个清晰的认识。这里以微信公众号支付为例,因此也借用微信支付官方文档中的业务流程图:
接下来来关注几个开发过程中的关键点,包括:
1、生成商户订单与调用统一下单 API
2、微信服务器交互的数据格式
3、公众号支付下网页内通过 JS-API 调起支付
4、异步通知商户支付结果(回调)
一、生成商户订单与调用统一下单 API
这对应业务流程中的第 4 和 第 5 步,商户后台首先为用户生成订单,然后调用微信的【统一下单】接口向微信支付系统提交订单。这里有一个关键点就是签名的生成。
简单来讲分为以下几个步骤:
1、将所有有效参数以“k=v”的形式进行拼接,有效参数是指非空参数,也就是说如果参数为空,则不参与签名;
2、将所有的“k=v”对用“&”连接,得到“k1=v1&k2=v2&k3=v3”这样的字符串;
3、将微信支付 API 密钥 拼接在最后,如“k1=v1&k2=v2&k3=v3&key=secret”;
4、对整体进行 MD5 运算,即得到签名。
这种签名方法有一个高大上的名字叫做 HMAC(Hash-based Message Authentication Code,基于哈希的消息码)。基于此思路,可以实现如下签名方法:
def gen_sign(params, key):
"""
签名生成函数
:param params: 参数,dict 对象
:param key: API 密钥
:return: sign string
"""
param_list = [] for k in sorted(params.keys()):
v = params.get(k)
if not v:
# 参数的值为空不参与签名
continue
param_list.append('{0}={1}'.format(k, v))
# 在最后拼接 key
param_list.append('key={}'.format(key))
# 用 & 连接各 k-v 对,然后对字符串进行 MD5 运算
return md5('&'.join(param_list).encode('utf8')).hexdigest()
参与签名的参数中有一个随机字符串,在 Python 中有很多方法,当然也可以利用uuid库来生成:
def gen_nonce_str():
"""
生成随机字符串,有效字符a-zA-Z0-9