소스 검색

修改套餐类型为AI+云存

peng 1 년 전
부모
커밋
49784cea4a
1개의 변경된 파일134개의 추가작업 그리고 0개의 파일을 삭제
  1. 134 0
      Object/UnionPayObject.py

+ 134 - 0
Object/UnionPayObject.py

@@ -0,0 +1,134 @@
+import hashlib
+
+import requests
+import base64
+from OpenSSL import crypto
+from Ansjer.config import BASE_DIR, SERVER_DOMAIN_SSL
+import datetime
+from urllib.parse import parse_qs
+
+
+class UnionPayObject:
+    def __init__(self):
+        self.cert_password = b'000000'
+        self.cert_path = '{}/Ansjer/file/unionpay/acp_test_sign.pfx'.format(BASE_DIR)
+        self.x509_filepath = '{}/Ansjer/file/unionpay/verify_sign_acp.cer'.format(BASE_DIR)
+        self.cert = self.get_cert()
+        self.pay_url = 'https://gateway.test.cup.com.cn/gateway/api/appTransReq.do'
+        self.query_url = 'https://gateway.test.95516.com/gateway/api/queryTrans.do'
+        self.refund_url = 'https://101.231.204.80:5000/gateway/api/backTransReq.do'
+        self.param = {
+            "version": '5.1.0',  # 版本
+            "encoding": "utf-8",  # 编码 可以使用UTF-8,GBK两种方式
+            "bizType": "000201",  # 产品类型  000201:B2C网关支付
+            "signMethod": "01",  # 签名方法  01:RSA签名
+            "accessType": "0",  # 接入类型  0:普通商户直连接入
+            "merId": '777290058205683',  # 商户代码
+            "txnTime": datetime.datetime.now().strftime("%Y%m%d%H%M%S"),  # 订单发送时间
+            "certId": self.cert['certid'],
+        }
+
+    def pay(self, order_id, price):
+        request_data = {
+            "txnType": '01',  # 交易类型  01:消费
+            "txnSubType": "01",  # 交易子类  01:自助消费
+            "backUrl": 'https://test.zositechc.cn/cloudstorage/doapplenotify',  # 后台通知地址 需外网
+            "currencyCode": "156",  # 交易币种  156:人民币
+            # "accType": "01",  # 账号类型 01:银行卡02:存折03:IC卡帐号类型(卡介质)
+            "txnAmt": price,  # 订单金额(单位: 分)
+            "orderId": order_id,
+            "channelType": "08",  # 渠道类型  08:移动
+        }
+        self.param.update(request_data)
+        self.get_sign(self.param)
+        response = requests.post(self.pay_url, self.param)
+        data = self.parse_arguments(response.content.decode('utf-8'))
+        if data['respCode'] != '00':
+            return False
+        # self.validate(data)
+        return data
+
+    def get_cert(self):
+        with open(self.cert_path, "rb") as f:
+            certs = crypto.load_pkcs12(f.read(), self.cert_password)
+            x509data = certs.get_certificate()
+            return {'certid': x509data.get_serial_number(), 'pkey': certs.get_privatekey()}
+
+    def get_sign(self, data):
+        sha256 = hashlib.sha256(self.build_sign_str(data).encode("utf-8")).hexdigest()
+        private = crypto.sign(self.cert["pkey"], sha256, "sha256")
+        data["signature"] = str(base64.b64encode(private), encoding="utf-8")
+
+    @staticmethod
+    def build_sign_str(data):
+        """
+        排序
+        :param data:
+        :return:
+        """
+        req = []
+        for key in sorted(data.keys()):
+            if data[key] != '':
+                req.append("%s=%s" % (key, data[key]))
+
+        return '&'.join(req)
+
+    @staticmethod
+    def parse_arguments(raw):
+        """
+        @raw: raw data to parse argument
+        """
+        data = {}
+        qs_params = parse_qs(str(raw))
+        for name in qs_params.keys():
+            data[name] = qs_params.get(name)[-1]
+        return data
+
+    def validate(self, data):
+        """
+        @data: a dict ready for validate, must contain "signature" key name
+        """
+        signature = base64.b64decode(data.pop('signature'))  # 获取签名
+        sign_pubkey_cert = data.get("signPubKeyCert", None)
+        digest = hashlib.sha256(self.build_sign_str(data).encode("utf-8")).hexdigest()
+        # sign_pubkey_cert = open(self.x509_filepath, 'rb').read()
+
+        try:
+            x509_ert = crypto.load_certificate(crypto.FILETYPE_PEM, sign_pubkey_cert.encode('utf-8'))
+            crypto.verify(x509_ert, signature, digest, 'sha256')
+            return True
+        except Exception as exc:
+            return False
+
+    def query_order(self, order_id):
+        request_data = {
+            "txnType": '00',  # 交易类型  00:查询交易
+            "txnSubType": "00",  # 交易子类  00:查询交易
+            "orderId": order_id,
+        }
+        self.param.update(request_data)
+        self.get_sign(self.param)
+        response = requests.post(self.query_url, self.param)
+        data = self.parse_arguments(response.content.decode('utf-8'))
+        if data['respCode'] != '00':
+            return False
+        return data
+
+    def refund(self, order_id, query_id, price):
+        request_data = {
+            "txnType": "04",  # 交易类型  00:退货
+            "txnSubType": "00",  # 交易子类  00:查询交易
+            "orderId": order_id,
+            "origQryId": query_id,
+            "backUrl": "https://test.zositechc.cn/cloudstorage/doapplenotify",
+            "currencyCode": "156",
+            "channelType": "08",
+            "txnAmt": price
+        }
+        self.param.update(request_data)
+        self.get_sign(self.param)
+        response = requests.post(self.refund_url, self.param)
+        data = self.parse_arguments(response.content.decode('utf-8'))
+        if data['respCode'] != '00':
+            return False
+        return data