Skip to content

fix(resources): a run profile is validated for shape at load; its references at resolve - #862

Open
antoinetoussaint-byte wants to merge 1 commit into
mainfrom
fix/run-profiles-validate-shape-at-load
Open

antoinetoussaint-byte wants to merge 1 commit into
mainfrom
fix/run-profiles-validate-shape-at-load

Conversation

@antoinetoussaint-byte

Copy link
Copy Markdown
Contributor

What this fixes

Declaring a run-profiles entry with exclusions in a workspace that composes pinned modules made the workspace unloadable for every command, doctor included:

cannot load workspace: LoadFromDir: Workspace::postLoad: invalid run profiles:
cannot load services for run profiles: … module <wiki> resolves to a pinned artifact
(source "obin-ai/core-solutions", version "0a18964f…"); pinned modules are pulled by the CLI,
not loadable as a local checkout

Workspace.postLoad → validateRunProfiles loaded every service to confirm each exclusion exists. A pinned module is materialized by the CLI after the first load (MaterializePinnedModules, resolveRunPins), so the check ran before the only thing that could make it pass. ResolveRunProfile performs the same inventory check at run time, once the composition is loadable — the eager copy was the one that could not work. Found on obin-ai/platform-obin (finding: the handbook session's FINDING-run-profile-breaks-pinned-workspace-load.md); the stopgap there is to keep the four --exclude-dependency flags on the command line.

The change (head 846ed1eba38c1235a6f701b9f3f471ae717954c8)

  • validateRunProfiles (load and pre-save) checks shape only: non-empty profile name; every excluded dependency non-empty and a well-formed service reference (ParseServiceWithOptionalModule); every excluded workspace configuration non-empty. No inventory load.
  • Reference validation (unknown service, ambiguous name, unknown workspace configuration) stays where it already was and where the inventory exists: ResolveRunProfile.

Tests

  • TestWorkspaceRunProfileValidation: the two at-load "unknown …" cases become shape cases (malformed dependency a/b/c, empty configuration), still refused at load.
  • TestRunProfileReferencesAreCheckedAtResolveNotLoad: the mutated fixtures now load and are refused by ResolveRunProfile(ctx, "local", …) with the same messages.
  • TestRunProfileDoesNotMakeAPinnedCompositionUnloadable: a workspace with a pinned module and a profile with exclusions loads; fails on main with the error above.

go test ./resources/ green (2.2 s). Not released by this PR: v0.19.9 carries it.

🤖 Generated with Claude Code

…erences at resolve

Workspace.postLoad validated every run profile that carries an exclusion by
loading every service, which a composition of pinned modules cannot do: those
modules are materialized by the CLI after this load, so declaring a profile
made the workspace unloadable for every command, doctor included
("module <wiki> resolves to a pinned artifact … not loadable as a local
checkout"). ResolveRunProfile already runs the same inventory check at run
time, once the composition is loadable; the eager copy was the one that could
not work.

Load now checks shape only: a non-empty profile name, every excluded
dependency a non-empty, well-formed service reference, every excluded
workspace configuration non-empty. An unknown service or configuration is
reported by ResolveRunProfile, where the inventory exists. The at-load tests
for unknown references move to resolve time; a new test loads a pinned
composition with a profile, and fails before this change.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
antoinetoussaint-byte added a commit that referenced this pull request Oct 28, 2026
…top (#863)

* release: v0.19.9 — a local image named by digest is present, not pulled (#861)

Bump version/info.codefly.yaml 0.19.8 → 0.19.9; version-tag.yml cuts the tag
from the merged commit once the suite is green. Merge AFTER #861 (and #862 if
it is to ride along): the tag carries exactly what main holds at this merge.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>

* feat(runners): condition orphan recovery on exact registration evidence

* fix(runners): bound recovery receipts consistently with preview output

* test(runners): wait for leaderless fixture exec evidence

* feat(dockerrun): stop an explicit container generation with custody checks

* docs(dockerrun): define local stop receipt contract exception

---------

Co-authored-by: Antoine Toussaint <312536060+antoinetoussaint-byte@users.noreply.github.com>
Co-authored-by: Claude Fable 5.1 <noreply@anthropic.com>
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