微信支付接口V3版python库

Overview

wechatpayv3

PyPI version Download count

介绍

微信支付接口V3版python库。

适用对象

wechatpayv3支持微信支付直连商户,接口说明详见 官网

特性

  1. 平台证书自动更新,无需开发者关注平台证书有效性,无需手动下载更新;
  2. 支持本地缓存平台证书,初始化时指定平台证书保存目录即可。

适配进度

微信支付V3版API接口

其中:

基础支付

JSAPI支付 已适配
APP支付 已适配
H5支付 已适配
Native支付 已适配
小程序支付 已适配
合单支付 已适配
付款码支付 待官网更新
刷脸支付 无需适配

行业方案

智慧商圈 已适配

需要的接口适配怎么办?

由于wechatpayv3包内核心的core.py已经封装了请求签名和消息验证过程,开发者无需关心web请求细节,直接根据官方文档参考以下基础支付的申请退款接口代码自行适配,测试OK的话,欢迎提交代码。 必填的参数建议加上空值检查,可选的参数默认传入None。参数类型对照参考下表:

文档声明 wechatpayv3
string string
int int
object dict: {}
array list: []
boolean bool: True, False
def refund(self,
           out_refund_no,
           amount,
           transaction_id=None,
           out_trade_no=None,
           reason=None,
           funds_account=None,
           goods_detail=None,
           notify_url=None):
    """申请退款
    :param out_refund_no: 商户退款单号,示例值:'1217752501201407033233368018'
    :param amount: 金额信息,示例值:{'refund':888, 'total':888, 'currency':'CNY'}
    :param transaction_id: 微信支付订单号,示例值:'1217752501201407033233368018'
    :param out_trade_no: 商户订单号,示例值:'1217752501201407033233368018'
    :param reason: 退款原因,示例值:'商品已售完'
    :param funds_account: 退款资金来源,示例值:'AVAILABLE'
    :param goods_detail: 退款商品,示例值:{'merchant_goods_id':'1217752501201407033233368018', 'wechatpay_goods_id':'1001', 'goods_name':'iPhone6s 16G', 'unit_price':528800, 'refund_amount':528800, 'refund_quantity':1}
    :param notify_url: 通知地址,示例值:'https://www.weixin.qq.com/wxpay/pay.php'
    """
    params = {}
    params['notify_url'] = notify_url or self._notify_url
    # 
    if out_refund_no:
        params.update({'out_refund_no': out_refund_no})
    else:
        raise Exception('out_refund_no is not assigned.')
    if amount:
        params.update({'amount': amount})
    else:
        raise Exception('amount is not assigned.')
    if transaction_id:
        params.update({'transaction_id': transaction_id})
    if out_trade_no:
        params.update({'out_trade_no': out_trade_no})
    if reason:
        params.update({'reason': reason})
    if funds_account:
        params.update({'funds_account': funds_account})
    if goods_detail:
        params.update({'goods_detail': goods_detail})
    path = '/v3/refund/domestic/refunds'
    return self._core.request(path, method=RequestType.POST, data=params)

源码

github

gitee

安装

$ pip install wechatpayv3

使用方法

准备

参考微信官方文档准备好密钥, 证书文件和配置(证书/密钥/签名介绍)

初始化

from wechatpayv3 import WeChatPay, WeChatPayType

# 微信支付商户号
MCHID = '1230000109'
# 商户证书私钥
PRIVATE_KEY = 'MIIEvwIBADANBgkqhkiG9w0BAQE...'
# 商户证书序列号
CERT_SERIAL_NO = '444F4864EA9B34415...'
# API v3密钥, https://pay.weixin.qq.com/wiki/doc/apiv3/wechatpay/wechatpay3_2.shtml
APIV3_KEY = 'MIIEvwIBADANBgkqhkiG9w0BAQE...'
# APPID
APPID = 'wxd678efh567hg6787'
# 回调地址,也可以在调用接口的时候覆盖
NOTIFY_URL = 'https://www.weixin.qq.com/wxpay/pay.php'

wxpay = WeChatPay(
    wechatpay_type=WeChatPayType.MINIPROG,
    mchid=MCHID,
    parivate_key=PRIVATE_KEY,
    cert_serial_no=CERT_SERIAL_NO,
    apiv3_key=APIV3_KEY,
    appid=APPID,
    notify_url=NOTIFY_URL)

