bugfix
This commit is contained in:
parent
08f1939601
commit
0b8d9f4bd6
15
json/transfercode.json
Normal file
15
json/transfercode.json
Normal file
@ -0,0 +1,15 @@
|
||||
{
|
||||
"tblname": "transfercode",
|
||||
"title": "转账码",
|
||||
"params": {
|
||||
"sortby": "id",
|
||||
"browserfields": {
|
||||
"exclouded": ["id"],
|
||||
"alters": {
|
||||
}
|
||||
},
|
||||
"editexclouded": [
|
||||
"id"
|
||||
]
|
||||
}
|
||||
}
|
||||
BIN
models/transfercode.xlsx
Normal file
BIN
models/transfercode.xlsx
Normal file
Binary file not shown.
@ -8,6 +8,12 @@ from .payfee import get_pay_fee, sor_get_pay_fee, get_paychannels, get_pay_feera
|
||||
|
||||
# 从 env 或配置载入 provider conf(这里只示例)
|
||||
CONF = {
|
||||
"transfer":{
|
||||
"pop3server": os.getenv("POP3SERVER", ""),
|
||||
"mail": os.getenv("MAIL", ""),
|
||||
"password": os.getenv("PASSWORD", "")
|
||||
"from_mail": os.getenv("FROM_MAIL", "")
|
||||
}
|
||||
"wechat": {
|
||||
"mchid": os.getenv("WXP_MCHID",""),
|
||||
"appid": os.getenv("WXP_APPID", ""),
|
||||
@ -132,6 +138,7 @@ async def payment_notify(request, callback, params_kw=None):
|
||||
# callback url= "/unipay/notify/{provider}"
|
||||
|
||||
def load_unipay():
|
||||
PROVIDERS["transfer"] = get_provider("transfer", CONF["transfer"]),
|
||||
PROVIDERS["wechat"] = get_provider("wechat", CONF["wechat"]),
|
||||
PROVIDERS["paypal"] = get_provider("paypal", CONF["paypal"]),
|
||||
PROVIDERS["alipay"] = get_provider("alipay", CONF["alipay"]),
|
||||
|
||||
@ -1,5 +1,7 @@
|
||||
# unipay/notify.py
|
||||
from typing import Dict
|
||||
from appPublic.log import exception
|
||||
from .providers.transfer import TransferGateway
|
||||
from .providers.wechat import WechatGateway
|
||||
from .providers.paypal import PaypalGateway
|
||||
from .providers.alipay import AlipayGateway
|
||||
@ -12,12 +14,15 @@ def get_provider_channel(name:str):
|
||||
"wechat":"0",
|
||||
"paypal":"1",
|
||||
"alipay":"2",
|
||||
"stripe":"3"
|
||||
"stripe":"3",
|
||||
"transfer":"4"
|
||||
}
|
||||
return channels.get(name, '9')
|
||||
|
||||
def get_provider(name: str, conf: Dict):
|
||||
try:
|
||||
if name == "transfer":
|
||||
return TransferGateway(**conf)
|
||||
if name == "wechat":
|
||||
return WechatGateway(**conf)
|
||||
if name == "paypal":
|
||||
@ -26,7 +31,8 @@ def get_provider(name: str, conf: Dict):
|
||||
return AlipayGateway(**conf)
|
||||
if name == "stripe":
|
||||
return StripeGateway(**conf)
|
||||
except:
|
||||
except Exception as e:
|
||||
exception(f'get_proveder() error {name=}, {conf=}, {e}')
|
||||
return None
|
||||
raise ValueError("unknown provider")
|
||||
|
||||
|
||||
114
unipay/providers/transfer.py
Normal file
114
unipay/providers/transfer.py
Normal file
@ -0,0 +1,114 @@
|
||||
import re
|
||||
from random import randint
|
||||
import poplib
|
||||
from appPublic.log import debug
|
||||
from appPublic.dictObject import DictObject
|
||||
from appPublic.timeUtils import curDateString, timestampstr
|
||||
from email.parser import Parser
|
||||
from email.header import decode_header
|
||||
from email.utils import parseaddr
|
||||
from ..core import Gateway
|
||||
|
||||
|
||||
def guess_charset(msg):
|
||||
charset = msg.get_charset()
|
||||
if charset is None:
|
||||
content_type = msg.get('Content-Type', '').lower()
|
||||
pos = content_type.find('charset=')
|
||||
if pos >= 0:
|
||||
charset = content_type[pos + 8:].strip()
|
||||
return charset
|
||||
|
||||
class EmailClient:
|
||||
def __init__(self, pop3_server, emailaddress, password):
|
||||
self.client = poplib.POP3(pop3_server)
|
||||
self.client.user(emailaddress)
|
||||
self.client.pass_(password)
|
||||
|
||||
def stat(self):
|
||||
return self.client.stat()
|
||||
|
||||
def mail_list(self):
|
||||
resp, mails, octets = self.client.list()
|
||||
|
||||
def get_mail(self, index):
|
||||
resp, lines, octets = self.client.retr(index)
|
||||
debug(f'{resp=}, {octets=}')
|
||||
msg_content = b'\r\n'.join(lines).decode('utf-8')
|
||||
msg = Parser().parsestr(msg_content)
|
||||
mail = {
|
||||
"mailfrom": msg.get('From'),
|
||||
"mailto": msg.get('To'),
|
||||
"subject": msg.get('Subject'),
|
||||
"body": self.get_body(msg)
|
||||
}
|
||||
return DictObject(**mail)
|
||||
|
||||
def get_body(self, msg):
|
||||
if msg.is_multipart():
|
||||
parts = msg.get_payload()
|
||||
content = ''
|
||||
for part in parts:
|
||||
content += self.get_body(part)
|
||||
return content
|
||||
else:
|
||||
content_type = msg.get_content_type()
|
||||
content = msg.get_payload(decode=True)
|
||||
charset = guess_charset(msg)
|
||||
if charset:
|
||||
content = content.decode(charset)
|
||||
else:
|
||||
content = content.decode('utf-8')
|
||||
return content
|
||||
|
||||
class TransferPay(Gateway):
|
||||
def __init__(self, from_mail="", pop3server="", email="", password=""):
|
||||
self.from_email = from_email
|
||||
self.pop3server = pop3server
|
||||
self.email = email
|
||||
self.password = password
|
||||
self.running = False
|
||||
|
||||
async def create_payment(self, payload: Dict[str, Any]) -> str:
|
||||
"""
|
||||
返回一个可以在 H5 里直接重定向的支付宝支付 URL
|
||||
"""
|
||||
ns = {
|
||||
"id": payload["out_trade_no"],
|
||||
"customerid": payload['customerid'],
|
||||
"amount": payload["amount"],
|
||||
"tcode": self.gen_mailcode(),
|
||||
"curdate": curDateString(),
|
||||
"curtime": timestampstr(),
|
||||
"status": '0'
|
||||
}
|
||||
return
|
||||
|
||||
def get_transfer_data(self, mail):
|
||||
assert mail.mailfrom == '95555@message.cmbchina.com'
|
||||
assert mail.mailto == self.email
|
||||
assert mail.body.startswith('动账业务通知')
|
||||
ns = DictObject()
|
||||
match = re.search(r'交易金额\s*[::]?\s*(\d+(?:\.\d+)?)', mail.body)
|
||||
if match:
|
||||
ns.amount = float(match.group(1))
|
||||
p = r'摘要[::]\s*(\d{7})(?!\d)'
|
||||
match = re.search(r'摘要[::]\s*(\d{7})(?!\d)', mail.body)
|
||||
if match:
|
||||
ns.code = match.group(1)
|
||||
assert ns.amount
|
||||
assert ns.code
|
||||
return ns
|
||||
|
||||
def gen_mailcode(self):
|
||||
c = '1'
|
||||
for range(6):
|
||||
c += randint(0,9)
|
||||
return c
|
||||
|
||||
def run(self):
|
||||
self.running = True
|
||||
while self.running:
|
||||
ec = EmailClient(self.pop3server, self.email, self.password)
|
||||
mail = ec.get_mail(1)
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user