gatewayController.py 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332
  1. # -*- coding: utf-8 -*-
  2. """
  3. @Author : Rocky
  4. @Time : 2022/5/9 10:51
  5. @File :gatewayController.py
  6. """
  7. import logging
  8. import time
  9. from django.views.generic.base import View
  10. from AnsjerPush.Config.gatewaySensorConfig import SENSOR_TYPE, EVENT_TYPE
  11. from Model.models import SensorRecord, GatewaySubDevice, GatewayPush, Device_Info, SceneLog, SmartScene
  12. from Object.RedisObject import RedisObject
  13. from Object.ResponseObject import ResponseObject
  14. from Object.utils import LocalDateTimeUtil
  15. from Service.CommonService import CommonService
  16. from Service.EquipmentInfoService import EquipmentInfoService
  17. from Service.HuaweiPushService.HuaweiPushService import HuaweiPushObject
  18. from Service.PushService import PushObject
  19. LOGGER = logging.getLogger('info')
  20. class GatewayView(View):
  21. def get(self, request, *args, **kwargs):
  22. request.encoding = 'utf-8'
  23. operation = kwargs.get('operation')
  24. return self.validation(request.GET, operation)
  25. def post(self, request, *args, **kwargs):
  26. request.encoding = 'utf-8'
  27. operation = kwargs.get('operation')
  28. return self.validation(request.POST, operation)
  29. def validation(self, request_dict, operation):
  30. response = ResponseObject()
  31. if operation == 'gatewayPush': # 网关推送
  32. return self.gateway_push(request_dict, response)
  33. elif operation == 'sceneLogPush': # 场景日志推送
  34. return self.scene_log_push(request_dict, response)
  35. elif operation == 'socketPush': # 插座推送
  36. return self.socket_msg_push(request_dict, response)
  37. else:
  38. return response.json(414)
  39. @staticmethod
  40. def gateway_push(request_dict, response):
  41. """
  42. 网关推送
  43. @param request_dict: 请求参数
  44. @request_dict serial_number: 序列号
  45. @request_dict ieee_addr: 长地址
  46. @request_dict src_addr: 短地址
  47. @request_dict sensor_type: 传感器类型
  48. @request_dict event_type: 事件类型
  49. @request_dict alarm: 消息内容
  50. @request_dict defense: 防御状态,0:撤防,1:防御
  51. @request_dict sensor_status: 拆动状态,拆动时传参
  52. @param response: 响应对象
  53. @return: response
  54. """
  55. logger = logging.getLogger('info')
  56. serial_number = request_dict.get('serial_number', None)
  57. ieee_addr = request_dict.get('ieee_addr', None)
  58. src_addr = request_dict.get('src_addr', None)
  59. sensor_type = int(request_dict.get('sensor_type', None))
  60. event_type = int(request_dict.get('event_type', None))
  61. alarm = request_dict.get('alarm', None)
  62. defense = int(request_dict.get('defense', None))
  63. sensor_status = request_dict.get('sensor_status', None)
  64. logger.info('---调用网关推送接口--- request_dict:{}'.format(request_dict))
  65. if not all([serial_number, ieee_addr, src_addr, sensor_type, event_type, alarm]):
  66. return response.json(444)
  67. n_time = int(time.time())
  68. try:
  69. # 查询子设备表id
  70. gateway_sub_device_qs = GatewaySubDevice.objects.filter(device__serial_number=serial_number,
  71. device_type=sensor_type, ieee_addr=ieee_addr,
  72. src_addr=src_addr).values('id', 'nickname')
  73. if not gateway_sub_device_qs.exists():
  74. return response.json(173)
  75. else:
  76. gateway_sub_device_id = gateway_sub_device_qs[0]['id']
  77. nickname = gateway_sub_device_qs[0]['nickname']
  78. sensor_record_dict = {
  79. 'gateway_sub_device_id': gateway_sub_device_id,
  80. 'alarm': alarm,
  81. 'event_type': event_type,
  82. 'created_time': n_time,
  83. }
  84. # 处理温湿度,不推送
  85. if sensor_type == SENSOR_TYPE['tem_hum_sensor'] and (
  86. event_type == EVENT_TYPE['temperature'] or event_type == EVENT_TYPE['humidity']):
  87. num = request_dict.get('num', None)
  88. num = str(int(num) / 100)
  89. sensor_record_dict['alarm'] = num
  90. SensorRecord.objects.create(**sensor_record_dict)
  91. return response.json(0)
  92. SensorRecord.objects.create(**sensor_record_dict)
  93. # (门磁,烟雾,人体)传感器被拆动/拆动恢复,修改拆动状态
  94. if sensor_status:
  95. if sensor_type != SENSOR_TYPE['smart_button']: # 智能按钮不更新
  96. gateway_sub_device_qs.update(is_tampered=1)
  97. elif sensor_type == SENSOR_TYPE['door_magnet'] or sensor_type == SENSOR_TYPE['smoke_sensor'] or \
  98. sensor_type == SENSOR_TYPE['body_sensor']:
  99. gateway_sub_device_qs.update(is_tampered=0)
  100. # 撤防状态不推送
  101. if defense == 0:
  102. return response.json(0)
  103. device_info_qs = Device_Info.objects.filter(serial_number=serial_number).values('userID_id')
  104. if not device_info_qs.exists():
  105. return response.json(173)
  106. equipment_info_list = []
  107. for device_info in device_info_qs:
  108. user_id = device_info['userID_id']
  109. # 组织存储数据
  110. local_date_time = CommonService.get_now_time_str(n_time=n_time, tz=0, lang='cn')[:10]
  111. equipment_info_list.append(EquipmentInfoService.get_equipment_info_obj(
  112. local_date_time,
  113. add_time=n_time,
  114. event_time=n_time,
  115. receive_time=n_time,
  116. device_uid=serial_number,
  117. device_nick_name=nickname,
  118. alarm=alarm,
  119. event_type=event_type,
  120. device_user_id=user_id,
  121. ))
  122. if equipment_info_list:
  123. # 根据日期获得星期几
  124. week = LocalDateTimeUtil.date_to_week(local_date_time)
  125. EquipmentInfoService.equipment_info_bulk_create(week, equipment_info_list)
  126. # 查询推送配置数据
  127. gateway_push_qs = GatewayPush.objects.filter(user_id=user_id, logout=False). \
  128. values('user_id', 'app_bundle_id', 'app_type', 'push_type', 'token_val', 'm_code', 'lang', 'm_code',
  129. 'tz')
  130. if not gateway_push_qs.exists():
  131. continue
  132. kwargs = {
  133. 'n_time': n_time,
  134. 'event_type': event_type,
  135. 'nickname': nickname,
  136. }
  137. # 推送到每台登录账号的手机
  138. for gateway_push in gateway_push_qs:
  139. app_bundle_id = gateway_push['app_bundle_id']
  140. push_type = gateway_push['push_type']
  141. token_val = gateway_push['token_val']
  142. lang = gateway_push['lang']
  143. tz = gateway_push['tz'] if gateway_push['tz'] else 0
  144. # 获取推送所需数据
  145. msg_title = PushObject.get_msg_title(nickname)
  146. msg_text = PushObject.get_gateway_msg_text(n_time, tz, lang, alarm)
  147. kwargs['msg_title'] = msg_title
  148. kwargs['msg_text'] = msg_text
  149. kwargs['app_bundle_id'] = app_bundle_id
  150. kwargs['token_val'] = token_val
  151. try:
  152. if 'loocam' in app_bundle_id:
  153. # 推送消息
  154. if push_type == 0: # ios apns
  155. PushObject.ios_apns_push(**kwargs)
  156. elif push_type == 1: # android gcm
  157. PushObject.android_fcm_push(**kwargs)
  158. elif push_type == 2: # android 极光推送
  159. PushObject.android_jpush(**kwargs)
  160. elif push_type == 3:
  161. huawei_push_object = HuaweiPushObject()
  162. huawei_push_object.send_push_notify_message(**kwargs)
  163. elif push_type == 4: # android 小米推送
  164. channel_id = 104551
  165. PushObject.android_xmpush(channel_id=channel_id, **kwargs)
  166. elif push_type == 5: # android vivo推送
  167. PushObject.android_vivopush(**kwargs)
  168. elif push_type == 6: # android oppo推送
  169. channel_id = 'DEVICE_REMINDER'
  170. PushObject.android_oppopush(channel_id=channel_id, **kwargs)
  171. elif push_type == 7: # android 魅族推送
  172. PushObject.android_meizupush(**kwargs)
  173. except Exception as e:
  174. logger.info('网关推送消息异常,errLine:{}, errMsg:{}'.format(e.__traceback__.tb_lineno, repr(e)))
  175. continue
  176. return response.json(0)
  177. except Exception as e:
  178. logger.info('---网关推送接口异常--- {}'.format(repr(e)))
  179. return response.json(500, repr(e))
  180. @staticmethod
  181. def scene_log_push(request_dict, response):
  182. """
  183. 网关智能场景日志推送
  184. @param request_dict: 请求参数
  185. @request_dict sceneId: 场景id
  186. @request_dict status: 状态
  187. @param response: 响应对象
  188. @return: response
  189. """
  190. logger = logging.getLogger('info')
  191. scene_id = request_dict.get('sceneId', None)
  192. status = request_dict.get('status', None)
  193. logger.info('---场景日志推送接口--- request_dict:{}'.format(request_dict))
  194. if not all([scene_id, status]):
  195. return response.json(444)
  196. smart_scene_qs = SmartScene.objects.filter(id=scene_id).values('scene_name', 'conditions', 'tasks', 'device_id',
  197. 'sub_device_id', 'user_id')
  198. if not smart_scene_qs.exists():
  199. return response.json(173)
  200. scene_name = smart_scene_qs[0]['scene_name']
  201. tasks = smart_scene_qs[0]['tasks']
  202. device_id = smart_scene_qs[0]['device_id']
  203. sub_device_id = smart_scene_qs[0]['sub_device_id']
  204. n_time = int(time.time())
  205. user_id = smart_scene_qs[0]['user_id']
  206. if sub_device_id:
  207. gateway_sub_device_qs = GatewaySubDevice.objects.filter(id=sub_device_id).values('nickname')
  208. nickname = gateway_sub_device_qs[0]['nickname'] if gateway_sub_device_qs.exists() else ''
  209. else:
  210. device_qs = Device_Info.objects.filter(id=device_id).values('NickName')
  211. nickname = device_qs[0]['NickName'] if device_qs.exists() else ''
  212. log_dict = {
  213. 'scene_id': scene_id,
  214. 'scene_name': scene_name,
  215. 'tasks': tasks,
  216. 'status': status,
  217. 'device_id': device_id,
  218. 'sub_device_id': sub_device_id,
  219. 'created_time': n_time,
  220. }
  221. tasks = eval(tasks)
  222. try:
  223. SceneLog.objects.create(**log_dict)
  224. # 推送日志
  225. gateway_push_qs = GatewayPush.objects.filter(user_id=user_id, logout=False). \
  226. values('user_id', 'app_bundle_id', 'app_type', 'push_type', 'token_val', 'm_code', 'lang', 'm_code',
  227. 'tz')
  228. if not gateway_push_qs.exists():
  229. return response.json(174)
  230. for task in tasks:
  231. event_type = task['event_type']
  232. if event_type == '1001':
  233. kwargs = {
  234. 'n_time': n_time,
  235. 'event_type': event_type,
  236. 'nickname': nickname,
  237. }
  238. event_info = task['value']
  239. # 推送到每台登录账号的手机
  240. for gateway_push in gateway_push_qs:
  241. app_bundle_id = gateway_push['app_bundle_id']
  242. push_type = gateway_push['push_type']
  243. token_val = gateway_push['token_val']
  244. kwargs['msg_title'] = PushObject.get_msg_title(nickname)
  245. kwargs['msg_text'] = event_info
  246. kwargs['app_bundle_id'] = app_bundle_id
  247. kwargs['token_val'] = token_val
  248. try:
  249. # 推送消息
  250. if push_type == 0: # ios apns
  251. PushObject.ios_apns_push(**kwargs)
  252. elif push_type == 1: # android gcm
  253. PushObject.android_fcm_push(**kwargs)
  254. elif push_type == 2: # android 极光推送
  255. PushObject.android_jpush(**kwargs)
  256. elif push_type == 3:
  257. huawei_push_object = HuaweiPushObject()
  258. huawei_push_object.send_push_notify_message(**kwargs)
  259. elif push_type == 4: # android 小米推送
  260. channel_id = 104551
  261. PushObject.android_xmpush(channel_id=channel_id, **kwargs)
  262. elif push_type == 5: # android vivo推送
  263. PushObject.android_vivopush(**kwargs)
  264. elif push_type == 6: # android oppo推送
  265. channel_id = 'DEVICE_REMINDER'
  266. PushObject.android_oppopush(channel_id=channel_id, **kwargs)
  267. elif push_type == 7: # android 魅族推送
  268. PushObject.android_meizupush(**kwargs)
  269. except Exception as e:
  270. logger.info('场景日志推送消息异常,errLine:{}, errMsg:{}'.format(e.__traceback__.tb_lineno, repr(e)))
  271. continue
  272. return response.json(0)
  273. except Exception as e:
  274. logger.info('---场景日志推送接口异常--- {}'.format(repr(e)))
  275. return response.json(500, repr(e))
  276. @classmethod
  277. def socket_msg_push(cls, request_dict, response):
  278. """
  279. 智能插座开关状态推送
  280. """
  281. try:
  282. serial_number = request_dict.get('serialNumber', None)
  283. device_time = request_dict.get('deviceTime', None)
  284. status = request_dict.get('status', None)
  285. if not all([serial_number, status, device_time]):
  286. return response.json(444)
  287. status = int(status)
  288. now_time = int(device_time) if device_time else int(time.time())
  289. # 获取主用户设备id
  290. log_dict = {
  291. 'status': status,
  292. 'device_id': serial_number,
  293. 'created_time': now_time,
  294. }
  295. SceneLog.objects.create(**log_dict)
  296. LOGGER.info('成功接收并保存,插座序列号{},状态:{}'.format(serial_number, status))
  297. return response.json(0)
  298. except Exception as e:
  299. print(repr(e))
  300. LOGGER.info('---插座开关日志推送接口异常--- {}'.format(repr(e)))
  301. return response.json(500, repr(e))