接口

# 统一下单
def pay():
    code, message = wxpay.pay(
        description='demo-description',
        out_trade_no='demo-trade-no',
        amount={'total': 100},
        payer={'openid': 'demo-openid'})
    print('code: %s, message: %s' % (code, message))

# 订单查询
def query():
    code, message = wxpay.query(transaction_id='demo-transation-id')
    print('code: %s, message: %s' % (code, message))

# 关闭订单
def close():
    code, message = wxpay.close(out_trade_no='demo-out-trade-no')
    print('code: %s, message: %s' % (code, message))

# 申请退款
def refund():
    code, message=wxpay.refund(
        out_refund_no='demo-out-refund-no',
        amount={'refund': 100, 'total': 100, 'currency': 'CNY'},
        transaction_id='1217752501201407033233368018')
    print('code: %s, message: %s' % (code, message))

# 退款查询
def query_refund():
    code, message = wxpay.query_refund(out_refund_no='demo-out-refund-no')
    print('code: %s, message: %s' % (code, message))

# 申请交易账单
def trade_bill():
    code, message = wxpay.trade_bill(bill_date='2021-04-01')
    print('code: %s, message: %s' % (code, message))

# 申请资金流水账单
def fundflow_bill():
    code, message = wxpay.fundflow_bill(bill_date='2021-04-01')
    print('code: %s, message: %s' % (code, message))

# 下载账单
def download_bill():
    code, message = wxpay.download_bill(url='https://api.mch.weixin.qq.com/v3/billdownload/file?token=demo-token')
    print('code: %s, message: %s' % (code, message))

# 合单支付下单
def combine_pay():
    code, message = wxpay.combine_pay(
        combine_out_trade_no='demo_out_trade_no',
        sub_orders=[{'mchid':'1900000109',
                     'attach':'深圳分店',
                     'amount':{'total_amount':100,'currency':'CNY'},
                     'out_trade_no':'20150806125346',
                     'description':'腾讯充值中心-QQ会员充值',
                     'settle_info':{'profit_sharing':False, 'subsidy_amount':10}}])
    print('code: %s, message: %s' % (code, message))

# 合单订单查询
def combine_query():
    code, message = wxpay.combine_query(combine_out_trade_no='demo_out_trade_no')
    print('code: %s, message: %s' % (code, message))

# 合单订单关闭
def combine_close():
    code, message = wxpay.combine_close(
        combine_out_trade_no='demo_out_trade_no', 
        sub_orders=[{'mchid': '1900000109', 'out_trade_no': '20150806125346'}])
    print('code: %s, message: %s' % (code, message))

# 计算签名供调起支付时拼凑参数使用
# 注意事项:注意参数顺序,某个参数为空时不能省略,以空字符串''占位
def sign():
    print(wxpay.sign(['wx888','1414561699','5K8264ILTKCH16CQ2502S....','prepay_id=wx201410272009395522657....']))

# 验证并解密回调消息,把回调接口收到的headers和body传入
def decrypt_callback(headers, body):
    print(wxpay.decrypt_callback(headers, body))

# 智慧商圈积分通知
def points_notify():
    code, message = wxpay.points_notify(
        transaction_id='4200000533202000000000000000',
        openid='otPAN5xxxxxxxxrOEG6lUv_pzacc',
        earn_points=True,
        increased_points=100,
        points_update_time='2020-05-20T13:29:35.120+08:00')
    print('code: %s, message: %s' % (code, message))

# 智慧商圈积分授权查询
def user_authorization():
    code, message = wxpay.user_authorizations(openid='otPAN5xxxxxxxxrOEG6lUv_pzacc')
    print('code: %s, message: %s' % (code, message))
