Commit Graph

56 Commits

Author SHA1 Message Date
darroyo 02c1fd55fb Bump version to 1.0.56 2026-07-19 22:18:42 -04:00
darroyo 867794d846 Bump version to 1.0.55 2026-07-19 22:18:12 -04:00
darroyo a7ae619b76 Bump version to 1.0.54 2026-07-19 22:14:38 -04:00
darroyo 84b185be39 Phase A-E: stability, security, observability, and test coverage
Phase A - Stability:
- Engine.Start(): recovers orphaned jobs (running/queued/waking_up) after crash
- Engine.Stop(): graceful shutdown - cancels all in-flight jobs and waits
- Queue keyed by jobID (not syncPairID): cancel now targets exact job
- Local rsync uses jobCtx (context.Background() replaced)
- Migrations wrapped in transactions; checksums stored

Phase B - Security:
- admin/admin default removed: SYNCSERVER_ADMIN_PASSWORD required on first run
- Path validation: rejects .., leading -, null bytes in sync pair paths
- Rsync flags allowlist: dangerous flags blocked (--rsync-path, -e, --files-from)
- Shell concat in RunRemote replaced with proper sh -c escaping
- knownhosts: replaced custom parser with golang.org/x/crypto/ssh/knownhosts
- RequireAdmin wired: machine CRUD, SSH key ops, settings require admin role
- deploy-keys: uses authorized_keys only (no private key upload)
- Hardcoded /var/lib/syncserver/ssh paths replaced with cfg.SSHDir()

Phase C - Operational:
- /readyz health check: DB query + SSH dir accessibility
- /metrics endpoint: Prometheus text format (jobs, queue, machines)
- Event struct JSON tags: job_id, machine_id, type (snake_case)
- EventBus broadcast: fanned out to all subscribers
- SQLite VACUUM INTO backup: scheduled before cleanup if BackupDir set
- Filesystem job log cleanup: removes .log files for purged jobs
- Backup retention: old backups auto-purged

Phase D - Frontend:
- Schedules page: REST API + full CRUD UI for cron schedules
- Dashboard: cancel button for running/queued jobs
- JobDetail: server-side log download via API
- Settings: displays data_dir from server
- 404 page: proper NotFound component

Phase E - Tests:
- auth_test.go: JWT, bcrypt, middleware, seed (18 tests)
- models_test.go: Job, Machine, SyncPair, Schedule repos (18 tests)
- go test -race: no data races found
2026-07-19 22:14:30 -04:00
darroyo 300555d35f Bump version to 1.0.52 2026-07-19 19:49:10 -04:00
darroyo 6b29a4b419 Bump version to 1.0.51 2026-07-19 19:49:00 -04:00
darroyo 4ccf2fc2d6 Bump version to 1.0.50 2026-07-19 18:17:42 -04:00
darroyo ae33703ef9 Bump version to 1.0.49 2026-07-19 18:17:36 -04:00
darroyo 2ec031c9dc Bump version to 1.0.48 2026-07-17 18:40:23 -04:00
darroyo 340370a43b Bump version to 1.0.47 2026-07-17 18:26:26 -04:00
darroyo 0437a7b248 Bump version to 1.0.46 2026-07-13 15:20:20 -04:00
darroyo e6d550b3ab Bump version to 1.0.45 2026-07-13 13:43:40 -04:00
darroyo d12f76ca56 Bump version to 1.0.44 2026-07-13 13:35:02 -04:00
darroyo bc3bc44c4a Add shutdown machine feature with configurable command
Backend:
- New migration: add shutdown_command TEXT column to machines table
- Machine model updated with ShutdownCommand field (Create/GetAll/GetByID/Update)
- MachineRequest/MachineResponse DTOs updated with shutdown_command field
- New ShutdownResponse DTO
- New POST /api/machines/{id}/shutdown handler via SSH
- Refactor sshmanager/testconn.go: extract dialSSH() helper shared with shutdown.go
- New sshmanager/shutdown.go: RunRemoteCommand with 15s timeout

