コード例 #1
0
ファイル: ION.py プロジェクト: customr/tracker_receiver
 def close(self):
     ION.TRACKERS.remove(self)
     self.sock.close()
     self.db.close()
     self.stop = True
     logger.info(
         f'ION {self.imei} отключен [{self.addr[0]}:{self.addr[1]}]')
コード例 #2
0
    def start(self):
        ADM.TRACKERS.add(self)
        self.db = pymysql.connect(**CONN)

        self.need_reply = 0
        self.imei = self.handle_imei()

        if not self.imei is None:
            logger.info(
                f'ADM{self.model} {self.imei} подключен [{self.addr[0]}:{self.addr[1]}]'
            )

            self.assign = get_configuration(self.NAME, self.imei, self.model)
            self.ign_v = get_ignition_v(self.imei)

            self.stop = False
            self.data = {}
            self.command_response = {}

            try:
                self.handle_packet()
            except Exception as e:
                self.close()
                logger.error('ADM ERROR {e}')
                raise e
コード例 #3
0
 def close(self):
     ADM.TRACKERS.remove(self)
     self.sock.close()
     self.db.close()
     self.stop = True
     logger.info(
         f'ADM{self.model} {self.imei} отключен [{self.addr[0]}:{self.addr[1]}]'
     )
コード例 #4
0
    def start(self):
        logger.info(f'WialonCombine подключен [{self.addr[0]}:{self.addr[1]}]')
        WialonCombine.TRACKERS.add(self)
        self.db = pymysql.connect(**CONN)

        self.pid = 0
        self.stop = False
        self.handle_packet()
コード例 #5
0
    def handle_packet(self):
        if self.stop:
            self.stop = False

        while not self.stop:
            self.msg_type = 0

            packet = binascii.hexlify(self.sock.recv(1024))
            if len(packet) == 4:
                packet = binascii.hexlify(self.sock.recv(1024))
            if len(packet) == 0:
                continue

            logger.debug(
                f'[ADM{self.model}] {self.imei} принят пакет {packet}')

            all_data = []
            while len(packet) > 0:
                packet, data = self.data_main(packet)
                if packet is None:
                    break
                logger.debug(
                    f'[ADM{self.model}] {self.imei} основные данные обработаны\n{data}'
                )
                logger.debug(
                    f'[ADM{self.model}] {self.imei} статус пакета {data["typ"]}'
                )
                bits = list(map(int, str(bin(data['typ']))[2:][::-1]))[2:]
                for n, bit in enumerate(bits):
                    if bit:
                        before = packet[:]
                        packet, d = getattr(ADM, ADM.DATA_BLOCKS[n])(self,
                                                                     packet)
                        logger.debug(
                            f'[ADM{self.model}] {self.imei} блок {ADM.DATA_BLOCKS[n]}\nПакет до: {before}\nПакет после: {packet}\nДанные: {d}'
                        )
                        data.update(d)

                data = self.rename_data(data)
                logger.debug(
                    f'[ADM{self.model}] {self.imei} данные после переименования: {data}'
                )
                data = self.prepare_geo(data)
                logger.debug(
                    f'[ADM{self.model}] {self.imei} данные после обработки: {data}'
                )
                all_data.append(data)

            if all_data:
                count = insert_geo(all_data)
                logger.info(
                    f'ADM{self.model} {self.imei} принято {count}/{len(all_data)} записей'
                )
                if self.need_reply == 1:
                    pass
                elif self.need_reply == 2:
                    self.sock.send(b'***' + str(count).encode('ascii') + b'*')
コード例 #6
0
    def start(self):
        self.imei = self.handle_imei()
        logger.info(
            f'Teltonika{self.model} {self.imei} подключен [{self.addr[0]}:{self.addr[1]}]'
        )
        Teltonika.TRACKERS.add(self)

        self.assign = get_configuration(self.NAME, self.imei, self.model)
        self.decoder = self.get_decoder(self.model)
        self.ign_v = get_ignition_v(self.imei)

        self.lock = threading.Lock()
        self.stop = False
        main_th = threading.Thread(target=self.handle_packet)
        main_th.start()
