feat(wechat): switch from H5 to Native payment (QR code scan)
- Change API endpoint from /v3/pay/transactions/h5 to /v3/pay/transactions/native - Remove scene_info (not needed for native mode) - Return code_url instead of h5_url - recharge.dspy: display QR code image via api.qrserver.com - user_recharge.dspy: return both code_url and qr_url
This commit is contained in:
parent
0266f9fb65
commit
1a2d8f8f2d
@ -143,7 +143,7 @@ class WechatGateway(Gateway):
|
|||||||
# -----------------------------------------------------
|
# -----------------------------------------------------
|
||||||
async def create_payment(self, payload: Dict[str, Any]) -> str:
|
async def create_payment(self, payload: Dict[str, Any]) -> str:
|
||||||
"""
|
"""
|
||||||
H5 下单(默认 H5,可改为 jsapi/native)
|
Native 下单(扫码支付)
|
||||||
"""
|
"""
|
||||||
body = {
|
body = {
|
||||||
"appid": self.appid,
|
"appid": self.appid,
|
||||||
@ -154,15 +154,11 @@ class WechatGateway(Gateway):
|
|||||||
"amount": {
|
"amount": {
|
||||||
"total": int(payload["amount"]),
|
"total": int(payload["amount"]),
|
||||||
"currency": payload.get("currency", "CNY")
|
"currency": payload.get("currency", "CNY")
|
||||||
},
|
|
||||||
"scene_info": {
|
|
||||||
"payer_client_ip": payload.get("client_ip", "127.0.0.1"),
|
|
||||||
"h5_info": {"type": "Wap"}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
body_str = json.dumps(body, ensure_ascii=False)
|
body_str = json.dumps(body, ensure_ascii=False)
|
||||||
|
|
||||||
url_path = "/v3/pay/transactions/h5"
|
url_path = "/v3/pay/transactions/native"
|
||||||
url = WECHAT_API_BASE + url_path
|
url = WECHAT_API_BASE + url_path
|
||||||
auth = self._sign("POST", url_path, body_str)
|
auth = self._sign("POST", url_path, body_str)
|
||||||
|
|
||||||
@ -176,10 +172,10 @@ class WechatGateway(Gateway):
|
|||||||
err_code = ret.get("code", "UNKNOWN")
|
err_code = ret.get("code", "UNKNOWN")
|
||||||
err_msg = ret.get("message", str(ret))
|
err_msg = ret.get("message", str(ret))
|
||||||
raise Exception(f"WeChat API error (HTTP {resp.status}): [{err_code}] {err_msg}")
|
raise Exception(f"WeChat API error (HTTP {resp.status}): [{err_code}] {err_msg}")
|
||||||
h5_url = ret.get("h5_url")
|
code_url = ret.get("code_url")
|
||||||
if not h5_url:
|
if not code_url:
|
||||||
raise Exception(f"WeChat API response missing h5_url: {json.dumps(ret, ensure_ascii=False)}")
|
raise Exception(f"WeChat Native API response missing code_url: {json.dumps(ret, ensure_ascii=False)}")
|
||||||
return h5_url
|
return code_url
|
||||||
|
|
||||||
# -----------------------------------------------------
|
# -----------------------------------------------------
|
||||||
async def refund(self, payload: Dict[str, Any]) -> Dict[str, Any]:
|
async def refund(self, payload: Dict[str, Any]) -> Dict[str, Any]:
|
||||||
|
|||||||
@ -1,13 +1,15 @@
|
|||||||
|
import urllib.parse
|
||||||
params_kw.amount = float(params_kw.amount)
|
params_kw.amount = float(params_kw.amount)
|
||||||
debug(f'recharge.dspy: {params_kw=}')
|
debug(f'recharge.dspy: {params_kw=}')
|
||||||
try:
|
try:
|
||||||
url = await create_payment(request, params_kw)
|
code_url = await create_payment(request, params_kw)
|
||||||
|
qr_img_url = 'https://api.qrserver.com/v1/create-qr-code/?size=280x280&data=' + urllib.parse.quote(code_url, safe='')
|
||||||
return {
|
return {
|
||||||
"widgettype":"NewWindow",
|
"widgettype":"NewWindow",
|
||||||
"options":{
|
"options":{
|
||||||
"url": url,
|
"url": qr_img_url,
|
||||||
"height": "100%",
|
"height": "340",
|
||||||
"width":"100%"
|
"width":"340"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
|
|||||||
@ -1,3 +1,4 @@
|
|||||||
|
import urllib.parse
|
||||||
if params_kw.amount is None:
|
if params_kw.amount is None:
|
||||||
return {
|
return {
|
||||||
"status": "error",
|
"status": "error",
|
||||||
@ -20,14 +21,16 @@ if params_kw.currency != 'CNY':
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
params_kw.amount = float(params_kw.amount)
|
params_kw.amount = float(params_kw.amount)
|
||||||
debug(f'recharge.dspy: {params_kw=}')
|
debug(f'user_recharge.dspy: {params_kw=}')
|
||||||
|
|
||||||
try:
|
try:
|
||||||
url = await create_payment(request, params_kw)
|
url = await create_payment(request, params_kw)
|
||||||
|
qr_url = 'https://api.qrserver.com/v1/create-qr-code/?size=280x280&data=' + urllib.parse.quote(url, safe='')
|
||||||
return {
|
return {
|
||||||
"status": "ok",
|
"status": "ok",
|
||||||
"data": {
|
"data": {
|
||||||
"url": url
|
"code_url": url,
|
||||||
|
"qr_url": qr_url
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user