fix: authenticate after firmware update
- удалена повторная авторизация перед отправкой команды 04 - полный AES-256 handshake запускается только после успешного OTA и перезагрузки контроллера - обновлены сообщения интерфейса и документация порядка обновления - тесты теперь проверяют, что команда 04 предшествует команде авторизации 07 - версия приложения повышена до 1.5.1 - локальные каталоги релизных артефактов исключены из Git
This commit is contained in:
parent
c34cb0cd7e
commit
e163b63666
1
.gitignore
vendored
1
.gitignore
vendored
@ -17,6 +17,7 @@ dist/
|
||||
build-linux/
|
||||
dist-linux/
|
||||
.venv-linux/
|
||||
release-builds/
|
||||
*.manifest
|
||||
*.spec.bak
|
||||
|
||||
|
||||
@ -118,9 +118,10 @@
|
||||
- Зеленый — подключено, плата готова к работе.
|
||||
|
||||
Кнопка переподключения (↻) позволяет быстро восстановить связь при обрыве.
|
||||
Перед запуском OTA и после успешного обновления приложение автоматически
|
||||
выполняет полную AES-256 авторизацию платы. В терминале команд доступна
|
||||
отдельная кнопка ручной авторизации.
|
||||
После успешного OTA и перезагрузки контроллера приложение автоматически
|
||||
выполняет полную AES-256 авторизацию платы. Перед командой `04` повторная
|
||||
авторизация не выполняется. В терминале команд доступна отдельная кнопка
|
||||
ручной авторизации.
|
||||
|
||||
---
|
||||
|
||||
|
||||
@ -1,3 +1,3 @@
|
||||
"""Plate Config App package."""
|
||||
|
||||
__version__ = "1.5.0"
|
||||
__version__ = "1.5.1"
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
"""Авторизованный запуск OTA-обновления контроллера."""
|
||||
"""Запуск OTA с повторной авторизацией после обновления контроллера."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
@ -12,7 +12,6 @@ from .auth_service import (
|
||||
READY_TIMEOUT_SECONDS,
|
||||
STARTUP_BANNER_TIMEOUT_SECONDS,
|
||||
STARTUP_DELAY_SECONDS,
|
||||
perform_handshake,
|
||||
perform_startup_handshake,
|
||||
)
|
||||
from .com_service import ComConnection
|
||||
@ -24,7 +23,6 @@ OTA_TIMEOUT_SECONDS = 60.0
|
||||
class FirmwareUpdateResult:
|
||||
success: bool
|
||||
detail: str
|
||||
pre_auth: AuthResult | None = None
|
||||
post_auth: AuthResult | None = None
|
||||
|
||||
|
||||
@ -39,29 +37,11 @@ def perform_authenticated_ota(
|
||||
ready_timeout: float = READY_TIMEOUT_SECONDS,
|
||||
sleep_fn: Callable[[float], None] = time.sleep,
|
||||
) -> FirmwareUpdateResult:
|
||||
"""Повторно авторизоваться, выполнить ``04`` и авторизоваться после OTA."""
|
||||
"""Выполнить ``04`` и полностью авторизоваться после успешного OTA."""
|
||||
emit = log_message or (lambda _message: None)
|
||||
if not conn.is_connected:
|
||||
return FirmwareUpdateResult(False, "Порт не подключён")
|
||||
|
||||
emit("Авторизация перед запуском OTA…")
|
||||
try:
|
||||
pre_auth = perform_handshake(
|
||||
conn,
|
||||
timeout=handshake_timeout,
|
||||
ready_timeout=ready_timeout,
|
||||
)
|
||||
except Exception as exc:
|
||||
return FirmwareUpdateResult(False, f"Ошибка авторизации перед OTA: {exc}")
|
||||
|
||||
if pre_auth.status != AuthStatus.OK:
|
||||
return FirmwareUpdateResult(
|
||||
False,
|
||||
f"Авторизация перед OTA не выполнена: {pre_auth.detail}",
|
||||
pre_auth=pre_auth,
|
||||
)
|
||||
emit("✓ Авторизация перед OTA выполнена.")
|
||||
|
||||
try:
|
||||
conn.send_command("04")
|
||||
emit("→ 04")
|
||||
@ -82,7 +62,6 @@ def perform_authenticated_ota(
|
||||
return FirmwareUpdateResult(
|
||||
False,
|
||||
"Таймаут ожидания подтверждения успешного обновления",
|
||||
pre_auth=pre_auth,
|
||||
)
|
||||
|
||||
emit("✓ Обновление подтверждено. Ожидание перезагрузки и авторизации…")
|
||||
@ -98,7 +77,6 @@ def perform_authenticated_ota(
|
||||
return FirmwareUpdateResult(
|
||||
False,
|
||||
f"Авторизация после OTA не выполнена: {post_auth.detail}",
|
||||
pre_auth=pre_auth,
|
||||
post_auth=post_auth,
|
||||
)
|
||||
|
||||
@ -106,14 +84,12 @@ def perform_authenticated_ota(
|
||||
return FirmwareUpdateResult(
|
||||
True,
|
||||
"Прошивка обновлена, плата перезагружена и авторизована",
|
||||
pre_auth=pre_auth,
|
||||
post_auth=post_auth,
|
||||
)
|
||||
except Exception as exc:
|
||||
return FirmwareUpdateResult(
|
||||
False,
|
||||
f"Ошибка OTA: {exc}",
|
||||
pre_auth=pre_auth,
|
||||
)
|
||||
finally:
|
||||
conn.release()
|
||||
|
||||
@ -244,7 +244,7 @@ class FirmwareDialog(StyledDialog):
|
||||
|
||||
self._flash_btn.setEnabled(False)
|
||||
self._upload_btn.setEnabled(False)
|
||||
self._log.append("Запуск авторизованного OTA…")
|
||||
self._log.append("Запуск OTA (04)…")
|
||||
|
||||
from PySide6.QtCore import QCoreApplication
|
||||
|
||||
|
||||
@ -50,11 +50,8 @@ class AuthenticatedOtaTests(unittest.TestCase):
|
||||
sleep_fn=lambda _seconds: None,
|
||||
)
|
||||
|
||||
def test_authenticates_before_04_and_after_successful_update(self) -> None:
|
||||
def test_sends_04_before_authentication_after_successful_update(self) -> None:
|
||||
conn = FakeConnection([
|
||||
self._CHAL,
|
||||
self._RAES,
|
||||
"READY!",
|
||||
"Writing 100%",
|
||||
"Successful update",
|
||||
"periphery controller ver_2.4.0 release",
|
||||
@ -66,27 +63,22 @@ class AuthenticatedOtaTests(unittest.TestCase):
|
||||
result = self._run(conn)
|
||||
|
||||
self.assertTrue(result.success)
|
||||
self.assertEqual(AuthStatus.OK, result.pre_auth.status)
|
||||
self.assertEqual(AuthStatus.OK, result.post_auth.status)
|
||||
send_events = [event for event in conn.events if event.startswith("send:")]
|
||||
self.assertEqual("send:04", send_events[1])
|
||||
self.assertTrue(send_events[0].startswith("send:07"))
|
||||
self.assertTrue(send_events[2].startswith("send:07"))
|
||||
self.assertEqual("send:04", send_events[0])
|
||||
self.assertTrue(send_events[1].startswith("send:07"))
|
||||
|
||||
def test_does_not_send_04_when_pre_authentication_fails(self) -> None:
|
||||
def test_sends_04_without_pre_authentication(self) -> None:
|
||||
conn = FakeConnection([None])
|
||||
|
||||
result = self._run(conn)
|
||||
|
||||
self.assertFalse(result.success)
|
||||
self.assertEqual(AuthStatus.TIMEOUT, result.pre_auth.status)
|
||||
self.assertFalse(any(event == "send:04" for event in conn.events))
|
||||
self.assertEqual("send:04", conn.events[0])
|
||||
self.assertFalse(any(event.startswith("send:07") for event in conn.events))
|
||||
|
||||
def test_reports_post_authentication_failure_after_update(self) -> None:
|
||||
conn = FakeConnection([
|
||||
self._CHAL,
|
||||
self._RAES,
|
||||
"READY!",
|
||||
"Successful update",
|
||||
None,
|
||||
])
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user