コード例 #7
0
ファイル: core.py プロジェクト: customr/retranslator
    def __init__(self, protocol_name: str):
        """Родитель всех протоколов

		protocol_name (str): имя протокола, как в папке PROTOCOLS_DIR без расширения
		"""
        assert isinstance(protocol_name, str)
        self.protocol_name = protocol_name

        self.packet = bytes()
        self.data = {}
        self.settings = {}

        self.protocol = Retranslator.get_json(self.PROTOCOLS_DIR,
                                              self.protocol_name + ".json")
        logger.info(f"Протокол {protocol_name} инициализирован\n")
コード例 #8
0
    def __init__(self, protocol, server, model=''):
        self.ip, self.port = server.split(':')
        self.model = model
        self.sock = socket.socket()
        self.sock.bind((self.ip, int(self.port)))
        self.sock.listen(1024)

        if self.ip == '': self.ip = 'ANY'
        logger.info(
            f'Сервер для {protocol.NAME}{model} запущен - [{self.ip}:{self.port}]\n'
        )

        listen_th = threading.Thread(target=self.connecter,
                                     args=(protocol, model))
        listen_th.start()
コード例 #9
0
 def send_command(self, command):
     packet = ''
     # packet = add_ushort(packet, 0x4040)
     # packet = add_ubyte(packet, 0xFF)
     # packet = add_ushort(packet, len(command)+5)
     # packet = add_uint(packet, int(time()))
     # packet = add_ubyte(packet, 0x00)
     packet = add_str(packet, command)
     # crc16_pack = struct.unpack(f'{len(packet)//2}s', binascii.a2b_hex(packet.encode('ascii')))[0]
     # packet = add_ushort(packet, crc16(crc16_pack))
     # logger.info(f'[WialonCombine] командный пакет сформирован:\n{packet}\n')
     packet = pack(packet)
     try:
         self.sock.send(packet)
         logger.info(f'[WialonCombine]  команда {command} отправлена\n')
     except Exception as e:
         logger.error(
             f'[WialonCombine]  команда {command} не отправлена {str(e)}\n')
コード例 #10
0
    def start(self):
        GalileoSky.TRACKERS.add(self)
        self.db = pymysql.connect(**CONN)

        self.imei = self.handle_imei()
        logger.info(
            f'ADM{self.model} {self.imei} подключен [{self.addr[0]}:{self.addr[1]}]'
        )

        self.assign = get_configuration(self.NAME, self.imei)
        self.ign_v = get_ignition_v(self.imei)

        self.stop = False
        self.data = {}

        try:
            self.handle_packet()
        except Exception as e:
            self.close()
            raise e
コード例 #11
0
    def run(self):
        logger.info(
            f"START {self.retranslator.protocol_name} {self.imei} [{self.ip}:{self.port}]"
        )
        while True:
            while self.socket == -1:
                self.socket = self.connect()
                sleep(Tracker.CONN_DELAY)

            while self.queue.qsize() == 0:
                self.fill_queue()

            row = self.queue.get()

            if row.get('reserve', None):
                row['imei'] = str(row['imei'])
                row['reserve'] = loads('{' + row['reserve'] + '}')
                row.update(row['reserve'])
                del (row['reserve'])

                if not row.get('sat_num', ''):
                    row.update({"sat_num": 0})

                row['lon'] = float(row['lon'])
                row['lat'] = float(row['lat'])

            sended, status = self.retranslator.send(self.send, row,
                                                    self.settings, self.ip,
                                                    int(self.port))

            if sended:
                msg = "Запись ОТПРАВЛЕНА\n"
            else:
                msg = "Запись НЕ ОТПРАВЛЕНА\n"

            msg += "Сервер".ljust(26, '-') + f"{self.ip}:" + f"{self.port}\n"
            msg += "Ретранслятор".ljust(
                26, '-') + f"{self.retranslator.protocol_name}\n"
            msg += "ID записи".ljust(26, '-') + f"{row['id']}\n"
            msg += "imei".ljust(26, '-') + f"{row['imei']}\n"
            msg += "Время точки".ljust(
                26, '-') + f"{datetime.fromtimestamp(row['datetime'])}\n"
            msg += "Статус отправки".ljust(26, '-') + f"{status}\n"
            msg += f"Записей для {self.imei}".ljust(
                30, '-') + f"{self.queue.qsize()}\n"

            if not sended:
                logger.error(msg)
            else:
                logger.info(msg)
                condition = f" WHERE `ip`='{self.ip}' AND `port`={self.port} AND `imei`={row['imei']}"
                query = f"SELECT * FROM `sent_id`" + condition
                with self.dbconn.cursor() as cursor:
                    cursor.execute(query)
                    if cursor.rowcount == 0:
                        query = f"INSERT INTO `sent_id` VALUES ({row['id']}, '{self.ip}', {self.port}, {row['imei']})"
                    else:
                        query = f"UPDATE `sent_id` SET `id`={row['id']}" + condition

                    cursor.execute(query)
                    self.dbconn.commit()

            self.queue.task_done()
