diff --git a/bin/llm-tui b/bin/llm-tui index ce2bd11..78a0857 100755 --- a/bin/llm-tui +++ b/bin/llm-tui @@ -220,6 +220,15 @@ def check_port_status(port: int) -> tuple[bool, str]: data = json.loads(response.read().decode()) status = data.get("status", "unknown") return True, f"Online ({status})" + except urllib.error.HTTPError as e: + if e.code == 503: + try: + data = json.loads(e.read().decode()) + msg = data.get("error", {}).get("message", "Loading model") + return True, f"Loading ({msg})" + except Exception: + return True, "Loading model..." + return False, f"HTTP Error {e.code}" except Exception: return False, "Offline" @@ -246,6 +255,7 @@ class LLMConfigApp(App): border: solid #3b4252; padding: 1 2; margin-bottom: 1; + height: auto; } .title { color: #88c0d0; @@ -302,18 +312,21 @@ class LLMConfigApp(App): border-left: thick #88c0d0; padding: 1 2; margin-bottom: 1; + height: auto; } #vram-meter { background: #232834; border: solid #4c566a; padding: 1; margin-top: 1; + height: auto; } #status-card { background: #1e222b; border: solid #4c566a; padding: 1; margin-bottom: 1; + height: auto; } Log { background: #0f1117; @@ -339,6 +352,8 @@ class LLMConfigApp(App): _sync_lock: bool = False _last_selected_model: str = "" _last_selected_mmproj: str = "" + _last_log_size: int = -1 + _last_log_name: str = "" def compose(self) -> ComposeResult: yield Header(show_clock=True) @@ -672,7 +687,12 @@ class LLMConfigApp(App): lines = [] for port, label in [(11434, "Planner / Solo"), (11435, "Worker 1"), (11436, "Worker 2")]: online, msg = check_port_status(port) - badge = "[green]● ONLINE[/]" if online else "[yellow]○ OFFLINE[/]" + if not online: + badge = "[yellow]○ OFFLINE[/]" + elif "loading" in msg.lower(): + badge = "[cyan]⏳ LOADING[/]" + else: + badge = "[green]● ONLINE[/]" lines.append(f"Port {port} ({label}): {badge} - {msg}") card = self.query_one("#status-card", Static) @@ -684,8 +704,13 @@ class LLMConfigApp(App): if logs: latest = logs[0] try: + cur_size = latest.stat().st_size + if cur_size == self._last_log_size and latest.name == self._last_log_name: + return + self._last_log_size = cur_size + self._last_log_name = latest.name with open(latest, "r", errors="ignore") as f: - f.seek(max(0, latest.stat().st_size - 8192)) + f.seek(max(0, cur_size - 16384)) tail = f.read() log_widget.clear() log_widget.write(f"--- Streaming {latest.name} ---\n" + tail) @@ -732,7 +757,8 @@ class LLMConfigApp(App): ) subprocess.Popen(cmd, env=env, cwd=str(SCRIPT_DIR), start_new_session=True) - self.notify(f"Launching {preset} server. Check Status & Live Logs tab.", severity="information") + self.notify(f"Launching {preset} server. Switching to Status & Logs...", severity="information") + self.query_one(TabbedContent).active = "tab-status" self.action_refresh_status() def action_stop(self) -> None: