refactor(telemetry): registry prefixes come from the hub adapters; update reasons use tables

- `skills_hub._registry_prefixes` builds the identifier prefixes from the adapters' own
  SOURCE_IDs and `SkillsShSource._ID_PREFIX_ALIASES`, case-insensitively, so `skills.sh/...`,
  `skils-sh/...` and `OFFICIAL/...` stop reading `unresolved`. A matched source is named by
  `source_id()`, the method the router and the contract test use; two test fakes gain it.
- `update_failure_class`: exception type -> class and fixed stop-reason prefix -> class are
  tables instead of an if-ladder. `Windows gateway recovery failed: ...`, the fixed prefix
  update_completion writes when the post-update gateway resume fails, now reads
  `restart_failed` instead of `other` (prefix only, never the message).
- `mcp.servers.add` records through `mcp_rpc_helpers.record_mcp_add`, dropping the 175-column
  noqa line that kept methods_tools.py at its cap (2011 lines now).
This commit is contained in:
Teknium
2026-10-06 05:39:53 -07:00
parent d6813a5dd7
commit e032fdbca1
8 changed files with 61 additions and 21 deletions

View File

@@ -506,7 +506,7 @@ they failed. Rows recorded before the change keep their old field set and still
| Metric | Dimensions added | Question it answers |
|---|---|---|
| `hermes.extension.install.count` | failure class, registry | Why skill, plugin and MCP installs fail, and which skills-hub source fails. `failure_class` is `none` on success, else a closed name for the failure exit that stopped the install. Skills: `ambiguous`, `auth_rejected`, `fetch_failed`, `invalid_bundle`, `invalid_name`, `not_found`, `rate_limited`, `scan_blocked`, `stale_index`. Plugins: `already_installed`, `clone_failed`, `deps_declined`, `deps_failed`, `git_missing`, `incompatible`, `invalid_source`, `manifest_invalid`, `non_interactive`, `removed_from_catalog`, `scan_blocked`. MCP servers: `auth_required`, `bootstrap_failed`, `clone_failed`, `config_invalid`, `config_rejected`, `connect_failed`, `git_missing`, `missing_credentials`, `server_start_failed`. Every kind may also read `exception`, `filesystem_error`, `network`, `other`, `permission`. A raised error without a named class is classified by its Python type only (`PermissionError` reads `permission`, connection and timeout errors `network`, other `OSError`s `filesystem_error`, anything else `exception`, its type name dropped). `registry` is set on skill rows only: the skills-hub adapter that resolved or served the skill, one of `browse-sh`, `clawhub`, `github`, `hermes-index`, `lobehub`, `official`, `skills-sh`, `url`, `well-known` (the adapter ids `tools/skills_hub_search.py::create_source_router` builds), `unresolved` when no adapter answered, `none` for built-in restores and every plugin/MCP row, `other` otherwise. A row whose `failure_class` is outside its kind's set, is `none` on a failure or set on a success, or that names a registry on a plugin/MCP row is invalid. Never the identifier, URL, error text or path; `name` keeps its existing catalog-or-`custom` rule. |
| `hermes.update.run` | failure class | Why `hermes update` fails, next to where (`failed_stage`). `none` unless the outcome is `failed` or `refused`. Derived from the final update receipt only: `aborted_before_apply`, `build_failed`, `deps_failed`, `exception`, `fleet_stale`, `fleet_unverified`, `git_failed`, `interrupted`, `lock_held`, `managed_install`, `os_error`, `restart_failed`, `subprocess_failed`, else `other`; Desktop packaged self-updates report `unknown` (their RPC carries a stage, never a reason). An exception that ended the run is read by its type name alone, never its message. A failed run whose every stage mark passed now reads `failed_stage` `verify` (the post-restart verification wrote `partial`) or `restart` (a skipped restart left the fleet owing one) instead of `other`; a `partial` run with a failed build or restart mark keeps that stage, and its verify stage row is failed only when the fleet has a stale or down row. |
| `hermes.update.run` | failure class | Why `hermes update` fails, next to where (`failed_stage`). `none` unless the outcome is `failed` or `refused`. Derived from the final update receipt only: `aborted_before_apply`, `build_failed`, `deps_failed`, `exception`, `fleet_stale`, `fleet_unverified`, `git_failed`, `interrupted`, `lock_held`, `managed_install`, `os_error`, `restart_failed`, `subprocess_failed`, else `other`; Desktop packaged self-updates report `unknown` (their RPC carries a stage, never a reason). An exception that ended the run is read by its type name alone, never its message; a failed Windows gateway resume after the update reads `restart_failed`. A failed run whose every stage mark passed now reads `failed_stage` `verify` (the post-restart verification wrote `partial`) or `restart` (a skipped restart left the fleet owing one) instead of `other`; a `partial` run with a failed build or restart mark keeps that stage, and its verify stage row is failed only when the fleet has a stale or down row. |
<!-- ---- end iuf c1 ---- -->
<!-- ---- iuf c2 ---- -->
#### Fresh installs