コード例 #12
0
    def data_main(self, packet):
        packet, _ = extract_ushort(packet, '=')
        packet, size = extract_ubyte(packet, '=')

        if size == 0x84:
            try:
                logger.debug(
                    f'[ADM{self.model}] {self.imei} принят ответ на команду {packet}'
                )
                result = self.handle_command(packet)
            except Exception as e:
                result = "Ошибка на сервере: " + str(e)

                resp = {"action": "response", "result": result}
                self.command_response = dumps(resp)
                logger.debug(
                    f'[ADM{self.model}] {self.imei} ошибка распаковки ответа на команду\n{result}\n'
                )
                logger.info(str(e))
            else:
                resp = {"action": "response", "result": result}
                self.command_response = dumps(resp)
                logger.debug(
                    f'[ADM{self.model}] {self.imei} ответ на команду принят\n{result}\n'
                )

            return None, None

        packet, typ = extract_ubyte(packet, '=')
        packet, _ = extract_ubyte(packet, '=')
        packet, ID = extract_ushort(packet, '=')
        packet, status = extract_ushort(packet, '=')
        packet, lat = extract_float(packet, '<')
        packet, lon = extract_float(packet, '<')
        packet, direction = extract_ushort(packet, '=')
        packet, speed = extract_ushort(packet, '=')
        packet, ACC = extract_ubyte(packet, '=')
        packet, HEIGHT = extract_ushort(packet, '=')
        packet, HDOP = extract_ubyte(packet, '=')
        packet, SAT_N = extract_ubyte(packet, '=')
        packet, timestamp = extract_uint(packet, '=')
        packet, V_POWER = extract_ushort(packet, '=')
        packet, V_BATTERY = extract_ushort(packet, '=')

        direction /= 10
        speed /= 10
        ACC /= 10

        if direction > 360:
            direction = 0
        else:
            direction = (direction / 2) % 0xff

        SAT_N = (SAT_N & 0x0f) + ((SAT_N & 0xf0) >> 4)
        dt = datetime.datetime.utcfromtimestamp(timestamp)
        data = {
            key: value
            for key, value in locals().items()
            if key not in ['self', 'packet']
        }
        return packet, data
コード例 #13
0
ファイル: run.py プロジェクト: customr/tracker_receiver
async def handler(ws, path):
	while True:
		try:
			rec = await ws.recv()
			try:
				rec = loads(rec)
			except Exception as e:
				logger.error(f'WEBSOCKET неизвестный пакет: {rec} {e}\n')
				continue

			if rec['action']=='command':
				teltonika = Teltonika.Teltonika.get_tracker(rec['imei'])
				adm = ADM.ADM.get_tracker(rec['imei'])
				ion = ION.ION.get_tracker(rec['imei'])
				wialoncombine = WialonCombine.WialonCombine.get_tracker(rec['imei'])
				if any([teltonika, adm, ion, wialoncombine]):
					command_response = dumps({})
					logger.debug(f"WEBSOCKET tracker {rec['imei']} found")
					if teltonika:
						teltonika.command_response = {}
						teltonika.send_command(int(rec['codec']), rec['command'])
						for _ in range(30):
							sleep(0.5)
							if teltonika.command_response!={}:
								command_response = teltonika.command_response
								break
					elif adm:
						adm.command_response = {}
						adm.send_command(rec['command'])
						for _ in range(30):
							sleep(0.5)
							if adm.command_response!={}:
								command_response = adm.command_response
								break
					elif ion:
						ion.command_response = {}
						ion.send_command(rec['command'])
						for _ in range(30):
							sleep(0.5)
							if ion.command_response!={}:
								command_response = ion.command_response
								break
					elif wialoncombine:
						wialoncombine.command_response = {}
						wialoncombine.send_command(rec['command'])
						for _ in range(30):
							sleep(0.5)
							if wialoncombine.command_response!={}:
								command_response = wialoncombine.command_response
								break
					

					if command_response!={}:
						logger.debug(f'WEBSOCKET command response\n{command_response}')
						try:
							await ws.send(command_response)
						except Exception as e:
							logger.error(f"WEBSOCKET ошибка при отправке ответа {e}")

					else:
						await ws.send(dumps({"action":"response", "result": "Время ожидания ответа истекло"}))

				else:
					await ws.send(dumps({"action":"response", "result": "Трекер не подключен"}))
					logger.info(f"WEBSOCKET {rec['imei']} не подключен")
					continue

			else:
				continue

		except Exception as e:
			raise e
