Browse Source

Merge branch 'test' of http://192.168.136.99:3000/servers/ASJServer into peng

peng 2 years ago
parent
commit
3f6e8755ee

+ 1 - 0
Ansjer/local_config/local_settings.py

@@ -67,6 +67,7 @@ MIDDLEWARE = [
     'django.contrib.messages.middleware.MessageMiddleware',
     'django.middleware.clickjacking.XFrameOptionsMiddleware',
     'django.middleware.security.SecurityMiddleware',
+    'MiddleWare.requestRecord.LogMiddleware',
 ]
 
 AUTHENTICATION_BACKENDS = (

+ 11 - 11
Controller/SensorGateway/SmartSocketController.py

@@ -379,10 +379,10 @@ class SmartSocketView(View):
                 data['created_time'] = now_time
                 socket_schedule = SocketSchedule.objects.create(**data)
                 task_id = socket_schedule.id
-            # 将排程任务下发给设备
-            cls.send_socket_schedule(serial_number, task_id, task_type, int(start_time),
-                                     end_time, int(repeat), device_switch,
-                                     task_switch)
+                # 将排程任务下发给设备
+                cls.send_socket_schedule(serial_number, task_id, task_type, int(start_time),
+                                         end_time, int(repeat), device_switch,
+                                         task_switch)
             return response.json(0)
         except Exception as e:
             LOGGER.info('智能插座异常,errLine:{}, errMsg:{}'.format(e.__traceback__.tb_lineno, repr(e)))
@@ -669,13 +669,13 @@ class SmartSocketView(View):
                 if not socket_schedule_qs.exists():
                     return response.json(173)
                 # 发布MQTT消息通知设备删除排程任务
-                for val in socket_schedule_qs:
-                    if val.task_status:
-                        switch_status = 1 if val.switch_status else 0
-                        result = SmartSocketView.send_socket_schedule(val.serial_number, val.id, val.time_type,
-                                                                      val.start_time, val.end_time,
-                                                                      val.repeat, switch_status, 0)
-                        LOGGER.info('删除排程发布结果:{}'.format(result))
+                # for val in socket_schedule_qs:
+                #     if val.task_status:
+                #         switch_status = 1 if val.switch_status else 0
+                #         result = SmartSocketView.send_socket_schedule(val.serial_number, val.id, val.time_type,
+                #                                                       val.start_time, val.end_time,
+                #                                                       val.repeat, switch_status, 0)
+                #         LOGGER.info('删除排程发布结果:{}'.format(result))
                 socket_schedule_qs.delete()
                 return response.json(0)
         except Exception as e:

+ 150 - 7
Controller/UnicomCombo/WXTechController.py

@@ -6,13 +6,22 @@
 @Email   : zhangdongming@asj6.wecom.work
 @Software: PyCharm
 """
+import time
+
 from django.http import QueryDict
 from django.views import View
 
 from Ansjer.config import LOGGER
+from Controller.UnicomCombo.UnicomComboController import UnicomComboView
+from Model.models import UnicomDeviceInfo, Order_Model, UnicomComboExperienceHistory, UnicomCombo
+from Object.Enums.WXOperatorEnum import WXOperatorEnum
+from Object.Enums.WXStartTypeEnum import WXStartTypeEnum
 from Object.ResponseObject import ResponseObject
-from Object.TokenObject import TokenObject
 from Object.WXTechObject import WXTechObject
+from Service.CommonService import CommonService
+
+# 五兴科技电信套餐编码 1G-15天流量包
+COMBO_ID = 'DX-DX-FDX-JCB-1G-15天-4DX-ASJ-YTC-AT-2022123020221230144615'
 
 
 class WXTechController(View):
@@ -42,13 +51,18 @@ class WXTechController(View):
             return self.validation(put, request, operation)
 
         def validation(self, request_dict, request, operation):
-            token = TokenObject(request.META.get('HTTP_AUTHORIZATION'))
-            lang = request_dict.get('lang', token.lang)
-            response = ResponseObject(lang)
-            if token.code != 0:
-                return response.json(token.code)
+            if operation == 'deleteCardPackage':
+                return self.delete_card_package(request_dict, ResponseObject('cn'))
+            token_code, user_id, response = CommonService \
+                .verify_token_get_user_id(request_dict, request)
+            if token_code != 0:
+                return response.json(token_code)
             if operation == 'getCardsInfo':
                 return self.get_cards_info(request_dict, response)
+            elif operation == 'getExperiencePackage':
+                return self.get_experience_package(request_dict, response)
+            elif operation == 'createOrder':
+                return self.create_order_package(request_dict, response)
 
         @classmethod
         def get_cards_info(cls, request_dict, response):
@@ -56,9 +70,9 @@ class WXTechController(View):
             五兴单卡获取信息
             """
             try:
+                LOGGER.info('*****WXTechController.get_cards_info:params:{}'.format(request_dict))
                 iccid = request_dict.get('iccid', None)
                 operator = int(request_dict.get('operator', 3))
-                LOGGER.info('*****WXTechController.get_cards_info:iccid:{},operator:{}'.format(iccid, operator))
                 if not iccid:
                     return response.json(444)
                 data = {'iccid': iccid, 'operator': operator}
@@ -68,3 +82,132 @@ class WXTechController(View):
                 LOGGER.info('*****WXTechController.get_cards_info:errLine:{}, errMsg:{}'
                             .format(e.__traceback__.tb_lineno, repr(e)))
                 return response.json(500, repr(e))
+
+        @classmethod
+        def get_experience_package(cls, request_dict, response):
+            """
+            获取体验套餐
+            """
+            try:
+                LOGGER.info('*****WXTechController.get_experience_package:params{}'.format(request_dict))
+                serial_no = request_dict.get('serialNo', None)
+                if not serial_no:
+                    return response.json(444)
+                # 查询是否注册iccid
+                unicom_device_qs = UnicomDeviceInfo.objects.filter(serial_no=serial_no) \
+                    .values('serial_no', 'user_id', 'iccid')
+                if not unicom_device_qs.exists():
+                    return response.json(173)
+                unicom_device_qs = unicom_device_qs.first()
+                iccid = unicom_device_qs['iccid']
+                # 查看是否体验过免费套餐
+                experience_history_qs = UnicomComboExperienceHistory.objects.filter(iccid=iccid)
+                if experience_history_qs.exists():
+                    return response.json(10062)
+                combo_info_qs = UnicomCombo.objects.filter(combo_type=1, status=0, is_del=False) \
+                    .values('combo_name')
+                if not combo_info_qs.exists():
+                    return response.json(173)
+                result = {'comboName': combo_info_qs[0]['combo_name']}
+                return response.json(0, result)
+            except Exception as e:
+                LOGGER.info('*****WXTechController.get_experience_package:errLine:{}, errMsg:{}'
+                            .format(e.__traceback__.tb_lineno, repr(e)))
+                return response.json(500, repr(e))
+
+        @classmethod
+        def create_order_package(cls, request_dict, response):
+            """
+            五兴电信领取1G15天流量体验包
+            """
+            try:
+                LOGGER.info('*****WXTechController.create_order_package:params:{}'.format(request_dict))
+                serial_no = request_dict.get('serialNo', None)
+                operator = request_dict.get('operator', None)
+                if not all([operator, serial_no]):
+                    return response.json(444)
+                unicom_device_qs = UnicomDeviceInfo.objects.filter(serial_no=serial_no) \
+                    .values('serial_no', 'user_id', 'iccid')
+                if not unicom_device_qs.exists():
+                    return response.json(173)
+                unicom_device_qs = unicom_device_qs.first()
+                user_id = unicom_device_qs['user_id']
+                iccid = unicom_device_qs['iccid']
+                # 查看是否体验过免费套餐
+                experience_history_qs = UnicomComboExperienceHistory.objects.filter(iccid=iccid)
+                if experience_history_qs.exists():
+                    return response.json(10062)
+                data = {'iccid': iccid, 'operator': WXOperatorEnum(int(operator)).value,
+                        'startType': str(WXStartTypeEnum.EFFECTIVE_IMMEDIATELY.value), 'packageCode': COMBO_ID}
+                wx_tech = WXTechObject()
+                # 请求五兴API创建套餐接口
+                res = wx_tech.create_order_package(**data)
+                LOGGER.info('*****五兴创建体验套餐信息:{}'.format(res))
+                if res['code'] == '0':
+                    trade_no = res['data']['orderNumber']
+                    experience_history_vo = {'iccid': iccid, 'experience_type': 0, 'do_time': int(time.time())}
+                    UnicomComboExperienceHistory.objects.create(**experience_history_vo)
+                    order_res = cls.created_order(serial_no, user_id, trade_no)
+                    LOGGER.info('*****系统创建体验订单:{}'.format(order_res))
+                    return response.json(0)
+                return response.json(10063)
+            except Exception as e:
+                LOGGER.info('*****WXTechController.create_order_package:errLine:{}, errMsg:{}'
+                            .format(e.__traceback__.tb_lineno, repr(e)))
+                return response.json(500, repr(e))
+
+        @classmethod
+        def created_order(cls, serial_no, user_id, trade_no):
+            """
+            创建系统订单
+            """
+            combo_info_qs = UnicomCombo.objects.filter(combo_type=1, status=0, is_del=False) \
+                .values('id', 'combo_name', 'price', 'virtual_price', 'remark').order_by('sort')
+            if not combo_info_qs.exists():
+                return False
+            combo_info_vo = combo_info_qs[0]
+            n_time = int(time.time())
+            # 根据序列号获取UID
+            uid = CommonService.query_uid_with_serial(serial_no)
+            order_id = CommonService.createOrderID()
+            # 生成订单必须添加该字段
+            rank_id, ai_rank_id = UnicomComboView().get_cloud_or_ai_combo()
+            order_dict = {'orderID': order_id, 'UID': uid, 'rank_id': rank_id, 'ai_rank_id': ai_rank_id,
+                          'userID_id': user_id, 'desc': combo_info_vo['combo_name'], 'payType': 10,
+                          'payTime': n_time, 'price': combo_info_vo['price'], 'addTime': n_time,
+                          'updTime': n_time, 'status': 1,
+                          'unify_combo_id': str(combo_info_vo['id']), 'order_type': 3,
+                          'store_meal_name': combo_info_vo['combo_name'],
+                          'trade_no': trade_no}
+            Order_Model.objects.create(**order_dict)
+            return True
+
+        @classmethod
+        def delete_card_package(cls, request_dict, response):
+            """
+            PC工具清空卡片的所有套餐订购记录
+            """
+            try:
+                LOGGER.info('*****WXTechController.delete_card_package:params:{}'.format(request_dict))
+                sign = request_dict.get('sign', None)
+                serial_no = request_dict.get('serialNo', None)
+                time_stamp = request_dict.get('timeStamp', None)
+                if not CommonService.check_time_stamp_token(sign, time_stamp):
+                    return response.json(13)
+                    # 查询是否注册iccid
+                unicom_device_qs = UnicomDeviceInfo.objects.filter(serial_no=serial_no) \
+                    .values('serial_no', 'user_id', 'iccid')
+                if not unicom_device_qs.exists():
+                    return response.json(173)
+                iccid = unicom_device_qs[0]['iccid']
+                data = {'iccids': iccid, 'operator': WXOperatorEnum.TELECOM.value}
+                wx_tech = WXTechObject()
+                res = wx_tech.delete_card_package(**data)
+                if res['code'] == '0':
+                    UnicomComboExperienceHistory.objects.filter(iccid=iccid).delete()
+                    return response.json(0)
+                return response.json(177)
+            except Exception as e:
+                LOGGER.info('*****WXTechController.delete_card_package:errLine:{}, errMsg:{}'
+                            .format(e.__traceback__.tb_lineno, repr(e)))
+                return response.json(500, repr(e))

+ 13 - 5
MiddleWare/requestRecord.py

@@ -18,6 +18,7 @@ class RequestRecordMiddleware(MiddlewareMixin):
         request.start_time = time.time()
 
     def process_response(self, request, response):
+        LOGGER = logging.getLogger('info')
         try:
             execute_time = time.time() - request.start_time
             method = request.method
@@ -30,8 +31,15 @@ class RequestRecordMiddleware(MiddlewareMixin):
                 parameter = json.dumps(request.POST.dict())
             else:
                 parameter = ''
-
-            if response.status_code == 500:     # 处理没有捕获异常的情况
+            content = eval(str(response.content, 'utf-8'))  # bytes 转为 dict
+            # 请求是否成功
+            if content['result_code'] != 0:
+                if method == 'GET':
+                    parameter = request.GET
+                elif method == 'POST':
+                    parameter = request.POST
+                LOGGER.info('请求路径:{}, 请求方式:{}, 输入数据:{}, 输出数据:{}, 响应状态:{}'.format(url, method, parameter, content, response.status_code))
+            if response.status_code == 500:  # 处理没有捕获异常的情况
                 request_record_data = {
                     'method': method,
                     'url': url,
@@ -41,9 +49,9 @@ class RequestRecordMiddleware(MiddlewareMixin):
                     'reason_phrase': response.reason_phrase,
                 }
                 RequestRecordModel.objects.create(**request_record_data)
-            elif response.content:     # 处理捕获异常的情况
+            elif response.content:  # 处理捕获异常的情况
                 # print('content: ', response.content)
-                content = eval(str(response.content, 'utf-8'))   # bytes 转为 dict
+                # content = eval(str(response.content, 'utf-8'))  # bytes 转为 dict
                 # logger = logging.getLogger('info')
                 # logger.info('content: {}'.format(content))
                 error_flag = False
@@ -51,7 +59,7 @@ class RequestRecordMiddleware(MiddlewareMixin):
                 if 'result_code' in content and (content['result_code'] == 500 or content['result_code'] == 474):
                     reason_phrase = content['result']
                     error_flag = True
-                elif 'code' in content and content['code'] == 500:    # ResponseObject.returntype == 'pc'
+                elif 'code' in content and content['code'] == 500:  # ResponseObject.returntype == 'pc'
                     reason_phrase = content['data']
                     error_flag = True
                 if error_flag:

+ 20 - 0
Object/Enums/WXOperatorEnum.py

@@ -0,0 +1,20 @@
+# -*- encoding: utf-8 -*-
+"""
+五兴科技 运营商枚举类
+@File    : WXOperatorEnum.py
+@Time    : 2023/5/8 13:53
+@Author  : stephen
+@Email   : zhangdongming@asj6.wecom.work
+@Software: PyCharm
+"""
+from enum import IntEnum, unique
+
+
+@unique
+class WXOperatorEnum(IntEnum):
+    # 联通
+    UNICOM = 1,
+    # 移动
+    MOBILE = 2,
+    # 电信
+    TELECOM = 3

+ 20 - 0
Object/Enums/WXStartTypeEnum.py

@@ -0,0 +1,20 @@
+# -*- encoding: utf-8 -*-
+"""
+五兴科技 运营商枚举类
+@File    : WXOperatorEnum.py
+@Time    : 2023/5/8 13:53
+@Author  : stephen
+@Email   : zhangdongming@asj6.wecom.work
+@Software: PyCharm
+"""
+from enum import IntEnum, unique
+
+
+@unique
+class WXStartTypeEnum(IntEnum):
+    # 立即生效
+    EFFECTIVE_IMMEDIATELY = 0,
+    # 次月生效
+    EFFECTIVE_FOLLOWING_MONTH = 1,
+    # 顺延生效(仅流量包)【未激活的卡片必须先订购一个立即生效,才允许订购次月生效】
+    EXTEND = 2

+ 4 - 0
Object/ResponseObject.py

@@ -124,6 +124,8 @@ class ResponseObject(object):
             10059: 'Order deactivation failure',
             10060: 'This device has purchased foreign cloud storage package, so it cannot buy domestic cloud storage package',
             10061: 'Add the limit reached',
+            10062: 'This device has experienced the package',
+            10063: 'Failed to claim',
         }
         data_cn = {
             0: '成功',
@@ -238,6 +240,8 @@ class ResponseObject(object):
             10059: '订单停用失败',
             10060: '此设备已购买过国外云存套餐,无法购买国内云存套餐',
             10061: '添加已达到上限',
+            10062: '此设备已体验过套餐',
+            10063: '领取失败',
         }
 
         msg = data_cn if self.lang == 'cn' or self.lang == 'zh-Hans' or self.lang == 'zh-Hant' else data_en

