Skip to content

feat(drivers): one place to see and choose a driver version - #1427

Merged
frahlg merged 3 commits into
masterfrom
feat/driver-versions-one-place
Sep 25, 2026
Merged

frahlg merged 3 commits into
masterfrom
feat/driver-versions-one-place

Conversation

@frahlg

@frahlg frahlg commented Sep 25, 2026

Copy link
Copy Markdown
Member

The owner's rule for driver versions: an owner picks which signed version runs; it is seen and changed in one place; nothing lights up on its own. Items 3 and 4 of #1423, plus the owner's request for a clear changelog per version.

What changes

One place: each device's Versions list under Settings → Devices.

  • The release's own copy comes first, with its version: "v2.1.2 · this release".
  • The list then shows the signed stable versions and any beta newer than stable, each marked with its channel.
    • A channel file with the release's version is listed only while it runs.
    • Beta history that stable has already passed is not listed.
  • The owner's choice is marked "chosen, kept across updates".
  • Every version has What changed. It links to the driver's history in device-drivers at the commit the version was published from, so the newest entries are the change. The release row links through the pin in BUNDLED_SOURCE.json. Only a GitHub source with a hex commit gets a link.
  • Check for new versions refreshes both signed channels and redraws the list. Nothing installs.

The device line says where the running driver comes from:

  • this release;
  • chosen, kept across updates · release has v2.1.2;
  • until a release has it · release has v…;
  • your own file.

The "Update to vX" button is gone.

Other surfaces:

  • Update Center lists no drivers. The header counts only Core, so a new driver never lights it up. On 0.x this panel was already dead code: native shows only the version, and Docker disables it with a 503.
  • System no longer refreshes driver catalogs. It says "versions under Devices".
  • Adding a device: "Look for more drivers" fetches the driver types the release does not carry into the same list.
    • They come from the driver channel, or from beta, marked "beta". Adding one installs it from its channel.
    • Before this change the add list never offered stable channel-only drivers (47 of them). They were reachable only through the beta selector.
    • The separate channel selector is gone.

API and CLI:

  • /versions returns release_version, chosen_version, logical_path and release_source (the pinned repository and commit).
  • Each candidate carries channel and repository.
  • The catalog marks a chosen override.
  • POST /refresh with no id reads the beta channel too.
  • ftw status tells a chosen override apart from an early one.

Known limit

For the ~21 bundled drivers whose source DRIVER.id is spelled differently from the channel (sungrow-shx vs sungrow, easee-cloud vs easee_cloud), the Versions list finds no channel versions yet. It shows only the release row. Item 1 of #1423 fixes this at the source in device-drivers: one id and one version per driver.

