commit 844652c7562f8290a2c29047f7055cd88b6bc438 Author: s.galanskiy Date: Fri Nov 7 16:45:53 2025 +0500 start diff --git a/config.py b/config.py new file mode 100644 index 0000000..84880b2 --- /dev/null +++ b/config.py @@ -0,0 +1,3 @@ +GNSS_PORT = '/dev/ttyAMA0' # UART порт GNSS модуля +GNSS_BAUD = 9600 +GNSS_TIMEOUT = 1 \ No newline at end of file diff --git a/gnss_core.py b/gnss_core.py new file mode 100644 index 0000000..003ffa4 --- /dev/null +++ b/gnss_core.py @@ -0,0 +1,58 @@ +import serial +import pynmea2 +import time +from .gnss_utils import current_utc_time + +class GNSSModule: + """ + Основной класс для работы с GNSS на Raspberry Pi. + Поддерживает GPS, GLONASS, BeiDou через NMEA-формат. + """ + def __init__(self, port='/dev/ttyAMA0', baudrate=9600, timeout=1): + self.port = port + self.baudrate = baudrate + self.timeout = timeout + self.serial_conn = None + self.last_position = None + + def connect(self): + """Подключение к GNSS модулю""" + try: + self.serial_conn = serial.Serial( + port=self.port, + baudrate=self.baudrate, + timeout=self.timeout + ) + print(f"GNSS подключен на {self.port} @ {self.baudrate} бод") + except Exception as e: + print(f"Ошибка подключения GNSS: {e}") + raise e + + def read_position(self): + """ + Считывает NMEA строку, парсит координаты. + Возвращает словарь с lat, lon, alt, timestamp + """ + if self.serial_conn is None or not self.serial_conn.is_open: + raise ConnectionError("GNSS модуль не подключен") + + try: + line = self.serial_conn.readline().decode('ascii', errors='replace') + if line.startswith('$G'): + msg = pynmea2.parse(line) + if isinstance(msg, pynmea2.GGA): + self.last_position = { + 'lat': msg.latitude, + 'lon': msg.longitude, + 'alt': msg.altitude, + 'timestamp': current_utc_time() + } + return self.last_position + except pynmea2.ParseError: + pass + return None + + def close(self): + if self.serial_conn and self.serial_conn.is_open: + self.serial_conn.close() + print("GNSS соединение закрыто") diff --git a/gnss_utils.py b/gnss_utils.py new file mode 100644 index 0000000..5a87fdb --- /dev/null +++ b/gnss_utils.py @@ -0,0 +1,5 @@ +from datetime import datetime, timezone + +def current_utc_time(): + """Возвращает текущее UTC-время, для синхронизации с RTC""" + return datetime.now(timezone.utc).isoformat() diff --git a/poetry.lock b/poetry.lock new file mode 100644 index 0000000..c82edf4 --- /dev/null +++ b/poetry.lock @@ -0,0 +1,60 @@ +# This file is automatically @generated by Poetry 2.2.1 and should not be changed by hand. + +[[package]] +name = "pynmea2" +version = "1.19.0" +description = "Python library for the NMEA 0183 protcol" +optional = false +python-versions = "*" +groups = ["main"] +files = [ + {file = "pynmea2-1.19.0-py3-none-any.whl", hash = "sha256:5138558b4fb5daa587b2c17de99eb43df0297039de1c98010c996624abfb00eb"}, + {file = "pynmea2-1.19.0.tar.gz", hash = "sha256:1daa79b93279f887d1c235e5cc5c79e32644564138ce46989ab0f4a2fc970d7c"}, +] + +[[package]] +name = "pyserial" +version = "3.5" +description = "Python Serial Port Extension" +optional = false +python-versions = "*" +groups = ["main"] +files = [ + {file = "pyserial-3.5-py2.py3-none-any.whl", hash = "sha256:c4451db6ba391ca6ca299fb3ec7bae67a5c55dde170964c7a14ceefec02f2cf0"}, + {file = "pyserial-3.5.tar.gz", hash = "sha256:3c77e014170dfffbd816e6ffc205e9842efb10be9f58ec16d3e8675b4925cddb"}, +] + +[package.extras] +cp2110 = ["hidapi"] + +[[package]] +name = "python-dateutil" +version = "2.9.0.post0" +description = "Extensions to the standard Python datetime module" +optional = false +python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,>=2.7" +groups = ["main"] +files = [ + {file = "python-dateutil-2.9.0.post0.tar.gz", hash = "sha256:37dd54208da7e1cd875388217d5e00ebd4179249f90fb72437e91a35459a0ad3"}, + {file = "python_dateutil-2.9.0.post0-py2.py3-none-any.whl", hash = "sha256:a8b2bc7bffae282281c8140a97d3aa9c14da0b136dfe83f850eea9a5f7470427"}, +] + +[package.dependencies] +six = ">=1.5" + +[[package]] +name = "six" +version = "1.17.0" +description = "Python 2 and 3 compatibility utilities" +optional = false +python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,>=2.7" +groups = ["main"] +files = [ + {file = "six-1.17.0-py2.py3-none-any.whl", hash = "sha256:4721f391ed90541fddacab5acf947aa0d3dc7d27b2e1e8eda2be8970586c3274"}, + {file = "six-1.17.0.tar.gz", hash = "sha256:ff70335d468e7eb6ec65b95b99d3a2836546063f63acc5171de367e834932a81"}, +] + +[metadata] +lock-version = "2.1" +python-versions = ">=3.13" +content-hash = "17f37c7813d145c3fdc878cf826ad205336172cfa15e2f59a0b82a304374da2a" diff --git a/pyproject.toml b/pyproject.toml new file mode 100644 index 0000000..391d42c --- /dev/null +++ b/pyproject.toml @@ -0,0 +1,19 @@ +[project] +name = "gnss" +version = "0.0.1" +description = "" +authors = [ + {name = "s.galanskiy",email = "s.galanskiy@gossys.dev"} +] +readme = "README.md" +requires-python = ">=3.13" +dependencies = [ + "pyserial (>=3.5,<4.0)", + "pynmea2 (>=1.19.0,<2.0.0)", + "python-dateutil (>=2.9.0.post0,<3.0.0)" +] + + +[build-system] +requires = ["poetry-core>=2.0.0,<3.0.0"] +build-backend = "poetry.core.masonry.api"