#!/usr/bin/env python3 """Тест AndrOBD-протокола против Mock ELM327 v2. Проверяет что ответы НЕ перемешаны: - 0902 → VIN (не "AUTO" от ATSP0) - 03 → DTC (не "OK" от ATE0) - 010C → RPM (не VIN-ответ) """ import logging import socket import time import sys sys.path.insert(0, ".") logging.basicConfig(level=logging.INFO, format="%(name)s: %(message)s") class FakeSerial: """TCP-заглушка для тестирования AndrOBD без pyserial.""" def __init__(self, host, port): self.sock = socket.socket() self.sock.connect((host, port)) self.sock.setblocking(False) self.sock.settimeout(0.1) self.is_open = True @property def in_waiting(self): import select r, _, _ = select.select([self.sock], [], [], 0) return 4096 if r else 0 def read(self, n): try: return self.sock.recv(n) except Exception: return b"" def write(self, data): self.sock.sendall(data) def flush(self): pass def close(self): self.sock.close() def test(): """Запускает AndrOBD против мока и проверяет ответы.""" from elmer.androbd import AndrOBD, AdaptiveTiming # Создаём протокол и подменяем serial на TCP-заглушку elm = AndrOBD("mock") elm._ser = FakeSerial("127.0.0.1", 35000) print("=== 1. ИНИТ ===") elm.init() print("\n=== 2. VIN (0902) ===") # Дадим моку дообработать ответы после инита time.sleep(0.5) vin = elm.send("0902") print(f" VIN ответ: [{vin}]") assert "490201" in vin.replace(" ", ""), f"VIN ответ не содержит 490201: {vin}" print("\n=== 3. DTC (03) ===") dtc = elm.send("03") print(f" DTC ответ: {dtc}") assert "43" in dtc.replace(" ", ""), f"DTC ответ не содержит 43: {dtc}" print("\n=== 4. RPM (010C) ===") rpm = elm.send("010C") print(f" RPM ответ: {rpm}") assert "410C" in rpm.replace(" ", ""), f"RPM ответ не содержит 410C: {rpm}" print("\n=== 5. ОЖ (0105) ===") ect = elm.send("0105") print(f" ОЖ ответ: {ect}") assert "4105" in ect.replace(" ", ""), f"ОЖ ответ не содержит 4105: {ect}" print("\n=== 6. ПРОВЕРКА: ответы не перепутаны ===") # VIN не должен быть "OK" или "AUTO" assert "AUTO" not in vin, f"VIN ответ содержит AUTO (чужой ответ!): {vin}" assert "OK" not in vin, f"VIN ответ содержит OK (чужой ответ!): {vin}" # DTC не должен быть OK assert "OK" not in dtc, f"DTC ответ содержит OK (чужой ответ!): {dtc}" # RPM — чистый PID-ответ assert "OK" not in rpm, f"RPM ответ содержит OK (чужой ответ!): {rpm}" elm._ser.close() print("\n✅ ВСЕ ТЕСТЫ ПРОЙДЕНЫ — ответы не перемешаны!") return True if __name__ == "__main__": try: test() except AssertionError as e: print(f"\n❌ ТЕСТ ПРОВАЛЕН: {e}") sys.exit(1)