cxjz.py 37 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800
  1. # -*- coding: utf-8 -*-
  2. # !/usr/bin/env python
  3. import datetime
  4. import time
  5. from apilib.utils_datetime import timestamp_to_dt
  6. from apps.web.constant import Const, DeviceCmdCode, MQTT_TIMEOUT
  7. from apps.web.core.adapter.base import SmartBox, fill_2_hexByte
  8. from apps.web.core.exceptions import ServiceException
  9. from apps.web.core.networking import MessageSender
  10. from apps.web.device.models import Device
  11. class ChargingCXJZBox(SmartBox):
  12. # 从设备侧获取端口状态
  13. def get_port_status_from_dev(self):
  14. devInfo = MessageSender.send(self.device, self.make_random_cmdcode(),
  15. {'IMEI': self._device['devNo'], "funCode": 'A0', 'data': '01FFFF'})
  16. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  17. if devInfo['rst'] == -1:
  18. raise ServiceException(
  19. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  20. elif devInfo['rst'] == 1:
  21. raise ServiceException(
  22. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  23. data = devInfo['data'][10::]
  24. workMode = self.A3_setting_data['workMode'] # 0 时间 1 电量
  25. result = {}
  26. portNum = 10
  27. ii = 0
  28. while ii < portNum:
  29. port = ii + 1
  30. statusTemp = data[4 + 16 * ii: 16 + 16 * ii]
  31. if workMode == 0:
  32. if statusTemp[0:4] == '0000':
  33. status = {'status': Const.DEV_WORK_STATUS_IDLE}
  34. elif statusTemp[0:4] != '0000':
  35. status = {'status': Const.DEV_WORK_STATUS_WORKING}
  36. else:
  37. status = {'status': Const.DEV_WORK_STATUS_WORKING}
  38. elif workMode == 1:
  39. if statusTemp[4:8] == '0000':
  40. status = {'status': Const.DEV_WORK_STATUS_IDLE}
  41. elif statusTemp[4:8] != '0000':
  42. status = {'status': Const.DEV_WORK_STATUS_WORKING}
  43. else:
  44. status = {'status': Const.DEV_WORK_STATUS_WORKING}
  45. else:
  46. if statusTemp == '000000000000':
  47. status = {'status': Const.DEV_WORK_STATUS_IDLE}
  48. else:
  49. status = {'status': Const.DEV_WORK_STATUS_WORKING}
  50. ii += 1
  51. result[str(port)] = status
  52. allPorts, usedPorts, usePorts = self.get_port_static_info(result)
  53. Device.update_dev_control_cache(self._device['devNo'],
  54. {'allPorts': allPorts, 'usedPorts': usedPorts, 'usePorts': usePorts})
  55. # 这里存在多线程更新缓存的场景,可能性比较低,但是必须先取出来,然后逐个更新状态,然后再记录缓存
  56. ctrInfo = Device.get_dev_control_cache(self._device['devNo'])
  57. for strPort, info in result.items():
  58. if ctrInfo.has_key(strPort):
  59. ctrInfo[strPort].update({'status': info['status']})
  60. else:
  61. ctrInfo[strPort] = info
  62. Device.update_dev_control_cache(self._device['devNo'], ctrInfo)
  63. return result
  64. # 获取端口状态
  65. def get_port_status(self, force = False):
  66. if force:
  67. return self.get_port_status_from_dev()
  68. ctrInfo = Device.get_dev_control_cache(self._device['devNo'])
  69. statusDict = {}
  70. allPorts = ctrInfo.get('allPorts', 10)
  71. for ii in range(allPorts):
  72. tempDict = ctrInfo.get(str(ii + 1), {})
  73. if tempDict.has_key('status'):
  74. statusDict[str(ii + 1)] = {'status': tempDict.get('status')}
  75. elif tempDict.has_key('isStart'):
  76. if tempDict['isStart']:
  77. statusDict[str(ii + 1)] = {'status': Const.DEV_WORK_STATUS_WORKING}
  78. else:
  79. statusDict[str(ii + 1)] = {'status': Const.DEV_WORK_STATUS_IDLE}
  80. else:
  81. statusDict[str(ii + 1)] = {'status': Const.DEV_WORK_STATUS_IDLE}
  82. allPorts, usedPorts, usePorts = self.get_port_static_info(statusDict)
  83. Device.update_dev_control_cache(self._device['devNo'],
  84. {'allPorts': allPorts, 'usedPorts': usedPorts, 'usePorts': usePorts})
  85. return statusDict
  86. # 支付成功启动设备
  87. def start_device(self, package, openId, attachParas):
  88. if attachParas is None:
  89. raise ServiceException({'result': 2, 'description': u'请您选择合适的充电线路、电池类型信息'})
  90. if not attachParas.has_key('chargeIndex'):
  91. raise ServiceException({'result': 2, 'description': u'请您选择合适的充电线路'})
  92. port = hex(int(attachParas['chargeIndex']))
  93. hexPort = fill_2_hexByte(port, 2)
  94. needTime = int(package['time'])
  95. needCoins = int(package['coins'])
  96. needElec = round(needCoins / float(self.elec_fee['elecFee']), 1)
  97. workMode = self.A3_setting_data['workMode']
  98. unit = package.get('unit', u'分钟')
  99. if unit == u'小时':
  100. needTime = int(package['time']) * 60
  101. elif unit == u'天':
  102. needTime = int(package['time']) * 1440
  103. hexTime = fill_2_hexByte(hex(needTime))
  104. hexElec = fill_2_hexByte(hex(int(needElec * 10)))
  105. devInfo = MessageSender.send(device = self.device, cmd = DeviceCmdCode.OPERATE_DEV_SYNC, payload = {
  106. 'IMEI': self._device['devNo'],
  107. "funCode": 'CA',
  108. 'data': hexPort + hexTime + hexElec
  109. }, timeout = MQTT_TIMEOUT.START_DEVICE)
  110. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  111. if devInfo['rst'] == -1:
  112. raise ServiceException({'result': 2, 'description': u'充电桩正在玩命找网络,您的金币还在,重试不需要重新付款,建议您试试旁边其他设备,或者稍后再试哦'})
  113. elif devInfo['rst'] == 1:
  114. raise ServiceException({'result': 2, 'description': u'充电桩正在忙,无响应,您的金币还在,请试试其他线路,或者请稍后再试哦'})
  115. start_timestamp = int(time.time())
  116. devInfo['finishedTime'] = start_timestamp + needTime * 60
  117. Device.update_dev_control_cache(
  118. self._device['devNo'],
  119. {
  120. str(attachParas['chargeIndex']):
  121. {
  122. 'startTime': timestamp_to_dt(start_timestamp).strftime('%Y-%m-%d %H:%M:%S'),
  123. 'coins': needCoins,
  124. 'needTime': needTime,
  125. 'isStart': True,
  126. 'workMode': workMode,
  127. 'needElec': needElec,
  128. 'openId': openId,
  129. 'refunded': False,
  130. 'status': Const.DEV_WORK_STATUS_WORKING,
  131. 'finishedTime': devInfo['finishedTime']
  132. }
  133. })
  134. return devInfo
  135. def get_port_info(self, line):
  136. data = fill_2_hexByte(hex(int(line)), 2)
  137. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  138. {'IMEI': self._device['devNo'], "funCode": 'A1', 'data': data + 'FFFF'})
  139. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  140. if devInfo['rst'] == -1:
  141. raise ServiceException(
  142. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  143. elif devInfo['rst'] == 1:
  144. raise ServiceException(
  145. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  146. portData = devInfo['data'][10::]
  147. port = int(portData[0:2], 16)
  148. leftTime = int(portData[4:8], 16)
  149. leftElec = int(portData[8:12], 16) / 100
  150. power = int(portData[12:16], 16)
  151. return {'port': port, 'leftTime': leftTime, 'leftElec': leftElec, 'power': power}
  152. # 配合stop_charging_port使用
  153. def active_deactive_port(self, port, active):
  154. if active:
  155. raise ServiceException({'result': 2, 'description': u'该设备不支持直接打开端口'})
  156. self.stop_charging_port(port)
  157. devInfo = Device.get_dev_control_cache(self._device['devNo'])
  158. portCtrInfo = devInfo.get(str(port), {})
  159. portCtrInfo.update({'isStart': False, 'status': Const.DEV_WORK_STATUS_IDLE,
  160. 'endTime': datetime.datetime.now().strftime(Const.DATETIME_FMT)})
  161. newValue = {str(port): portCtrInfo}
  162. Device.update_dev_control_cache(self._device['devNo'], newValue)
  163. # 远程停止某个端口的使用
  164. def stop_charging_port(self, port):
  165. data = {}
  166. portStr = fill_2_hexByte(hex(int(port)), 2)
  167. portData = self.get_port_info(port)
  168. devData = Device.get_dev_control_cache(self._device['devNo'])
  169. portCtrInfo = devData.get(str(port), {})
  170. data.update(portData)
  171. data.update(portCtrInfo)
  172. Device.update_dev_control_cache(self._device['devNo'],
  173. {str(port): data})
  174. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  175. {'IMEI': self._device['devNo'], "funCode": 'CB',
  176. 'data': portStr + 'FFFF' + 'FFFF'})
  177. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  178. if devInfo['rst'] == -1:
  179. raise ServiceException(
  180. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  181. elif devInfo['rst'] == 1:
  182. raise ServiceException(
  183. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  184. # 分析事件上报
  185. def analyze_event_data(self, data):
  186. cmdCode = data[2:4]
  187. if cmdCode in ['88', '80' '01', '02', '03', '04']:
  188. if cmdCode == '88': # 断电和正常都走这个
  189. reason = u'充电结束。'
  190. elif cmdCode == '01':
  191. reason = u'线路过载。'
  192. elif cmdCode == '02':
  193. reason = u'线路空载。'
  194. elif cmdCode == '03':
  195. reason = u'电池已充满。'
  196. elif cmdCode == '80':
  197. reason = u'购买电量已用完。'
  198. elif cmdCode == '04':
  199. reason = u'设备故障'
  200. return {'status': Const.DEV_WORK_STATUS_FAULT, 'reason': reason}
  201. else:
  202. reason = u''
  203. port = int(data[10:12], 16)
  204. leftTime = int(data[14:18], 16)
  205. leftElec = int(data[18:22], 16) / 100
  206. power = int(data[22:26], 16)
  207. return {
  208. 'status': Const.DEV_WORK_STATUS_IDLE,
  209. 'cmdCode': cmdCode, 'port': port,
  210. 'leftTime': leftTime, 'leftElec': leftElec,
  211. 'power': power, 'reason': reason
  212. }
  213. # 故障上报
  214. if cmdCode == 'AE':
  215. temperature = int(data[14: 18], 16) # 温度数值
  216. smokeCon = int(data[18: 22], 16) # 烟感浓度
  217. buzzer = bool(int(data[22: 24])) # 蜂鸣状态 表示设备是否处于告警状态
  218. smokeSwitch = bool(int(data[24: 26])) # 烟感开关
  219. return {
  220. "cmdCode": cmdCode,
  221. "temperature": temperature,
  222. "smokeCon": smokeCon,
  223. "buzzer": buzzer,
  224. "smokeSwitch": smokeSwitch
  225. }
  226. # 总获取设备参数: A2, A3, A4, A9, 电量计费
  227. def get_dev_setting(self):
  228. """
  229. 从设备端获取参数
  230. 可以修改为 从设备上直接读取 新建指令一次性回复
  231. 目前暂时不处理
  232. :return:
  233. """
  234. if self.device.devTypeCode == Const.DEVICE_TYPE_CODE_CHANGING_CXJZ: # 无烟感版本
  235. data = {}
  236. data.update(self.A2_setting_data)
  237. data.update(self.A3_setting_data)
  238. data.update(self.A4_setting_data)
  239. data.update(self.A9_setting_data)
  240. data.update(self.elec_fee)
  241. data.update(self.lock_device)
  242. else:
  243. data = self.FA_setting_data
  244. return data
  245. # A2: 本机区号, 刷卡统计, 投币统计
  246. @property
  247. def A2_setting_data(self):
  248. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  249. {'IMEI': self._device['devNo'], "funCode": 'A2', 'data': '01FFFF'})
  250. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  251. if devInfo['rst'] == -1:
  252. raise ServiceException(
  253. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  254. elif devInfo['rst'] == 1:
  255. raise ServiceException(
  256. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  257. data = devInfo['data'][14::]
  258. deviceNum = int(data[0:4], 16) # 本机区号
  259. putCards = int(data[4:8], 16) # 刷卡统计
  260. putCoins = int(data[8:12], 16) # 投币统计
  261. return {'deviceNum': deviceNum, 'putCards': putCards, 'putCoins': putCoins}
  262. # A3: 工作模式, 限定功率, 断电开关, 预设记币, 预设开关
  263. @property
  264. def A3_setting_data(self):
  265. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  266. {'IMEI': self._device['devNo'], "funCode": 'A3', 'data': '01FFFF'})
  267. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  268. if devInfo['rst'] == -1:
  269. raise ServiceException(
  270. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  271. elif devInfo['rst'] == 1:
  272. raise ServiceException(
  273. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  274. data = devInfo['data'][12::]
  275. workMode = int(data[0:2], 16) # 工作模式
  276. limitedPower = int(data[2:6], 16) # 限定功率
  277. powerOffSwitch = True if int(data[6:8], 16) == 1 else False # 断电开关
  278. presetCoins = int(data[8:12], 16) # 预设记币
  279. presetSwitch = True if int(data[12:14], 16) == 1 else False # 预设开关
  280. return {'workMode': workMode, 'limitedPower': limitedPower, 'powerOffSwitch': powerOffSwitch,
  281. 'presetCoins': presetCoins, 'presetSwitch': presetSwitch}
  282. # A4: 刷卡投币电量设置, 刷卡时间, 投币时间
  283. @property
  284. def A4_setting_data(self):
  285. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  286. {'IMEI': self._device['devNo'], "funCode": 'A4', 'data': '01FFFF'})
  287. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  288. if devInfo['rst'] == -1:
  289. raise ServiceException(
  290. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  291. elif devInfo['rst'] == 1:
  292. raise ServiceException(
  293. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  294. data = devInfo['data'][12::]
  295. elecSetting = int(data[0:4], 16) / 10 # 刷卡投币电量设置
  296. cardTime = int(data[4:8], 16) # 刷卡充电时间
  297. coinTime = int(data[8:12], 16) # 投币充电时间
  298. maxCoins = int(data[12:14], 16)
  299. return {'elecSetting': elecSetting, 'cardTime': cardTime, 'coinTime': coinTime, 'maxCoins': maxCoins}
  300. # A9: 空载断电时间, 充满功率判断
  301. @property
  302. def A9_setting_data(self):
  303. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  304. {'IMEI': self._device['devNo'], "funCode": 'A9', 'data': '01FFFF'})
  305. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  306. if devInfo['rst'] == -1:
  307. raise ServiceException(
  308. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  309. elif devInfo['rst'] == 1:
  310. raise ServiceException(
  311. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  312. data = devInfo['data'][14::]
  313. powerOffTime = int(data[0:4], 16) # 断电时间
  314. fullElecJudgPower = int(data[4:8], 16) # 充满检测功率
  315. return {'powerOffTime': powerOffTime, 'fullElecJudgPower': fullElecJudgPower}
  316. @property
  317. def AE_setting_data(self):
  318. """
  319. 烟雾告警指令
  320. :return:
  321. """
  322. devInfo = MessageSender.send(
  323. self.device,
  324. DeviceCmdCode.OPERATE_DEV_SYNC,
  325. {
  326. "IMEI": self.device.devNo,
  327. "funCode": "AE",
  328. "data": "01FFFF"
  329. }
  330. )
  331. if 'rst' in devInfo and devInfo['rst'] != 0:
  332. if devInfo['rst'] == -1:
  333. raise ServiceException({'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  334. if devInfo['rst'] == 1:
  335. raise ServiceException({'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  336. # 两个数值两个开关
  337. temperature = int(devInfo["data"][14: 18], 16) # 温度数值
  338. smokeCon = int(devInfo["data"][18: 22], 16) # 烟感浓度
  339. buzzer = bool(int(devInfo["data"][22: 24])) # 蜂鸣状态 表示设备是否处于告警状态
  340. smokeSwitch = bool(int(devInfo["data"][24: 26])) # 烟感开关
  341. return {
  342. "temperature": temperature,
  343. "smokeCon": smokeCon,
  344. "buzzer": buzzer,
  345. "smokeSwitch": smokeSwitch
  346. }
  347. @property
  348. def FA_setting_data(self):
  349. """
  350. 自定义指令合集
  351. 一次性将所有的数据从主板获取
  352. :return:
  353. """
  354. devInfo = MessageSender.send(
  355. self.device,
  356. DeviceCmdCode.OPERATE_DEV_SYNC,
  357. {
  358. "IMEI": self.device.devNo,
  359. "funCode": "FA",
  360. }
  361. )
  362. if 'rst' in devInfo and devInfo['rst'] != 0:
  363. if devInfo['rst'] == -1:
  364. raise ServiceException({'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  365. if devInfo['rst'] == 1:
  366. raise ServiceException({'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  367. data = devInfo["data"][10:]
  368. return {
  369. # A2
  370. "deviceNum": int(data[0: 16][4: 8], 16), # 本机区号
  371. "putCards": int(data[0: 16][8: 12], 16), # 刷卡统计
  372. "putCoins": int(data[0: 16][12: 16], 16), # 投币统计
  373. # A3
  374. "workMode": int(data[16: 32][2: 4], 16),
  375. "limitedPower": int(data[16: 32][4: 8], 16),
  376. "powerOffSwitch": bool(int(data[16: 32][8: 10], 16)),
  377. "presetCoins": int(data[16: 32][10: 14], 16),
  378. "presetSwitch": bool(int(data[16: 32][14: 16], 16)),
  379. # A4
  380. "elecSetting": int(data[32: 48][2: 6], 16) / 10,
  381. "cardTime": int(data[32: 48][6: 10], 16),
  382. "coinTime": int(data[32: 48][10: 14], 16),
  383. "maxCoins": int(data[32: 48][14: 16], 16),
  384. # A9
  385. "powerOffTime": int(data[48: 64][4: 8], 16),
  386. "fullElecJudgPower": int(data[48: 64][8: 12], 16),
  387. # AE
  388. "temperature": int(data[64: 80][4: 8], 16),
  389. "smokeCon": int(data[64: 80][8: 12], 16),
  390. "buzzer": bool(int(data[64: 80][12: 14], 16)),
  391. "smokeSwitch": bool(int(data[64: 80][14: 16], 16))
  392. }
  393. # 获取电量计费标准
  394. @property
  395. def elec_fee(self):
  396. devs = Device.get_collection().find({'devNo': self._device['devNo']})
  397. if devs.count == 0:
  398. raise ServiceException(
  399. {'result': 2, 'description': u'没有找到设备哦'})
  400. return {'elecFee': devs[0].get('otherConf', {}).get('elecFee', 1)}
  401. # 获取设备锁定状态
  402. @property
  403. def lock_device(self):
  404. devs = Device.get_collection().find({'devNo': self._device['devNo']})
  405. if devs.count == 0:
  406. raise ServiceException(
  407. {'result': 2, 'description': u'没有找到设备哦'})
  408. return {'lockDevice': devs[0].get('otherConf', {}).get('lockDevice', False)}
  409. # 设置电量计费标准
  410. def set_elec_fee(self, elecFee):
  411. dev = Device.objects(devNo = self._device['devNo']).first()
  412. if not dev:
  413. raise ServiceException({'result': 2, 'description': u'没有找到设备哦'})
  414. dev.otherConf['elecFee'] = elecFee
  415. dev.save()
  416. # 设置清除记币按钮
  417. def clear_put_coins(self, clear = False):
  418. if clear is True:
  419. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  420. {'IMEI': self._device['devNo'], "funCode": 'B0', 'data': '01FFFF'})
  421. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  422. if devInfo['rst'] == -1:
  423. raise ServiceException(
  424. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  425. elif devInfo['rst'] == 1:
  426. raise ServiceException(
  427. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  428. # 设置设备区号
  429. def set_device_num(self, deviceNum):
  430. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  431. {'IMEI': self._device['devNo'], "funCode": 'B2', 'data': '01' + deviceNum})
  432. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  433. if devInfo['rst'] == -1:
  434. raise ServiceException(
  435. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  436. elif devInfo['rst'] == 1:
  437. raise ServiceException(
  438. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  439. # 设置工作模式
  440. def set_work_mode(self, workMode):
  441. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  442. {'IMEI': self._device['devNo'], "funCode": 'B3', 'data': '01' + workMode})
  443. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  444. if devInfo['rst'] == -1:
  445. raise ServiceException(
  446. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  447. elif devInfo['rst'] == 1:
  448. raise ServiceException(
  449. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  450. # 设置限定功率
  451. def set_limited_power(self, limitedPower):
  452. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  453. {'IMEI': self._device['devNo'], "funCode": 'B4', 'data': '01' + limitedPower})
  454. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  455. if devInfo['rst'] == -1:
  456. raise ServiceException(
  457. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  458. elif devInfo['rst'] == 1:
  459. raise ServiceException(
  460. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  461. # 设置断电开关
  462. def set_power_off_switch(self, switch = True):
  463. data = '0001' if switch is True else '0000'
  464. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  465. {'IMEI': self._device['devNo'], "funCode": 'B5', 'data': '01' + data})
  466. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  467. if devInfo['rst'] == -1:
  468. raise ServiceException(
  469. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  470. elif devInfo['rst'] == 1:
  471. raise ServiceException(
  472. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  473. # 设置预设开关
  474. def set_preset_switch(self, switch = False):
  475. data = '0000' if switch is False else '0001'
  476. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  477. {'IMEI': self._device['devNo'], "funCode": 'B6', 'data': '01' + data})
  478. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  479. if devInfo['rst'] == -1:
  480. raise ServiceException(
  481. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  482. elif devInfo['rst'] == 1:
  483. raise ServiceException(
  484. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  485. # 设置烟感开关
  486. def set_smoke(self, smokeSwitch):
  487. if self.device.devTypeCode not in [Const.DEVICE_TYPE_CODE_CHANGING_CXJZ_SMOKE, '1002171']:
  488. raise ServiceException({"result": 2, "description": "当前设备不支持"})
  489. if smokeSwitch is None:
  490. return
  491. data = "01{:04X}".format(int(smokeSwitch))
  492. devInfo = MessageSender.send(
  493. self.device,
  494. DeviceCmdCode.OPERATE_DEV_SYNC,
  495. {
  496. 'IMEI': self._device['devNo'],
  497. "funCode": 'C6',
  498. 'data': data
  499. }
  500. )
  501. if 'rst' in devInfo and devInfo['rst'] != 0:
  502. if devInfo['rst'] == -1:
  503. raise ServiceException({'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  504. elif devInfo['rst'] == 1:
  505. raise ServiceException({'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  506. # 设置预设投币数
  507. def set_preset_coins(self, presetCoins):
  508. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  509. {'IMEI': self._device['devNo'], "funCode": 'B7', 'data': '01' + presetCoins})
  510. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  511. if devInfo['rst'] == -1:
  512. raise ServiceException(
  513. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  514. elif devInfo['rst'] == 1:
  515. raise ServiceException(
  516. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  517. # 设置断电时间
  518. def set_power_off_time(self, powerOffTime):
  519. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  520. {'IMEI': self._device['devNo'], "funCode": 'B8', 'data': '01' + powerOffTime})
  521. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  522. if devInfo['rst'] == -1:
  523. raise ServiceException(
  524. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  525. elif devInfo['rst'] == 1:
  526. raise ServiceException(
  527. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  528. # 设置负载功率
  529. def set_full_elec_judg_power(self, fullElecJudgPower):
  530. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  531. {'IMEI': self._device['devNo'], "funCode": 'B8', 'data': '01' + fullElecJudgPower})
  532. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  533. if devInfo['rst'] == -1:
  534. raise ServiceException(
  535. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  536. elif devInfo['rst'] == 1:
  537. raise ServiceException(
  538. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  539. # 设置刷卡投币电量
  540. def set_elec_setting(self, elecSetting):
  541. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  542. {'IMEI': self._device['devNo'], "funCode": 'C2', 'data': '01' + elecSetting})
  543. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  544. if devInfo['rst'] == -1:
  545. raise ServiceException(
  546. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  547. elif devInfo['rst'] == 1:
  548. raise ServiceException(
  549. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  550. # 设置刷卡时间
  551. def set_card_time(self, cardTime):
  552. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  553. {'IMEI': self._device['devNo'], "funCode": 'C1', 'data': '01' + cardTime})
  554. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  555. if devInfo['rst'] == -1:
  556. raise ServiceException(
  557. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  558. elif devInfo['rst'] == 1:
  559. raise ServiceException(
  560. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  561. # 设置投币时间
  562. def set_coin_time(self, coinTime):
  563. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  564. {'IMEI': self._device['devNo'], "funCode": 'C3', 'data': '01' + coinTime})
  565. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  566. if devInfo['rst'] == -1:
  567. raise ServiceException(
  568. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  569. elif devInfo['rst'] == 1:
  570. raise ServiceException(
  571. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  572. # 设置单次最大投币数
  573. def set_max_coins(self, maxCoins):
  574. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  575. {'IMEI': self._device['devNo'], "funCode": 'C4', 'data': '01' + maxCoins})
  576. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  577. if devInfo['rst'] == -1:
  578. raise ServiceException(
  579. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  580. elif devInfo['rst'] == 1:
  581. raise ServiceException(
  582. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  583. # 锁定设备
  584. def lock_unlock_device(self):
  585. dev = Device.objects(devNo = self._device['devNo']).first()
  586. if not dev:
  587. raise ServiceException({'result': 2, 'description': u'没有找到设备哦'})
  588. lockDev = dev.otherConf.get('lockDevice', False)
  589. if lockDev is False:
  590. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  591. {'IMEI': self._device['devNo'], "funCode": 'D0', 'data': '01' + 'FFFF'})
  592. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  593. if devInfo['rst'] == -1:
  594. raise ServiceException(
  595. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  596. elif devInfo['rst'] == 1:
  597. raise ServiceException(
  598. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  599. dev.otherConf['lockDevice'] = True
  600. dev.save()
  601. else:
  602. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  603. {'IMEI': self._device['devNo'], "funCode": 'D1', 'data': '01' + 'FFFF'})
  604. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  605. if devInfo['rst'] == -1:
  606. raise ServiceException(
  607. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  608. elif devInfo['rst'] == 1:
  609. raise ServiceException(
  610. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  611. dev.otherConf['lockDevice'] = False
  612. dev.save()
  613. # 重启设备
  614. def restart_the_device(self, restart = False):
  615. if restart is True:
  616. devInfo = MessageSender.send(self.device, DeviceCmdCode.OPERATE_DEV_SYNC,
  617. {'IMEI': self._device['devNo'], "funCode": 'DE', 'data': '01' + 'FFFF'})
  618. if devInfo.has_key('rst') and devInfo['rst'] != 0:
  619. if devInfo['rst'] == -1:
  620. raise ServiceException(
  621. {'result': 2, 'description': u'充电桩正在玩命找网络,请您稍候再试'})
  622. elif devInfo['rst'] == 1:
  623. raise ServiceException(
  624. {'result': 2, 'description': u'充电桩忙,无响应,请您稍候再试。也可能是您的设备版本过低,暂时不支持此功能'})
  625. # 设置设备参数(单个)
  626. def set_device_function(self, request, lastSetConf):
  627. if 'clearPutCoins' in request.POST:
  628. clearPutCoins = request.POST.get("clearPutCoins", False)
  629. self.clear_put_coins(clearPutCoins)
  630. if 'powerOffSwitch' in request.POST:
  631. powerOffSwitch = request.POST.get("powerOffSwitch", False)
  632. self.set_power_off_switch(powerOffSwitch)
  633. if 'presetSwitch' in request.POST:
  634. presetSwitch = request.POST.get("presetSwitch", False)
  635. self.set_preset_switch(presetSwitch)
  636. # TODO zjl 感觉这个指令做的有问题
  637. if 'lockDevice' in request.POST:
  638. self.lock_unlock_device()
  639. if 'restartDevice' in request.POST:
  640. restartDevice = request.POST.get("restartDevice", False)
  641. self.restart_the_device(restartDevice)
  642. if 'smokeSwitch' in request.POST:
  643. smokeSwitch = request.POST.get("smokeSwitch")
  644. self.set_smoke(smokeSwitch)
  645. # 设置设备参数(整体)
  646. def set_device_function_param(self, request, lastSetConf):
  647. deviceNum = request.POST.get('deviceNum', None)
  648. workMode = request.POST.get('workMode', None)
  649. limitedPower = request.POST.get('limitedPower', None)
  650. presetCoins = request.POST.get('presetCoins', None)
  651. powerOffTime = request.POST.get('powerOffTime', None)
  652. fullElecJudgPower = request.POST.get('fullElecJudgPower', None)
  653. cardTime = request.POST.get('cardTime', None)
  654. elecSetting = request.POST.get('elecSetting', None)
  655. coinTime = request.POST.get('coinTime', None)
  656. maxCoins = request.POST.get('maxCoins', None)
  657. elecFee = request.POST.get('elecFee', None)
  658. if deviceNum:
  659. self.set_device_num(fill_2_hexByte(hex(int(deviceNum))))
  660. if workMode:
  661. self.set_work_mode(fill_2_hexByte(hex(int(workMode))))
  662. if limitedPower:
  663. self.set_limited_power(fill_2_hexByte(hex(int(limitedPower))))
  664. if presetCoins:
  665. self.set_preset_coins(fill_2_hexByte(hex(int(presetCoins))))
  666. if powerOffTime:
  667. self.set_power_off_time(fill_2_hexByte(hex(int(powerOffTime))))
  668. if fullElecJudgPower:
  669. self.set_full_elec_judg_power(fill_2_hexByte(hex(int(fullElecJudgPower))))
  670. if cardTime:
  671. self.set_card_time(fill_2_hexByte(hex(int(cardTime))))
  672. if elecSetting:
  673. self.set_elec_setting(fill_2_hexByte(hex(int(elecSetting) * 10)))
  674. if coinTime:
  675. self.set_coin_time(fill_2_hexByte(hex(int(coinTime))))
  676. if maxCoins:
  677. self.set_max_coins(fill_2_hexByte(hex(int(maxCoins))))
  678. if elecFee:
  679. self.set_elec_fee(elecFee)