chore: unify semver handling across the packaging stack - #93
Conversation
Ties together the six-PR chain that replaces five divergent semver implementations -- and a catalog that was not sorted by semver at all -- with a single one, living in logos-package. logos-package#30 the shared implementation (root) logos-package-manager#25 \ both consume it logos-package-downloader#17/ logos-package-manager-ui#51 header-only, via the flake's preConfigure logos-modules-release-tool#4 catalog ordering, via `lgx semver` Registers the release/catalog pipeline repos as workspace submodules. They are non-flake (index.py is a stdlib Python script; -action and -base are GitHub Actions YAML and bash), so they join as plain submodules and stay out of the flake dep graph. Only -tool takes a code change. package-manager-ui gains a logos-package input -- it is the one repo in the chain that needed a new dependency edge -- so the workspace follows it to keep a single logos-package (and a single nixpkgs) across the graph. dep-graph.nix is edited by hand rather than regenerated: `ws sync-graph` rebuilds from local submodule state, which here reverted logos-protocol to an older rev and deleted logos-delivery-demo plus all seven logos-evm-* entries. Only the package-manager-ui edge actually changed. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
There was a problem hiding this comment.
Pull request overview
This PR updates the Logos workspace wiring to support a broader effort to unify SemVer handling across the packaging/release stack by registering additional release/catalog repositories as submodules and adding a new dependency edge so logos-package-manager-ui can follow the shared logos-package semver implementation.
Changes:
- Add
logos-modules-release-*repos to the workspace submodule registry (scripts/ws,.gitmodules). - Add
logos-packageas a declared dependency forlogos-package-manager-ui(nix/dep-graph.nix). - Configure
logos-package-manager-uito follow the workspacelogos-packageinput (flake.nix).
Reviewed changes
Copilot reviewed 11 out of 11 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
| scripts/ws | Registers release/catalog pipeline repos as non-flake workspace submodules. |
| nix/dep-graph.nix | Adds logos-package to logos-package-manager-ui deps/follows in the workspace dep graph. |
| flake.nix | Adds inputs.logos-package.follows = "logos-package" for logos-package-manager-ui. |
| .gitmodules | Adds the three new logos-modules-release-* submodules. |
| logos-package-manager-ui = { | ||
| url = "github:logos-co/logos-package-manager-ui/7c8c3acd7b1215fef956a05b9423ab169a09becc"; | ||
| inputs.logos-module-builder.follows = "logos-module-builder"; | ||
| inputs.logos-package.follows = "logos-package"; | ||
| inputs.package_downloader.follows = "logos-package-downloader-module"; | ||
| inputs.package_manager.follows = "logos-package-manager-module"; | ||
| }; |
| logos-package-manager-module = { deps = [ "logos-module-builder" "logos-package-manager" ]; follows = { "logos-module-builder" = "logos-module-builder"; "logos-package-manager" = "logos-package-manager"; }; hasTests = false; }; | ||
| logos-package-downloader-module = { deps = [ "logos-module-builder" "logos-package-downloader" ]; follows = { "logos-module-builder" = "logos-module-builder"; "logos-package-downloader" = "logos-package-downloader"; }; hasTests = false; }; | ||
| logos-package-manager-ui = { deps = [ "logos-module-builder" "logos-package-manager-module" "logos-package-downloader-module" ]; follows = { "logos-module-builder" = "logos-module-builder"; "package_downloader" = "logos-package-downloader-module"; "package_manager" = "logos-package-manager-module"; }; hasTests = false; }; | ||
| logos-package-manager-ui = { deps = [ "logos-module-builder" "logos-package" "logos-package-manager-module" "logos-package-downloader-module" ]; follows = { "logos-module-builder" = "logos-module-builder"; "logos-package" = "logos-package"; "package_downloader" = "logos-package-downloader-module"; "package_manager" = "logos-package-manager-module"; }; hasTests = false; }; |
logos-package: <cstdint> before cpp-semver (libstdc++ needs it, libc++ leaks it) plus a headers-only package output. package-manager-ui: consume that headers output rather than the library -- the builder was copying liblgx.dylib next to the plugin and ui-host tried to load it as a Qt plugin, taking the whole UI down. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Pins the four chain repos at their PR branch heads so the workspace can actually build them. These must be re-pinned to the merged master commits as the chain lands -- that is what the workspace re-pin is for. dep-graph: sync-graph emits logos-package first in package-manager-ui's deps; the hand-applied edit had it second, which the CI staleness check caught. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
|
Both Copilot comments here are already resolved. They were accurate at PR-creation time — the pinned |
basecamp's AppsModel had a seventh copy of the buggy versionCmp (drives the app-manager Upgrade/Downgrade decision); logos-basecamp#257 reroutes it to the shared logos::semver and re-pins the chain inputs it consumes. Bump the submodule + flake pin so the integrated workspace build ships it. The logos-package follow edge already existed. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
|
Folded in logos-co/logos-basecamp#257 — basecamp's Updated merge order: logos-package#30 → package-manager#25 / package-downloader#17 → package-manager-ui#51 / basecamp#257 → modules-release-tool#4 → this. |
logos-co/logos-package#30 merged. Move the logos-package submodule + flake pin to master (8d4236f), and bump the downstream repos to their re-pinned branch heads (they now consume logos-package master). pm/pd/ui/basecamp stay on their branches until their own PRs merge. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Both module re-pins merged. Move logos-package-manager-module (439b580) and logos-package-downloader-module (02fcb4a) submodules + flake pins to master, and bump the ui + basecamp submodules to their module-re-pinned heads. ui stays on its branch until #51 merges. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
logos-package-manager-ui#51 merged -> ui submodule + flake to master (33f5ba0). basecamp -> 7769ed9 (its pushed branch head, which the previous workspace pin d1b9b68 was an unpushed ancestor of). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
basecamp#257 rebased onto master (#244); the previous pin 7769ed9 was orphaned by the force-push. Point at the rebased head. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Entry point for a 6-PR chain. Feed this to
/merge-chain.Why
Version handling was duplicated across the packaging repos and the copies disagreed — with each other and with the spec. Pre-release ordering (
-alpha/-beta/-rcN) was reported as broken. It was, but the survey found six divergent implementations, and the worst one wasn't a duplicate sort at all: the catalog was never ordered by semver.index.pysorted each package'sversions[]byreleasedAttimestamp, and every client readsversions[0]as "latest":So publishing
2.0.0-alphaafter1.9.0advertised an unreleased alpha to every user as the newest release. A backport cut after a higher version did the same, as did a forced republish.Three more real bugs, each proven by replicating the old semantics exactly:
1.0.0-rc.2ranked above1.0.0-rc.11(pre-release tag compared as one ASCII string; lgpm and the UI dropped it entirely —atoi("0-rc1") == 0)^1.0.0matched2.0.0-alpha— an unreleased alpha of the next major satisfying a caret range on 1.x, resolvable as a dependencyreleasedAt, so a late-published backport beat a higher versionlgpm install --dirsorted.lgxfilenames, so1.9.0was installed last and clobbered1.10.0The design
Split the problem the way the specs do.
Precedence is specified → delegated to a vendored library, z4kn4fein/cpp-semver v0.4.0 (MIT, single header, C++17, zero deps).
Ranges are not in the semver spec —
^ ~ x * ||are an npm convention the manifests already use — so that layer is written once, inlogos-package/include/logos/semver.hpp, on top of the library. It adopts npm's pre-release rule, which is what stops^1.0.0resolving to2.0.0-alpha.Two findings worth recording, because both contradict their own documentation:
neargye-semver— the only semver library in nixpkgs — is not actually SemVer 2.0.0 compliant. Its pre-release is an enum{alpha,beta,rc}+uint16: it cannot represent1.0.0-alpha.betaor build metadata, and majors cap at 65535. Hence vendoring.index.pyshells out to a newlgx semversubcommand rather than growing a second implementation in Python — it's stdlib-only but already requiredlgxfor exactly the two subcommands that sort. So this is genuinely one implementation across both languages, and the catalog cannot drift from the clients again.Merge order
Every downstream
flake.lockis pinned at #30's branch head so its CI can build; each must be re-pinned tomasteras it merges. logos-modules-release-tool#4's CI buildslgxfromlogos-packagemaster, so it stays red until #30 lands and then goes green on its own.This PR
index.pyis a stdlib Python script;-actionand-baseare Actions YAML and bash), so they join as plain submodules and stay out of the flake dep graph. Only-tooltakes a code change.package-manager-uigains alogos-packageinput — it's the one repo in the chain that needed a new dependency edge — so the workspacefollowsit, keeping a singlelogos-package(and a singlenixpkgs) across the graph. It takes headers only: noliblgx, ICU, libsodium or zlib enters the plugin (otool -Lverified).dep-graph.nixis edited by hand here, deliberately.ws sync-graphregenerates from local submodule state, and in this workspace that revertedlogos-protocolto an older rev and deletedlogos-delivery-demoplus all sevenlogos-evm-*entries. Only thepackage-manager-uiedge actually changed, so that one line is applied directly.Verification
The release-tool tests were run against the old implementation too: 4 of 7 fail, so they're genuine regression tests rather than tautologies.
🤖 Generated with Claude Code