Commit Graph

13 Commits

Author SHA1 Message Date
shuki
280b80c956 Add tabbed settings screen and Send Test Email button
Organize settings into General, Email, SSH, and Web Dashboard tabs
using TabbedContent. Add test-email CLI command and button that
auto-saves settings then sends a test email via SMTP.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-07 06:00:30 +02:00
shuki
04a0c45abc Add rsync auto-retry on partial transfer and show running tasks in header
Rsync exit 23 (partial transfer) now triggers an automatic retry to recover
failed files before accepting with a warning. Also adds a task counter next
to the clock in the header bar showing running job count.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-07 03:26:13 +02:00
shuki
b28146529e Add contextual Help panel to all TUI screens (F1 toggle)
Split each screen into two columns: existing controls on the left,
a DocsPanel with Rich-markup documentation on the right (30% width).
Press F1 to toggle the help panel on/off from any screen.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 23:38:47 +02:00
shuki
ae1563396c Fix WORK_DIR override: config file was clobbering detect_mode
The settings screen wrote WORK_DIR="/usr/local/gniza/workdir" (root-mode
path) into gniza.conf. load_config then overrode the correct user-mode
path set by detect_mode, causing mktemp and rsync log redirects to fail
with Permission denied — crashing the bash script while rsync continued
as an orphan.

- Remove WORK_DIR from AppSettings model and settings screen
- Re-run detect_mode after config load to restore correct paths
- Removed stale WORK_DIR from user's gniza.conf

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 21:14:14 +02:00
shuki
63cc7f842e Fix security and correctness bugs found in code review
- Add shquote() to escape single quotes in paths passed to remote_exec,
  preventing shell injection via REMOTE_BASE containing single quotes
- Apply shquote to remote_exec calls in remotes.sh, backup.sh, transfer.sh, ssh.sh
- Add DISK_USAGE_THRESHOLD validation in config.sh
- Export SMTP_PASSWORD (was missing from export list)
- Fix WEB_PORT default mismatch: use 2323 consistently in from_conf and settings save
- Narrow exception catch in remotes.py disk info fetch to KeyError/LookupError
- Quote REMOTE_KEY in build_rsync_ssh_cmd for paths with spaces

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 08:13:20 +02:00
shuki
590b87843d Add configurable disk usage threshold setting
Disk usage threshold (default 95%) can now be controlled from
Settings. Set to 0 to disable the check.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 07:08:42 +02:00
shuki
f7c5836db0 Show system clock in top right corner of all screens
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 06:35:51 +02:00
shuki
133ae1e7a4 Restore Flask dashboard with redesigned UI and API key auth
- Revert from textual-serve back to Flask (textual-serve had WebSocket issues)
- Completely redesigned dashboard: modern dark theme, stat cards, clean tables
- Redesigned login page to match
- Restored API key generation in install script
- Keep API key field in TUI settings

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 06:09:39 +02:00
shuki
1a24371446 Replace Flask web dashboard with textual-serve
Serves the exact same TUI in the browser via textual-serve.
No more separate Flask app, API keys, or login page needed.

- gniza web start now runs textual-serve instead of Flask
- Simplified systemd service to use python3 -m tui --web
- Removed web_enabled and web_api_key from settings/models
- Simplified install script web setup (no API key generation)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 06:05:29 +02:00
shuki
cf00ecdd4b Add web dashboard with systemd service support
- Flask web dashboard with dark theme matching TUI
- Login with API key authentication
- Dashboard shows targets, remotes, schedules, last backup status
- Trigger backups from web UI per target
- View logs via /api/logs endpoint
- systemd service: gniza web install-service / remove-service / status
- CLI: gniza web start [--port=PORT] [--host=HOST]
- TUI settings: web enabled, port, host, API key fields
- Install script: optional web dashboard setup with auto-generated API key
- Uninstall script: removes systemd service

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 05:34:02 +02:00
shuki
b3c055c9be Add configurable WORK_DIR instead of /tmp for temp files
Default: /usr/local/gniza/workdir (root) or ~/.local/state/gniza/workdir
(user). MySQL dumps and rclone temp configs now use WORK_DIR. Configurable
via gniza.conf or TUI Settings screen. Created during install.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 03:00:21 +02:00
shuki
4bd9df3b5e Fix Select.BLANK checks across all screens
Replace `is Select.BLANK` / `is not Select.BLANK` with isinstance
checks, as the sentinel identity varies across Textual versions.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-06 02:12:58 +02:00
shuki
587149f062 Add Python Textual TUI replacing gum-based bash TUI
New tui/ package with 14 screens (main menu, backup, restore, targets,
remotes, snapshots, verify, retention, schedule, logs, settings, wizard),
3 custom widgets (folder picker, confirm dialog, operation log), async
backend wrapper, pure-Python config parser, and TCSS theme.

bin/gniza now launches Textual TUI when available, falls back to gum.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-05 23:39:48 +02:00