Comments
  • 微信支付回调函数验证签名不正确,求助!

    微信支付回调函数验证签名不正确,求助!

    你好,

    在回调地址notify_url中接受request.header和request.body,并传入wxpay.decrypt_callback函数验证签名和解密返回值,验证签名失败,但解密返回值正确。

    服务器为centos 7,已设置平台证书路径为“\cert”,运行decrypt_callback函数时,系统已下载签名并存放到该文件夹。verify(timestamp, nonce, body, signature, certificate)时可以通过该证书生成公钥文件:<cryptography.hazmat.backends.openssl.rsa._RSAPublicKey object at 0x7f0dcf7b6eb0>

    然后在public_key.verify(signature, message, PKCS1v15(), SHA256())时,验证不过去。以下为拼凑的sign_str,还请帮助看看在哪一步出现了问题,非常感谢!

    例如,验签拼凑字符串为: 1627890132 Fnqw2Aw6k1fIxb8DhPAKogL76BeSnvQ6 {"id": "3e283601-7c3d-5c04-8ebf-225474439c26", "create_time": "2021-08-02T15:42:11+08:00", "resource_type": "encrypt-resource", "event_type": "TRANSACTION.SUCCESS", "summary": "支付成功", "resource": {"original_type": "transaction", "algorithm": "AEAD_AES_256_GCM", "ciphertext": "ECIKoyOZBc9soYj7gVqD1JRzXA+0LSPcbm6lPXqIqB/iLTWk9jR6En9z6vVPHpTDKIySzFb4/A9+fViPQJYMCa8tGqwA2HzMCB52PyRTRQ7nrBLBR7lQyHMZbWDqU35tujTmu4KGuO8nplOV4Q7rm+dXFt5RN7XJwbyufTQmU1FviWfzTwe7sT4ndnf4YhY7V0z7m2AhboQXGxdpSYccHLIGFpZctL4VFE1qJ4ikHdNJNvj6RF/yTElP2ssDVHd4lKckuqZ8u7xa5jmhvxzqkJIAFsVDEHKvM4wUkmgV6B6XIeuXMvxi1JNTW33hTnNWTZphcE467Ge/l2ajJckDNKJTeRv50nY+JLm6K2I7f2kmvxHm9OYpCkHlzXWqieMrPrwQs1KbfTqxYaUYW9vOESRXAAOV7q7YfMCkvfjnyX7KQEKYIsKYHPUnpWpJbBRriAH1oY5DC0SoLmlbaCEvwiaEJg7MFwhFVQYLxwk2DsIjbFC1UUxLIs5tZvKUrWFmbQOUTzmnCv/0qU7KbVZbeaHVEFzZ8d1UG1SK/db+medh65ueEwgko9DIvdCITnXTceS3AwTdre2T", "associated_data": "transaction", "nonce": "123RUOfxtcAL"}}

    opened by carter8225 7
  • 请问“敏感信息加解密”的实现代码在哪里?

    请问“敏感信息加解密”的实现代码在哪里?

    微信支付官方文档中有“敏感信息加解密”的相关要求: https://pay.weixin.qq.com/wiki/doc/apiv3_partner/wechatpay/wechatpay4_3.shtml

    “开发者应当使用微信支付平台证书中的公钥,对上送的敏感信息进行加密。这样只有拥有私钥的微信支付才能对密文进行解密,从而保证了信息的机密性。 另一方面,微信支付使用 商户证书中的公钥对下行的敏感信息进行加密。开发者应使用商户私钥对下行的敏感信息的密文进行解密。”

    大佬,请问wechatpayv3中有相关实现代码吗?找了半天没找到,请恕我愚钝。

    opened by Odyssey166 7
  • wechatpayv3也支持微信支付服务商吧?

    wechatpayv3也支持微信支付服务商吧?

    大佬,再问一个可能比较普遍的问题。wechatpayv3文档上说:”适用对象wechatpayv3支持微信支付直连商户“,然后给出了接口适配的方法。通过阅读微信支付官方文档,我发现直连商户和服务商的签名验签、加密解密过程都是一样的。API本质上貌似也没什么区别。例如,以下是服务商电商收付通的API列表: https://pay.weixin.qq.com/wiki/doc/apiv3_partner/open/pay/chapter3_3_3.shtml

    所以我认为wechatpayv3也支持微信支付服务商,只要开发者自己适配相关接口即可。

    请问我的理解是正确的吗?

    opened by Odyssey166 3
  • 微信支付分退款接口无法使用

    微信支付分退款接口无法使用

    该接口在return refund时掉了一个self参数。因此会报如下错误: File "/usr/local/lib/python3.9/site-packages/wechatpayv3/payscore.py", line 361, in payscore_refund sharedpowerbankdocker-web_api-1 | return refund(out_refund_no=out_refund_no, amount=amount, transaction_id=transaction_id, reason=reason, sharedpowerbankdocker-web_api-1 | TypeError: refund() missing 1 required positional argument: 'self'

    opened by MacGuffinLife 2
  • 【BUG】在本地证书需要更新时,程序会因无法通过证书验证而陷入死循环

    【BUG】在本地证书需要更新时,程序会因无法通过证书验证而陷入死循环

    方法路径:wechatpayv3 > core.py > _verify_signature(self, headers, body)

    方法源码:

        def _verify_signature(self, headers, body):
            signature = headers.get('Wechatpay-Signature')
            timestamp = headers.get('Wechatpay-Timestamp')
            nonce = headers.get('Wechatpay-Nonce')
            serial_no = headers.get('Wechatpay-Serial')
            cert_found = False
            for cert in self._certificates:
                if int('0x' + serial_no, 16) == cert.serial_number:
                    cert_found = True
                    certificate = cert
                    break
            if not cert_found:
                self._update_certificates()
                for cert in self._certificates:
                    if int('0x' + serial_no, 16) == cert.serial_number:
                        cert_found = True
                        certificate = cert
                        break
                if not cert_found:
                    return False
            if not rsa_verify(timestamp, nonce, body, signature, certificate):
                return False
            return True
    

    cert_foundFalse 时,程序将会执行 _update_certificates() 方法,在此更新证书的方法中,self._certificates 中的信息仍然错误,从而导致接下来的验证依旧不能通过,进而再次执行 _update_certificates() 方法,最终产生死循环

    opened by worship76 2
  • 小程序回调方法

    小程序回调方法

    请问一下,为什么我的回调方法接收到的request.data格式不对 { "id": "EV-2018022511223320873", "create_time": "2015-05-20T13:29:35+08:00", "resource_type": "encrypt-resource", "event_type": "TRANSACTION.SUCCESS", "summary": "支付成功", "resource": { "original_type": "transaction", "algorithm": "AEAD_AES_256_GCM", "ciphertext": "", "associated_data": "", "nonce": "" } }

    我得到的是这样的 {"data":[ {"effective_time":"2022-04-15T13:46:12+08:00", "encrypt_certificate": {"algorithm":"AEAD_AES_256_GCM", "associated_data":"certificate", "ciphertext":"MpxtKsvcoF3Jmuofu/L/NjZ+aUqJ4yrQG824VT4At5WHoDyd4x2ydRAJwwy+zuvZ4MsQfGyjjNkO2xAF9G7oN3cnwJAyL0Oo4ZWcrPoMZDLqccaYJaMogun/qz6u8FHP9x5CIBi3HAQzZl+FP9MhpIEuUhj/nMl8yksTWDU9R5MFdw+0CGymglJ6P3kGDIeQACXALRLT6eL0NGQSCQwFAoQpVEwDBVRIjh6beWYOKySP8KLJasL3MH3XthYcS/rvjO0lQxLER2ByZsfBg/yM+3eQuyFJUauqWlY8iPuO8GAYalhomdPWpe2TwAqwce0ZLdKfDOvDxd96TKKGeR5+BD8Ws5+b6y8PYnkcMd+WUyv8BVGl2dHf6tno3QHuqVxm61Km2Ze+6lEKjPXNr7CMX8k1rqeMhlrVxYbUhGWrNXXL+CKOJTNnQgMRO1aU46Kx0N/x9sepKL72RpYbTzcbcRwsZ4WFw+qqd2nO4afusV7HmYsztSvxxcD8fTg19kTEhI3HMWLHf8CCyQ+uRAm7ZiCi/g6WlMT5a2JYMzx4/kKucS1PCHs+3k7OYDocxXDUhVt9YlMJGPdZLMjmQzEt3CP/8zGl4ndJmOuLZsO1xGuJNN5P/h2K+JuZ0Y5toQrR6m9zlWdhmbaxiENVDzaxn9FEyR3Tj1ioRVpFhIBvmyLhZuRr+uHX/9ZcxNqKuP+pVntu+oEnd+aUSZsNV3U+S/vF2d78cFsJMgx1k9dbyYOflmAJB6qhf4MUxumqMXhu6verAs7K9RYy3B/8D+1DLv88gxRSSZVr0iqXYped6EGe0Gfp10oy0OKWAjsXmiIQaX/d4NGnFFfi0HdvaxhFokkh/Nktam0fxl40OZGeyKgqZl/NcfirjtLpRUu3YZV1ASYdbHLe8kqn0HYnMfKUdcw//5AIT9mDTnvP+wHadHicLRQHVzPR2z4IlBGm+Rr6J0yBC9LWzxFstBv/yHq9SmcqiC6C9RVOtrHpqb2HbE4kD0TbpTcofp3KGVsMOEf+hAYob94OEUU74H6tulxI1UiTr6JQzJykxP3M1FnEqb3/JN8aDZPIAwilgE/NjySpRvedkl4apvanNI8gHOK3SYyrD+RvrHrY3LcHjpiR6V5inCXYM3tmPmNiURBoIVLRLzbb84Q11lRJCVmWfE1zU62OCckmlqDJMck58QPI75EEk5sCQbBumuICKwfDfj//uU49KtvcHLVdj3WhmQtz660x2NU80ndB5WBk2AAv/rT3zFd3zGzXeM+jBy/4623dXnDEaSXHQk4BP7FLULhIsQiM/JNP+hbkyHTDq+bbJ3JzQpZtR8aTlP5wZpwWvclDCnisi65JHeEublKe2wIKoiYo9RYsHDzsqy6FlJlSqaJMu6mC6oYsF3ZG21x2Dv+WRIsf3SaPpGLpcOkVJNtT+tdT12z1i//rbLK53DADhTN2h2djPiHkx2KiMlNxocFQXtFcJIR0zmde8UQ54sLg4SMh1An+bJitpNleeCcNZuDJIQCAkpCShztQB9lFdEbeG7bWI28sMYVVOVuSYgqanmEh5CyNteqcqG21A91uMQmmQLG3dJmD9VyTvakBf3R6Qm7rLoXXUJ+yoAVJie6Te12ALLzuyE8pwI8OfvpK+BNLXBS7W3KzENTsIkx/i/IqtgGFzRkQ9guVCwA71JHiuU3+K0KLKXjN4ynLDbk2r0ZIL9m8aBHoguyoIWtFwI76Fz3B4ZwXDX7U9N9VqNGO+UjCljrTZjRQy+FSOh1DJIXKaePEROggGSOjcD3QEE9Q1va2WW7M/uv+yHh8u/V9HnsBnTQrPK09U0BIqy+3ALEhfGgZef6L5kHUY/nWDLcRwtnSq/W0NPf16XjcgQ/29Krq3OXadQ==", "nonce":"0401acb66488"}, "expire_time":"2027-04-14T13:46:12+08:00","serial_no":"474A7CDC898039BEC0F1D6F4A0F7F8C9D8113412"} ] } 麻烦帮忙看一下,非常感谢

    opened by Warzonee 1
  • applyment_submit

    applyment_submit

    path should end with ‘/’, path = '/v3/applyment4sub/applyment/', otherwise will return 404. Also,some field should encrypt too, add logic as follows in applyment_submit function: if params.get('subject_info').get('identity_info'): id_card_info = params.get('subject_info').get('identity_info').get('id_card_info') if id_card_info is not None: id_card_info['id_card_name'] = self._core.encrypt(id_card_info['id_card_name']) id_card_info['id_card_number'] = self._core.encrypt(id_card_info['id_card_number']) cipher_data = True

    opened by realwrtoff 1
Releases(1.2.35)
Owner
chen gang
chen gang
Fully asynchronous trace.moe API wrapper

AioMoe Fully asynchronous trace.moe API wrapper Installation You can install the stable version from PyPI: $ pip install aiomoe Or get it from github

2 Jun 26, 2022
Nyon-stream - A python script that uses webtorrent to stream nyaa videos directly to mpv

nyon-stream A rather shitty script that uses webtorrent to stream nyaa videos di

18 Feb 08, 2022
DeleteAllBot - Telegram bot to delete all messages in a group

Delete All Bot A star ⭐ from you means a lot to me ! Telegram bot to delete all

Stark Bots 15 Dec 26, 2022
Opensea-upload-with-recaptcha-solution - Updated opensea uploading solution with recaptcha pass

opensea-upload-with-recaptcha-solution updated opensea uploading solution with r

byeonggeon sim 25 Nov 15, 2022
This is a Telegram video compress bot repo. By Binary Tech💫

This is a Telegram Video Compress Bot. Prouduct By Binary Tech 💫 Features Compresse videos and generate screenshots too.You can set custom video name

silentz lk 2 Jan 06, 2022
A Telegram bot that add a dynamic caption to musics

Music Channel Manager A Telegram bot that add a dynamic caption to musics Deploy to Heroku What is it ? It manage your music channel. With just adding

13 Oct 18, 2022
Discord RPC for Notion written in Python

Discord RPC for Notion This is a program that allows you to add your Notion workspace activities to your Discord profile. This project is currently un

Thuliumitation 1 Feb 10, 2022
multi-purpose discord bot

virus multi-purpose discord bot ⚠️ WARNING This project is incomplete and may not work as expected. Download & Run Install Python =3.10 Clone the sou

miten 2 Jan 17, 2022
Azure Neural Speech Service TTS

Written in Python using the Azure Speech SDK. App.py provides an easy way to create an Text-To-Speech request to Azure Speech and download the wav file.

Rodney 1 Oct 11, 2021
TESSARECT A Powerful Bot you'll ever need for anything

Tessarect TESSARECT A Powerful Bot you'll ever need for anything TESSARECT It is my First bot but very advanced and designed for all your needs , from

Prakarsh Prp 4 Aug 27, 2022
Bot that embeds a random hysterical meme from Reddit into your text channel as an embedded message, using an API call.

Discord_Meme_Bot 🤣 Bot that embeds a random hysterical meme from Reddit into your text channel as an embedded message, using an API call. Add the bot

2 Jan 16, 2022
universal messaging & notifications api

Pronounced "boat-shahft" What is botschaft? Botschaft is unified messaging & notifications appliance. Want to text yourself when a long-running task c

Tyler M. Kontra 25 Aug 16, 2022
This repository will (hopefully) always contain the latest version of the libProfessorP.asm.so shared object.

libPuhfessorP - Deploy Repo This repo should (hopefully) always contain the latest version of the libPuhfessorP.asm.so shared object, to be linked wit

Puhfessor P - CPSC 240 3 Sep 30, 2021
A Slack bot for playing Texas Hold 'Em where the currency is various workout tasks e.g. pushups

A Slack app/bot for playing Texas Hold 'Em where the currency is various workout tasks e.g. pushups. The intent is to make the workday more fun & active for remote teams.

Kyle McIntyre 3 Sep 19, 2022
Python library to interact with a Z-Wave JS server.

zwave-js-server-python Python library for communicating with zwave-js-server. Goal for this library is to replicate the structure and the events of Z-

Home Assistant Libraries 54 Dec 18, 2022
telegram bot that calculates file hash / Dosya toplamı hesaplayan telegram botu

Telegram File Hash Bot FileHashBot: 🇬🇧 Bot that calculates file hashes. 🇹🇷 Dosya toplamları hesaplayan bot. Demo in Telegram: @FileHashBot 🇬🇧 Se

Hüzünlü Artemis [HuzunluArtemis] 5 Jun 29, 2022
A bot that downloads all the necessary files from WeLearn and lists your assignments, filter due assignments, etc.

Welearn-bot This is a bot which lets you interact with WeLearn from the command line. It can Download all files/resources from your courses and organi

Parth Bibekar 17 Oct 19, 2022
Mini Tool to lovers of debe from eksisozluk (one of the most famous website -reffered as collaborative dictionary like reddit- in Turkey) for pushing debe (Most Liked Entries of Yesterday) to kindle every day via Github Actions.

debe to kindle Mini Tool to lovers of debe from eksisozluk (one of the most famous website -refered as collaborative dictionary like reddit- in Turkey

11 Oct 11, 2022
Keypirinha plugin to install packages via Chocolatey

Keypiriniha Chocolatey This is a package for the fast keystroke launcher keypirinha (http://keypirinha.com/) It allows you to search & install package

Shadab Zafar 4 Nov 26, 2022
A Discord bot written in Python to help with guild administration

forgotten-hydra A Discord bot written in Python to help with guild administration. External libraries Pycord-Development/pycord 1.7.3 djc/couchdb-pyth

1 May 14, 2022