コード例 #14
0
ファイル: ION.py プロジェクト: customr/tracker_receiver
    def handle_packet(self):
        if self.stop:
            self.stop = False

        while not self.stop:
            try:
                packet = binascii.hexlify(self.sock.recv(4096))
            except Exception as e:
                raise e

            if len(packet) == 0:
                continue

            logger.debug(f'[ION] получен пакет {packet}')
            packet, packet_type = extract_ubyte(packet)

            packets = None
            if packet_type == 0xe7 or packet_type == 0x83:
                packet, packets = extract_ubyte(packet)
            elif packet_type == 0xf0 or packet_type == 0xf1:
                result = self.handle_command(packet, packet_type)
                resp = {"action": "response", "result": result}
                self.command_response = dumps(resp)

            if not self.imei:
                first_time = True
            else:
                first_time = False

            packet, self.imei = ION.parse_imei(packet)

            if first_time:
                logger.info(
                    f'ION {self.imei} подключен [{self.addr[0]}:{self.addr[1]}]'
                )
                self.assign = get_configuration(self.NAME, self.imei)
                self.ign_v = get_ignition_v(self.imei)

            logger.debug(f'[ION] {self.imei} всего записей: {packets}')
            all_data = []
            if packets:
                for i in range(packets):
                    try:
                        packet, data = ION.parse_data(packet)
                        logger.debug(f'[ION] {self.imei} данные #{i} {data}')
                        data = self.rename_data(data)
                        logger.debug(
                            f'[ION] {self.imei} данные после переименования: {data}'
                        )
                        data = self.prepare_geo(data)
                        logger.debug(
                            f'[ION] {self.imei} данные после обработки: {data}'
                        )
                        all_data.append(data)
                    except Exception as e:
                        logger.error(
                            f'[ION] {self.imei} ошибка парсинга\n{str(e)}\nПакет {packet}'
                        )
                        break
            else:
                while len(packet) > 0:
                    try:
                        packet, data = ION.parse_data(packet)
                        logger.debug(f'[ION] {self.imei} данные #{i} {data}')
                        data = self.rename_data(data)
                        logger.debug(
                            f'[ION] {self.imei} данные после переименования: {data}'
                        )
                        data = self.prepare_geo(data)
                        logger.debug(
                            f'[ION] {self.imei} данные после обработки: {data}'
                        )
                        all_data.append(data)
                    except Exception as e:
                        logger.error(
                            f'[ION] {self.imei} ошибка парсинга\n{str(e)}\nПакет {packet}'
                        )
                        break

            count = insert_geo(all_data)
            logger.info(f'ION {self.imei} принято {count}/{packets} записей')
            if packet_type == 0x82 or packet_type == 0x83:
                self.sock.send(b'0')