+ 51 - 9
Object/WXTechObject.py

@@ -13,7 +13,7 @@ import time
 
 import requests
 
-from Ansjer.config import WX_TECH_URL, WX_TECH_APP_KEY, TWX_TECH_SECRET
+from Ansjer.config import WX_TECH_URL, WX_TECH_APP_KEY, TWX_TECH_SECRET, LOGGER
 from Object.UnicomObject import UnicomObjeect
 
 
@@ -38,26 +38,66 @@ class WXTechObject:
         """
         请求接口必传系统参数
         """
+        nonce = ''.join(str(random.choice(range(1, 10))) for _ in range(5))
         return {
             'appkey': WX_TECH_APP_KEY,
-            'nonce': int(''.join(str(random.choice(range(10))) for _ in range(5))),
+            'nonce': int(nonce),
             'timestamp': int(time.time()),
         }
 
-    def get_cards_info(self, **params):
+    @staticmethod
+    def get_request_params(**params):
         """
-        根据卡号,获取单卡信息及流量使用信息
-        @param params: iccid、operator
-        @return: 卡信息
+        将业务参数与系统参数合并后进行加签得到请求参数体
         """
-        url = WX_TECH_URL + '/api/v2/card/getCardsInfo'
-        # 系统参数
+        # 获取请求系统参数
         data = WXTechObject().get_system_params()
