diff options
| author | Danilo M. <danix@danix.xyz> | 2026-10-19 19:12:05 +0200 |
|---|---|---|
| committer | Danilo M. <danix@danix.xyz> | 2026-10-19 19:12:05 +0200 |
| commit | 6fdb31d538269136415ce71cbf58de6017f95463 (patch) | |
| tree | a37e51bdaf4783bce22cf121061d71e69ea2a862 /sb_builder/config.py | |
| parent | fb64c88bb8672ee9bdb8172eec0252966d67404a (diff) | |
| download | sb-builder-6fdb31d538269136415ce71cbf58de6017f95463.tar.gz sb-builder-6fdb31d538269136415ce71cbf58de6017f95463.zip | |
Add the PyQt6 GUI: Dashboard, Jobs, VM control, notifications
All VM access goes through remote.py (ssh with a shared ControlMaster,
local virsh). The main window polls jobs, backs off while ssh is down,
checks the libvirt domain and offers Start or Resume, and sends
freedesktop notifications when a job ends or the VM comes up. The Jobs
tab streams a job's log with job-follow and resumes at the last offset
after a drop. Config is TOML, validated against built-in defaults.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Diffstat (limited to 'sb_builder/config.py')
| -rw-r--r-- | sb_builder/config.py | 57 |
1 files changed, 57 insertions, 0 deletions
diff --git a/sb_builder/config.py b/sb_builder/config.py new file mode 100644 index 0000000..4549b66 --- /dev/null +++ b/sb_builder/config.py @@ -0,0 +1,57 @@ +# sb-builder - GUI configuration +# Copyright (C) 2026 Danilo M. <danix@danix.xyz> +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License version 2 as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License along +# with this program; if not, write to the Free Software Foundation, Inc., +# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + +"""GUI configuration: built-in defaults overlaid by the user's TOML file.""" + +import copy +import os +import tomllib + +DEFAULTS = { + "remote": {"target": "buildsystem", "ssh_options": []}, + "refresh": {"dashboard": 30, "jobs": 5}, + "notify": {"enabled": True, "events": ["finished", "failed", "killed", "lost", "vm-up"]}, + "vm": {"libvirt_uri": "qemu:///system", "domain": "buildsystem", "autostart": False}, +} + + +def path(): + base = os.environ.get("XDG_CONFIG_HOME") or os.path.expanduser("~/.config") + return os.path.join(base, "sb-builder", "config.toml") + + +def load(p=None): + """Return (config, error). On any problem: the defaults plus the error text.""" + p = p or path() + try: + with open(p, "rb") as f: + data = tomllib.load(f) + except FileNotFoundError: + return copy.deepcopy(DEFAULTS), None + except (OSError, tomllib.TOMLDecodeError) as e: + return copy.deepcopy(DEFAULTS), f"{p}: {e}" + cfg = copy.deepcopy(DEFAULTS) + for sec, keys in data.items(): + if sec not in DEFAULTS or not isinstance(keys, dict): + return copy.deepcopy(DEFAULTS), f"{p}: unknown section [{sec}]" + for k, v in keys.items(): + if k not in DEFAULTS[sec]: + return copy.deepcopy(DEFAULTS), f"{p}: unknown key {sec}.{k}" + want = type(DEFAULTS[sec][k]) + if type(v) is not want: + return copy.deepcopy(DEFAULTS), f"{p}: {sec}.{k}: expected {want.__name__}" + cfg[sec][k] = v + return cfg, None |