Evidence

  • go test: driverrepo, api, ftwcli, drivers and cmd/ftw pass. New tests:
    • the version list across stable and beta, with a promoted file listed once and passed beta hidden;
    • /versions returning the release version and the owner's choice;
    • the CLI override wording.
  • npm test: 633 pass (run with LC_ALL=C.UTF-8; see fix(drivers): keep the owner's driver choice and meet both id spellings #1426 for the locale-dependent backup test).
    • driver-versions.test.mjs drives the real code with a DOM shim. It now covers the release row first and running, rows found by what they are, beta install through the channel, the chosen mark, the "What changed" links (including a refused javascript: source) and the refresh-and-redraw.
  • A local instance against the real signed channels: goodwe with an older 2.1.1 chosen over the release's 2.1.2 shows the rows and links described above. "Look for more drivers" added 47 channel drivers.

A human needs to look at this in a browser before merge (AGENTS.md). Screenshots were sent to the owner.

🤖 Generated with Claude Code

https://claude.ai/code/session_01MuerPFZFG88kgu8sWVHeq7

@chatgpt-codex-connector

chatgpt-codex-connector Bot commented Sep 25, 2026 •

Copy link
Copy Markdown

Codex Review Summary

This comment shows the latest Codex review activity on this pull request.

Review Status Commit Review trigger
📝 Code Review ✅ Completed 2026-09-25T06:39:53.760870Z 699213b PR opened
ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review" or "@codex security review".

Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 699213b496

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread go/internal/driverrepo/manager.go Outdated
Comment on lines +309 to +312
if repositoryID == "" {
if err := m.refreshOne(ctx, m.betaRepo); err != nil {
errs = append(errs, fmt.Errorf("%s: %w", m.betaRepo.ID, err))
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Preserve stable results when the beta refresh fails

When the stable manifest refresh succeeds but the independent beta request fails, this error is joined into the overall Refresh result, so the API returns 502 and the Versions panel's promise chain never reloads its list. A beta-channel outage therefore hides newly fetched stable versions even though their verified cache was updated; return per-channel results or let the UI redraw from the successful cache while reporting the beta failure.

Useful? React with 👍 / 👎.

Comment thread web/settings/tabs/devices.js Outdated
Comment on lines +1841 to +1843
Promise.all([
fetchCatalog("/api/device_repository/catalog"),
fetchCatalog("/api/device_repository/catalog?channel=beta")

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Refresh stable before reporting newly available drivers

When the stable cache is stale, clicking “Look for more drivers” does not actually check the stable channel: /api/device_repository/catalog calls the cache-only Manager.Catalog, while only the beta endpoint performs a network refresh. A newly published stable-only driver can therefore remain absent until the 24-hour background refresh despite the UI saying it is checking both signed channels; refresh stable before fetching these catalogs.

AGENTS.md reference: AGENTS.md:L22-L23

Useful? React with 👍 / 👎.

@frahlg

frahlg commented Sep 25, 2026

Copy link
Copy Markdown
Member Author

Codex review: two findings. (1) Fixed in the latest commit: after a switch, "Check for new versions" redrew the picker from stale running-state options and hid the way back to the release's copy; covered by a new test that fails on the previous code. (2) For bundled drivers whose id is spelled differently from the channel, the Versions list finds no signed versions — resolved at the source by srcfl/device-drivers#132 and the FTW pin that follows it, so this PR should merge together with or after that pin.

frahlg added a commit that referenced this pull request Sep 25, 2026
Independent review of #1427:

- AvailableVersions matched an install to a candidate by repository,
  version and hash. A beta file that stable then published byte for
  byte lost its "running" and "chosen" marks, and "Use this" would
  fetch it again. Installs now match by version and hash.
- Refresh with no id also fetched the beta channel and failed the whole
  request when beta was unreachable, so "Check for new versions" did not
  redraw, and every box's daily refresh reached the beta channel.
  Refresh again reads only the configured sources; RefreshAll, used by
  the owner's check, adds beta and reports its failure as a warning,
  which the panel shows under a redrawn list.
- "Look for more drivers" used Promise.all, so an unreachable beta hid
  the stable channel's drivers. It uses allSettled and says which
  channel could not be reached.
- A channel version equal to the release's reads "same as this
  release", not "until a release has it".

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MuerPFZFG88kgu8sWVHeq7
frahlg and others added 3 commits September 25, 2026 10:06
The owner's rule: an owner picks which signed driver version runs, it is
seen and changed in one place, and nothing lights up on its own.

- Each device's Versions list under Settings > Devices is that place.
  It lists the release's own copy first (with its version), the signed
  stable versions and any beta newer than stable, marked. The owner's
  choice is marked "chosen, kept across updates". Every version links to
  what changed: the driver's history in device-drivers at the commit it
  was published from. "Check for new versions" refreshes both signed
  channels and redraws the list; nothing installs.
- The device line says where the running driver comes from: this
  release, chosen and kept across updates, until a release has it, or
  your own file. The "Update to vX" button is gone.
- Update Center lists no drivers and the header counts only Core. System
  no longer refreshes driver catalogs.
- Adding a device: "Look for more drivers" fetches the driver types the
  release does not carry, from the driver channel or, marked, from
  beta, into the same list. The add path installs them from their
  channel. The old list never offered stable channel-only drivers; they
  were reachable only through the beta selector.
- API: /versions returns release_version, chosen_version, logical_path
  and the release's pinned source; candidates carry channel and
  repository. The catalog marks a chosen override. One refresh reads
  both channels. `ftw status` tells a chosen override from an early one.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MuerPFZFG88kgu8sWVHeq7
Codex review: after a switch, "Check for new versions" rebuilt the
picker from the options captured when it was opened. With the release's
copy running at first, the redraw still marked it as running and hid
its "Use this" button, so the way back disappeared. refreshSummary now
updates the running source and version in those options, as it already
did for the button's dataset. The new test fails on the previous code.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MuerPFZFG88kgu8sWVHeq7
Independent review of #1427:

- AvailableVersions matched an install to a candidate by repository,
  version and hash. A beta file that stable then published byte for
  byte lost its "running" and "chosen" marks, and "Use this" would
  fetch it again. Installs now match by version and hash.
- Refresh with no id also fetched the beta channel and failed the whole
  request when beta was unreachable, so "Check for new versions" did not
  redraw, and every box's daily refresh reached the beta channel.
  Refresh again reads only the configured sources; RefreshAll, used by
  the owner's check, adds beta and reports its failure as a warning,
  which the panel shows under a redrawn list.
- "Look for more drivers" used Promise.all, so an unreachable beta hid
  the stable channel's drivers. It uses allSettled and says which
  channel could not be reached.
- A channel version equal to the release's reads "same as this
  release", not "until a release has it".

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MuerPFZFG88kgu8sWVHeq7
@frahlg
frahlg force-pushed the feat/driver-versions-one-place branch from 585f2dd to 29fc1f2 Compare September 25, 2026 08:06
@frahlg
frahlg merged commit 6c75162 into master Sep 25, 2026
15 checks passed
@frahlg
frahlg deleted the feat/driver-versions-one-place branch September 25, 2026 08:57
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant