- 接收不到微信回调通知排查指引
前言:相信很多朋友在开发微信支付接口时遇到无法收到回调问题非常的懊恼,不知道从何下手,相信看完本文章基本就能解决你无法收到回调的问题了。阅读本文章前,建议提前看一下文章右侧的目录,帮助你更好的阅读此文章。 -------- 提前需要准备的工具:postman(其他能调试API的工具也可以) -------- 什么情况下才会有回调通知 1、 支付成功后微信侧才会发送支付结果回调通知 可参考官方文档:支付通知API 2、 申请退款成功后,只有退款状态为退款异常、退款关闭、退款成功才会发送退款回调通知 可参考官方文档:退款结果通知API 注意: 1.上面只是举例了两个接口,还要更多的回调接口,每个回调接口都会有对应的 通知频率 和 回调触发条件 -------- 2.支付结果回调 是异步队列加公网通知的,支付完成后会立即发送回调消息,以支付结果回调为准,不存在回调支付成功,查询接口却一直返回的是未支付 -------- 3.退款回调 是异步的,申请退款接口返回的成功只是代表了申请退款这个操作成功了,退款整个流程可能经过银行等,所以 回调时长可能会长一些 -------- 4.申请退款成功后,用户侧长时间未到账,或商户查询退款状态一直都是退款中,则可能是退款到用户银行卡中,需要经过银行,一般在7个工作内是比较正常的,若7个工作日后还是退款中,请拨打95017协助排查 -------- 5.回调的作用是告诉商户结果是什么,商户应答回调是告诉接口已经成功收到回调,建议商户最好是按照文档要求去应答接口,若商户是自行查询接口来判断情况,而不是根据回调来判断,理论上是可以不去管回调(包括应答),但还是强烈建议按照正常流程正确的应答接口 -------- 下面介绍一下每一种无法接受到回调的情况及对应的检查方法 -------- 情况一:v3接口的回调未设置APIv3密钥(非常重要!!!非常重要!!!非常重要!!!一定要优先设置) 什么是APIv3密钥?如何设置? [图片] [图片] 注意(APIv2密钥以前也叫API密钥): 1.v2接口 使用的是 APIV2密钥,v2接口 下单能成功 说明就设置好了APIv2密钥。 -------- 2.APIv3密钥 与 APIV2密钥 是隔离的,设置APIv3密钥时,不会导致APIV2密钥发生变化,且 对v2接口没有影响。 -------- 情况二:下单时实际填写的回调地址跟自己实际想要的回调地址不一致,可能多了 / 或者 空格 [图片] -------- 比如想要的是:http://www.qqweixin.top/weixin/pay/callback/test -------- 实际的填写的:http://www.qqweixin.top/weixin/pay//callback/test -------- 情况三(硬性条件,不要抱着侥幸心理!!!):回调地址不规范,回调地址规则:回调地址不能携带参数及端口号且不能是直接的ip,请检查下单时的回调地址是否有携带参数或端口号,必须为 公网域名 且是 https 开头,现使用 http开头 、携带 端口号 或是 ip 能正常接收回调的用户,建议更换为 https 且去除 端口号 使用正常的域名,避免后期出现回调通知无法接收的情况,是post请求。 notify_url填写注意事项 [图片] -------- 错误示例: 携带端口号:http://www.qqweixin.top:443/weixin/pay/callback/test 携带参数:http://www.qqweixin.top/weixin/pay/callback/test?id=10086 使用ip地址:192.168.x.x 非公网域名:[图片](一定要使用公网ip映射的域名) -------- 如何检查域名是否有问题:核实回调地址是否可被外网访问,是否有DNS解析成功。 (检查ip地址/域名是否可以ping通:如何ping域名,建议是在不同网络下进行操作,这样可以检查是否是内网ip,ping不通可能的原因是ip地址和域名没有映射成功或者是内网ip(同网络能ping通,不同网络不能ping通,一般就是内网ip),需要到注册的域名网站重新进行映射) 成功示例:[图片] 失败示例:[图片] -------- 情况四:开通了防火墙,拦截了回调 (是否开通了防火墙导致回调地址被拦截了,开通防火墙后设置一下白名单,回调IP段白名单) [图片] -------- 情况五:商户侧网络波动导致部分回调丢失 商户侧由于网络波动导致部分部分回调数据没有正常存储或数据丢失等,可以按照网络监测工具检查 (一般商户侧出现就部分订单的回调丢失就是这种情况,微信侧目前没有出现过支付成功后未给商户发送回调的情况,若极端情况下出现,官方也肯定是会在第一时间通知商户,所以基本都是商户自身网络问题导致) -------- 情况六:域名转发(url转发)导致的DNS解析失败 域名转发:所谓URL转发,是通过服务器的特殊设置,将访问您当前域名的用户引导到您指定的另一个网络地址。 地址转向(也可称“URL转发”)即将一个域名指向到另外一个已存在的站点,英文称为“ URL FORWARDING ”。 DNS解析失败:解析失败就是找不到相关域名对应的IP 这种情况一般自己比较难排查吗,所以不要做域名转发,然后再进行测试,出现问题后再按照上述步骤进行检查(建议直接咨询自己的运维人员,他们知道如何处理) 情况七:程序代码问题(若使用的回调地址本身是在正常使用的回调地址,是对代码或者环境修改后出现的问题,则说明是代码层面或者环境的问题) 使用postman等API调试工具模拟微信支付回调的格式测试,检查代码是否能正常接收回调信息,v2接口的回调信息是xml格式,v3接口的回调格式json格式,上述两种格式都是以字符串的形式发送的数据流,特殊情况:只要是在商户平台进行 手动退款的回调通知都是xml格式。 (注意测试时,发送回调和接收回调尽量不要在同一网络当中,避免都是在是同一网络测试结果不准确,注意:接收到回调为空的现象一般都是接收格式的问题,比如xml格式的数据使用json格式接收) v2接口回调格式(固定为xml格式,v2部分接口需要解密,比如:退款接口,详情会在接口特别说明说明中有描述,退款结果通知) [图片] 示例: <xml> <appid><![CDATA[wx2421b1c4370ec43b]]></appid> <attach><![CDATA[支付测试]]></attach> <bank_type><![CDATA[CFT]]></bank_type> <fee_type><![CDATA[CNY]]></fee_type> <is_subscribe><![CDATA[Y]]></is_subscribe> <mch_id><![CDATA[10000100]]></mch_id> <nonce_str><![CDATA[5d2b6c2a8db53831f7eda20af46e531c]]></nonce_str> <openid><![CDATA[oUpF8uMEb4qRXf22hE3X68TekukE]]></openid> <out_trade_no><![CDATA[1409811653]]></out_trade_no> <result_code><![CDATA[SUCCESS]]></result_code> <return_code><![CDATA[SUCCESS]]></return_code> <sign><![CDATA[B552ED6B279343CB493C5DD0D78AB241]]></sign> <time_end><![CDATA[20140903131540]]></time_end> <total_fee>1</total_fee> <coupon_fee><![CDATA[10]]></coupon_fee> <coupon_count><![CDATA[1]]></coupon_count> <coupon_type><![CDATA[CASH]]></coupon_type> <coupon_id><![CDATA[10000]]></coupon_id> <trade_type><![CDATA[JSAPI]]></trade_type> <transaction_id><![CDATA[1004400740201409030005092168]]></transaction_id> </xml> v3接口回调格式(固定为json格式,格式固定,内容不一样,需要解密) [图片] 示例: { “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”: “3TxpOF8YqF5Zy2cYQWrZNnmC1FWrxwIPvIv4WejUr+8ctmM6L3kxqQ6JS56S7JkVFMiCvfcMGkQFMtUifq09Wrt6+bNwMUNLKQ52zLyMLwS9uML2Y2Qmi1obactel3rwwTs+IXGir505F2eLBG9ruqtJxGd2dlsLQ+0Sl7OUA/mMCnxMXUhfwJC84lv2oZDC3T827Mzy0BQ5YmXfdpgOA0OCTl+OwokWMXJz2DiGafE1n0pqH/R0VgDyUCEAOb6l+dFRR7S0I1yVe7/6czAYp+i7mTgNrmudG7EgDoOVfGga9Wq9epO6PEew1ypK5M8PmIopNSzg34WEouFhOqvPZfi2paqib2gxexcqtniQQbdechavr4SH/3JSpg8Zbnnbeo3ClFDU7eRVO2FCAPQaMlcSmjU4zv2H98dvB9TnIyon/so+QwSo/ZwWMnTKeztviuYd5ICbrtzAPoeeDrPlYlB0pwlFT8Tz3lqC0QZWKvL0+FIj0+9P+2/JvZpr5aVrFosMI1Afb17P7zx69jnLFPFX0ph4AgBK/N8oRNg12uVqvJM3E07/4P7LWLKyrf9FySovQplbhlasAyOf5PWb3aBwEv19hr71uMvAyuCll39zhIZ9M1CZTcSLpuyeWDOUwt3Y7ww0mOMruvK5a5mREuowqfP/OVv73yX/mf/7MEo9wAvz2bNqAuS0c9xc2yn5EHN4rNSTgApcJh2OTNUVEZXu7sL04S/pKpApS4eXxTS1bnLeqVfk5rePQagXFXwMFJVfAPmLyMRLsBLpdc2lO2LIof+nx8HnqjHvKYnolRgJYAlUuHx1mdjsPrZreDjK12b3cBznrfC7gac+3VW4r42f2b533RCAvchchxb7l+sdzQSFImbxZ1IAZFO/ZozZEFFko2FypOh2SdZYigW6Rq6hxw8EFOrvp6GwKpkhGbb4xnQsGHupDAMte5QmiMb9M8KUP5DSIo7gCsO7FMWtXFrdetyQfLXsZ/CidA+JOlSGKL+8s/ISyajpl8YseGNhlq39Zci53GoQCETs/ixLPz4BOTeTLC9FASUoEGPKet+OvYhdo4Xlopbhs95jl6jjgZcT6Bkr5ivG2ocqi2aP5hpnnVDXq/OwXvdofTHxlp2oydlYo9xqXhg+emzSQ8woub6XXO22KOKuEcWMSCiSMWYm9gsP2v0QkCw54ZmJHuDoivV2jVrFQjdH9nO2m68SHj9I9PBj4eSbDG235d/gSxp6VrrH+UaP5b4fjZi4xZ+9Nr1oUAc1Z6RRqqvCVLY1DTMpp2H/aXr9gNUs8fL8kkfuiWEKTkcoW/JKTZjiizzbHEkXSU3+dm4AITiKWrdvSUs80OGg==”, “associated_data”: “certificate”, “nonce”: “4de73afd28b6” } }
2023-05-10 - 无法收到回调全网最全图文指引,看完就能有效的解决你的问题!!!!
前言:相信很多朋友在开发微信支付接口时遇到无法收到回调问题非常的懊恼,不知道从何下手,相信看完本文章基本就能解决你无法收到回调的问题了。阅读本文章前,建议提前看一下文章右侧的目录,帮助你更好的阅读此文章。 -------- 提前需要准备的工具:postman(其他能调试API的工具也可以) -------- 特别说明:这里说的回调都是后端回调,跟前端的回调方法是没有关系,前端的方法需要到社区进行咨询,例如小程序支付的前端方法问题需要到社区小程序模块进行咨询 什么情况下才会有回调通知 1、 支付成功后微信侧才会发送支付结果回调通知 可参考官方文档:支付通知API 2、 申请退款成功后,只有退款状态为退款异常、退款关闭、退款成功才会发送退款回调通知 可参考官方文档:退款结果通知API 注意: 1.上面只是举例了两个接口,还要更多的回调接口,每个回调接口都会有对应的 通知频率 和 回调触发条件 -------- 2.支付结果回调 是异步队列加公网通知的,支付完成后会立即发送回调消息,以支付结果回调为准,不存在回调支付成功,查询接口却一直返回的是未支付 -------- 3.退款回调 是异步的,申请退款接口返回的成功只是代表了申请退款这个操作成功了,退款整个流程可能经过银行等,所以 回调时长可能会长一些 -------- 4.申请退款成功后,用户侧长时间未到账,或商户查询退款状态一直都是退款中,则可能是退款到用户银行卡中,需要经过银行,一般在7个工作内是比较正常的,若7个工作日后还是退款中,请拨打95017协助排查 -------- 5.回调的作用是告诉商户结果是什么,商户应答回调是告诉接口已经成功收到回调,建议商户最好是按照文档要求去应答接口,若商户是自行查询接口来判断情况,而不是根据回调来判断,理论上是可以不去管回调(包括应答),但还是强烈建议按照正常流程正确的应答接口 -------- 下面介绍一下每一种无法接受到回调的情况及对应的检查方法 -------- 情况一:v3接口能支付成功,未设置APIv3密钥则无法收到回调(非常重要!!!非常重要!!!非常重要!!!一定要优先设置,只要是v3接口,不设置APIv3密钥则无法收到回调) 什么是APIv3密钥?如何设置? [图片] [图片] 注意(APIv2密钥以前也叫API密钥): 1.v2接口 使用的是 APIV2密钥,v2接口 下单能成功 说明就设置好了APIv2密钥。 -------- 2.APIv3密钥 与 APIV2密钥 是隔离的,设置APIv3密钥时,不会导致APIV2密钥发生变化,且 对v2接口没有影响。 -------- 情况二:下单时实际填写的回调地址跟自己实际想要的回调地址不一致,可能多了 / 或者 空格 (注意退款接口需要填写退款回调地址, 不然无法收到回调) [图片] -------- 比如想要的是:http://www.qqweixin.top/weixin/pay/callback/test -------- 实际的填写的:http://www.qqweixin.top/weixin/pay//callback/test -------- 可以重新下一笔新的订单,仔细确认下单时传递的地址跟实际需要的地址是否一致 情况三(硬性条件,不要抱着侥幸心理!!!):回调地址不规范,回调地址规则:回调地址不能携带参数及端口号且不能是直接的ip,域名不能携带特殊符号(比如-等),请检查下单时的回调地址是否有携带参数或端口号,必须为 公网域名 且是 https 开头,现使用 http开头 、携带 端口号 或是 ip 能正常接收回调的用户,建议更换为 https 且去除 端口号 使用正常的域名,避免后期出现回调通知无法接收的情况,请求方式为post请求。 notify_url填写注意事项 [图片] -------- 错误示例: 携带端口号:http://www.qqweixin.top:443/weixin/pay/callback/test 携带参数:http://www.qqweixin.top/weixin/pay/callback/test?id=10086 使用ip地址:192.168.x.x 非公网域名:[图片](一定要使用公网ip映射的域名) -------- 如何检查域名是否有问题:核实回调地址是否可被外网访问,是否有DNS解析成功。 (检查ip地址/域名是否可以ping通:如何ping域名,建议是在不同网络下进行操作,这样可以检查是否是内网ip,ping不通可能的原因是ip地址和域名没有映射成功或者是内网ip(同网络能ping通,不同网络不能ping通,一般就是内网ip),需要到注册的域名网站重新进行映射) 成功示例:[图片] 失败示例:[图片] -------- 情况四:开通了防火墙,拦截了回调 (是否开通了防火墙导致回调地址被拦截了,开通防火墙后设置一下白名单,回调IP段白名单) [图片] -------- 情况五:商户侧网络波动导致部分回调丢失 商户侧由于网络波动导致部分部分回调数据没有正常存储或数据丢失等,可以按照网络监测工具检查 1.一般商户侧出现就部分订单的回调丢失就是这种情况,微信侧目前没有出现过支付成功后未给商户发送回调的情况,若极端情况下出现,官方也肯定是会在第一时间通知商户,所以基本都是商户自身网络问题导致 网络排查工具 [图片] 2.商户业务层已经对回调处理完成并成功应答, 但商户侧自身系统问题,导致这条回调数据丢失,需要商户自身排查 -------- 情况六:程序代码问题(若使用的回调地址本身是在正常使用的回调地址,是对代码或者环境修改后出现的问题,则说明是代码层面或者环境的问题) 使用postman等API调试工具模拟微信支付回调的格式测试,检查代码是否能正常接收回调信息,v2接口的回调信息是xml格式,v3接口的回调格式json格式,上述两种格式都是以字符串的形式发送的数据流,特殊情况:只要是在商户平台进行 手动退款的回调通知都是xml格式。 (注意测试时,发送回调和接收回调尽量不要在同一网络当中,避免都是在是同一网络测试结果不准确,注意:接收到回调为空的现象一般都是接收格式的问题,比如xml格式的数据使用json格式接收) v2接口回调格式(固定为xml格式,v2部分接口需要解密,比如:退款接口,详情会在接口特别说明说明中有描述,退款结果通知) [图片] 示例: <xml> <appid><![CDATA[wx2421b1c4370ec43b]]></appid> <attach><![CDATA[支付测试]]></attach> <bank_type><![CDATA[CFT]]></bank_type> <fee_type><![CDATA[CNY]]></fee_type> <is_subscribe><![CDATA[Y]]></is_subscribe> <mch_id><![CDATA[10000100]]></mch_id> <nonce_str><![CDATA[5d2b6c2a8db53831f7eda20af46e531c]]></nonce_str> <openid><![CDATA[oUpF8uMEb4qRXf22hE3X68TekukE]]></openid> <out_trade_no><![CDATA[1409811653]]></out_trade_no> <result_code><![CDATA[SUCCESS]]></result_code> <return_code><![CDATA[SUCCESS]]></return_code> <sign><![CDATA[B552ED6B279343CB493C5DD0D78AB241]]></sign> <time_end><![CDATA[20140903131540]]></time_end> <total_fee>1</total_fee> <coupon_fee><![CDATA[10]]></coupon_fee> <coupon_count><![CDATA[1]]></coupon_count> <coupon_type><![CDATA[CASH]]></coupon_type> <coupon_id><![CDATA[10000]]></coupon_id> <trade_type><![CDATA[JSAPI]]></trade_type> <transaction_id><![CDATA[1004400740201409030005092168]]></transaction_id> </xml> v3接口回调格式(固定为json格式,格式固定,内容不一样,需要解密) [图片] 示例: { “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”: “3TxpOF8YqF5Zy2cYQWrZNnmC1FWrxwIPvIv4WejUr+8ctmM6L3kxqQ6JS56S7JkVFMiCvfcMGkQFMtUifq09Wrt6+bNwMUNLKQ52zLyMLwS9uML2Y2Qmi1obactel3rwwTs+IXGir505F2eLBG9ruqtJxGd2dlsLQ+0Sl7OUA/mMCnxMXUhfwJC84lv2oZDC3T827Mzy0BQ5YmXfdpgOA0OCTl+OwokWMXJz2DiGafE1n0pqH/R0VgDyUCEAOb6l+dFRR7S0I1yVe7/6czAYp+i7mTgNrmudG7EgDoOVfGga9Wq9epO6PEew1ypK5M8PmIopNSzg34WEouFhOqvPZfi2paqib2gxexcqtniQQbdechavr4SH/3JSpg8Zbnnbeo3ClFDU7eRVO2FCAPQaMlcSmjU4zv2H98dvB9TnIyon/so+QwSo/ZwWMnTKeztviuYd5ICbrtzAPoeeDrPlYlB0pwlFT8Tz3lqC0QZWKvL0+FIj0+9P+2/JvZpr5aVrFosMI1Afb17P7zx69jnLFPFX0ph4AgBK/N8oRNg12uVqvJM3E07/4P7LWLKyrf9FySovQplbhlasAyOf5PWb3aBwEv19hr71uMvAyuCll39zhIZ9M1CZTcSLpuyeWDOUwt3Y7ww0mOMruvK5a5mREuowqfP/OVv73yX/mf/7MEo9wAvz2bNqAuS0c9xc2yn5EHN4rNSTgApcJh2OTNUVEZXu7sL04S/pKpApS4eXxTS1bnLeqVfk5rePQagXFXwMFJVfAPmLyMRLsBLpdc2lO2LIof+nx8HnqjHvKYnolRgJYAlUuHx1mdjsPrZreDjK12b3cBznrfC7gac+3VW4r42f2b533RCAvchchxb7l+sdzQSFImbxZ1IAZFO/ZozZEFFko2FypOh2SdZYigW6Rq6hxw8EFOrvp6GwKpkhGbb4xnQsGHupDAMte5QmiMb9M8KUP5DSIo7gCsO7FMWtXFrdetyQfLXsZ/CidA+JOlSGKL+8s/ISyajpl8YseGNhlq39Zci53GoQCETs/ixLPz4BOTeTLC9FASUoEGPKet+OvYhdo4Xlopbhs95jl6jjgZcT6Bkr5ivG2ocqi2aP5hpnnVDXq/OwXvdofTHxlp2oydlYo9xqXhg+emzSQ8woub6XXO22KOKuEcWMSCiSMWYm9gsP2v0QkCw54ZmJHuDoivV2jVrFQjdH9nO2m68SHj9I9PBj4eSbDG235d/gSxp6VrrH+UaP5b4fjZi4xZ+9Nr1oUAc1Z6RRqqvCVLY1DTMpp2H/aXr9gNUs8fL8kkfuiWEKTkcoW/JKTZjiizzbHEkXSU3+dm4AITiKWrdvSUs80OGg==”, “associated_data”: “certificate”, “nonce”: “4de73afd28b6” } } -------- 情况七:域名(url)转发导致的DNS解析失败 域名转发:所谓域名(url)转发,是通过服务器的特殊设置,将访问您当前域名的用户引导到您指定的另一个网络地址。 地址转向(也可称“URL转发”)即将一个域名指向到另外一个已存在的站点,英文称为“ URL FORWARDING ”。 DNS解析失败:解析失败就是找不到相关域名对应的IP 这种情况一般自己比较难排查吗,所以不要做域名转发,然后再进行测试,出现问题后再按照上述步骤进行检查(建议直接咨询自己的运维人员,他们知道如何处理)
2023-05-10 - 微信支付v3,php代码,包含签名,验签,获取token
<?php //设置为常量方便使用 const v3key = '*********';//v3秘钥 const pr = '******';//商户私钥文件apiclient_key.pem const mchid = '*******';//商户号 const serial_no = '*********';//证书序列号 $url = 'https://api.mch.weixin.qq.com/v3/certificates'; $url_parts = parse_url($url); $canonical_url = ($url_parts['path'] . (!empty($url_parts['query']) ? "?${url_parts['query']}" : "")); /* HTTP请求方法\n URL\n 请求时间戳\n 请求随机串\n 请求报文主体\n GET需要多一个换行符,有body就少一个换行符 */ $stime =time();//时间戳 $nostr = md5(time().mt_rand(000,999));//随机字符串 $message = "GET"."\n". $canonical_url."\n". $stime ."\n". $nostr ."\n"."\n"; //var_dump($message); openssl_sign($message, $sign, file_get_contents(pr), 'sha256WithRSAEncryption'); $sign = base64_encode($sign);//签名信息进行编码 $token = sprintf('mchid="%s",nonce_str="%s",timestamp="%d",serial_no="%s",signature="%s"', mchid, str_replace("\n","",$nostr), str_replace("\n","",$stime), serial_no, $sign);//格式化字符串 //var_dump($token,$sign);exit; $ch = curl_init(); curl_setopt($ch,CURLOPT_URL,$url);//设置请求网址 curl_setopt($ch,CURLOPT_RETURNTRANSFER,1);//返回数据流不输出 curl_setopt($ch,CURLOPT_HEADER,1);//返回header信息 curl_setopt($ch,CURLOPT_HTTPHEADER,array('Authorization: WECHATPAY2-SHA256-RSA2048 ' .$token, 'Accept:application/json', 'User-Agent:Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.108 Safari/537.36'));//设置header信息 $crt = curl_exec($ch); if (curl_getinfo($ch, CURLINFO_HTTP_CODE) == '200') { $headerSize = curl_getinfo($ch, CURLINFO_HEADER_SIZE); $header = substr($crt, 0, $headerSize);//把header信息单独拿出来 $body = substr($crt, $headerSize);}//把返回的数据拿出来 curl_close($ch); /* echo "<pre>"; var_dump("这是返回的body:\n".$body); echo "<hr>"; var_dump("这是header数据:\n".$header); */ //var_dump($crt); //echo $crt; //var_dump( getallheaders()); $str = get_header($header);//把header信息解析成数组 /* echo "<pre>"; var_dump($str); var_dump($body); */ $crs = json_decode($body,true);//把返回的数据解析成数组 //echo "<pre>"; $m = $crs['data'][0]['encrypt_certificate']['ciphertext'];//密文,需要解密 $m = base64_decode($m);//必须需要解码,不然会失败 $add_data = $crs['data'][0]['encrypt_certificate']['associated_data'];//额外数据 $nonce = $crs['data'][0]['encrypt_certificate']['nonce'];//解密字符串 //var_dump($crs['data'][0]['encrypt_certificate']['ciphertext']); // var_dump($crs); $crt = sodium_crypto_aead_aes256gcm_decrypt($m,$add_data,$nonce,v3key);//解密后获取的是证书 $res = openssl_pkey_get_public($crt);//从证书里面读取公钥资源 $ttr= openssl_pkey_get_details($res);//解析并获取公钥 $ttr = $ttr['key'];//证书公钥 //var_dump($ttr); //下面是验证是否为微信发来的信息 //var_dump($str); $v_sj =$str['Wechatpay-Timestamp']."\n". $str['Wechatpay-Nonce']."\n". $body."\n"; //var_dump($v_sj);exit; /* 应答时间戳\n 应答随机串\n 应答报文主体\n v_sj 是根据返回值生成的数据 $str['Wechatpay-Signature']是从请求头里面拿出来的数据 ttr就是证书解析出来的公钥 sha256WithRSAEncryption 验签方式 */ $wx_k = openssl_verify($v_sj,base64_decode($str['Wechatpay-Signature']),$ttr,'sha256WithRSAEncryption'); if($wx_k === 1){ echo '数据获取成功,你的微信支付平台证书序列号为:'.$str['Wechatpay-Serial']."<br>"."CR证书为:"."<br>".$crt."<br>"."公共秘钥为:"."<br>".$ttr."<br>"."已为你保存到文件,青岛系统里面进行查看。"; file_put_contents('wx.crt',$crt); file_put_contents('wx.pub',$ttr); }else{ echo '验签不通过,所有数据不予展示,请联系管理员'; }
2022-10-25 - 全网最全v3接口签名报错排查指引!!!!
前言:签名错误!估计很多朋友看到这个报错的时候就比较头大了,不知道如何下手,对什么是签名等都不是特别了解,所以很难处理好这类问题,下面是我总结的目前一些签名错误的排查指引。阅读本文章前,建议提前看一下文章右侧的目录,帮助你更好的阅读此文章。 确定自己使用的什么版本接口(通过这两个就可以直接判断使用的是什么版本): v3接口特征: 1、参数是JSON格式 [图片] 2、签名类型为非对称密钥SHA256-RSA参考的是:如何生成签名 v2接口特征: 1、参数是XML格式 [图片] 2、签名类型为MD5/HMAC-SHA256,参考的是:签名算法 --------- v2签名错误排查指引:点击 --------- 什么是签名: 1、这里解释的稍微通俗一点,就是把要传递给接口的参数,进行加密,加密的这个动作就是签名,作用就是保障这条请求是你的请求 2、v2接口使用的是APIv2密钥进行签名的(注意是APIv2密钥,跟APIv3密钥没有关系,二者互不影响) [图片] 3、v3接口使用的是商户API证书的私钥进行签名的(什么是商户API证书?如何获取商户API证书?,按照该文档下载后是一个压缩包,有个说明文件,建议先阅读一下说明文件,解压后找到apiclient_key.pem文件,双击选择文本方式打开,就是私钥内容了) [图片] 先确定自己是服务商还是直连商户: [图片] 需要提前准备的工具: 1、postman 2、v3接口签名生成工具(若签名长度过长可能会导致签名工具直接闪退,说明签名本身就有问题) [图片] 下载解压收拾打开这个文件(有些朋友打开时可能会提示[图片]这个错误,原因是电脑本身自己就缺少了 msvcr120.dll 该组件,可以到网上自行下载一个,这里也无法上传,所以需要自己去下载一下了) [图片] 打开后选择【签名/验签】 [图片] 3、微信支付API v3 Postman脚本使用指南,点击下载( 注意:该脚本只适用于v3接口进行测试) [图片] 下载后按照官方的步骤进行导入,然后配置,配置后是这样的(只需要配置下图配置的三个参数,其他的不用管,注意格式要跟下图一样),记得保存配置(ctrl+s) [图片] 注意看自己的请求头是否有这个,我这边配置好直接就有了,没有的手动添加一下即可,注意是:Authorization {{auth}} 别写错了 [图片] 如何确定是配置成功,点证书下载能成功则说明配置没有问题,若报签名错误(就是这个三个参数有问题,缺少了或者有空格或者商户号和证书序列号商户API证书私钥不匹配,注意服务商模式使用的是服务商的商户API证书私钥)或其他错误则是配置有问题(插件没有导入,或者不小心修改了插件的方法或者填入参数格式不对或者没有保存)[图片] 下面介绍一下签名错误的检查方法 小程序发券插件报错查看全网最全v2接口签名报错排查指引!!!! 若使用的是v3接口的SDK报《微信支付签名验证失败》,则说明是APIv3密钥错误 服务端接口签名错误(比如JSAPI下单、APP下单等接口,除调起支付和回调接口基本可以认为是服务端接口) [图片] 只要状态码是401和提示签名啥啥错的,都是签名有问题 1、先使用postman进行测试,按照上述v3接口postman插件配置好后,只要请求证书能成功,则代表使用的商户号、商户API证书私钥和商户API证书序列号是正确的(注意商户API证书序列号和商户API证书是一一对应的吗,如下图,使用的是第一个商户API证书序列号就使用使用第一个对应的后面的证书) 如何查看商户API证书序列号: [图片] [图片] 2、使用postman测试没有问题,则代表这三个参数没有问题,使用验签工具进行验签(注意:验签所使用到的商户API证书私钥一定要是postman当中配置的,若是服务商模式,则使用服务商的商户API证书私钥:apiclient_key.pem) v3接口post请求: [图片] 明文格式如下 ( 【对应我的,各位朋友根据自己真实参数进行填写,注意:里面的中文请求是怎么样,在验签工具就是怎么样,不要请求的是字符串,打印出来到签名工具是转义字符】 ): HTTP请求方法\n --> POST(换行,也就是我们常说的回车键) URL\n --> /v3/pay/transactions/native( 换行,也就是我们常说的回车键 ,注意v3前面一定要带,一定要注意自己真实请求的接口的url是什么,很多人都是使用证书的url,要注意看自己真实请求的接口) 请求时间戳\n --> 1651914100(换行,也就是我们常说的回车键) 请求随机串\n --> qwer12345(换行,也就是我们常说的回车键) 请求报文主体\n -->(这个就是自己真实的请求参数,就一行){“mchid”:“1900006xxxx”,“out_trade_no”:“native121775250120140703323355”,“appid”:“wxdace60xxxxxxx”,“description”:“Image形象店-深圳腾大-QQ公仔”,“notify_url”: “https://weixin.qq.com/","amount”: { “total”: 1,“currency”: “CNY”}}(换行,也就是我们常说的回车键) [图片] 签名值如下(各位朋友根据自己真实参数进行填写): bmxt36Iplhdc5vnA4J/yEG4jfgdeWEO3Ws7viQ6cXCjJdoKyFIJM8S7HL7aNpxxxxxJMi/PjMGSt2NdZdXrD35J9yq6JnpLnRYrmup8n7z3hAg2sqzqykvbPltQeLsTCwZEkP20CaPO4cxxxxxxxxxxxornI39iXJ6FcSgoffM0MO5BCzoDq+Q4iUTYjLBEysKRxxxxxRjaVo9E2buvEgl0eEb4b98FtpgZOiUg28fxl6O/dm+z7AaLfu9okuOuXhxKjH8J2/7k0x7hJW5viaaD0Bcq+Xg== (验签出现这个则说明签名本身就有问题,有空格或者长度有问题) v3接口get请求: [图片] HTTP请求方法\n --> GET(换行,也就是我们常说的回车键) [图片] URL\n --> /v3/pay/transactions/id/1217752501201407033233368018?mchid=1900006xxxx(换行,也就是我们常说的回车键) 请求时间戳\n --> 1651914100(换行,也就是我们常说的回车键) 请求随机串\n --> qwer12345(换行,也就是我们常说的回车键) [图片] 请求报文主体\n -->)换行(根据签名规则,一个换行,加上面的一个,所以是两个,可参考上面的验签截图,也就是我们常说的回车键) 签名长度: [图片] 若上述验签显示不通过则说明是你签名值有问题,没有按照官方的要求生成,可能的原因有 1、代码里面的 \n并不是换行,而且当成了字符串 2、参数有空格、特殊符号或者大小写不对,比如i、L(小写的L),可能是代码某个方法转义了 3、签名使用的 商户性质跟使用的商户API证书私钥不匹配,比如服务商模式使用了子商户的商户API证书私钥(注意使用的文档别搞错了,如何区分文档是不是服务商的,一般文档参数带了子商户号就是服务商的文档) 4、完整签名值Authorization跟不符合文档要求 [图片] 5、注意检查在验签工具当中的参数 是否有反斜杠 \,而你实际传递给接口的是没有的,导致你生成签名的参数是带\,接口校验时是没有,所以签名失败!注意举一反三,有可能是金额的问题,比如签名的时候是33.0,传递给接口的是33,或者反过来的,所以需要严格注意参数 注意,需要跟图片的格式一样,标点符号均为英文下的符号,不要有多余的空格,检查商户号、商户API证书序列号等是否正确且一一匹配 6、生成签名的请求参数部分(请求报文主体这部分),带有中文生成签名,单请求当中的中文却出现了乱码,所以导致接口检测到的签名是使用中文生成的,而传递的是乱码,导致签名问题 客户端签名错误(比如JSAPI调起支付、APP调起支付等,这类属于特殊签名方式,在对应的文档会有详细的说明情况,比如JSAPI调起支付就有介绍如何生成签名) 签名步骤(以JSAPI调起支付为例) [图片] 使用验签工具进行验签: [图片] 签名长度: [图片] 1.先确定前后端使用的是不是同一个签名方式(说白话就是前端必须需要使用一样的版本,比如都使用v2或者v3,本文介绍的是v3,所以服务端,比如下单接口必须是使用的v3版,json格式的参数),前后端签名方式或使用的版本不一致就会报签名错误 2.按照对应的文档检查参数格式及参数是否正确(比如: 签名时是否需要prepayid= ) 3.调起支付的前端方法尽量使用微信支付官方文档提供的方法,注意参数不要有空格等问题 [图片] 4.如果上面检查都没有问题,可能自己的代码有问题,前后端传输问题,比如时间戳timeStamp后端没有成功传递给接口,导致最终传递给微信接是空的也会报错,这种情况建议先把参数提前生成好,然后写死在前端,建议直接重新写个简单的测试页面(可以避免缓存的影响)
2022-09-06 - 微信统计的累计访问人数比调用login接口的人数少?
微信小程序后台统计的累计访问人数比数据库中的用户人数少6k。数据库中的人数是调用过Wx.login接口,就把open id存进去,也就是说数据库中存的open id有2W个,但是小程序后台统计的累计访问人数只有1.4W,请问小程序统计的累计访问人数是通过什么规则统计的?
2018-09-17