コード例 #15
0
    def handle_packet(self):
        while not self.stop:
            try:
                packet = binascii.hexlify(self.sock.recv(4096))
            except Exception:
                self.sock.close()
                self.stop = True
                Teltonika.TRACKERS.remove(self)
                logger.debug(
                    f'[Teltonika{self.model}] {self.imei} отключен [{self.addr[0]}:{self.addr[1]}]'
                )
                break

            self.lock.acquire()

            if len(packet) < 8:
                if packet == b'\xff' or packet == b'' or packet == b'ff':
                    continue

                else:
                    logger.error(f'[Teltonika] непонятный пакет: {packet}')
                    self.sock.close()
                    self.stop = True
                    Teltonika.TRACKERS.remove(self)
                    logger.debug(
                        f'[Teltonika{self.model}] {self.imei} отключен [{self.addr[0]}:{self.addr[1]}]'
                    )
                    break

            logger.debug(f'[Teltonika] получен пакет:\n{packet}\n')
            try:
                packet, z = extract_int(packet)  #preamble zero bytes
                assert z == 0, 'Not teltonika packet'
                packet, data_len = extract_uint(packet)
                packet, self.codec = extract_ubyte(packet)
                packet, self.count = extract_ubyte(packet)
                logger.debug(
                    f'[Teltonika] codec={self.codec} rec_count={self.count}\n')

            except Exception as e:
                with open('tracker_receiver/src/logs/errors.log', 'a') as fd:
                    fd.write(f'Ошибка в распаковке {packet}\n{e}\n')

            if self.codec in (8, 142, 16):
                self.data = self.handle_data(packet)
                self.data = prepare_geo(self.data)
                count = insert_geo(self.data)
                logger.info(
                    f'Teltonika{self.model} {self.imei} принято {count}/{len(self.data)} записей'
                )
                self.sock.send(struct.pack("!I", count))

            elif self.codec in (12, 13, 14):
                result = self.handle_command(packet)
                resp = {"action": "response", "result": result}
                resp = dumps(resp)
                self.command_response = resp
                logger.debug(
                    f'[Teltonika] ответ на команду принят\n{result}\n')

            else:
                logger.critical(f"Teltonika неизвестный кодек {self.codec}")
                raise ValueError('Unknown codec')

            self.lock.release()
            sleep(2)

        del (self)
コード例 #16
0
    def handle_packet(self):
        if self.stop:
            self.stop = False

        self.assign = None
        while not self.stop:
            try:
                packet = binascii.hexlify(self.sock.recv(2**17))
                self.success = True

            except Exception:
                self.sock.close()
                self.db.close()
                self.stop = True
                self.success = False
                WialonCombine.TRACKERS.remove(self)
                logger.debug(
                    f'[WialonCombine] отключен [{self.addr[0]}:{self.addr[1]}]'
                )
                break

            logger.debug(f'[WialonCombine] получен пакет:\n{packet}\n')

            count = 0
            command = False
            packet, packet_header = self.handle_header(packet)
            if packet_header['type'] == 0:
                try:
                    self.handle_login(packet)
                except:
                    logger.error(f'[WialonCombine] unknown packet\n')
                    continue

                logger.debug(f'[WialonCombine] imei:\n{self.imei}\n')
            elif packet_header['type'] == 1:
                self.assign = get_configuration(self.NAME, self.imei,
                                                self.model)
                while len(packet) > 4:
                    try:
                        packet, packet_data, packet_reserve = self.handle_data(
                            packet)
                    except Exception as e:
                        logger.debug(
                            f'[WialonCombine] error parsing {packet} {str(e)}\n'
                        )
                        break

                    if packet_reserve.get('DRIVERMESSAGE'):
                        command = True
                    else:
                        command = False

                    if not packet_data and packet_reserve:
                        packet_data.append({
                            "lat": 0,
                            "lon": 0,
                            "timestamp": int(time()),
                            "speed": 0,
                            "direction": 0,
                        })
                    for data in packet_data:
                        self.data, _ = self.prepare_data(packet_reserve, data)
                        c = insert_geo([self.data])
                        count += 1
            elif packet_header['type'] == 2:
                continue
            else:
                logger.debug(
                    f"[WialonCombine] unknown type {packet} {packet_header['type']}\n"
                )
                self.success = False

            if self.success:
                resp = ''
                resp = add_short(resp, 0x4040, '>')
                if not command:
                    resp = add_byte(resp, 0x00, '>')
                else:
                    resp = add_byte(resp, 255, '>')

                resp = add_ushort(resp, self.pid, '>')
                logger.debug(
                    f'[WialonCombine] {self.imei} response to tracker:\n{resp}\n'
                )
                resp = pack(resp)
                self.sock.send(resp)
                if count:
                    logger.info(
                        f"WialonCombine {self.imei} принято {count} записи")
            else:
                resp = ''
                resp = add_short(resp, 0x4040, '>')
                resp = add_byte(resp, 0x03, '>')
                resp = add_ushort(resp, self.pid, '>')
                resp = pack(resp)
                self.sock.send(resp)
                logger.warning(
                    f"WialonCombine {self.imei} пакет не был принят")