feat: add auto-update system with release checking, notification UI, and install-type-aware apply
- Abstract ReleaseProvider interface (Gitea impl, swappable for GitHub/GitLab) - Background UpdateService with periodic checks, debounce, dismissed version persistence - Install type detection (installer/portable/docker/dev) with platform-aware asset matching - Download with progress events, silent NSIS reinstall, portable ZIP/tarball swap scripts - Version badge pulse animation, dismissible banner with icon buttons, Settings > Updates tab - Single source of truth: pyproject.toml version via importlib.metadata, CI stamps tag with sed - API: GET/POST status, check, dismiss, apply, GET/PUT settings - i18n: en, ru, zh (27+ keys each)
This commit is contained in:
@@ -41,6 +41,8 @@ from wled_controller.core.mqtt.mqtt_service import MQTTService
|
||||
from wled_controller.core.devices.mqtt_client import set_mqtt_service
|
||||
from wled_controller.core.backup.auto_backup import AutoBackupEngine
|
||||
from wled_controller.core.processing.os_notification_listener import OsNotificationListener
|
||||
from wled_controller.core.update.update_service import UpdateService
|
||||
from wled_controller.core.update.gitea_provider import GiteaReleaseProvider
|
||||
from wled_controller.storage.database import Database
|
||||
from wled_controller.utils import setup_logging, get_logger, install_broadcast_handler
|
||||
|
||||
@@ -167,6 +169,18 @@ async def lifespan(app: FastAPI):
|
||||
db=db,
|
||||
)
|
||||
|
||||
# Create update service (checks for new releases)
|
||||
_release_provider = GiteaReleaseProvider(
|
||||
base_url="https://git.dolgolyov-family.by",
|
||||
repo="alexei.dolgolyov/wled-screen-controller-mixed",
|
||||
)
|
||||
update_service = UpdateService(
|
||||
provider=_release_provider,
|
||||
db=db,
|
||||
fire_event=processor_manager.fire_event,
|
||||
update_dir=_data_dir / "updates",
|
||||
)
|
||||
|
||||
# Initialize API dependencies
|
||||
init_dependencies(
|
||||
device_store, template_store, processor_manager,
|
||||
@@ -189,6 +203,7 @@ async def lifespan(app: FastAPI):
|
||||
gradient_store=gradient_store,
|
||||
weather_source_store=weather_source_store,
|
||||
weather_manager=weather_manager,
|
||||
update_service=update_service,
|
||||
)
|
||||
|
||||
# Register devices in processor manager for health monitoring
|
||||
@@ -235,6 +250,9 @@ async def lifespan(app: FastAPI):
|
||||
# Start auto-backup engine (periodic configuration backups)
|
||||
await auto_backup_engine.start()
|
||||
|
||||
# Start update checker (periodic release polling)
|
||||
await update_service.start()
|
||||
|
||||
# Start OS notification listener (Windows toast → notification CSS streams)
|
||||
os_notif_listener = OsNotificationListener(
|
||||
color_strip_store=color_strip_store,
|
||||
@@ -258,6 +276,12 @@ async def lifespan(app: FastAPI):
|
||||
except Exception as e:
|
||||
logger.error(f"Error stopping weather manager: {e}")
|
||||
|
||||
# Stop update checker
|
||||
try:
|
||||
await update_service.stop()
|
||||
except Exception as e:
|
||||
logger.error(f"Error stopping update checker: {e}")
|
||||
|
||||
# Stop auto-backup engine
|
||||
try:
|
||||
await auto_backup_engine.stop()
|
||||
|
||||
Reference in New Issue
Block a user