Replace schedule targets/remotes inputs with selection lists

Show checkable lists of existing targets and remotes instead of
free-text comma-separated inputs. Selected items are joined with
commas on save, empty selection means "all".

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
shuki
2026-03-06 03:08:41 +02:00
parent b3c055c9be
commit 1d9d32c15f
2 changed files with 25 additions and 7 deletions

View File

@@ -63,6 +63,12 @@ Select {
margin: 0 0 1 0; margin: 0 0 1 0;
} }
SelectionList {
height: auto;
max-height: 8;
margin: 0 0 1 0;
}
/* Browse row */ /* Browse row */
#restore-dest-row { #restore-dest-row {
height: auto; height: auto;

View File

@@ -1,7 +1,7 @@
import re import re
from textual.app import ComposeResult from textual.app import ComposeResult
from textual.screen import Screen from textual.screen import Screen
from textual.widgets import Header, Footer, Static, Button, DataTable, Input, Select from textual.widgets import Header, Footer, Static, Button, DataTable, Input, Select, SelectionList
from textual.containers import Vertical, Horizontal from textual.containers import Vertical, Horizontal
from textual import work from textual import work
@@ -49,12 +49,24 @@ class ScheduleScreen(Screen):
yield Input(id="sched-day", placeholder="Leave empty if not needed") yield Input(id="sched-day", placeholder="Leave empty if not needed")
yield Static("Custom cron (5 fields):") yield Static("Custom cron (5 fields):")
yield Input(id="sched-cron", placeholder="0 2 * * *") yield Input(id="sched-cron", placeholder="0 2 * * *")
yield Static("Targets (comma-separated, empty=all):") yield Static("Targets (empty=all):")
yield Input(id="sched-targets", placeholder="") yield SelectionList[str](
yield Static("Remotes (comma-separated, empty=all):") *self._build_target_choices(),
yield Input(id="sched-remotes", placeholder="") id="sched-targets",
)
yield Static("Remotes (empty=all):")
yield SelectionList[str](
*self._build_remote_choices(),
id="sched-remotes",
)
yield Footer() yield Footer()
def _build_target_choices(self) -> list[tuple[str, str]]:
return [(name, name) for name in list_conf_dir("targets.d")]
def _build_remote_choices(self) -> list[tuple[str, str]]:
return [(name, name) for name in list_conf_dir("remotes.d")]
def on_mount(self) -> None: def on_mount(self) -> None:
self._refresh_table() self._refresh_table()
@@ -115,8 +127,8 @@ class ScheduleScreen(Screen):
time=self.query_one("#sched-time", Input).value.strip() or "02:00", time=self.query_one("#sched-time", Input).value.strip() or "02:00",
day=self.query_one("#sched-day", Input).value.strip(), day=self.query_one("#sched-day", Input).value.strip(),
cron=self.query_one("#sched-cron", Input).value.strip(), cron=self.query_one("#sched-cron", Input).value.strip(),
targets=self.query_one("#sched-targets", Input).value.strip(), targets=",".join(self.query_one("#sched-targets", SelectionList).selected),
remotes=self.query_one("#sched-remotes", Input).value.strip(), remotes=",".join(self.query_one("#sched-remotes", SelectionList).selected),
) )
write_conf(conf, sched.to_conf()) write_conf(conf, sched.to_conf())
self.notify(f"Schedule '{name}' created.") self.notify(f"Schedule '{name}' created.")