Frontend:
- New shutdownMachine() API helper and ShutdownResponse type in client.ts
- New shutdown_command field in MachineForm
- Power button (amber) in machines table actions
- Shutdown confirmation modal with WoL warning notice
- shutdown_command input field in machine edit/create form
- Machine interface updated with shutdown_command and last_seen_at fields
2026-07-13 10:02:18 -04:00
darroyo bf9bcccde2 Fix MachineResponse: expose last_seen_at/created_at, clean status string
The status field was being decorated with "(last seen ...)" suffix
which broke frontend statusVariant() matching and prevented the
LastSeen column from showing the separate timestamp.

Changes:
- machineToResp() now returns clean status ("online"/"offline")
- MachineResponse includes last_seen_at and created_at as separate fields
- Fix whitespace typo in WakeCheckIntervalSeconds field
2026-07-10 11:05:27 -04:00
darroyo 7a2a7a4935 Add Last Seen column and color-coded status badges in Machines table
- New Last Seen column showing last_seen_at timestamp per machine
- Status badges: online=green (success), offline=red (error), waking/pending=amber
- Update Machine interface with last_seen_at and created_at fields
2026-07-10 10:51:10 -04:00
darroyo 175fdf4dff Bump version to 1.0.40 2026-07-09 21:58:50 -04:00
darroyo 683c489a24 Bump version to 1.0.39 2026-07-09 21:58:46 -04:00
darroyo fce8962f2b Bump version to 1.0.38 2026-07-09 21:51:25 -04:00
darroyo 147c6d8ead fix: rsync double SSH spec in RunRemote, restore dropped flags in Run
- Fix Bug A: RunRemote was re-prefixing destination with user@host: when
  engine.go:135 already pre-prefixed it for remote-to-remote, causing
  "admin@host:admin@host:/path" to be passed to rsync
- Fix Bug B: Run used args[1:] when inserting -e ssh, silently dropping
  the first rsync flag (e.g. -aP became flag-less)
- Fix Bug C: RunRemote extracted source/dest in wrong order for pull
  direction (buildArgs reverses them but RunRemote assumed push order)
- Add rsync_runner_test.go covering buildArgs, RunRemote prefixing,
  and flag preservation