+        # 系统参数与业务参数合并
         params = dict(data, **params)
         # 合并参数后进行升序加密得到sign
         sign = WXTechObject.getSign(TWX_TECH_SECRET, **params)
         params['sign'] = sign
-        response = requests.post(url, data=json.dumps(params), headers=self.headers)
+        params = json.dumps(params)
+        LOGGER.info('*****五兴API请求数据:{}'.format(params))
+        return params
+
+    def get_cards_info(self, **params):
+        """
+        根据卡号,获取单卡信息及流量使用信息
+        @param params: iccid、operator
+        @return: 卡信息
+        """
+        url = WX_TECH_URL + '/api/v2/card/getCardsInfo'
+        return self.wx_service_api(url, **params)
+
+    def create_order_package(self, **params):
+        """
+        卡片套餐订购,主套餐是立即生效,只有流量包可以顺延生效
+        @param params: iccid、operator、startType、packageCode
+        @return: 卡信息
+        """
+        url = WX_TECH_URL + '/api/v2/package/orderPackage'
+        return self.wx_service_api(url, **params)
+
+    def delete_card_package(self, **params):
+        """
+        清空卡片的所有套餐订购记录
+        @param params: operator、iccids
+        @return: 删除成功|失败
+        """
+        url = WX_TECH_URL + '/api/v2/outputApi/deleteCardPackage'
+        return self.wx_service_api(url, **params)
+
+    def wx_service_api(self, url, **params):
+        """
+        @param url 请求地址
+        @param 业务必填参数
+        五兴业务API 统一封装加签请求
+        """
+        # 系统参数合并业务参数并加签得到请求参数
+        rq_body = self.get_request_params(**params)
+        response = requests.post(url, data=rq_body, headers=self.headers)
+        assert response.status_code == 200
         return UnicomObjeect().get_text_dict(response)
 
 
@@ -65,3 +105,5 @@ if __name__ == '__main__':
     pass
     # data = {'iccid': '8986112128003439900', 'operator': 3}
     # print(WXTechObject().get_cards_info(**data))
+    # data = {'iccid': '8986112128003439900', 'operator': 3}
+    # print(WXTechObject().get_cards_info(**data))