HKUDS/nanobot · error · TuiUnavailableError
TUI release manifest is incomplete
Error message
TUI release manifest is incomplete
What it means
In _release_manifest, after parsing all valid lines the set of checksummed names does not equal the expected bundle names — the manifest is missing entries (or contains none). A complete manifest is required before any bundle file is trusted; the fault is an incomplete MANIFEST.sha256 in the release.
Solutions
- Re-publish the release with a manifest covering every bundle file (binary, sidecar files, manifest excluded)
- Compare the manifest against the archive contents to find the missing entry
- Retry the download in case the manifest was truncated
Defensive patterns
Strategy: validation
When it happens
Trigger: Thrown at nanobot/cli/tui_launcher.py:325 when the library encounters an invalid state.
Common situations: See trigger scenarios.
AI-assisted analysis of HKUDS/nanobot@42f37dc4c0 (2026-08-26).
Data as JSON: /api/errors/1abe197ddbb3d77b.
Report an issue: GitHub.
Appendix: source
Thrown at nanobot/cli/tui_launcher.py:325
try:
lines = raw.decode("utf-8").splitlines()
except UnicodeDecodeError as exc:
raise TuiUnavailableError("TUI release manifest is not valid UTF-8") from exc
checksums: dict[str, str] = {}
for line in lines:
digest, separator, name = line.partition(" ")
digest = digest.lower()
if (
separator != " "
or name not in expected_names
or name in checksums
or len(digest) != 64
or any(character not in "0123456789abcdef" for character in digest)
):
raise TuiUnavailableError("TUI release manifest is malformed")
checksums[name] = digest
if set(checksums) != expected_names:
raise TuiUnavailableError("TUI release manifest is incomplete")
return checksums
def _verified_release_archive(raw: bytes, asset: str) -> dict[str, bytes]:
expected_names = set(_release_bundle_names(asset))
files: dict[str, bytes] = {}
try:
with zipfile.ZipFile(io.BytesIO(raw)) as archive:
entries = archive.infolist()
names = [entry.filename for entry in entries if not entry.is_dir()]
if len(names) != len(entries) or len(names) != len(set(names)):
raise TuiUnavailableError("TUI release archive contains invalid entries")
if set(names) != expected_names:
raise TuiUnavailableError("TUI release archive is incomplete")
for entry in entries:
limit = 150 * 1024 * 1024 if entry.filename == asset else _TUI_RELEASE_LIMITS[
entry.filename
]View on GitHub (pinned to 42f37dc4c0)