2026-07-09 21:51:05 -04:00
darroyo 969ccacfc8 Bump version to 1.0.36 2026-07-09 21:25:53 -04:00
darroyo 0a82f4e777 Bump version to 1.0.35 2026-07-09 21:19:56 -04:00
darroyo 0a42f157f7 Bump version to 1.0.34 2026-07-09 20:58:52 -04:00
darroyo 048b99921e Bump version to 1.0.33 2026-07-09 20:52:37 -04:00
darroyo e0252829b3 Bump version to 1.0.32 2026-07-09 20:45:37 -04:00
darroyo be2d2d1a8d Bump version to 1.0.31 2026-07-09 20:38:45 -04:00
darroyo c0bf16f132 Bump version to 1.0.30 2026-07-09 20:33:43 -04:00
darroyo ee5372c9fd Bump version to 1.0.29 2026-07-09 20:33:19 -04:00
darroyo 5d708e1d7b fix: RunRemote SSH-to-source with pre-installed dest key, eliminating base64 round-trip
- Regenerate qnap.key and baby-nas.key to OpenSSH native format (387 bytes vs 119 PKCS8)
- Pre-install qnap.key on Baby NAS at /var/lib/syncserver/ssh/keys/
- Pre-populate Baby NAS known_hosts with Qnap host keys
- Simplify RunRemote: LXC SSH to Baby NAS, Baby NAS runs rsync with local qnap.key
- Remove wrapper script approach (rsync rejects remote-to-remote)
2026-07-09 20:03:00 -04:00
darroyo 727d8676a6 Bump version to 1.0.27 2026-07-09 18:41:13 -04:00
darroyo f76cdaf140 Bump version to 1.0.26 2026-07-09 18:40:30 -04:00
darroyo 83cc48e70f Bump version to 1.0.25 2026-07-09 18:30:24 -04:00
darroyo 63e82c502c Bump version to 1.0.24 2026-07-09 18:28:03 -04:00
darroyo 88cc7e88e6 Bump version to 1.0.23 2026-07-09 17:33:04 -04:00
darroyo be7d47c0e1 Bump version to 1.0.22 2026-07-09 16:54:38 -04:00
darroyo 6c48031dd7 Bump version to 1.0.21 2026-07-09 15:18:05 -04:00
darroyo acd50ec9c0 Bump version to 1.0.20 2026-07-09 15:13:35 -04:00
darroyo 7a70355b6d Bump version to 1.0.19 2026-07-09 15:00:40 -04:00
darroyo 73cad44769 Bump version to 1.0.18 2026-07-09 12:43:13 -04:00
darroyo f92b03c0ce Bump version to 1.0.17 2026-07-09 10:40:23 -04:00
darroyo ba4c6aa732 Bump version to 1.0.16 2026-07-09 00:04:56 -04:00
darroyo 48d8fff5df Bump version to 1.0.15 2026-07-08 23:56:05 -04:00
darroyo d0fd0e994f Bump version to 1.0.13 2026-07-08 23:36:24 -04:00
darroyo c015a47440 Bump version to 1.0.12 2026-07-08 22:39:08 -04:00
darroyo 1798fc6804 Bump version to 1.0.11
Machine status probe on page load:
- POST /api/machines/refresh probes all machines in parallel (max 20 concurrent, 1.5s timeout)
- Updates DB status and broadcasts via SSE to all connected browser tabs
- Server-side throttle: ignores refresh requests within 10s
- Machines.tsx and Dashboard.tsx fire probe on mount
- Visual "Checking machine status..." indicator in Machines table
- MachineHandler now accepts *Engine for ProbeAllMachines access
2026-07-08 21:44:50 -04:00
darroyo a77f84ad34 Bump version to 1.0.10
Smart WoL: TCP pre-check before sending magic packet (3s timeout).
Machine status updates via SSE: online/offline tracked in DB and
broadcast to all connected browser tabs in real-time.
- Pre-check: if machine already reachable, skip WoL and mark online
- WoL path: send 3 magic packets, wait for SSH, mark online/offline
- Backend: setMachineStatus() helper + machine_status SSE event
- Frontend: subscribeMachineStatus() SSE helper for Machines + Dashboard
- IsReachable() helper in wol package for TCP reachability checks
2026-07-08 19:56:08 -04:00
darroyo 5d5b6c99a7 Bump version to 1.0.9
Fix Wake-on-LAN: set SO_BROADCAST on UDP socket, send 3 magic packets,
expose broadcast_addr and wake timeout fields in UI, add Test Wake endpoint,
surface send errors in job status, bump default wake timeout to 180s.
2026-07-08 19:19:50 -04:00
darroyo 69c4898a56 Add cancellation reason tracking with user/system codes and UI 2026-07-08 17:31:22 -04:00
darroyo b185686d2b Bump version to 1.0.7 2026-07-08 00:05:37 -04:00
darroyo 9cef7173cb Visual redesign: design system, refined ops console aesthetic
- Full component library (Button, Input, Label, Select, Modal, Table, Badge, Card, etc.)
- Tailwind design tokens: IBM Plex Sans + JetBrains Mono, teal accent, semantic status colors
- NavBar with logo, responsive hamburger menu, real logout
- All pages redesigned: Login, Dashboard (KPI cards), Machines, SyncPairs, JobHistory, JobDetail, SSHKeys, Settings
- Fixed: hover:bg-gray-750 dead class, window.location.href navigation bug
- Replaced alert()/confirm() with sonner toasts and accessible modals
- Added ErrorBoundary, skip link, accessible modal dialogs (Radix)
- Icons: lucide-react throughout, copy/download buttons
- 1.0.5 → 1.0.6
2026-07-07 23:12:34 -04:00