Skip to content

Add source.crate field to decouple skill fetch target from activation predicates#236

Merged
nikomatsakis merged 8 commits into
symposium-dev:mainfrom
nikomatsakis:skills-from-specific-crate
Jun 3, 2026
Merged

Add source.crate field to decouple skill fetch target from activation predicates#236
nikomatsakis merged 8 commits into
symposium-dev:mainfrom
nikomatsakis:skills-from-specific-crate

Conversation

@nikomatsakis
Copy link
Copy Markdown
Member

@nikomatsakis nikomatsakis commented Jun 1, 2026

What does this PR do?

When fetching skills from a crate, check the Cargo.toml of the crate for Symposium metadata to allow overriding the path where skills are found or redirecting to other crates. This replaces the old crate_path field.

Example: The dial9 crate has centralized its skills in dial9-viewer. Therefore they would do:

crates = ["dial9-tokio-telemetry", "dial9", "dial9-viewer"]

[[skills]]
source = "crate"

Then in dial9-tokio-telemetry and dial9 they would put:

[[package.metadata.symposium.skills]]
crate = { name = "dial9-viewer" }

This would fetch skills from the latest version of dial9-viewer.

Disclosure questions

AI disclosure.

  • The AI tool authored large parts of the code

Questions for reviewers.

@nikomatsakis
Copy link
Copy Markdown
Member Author

cc @jlizen

@nikomatsakis nikomatsakis marked this pull request as ready for review June 1, 2026 13:58
nikomatsakis and others added 2 commits June 1, 2026 14:50
…on predicates

Previously, `source.crate_path` groups relied on predicate resolution
(plugin-level + group-level `crates`) to determine which crate to fetch
skills from. This forced authors to add a group-level `crates` filter
that also narrowed the activation condition — making it impossible to
say "activate for any of these crates, but fetch skills from this
specific one."

`source = { crate = "name" }` (optionally with `crate_path`) now names
the fetch target explicitly, leaving predicates to control only
activation. Example:

    crates = ["dial9-tokio-telemetry", "dial9", "dial9-viewer"]

    [[skills]]
    source = { crate = "dial9-viewer", crate_path = "skills" }

Co-authored-by: Claude <claude@anthropic.com>
@nikomatsakis nikomatsakis force-pushed the skills-from-specific-crate branch from 43fdb6e to 2046436 Compare June 1, 2026 14:51
Copy link
Copy Markdown
Member

@jlizen jlizen left a comment

Choose a reason for hiding this comment

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

Some nits

Comment thread src/skills.rs Outdated
Comment thread src/plugins.rs Outdated
Comment thread src/plugins.rs Outdated
Comment thread src/plugins.rs Outdated
nikomatsakis and others added 3 commits June 1, 2026 15:51
- Validate that source.crate is non-empty at parse time
- Fix misleading error message (crate + crate_path can co-exist)
- Remove redundant path+crate_path exclusivity check (already covered)

Co-authored-by: Claude <claude@anthropic.com>
Replaces the flat `source.crate`/`source.crate_path` fields with a
structured `source.crate = { name?, path?, version? }` table:

  source = "crate"                        # shorthand, unchanged
  source.crate.path = "guidance"          # replaces source.crate_path
  source.crate.name = "dial9-viewer"      # explicit fetch target
  source.crate.version = ">=1.0"          # version constraint (new)

Also:
- Removes the 0.0.0 version fallback when a named crate isn't in the
  workspace — now warns and skips instead
- Validates that source.crate.name is non-empty
- Keeps source.crate_path as a legacy alias during deserialization

Co-authored-by: Claude <claude@anthropic.com>
…o.toml

Crate authors now control where Symposium finds skills via their own
Cargo.toml metadata instead of plugin-side `source.crate` fields. This
gives authors full control over skill layout and enables recursive
redirects (A can point to B for skills, B can point to C, etc.).

Key changes:
- New `crate_metadata` module parses `[package.metadata.symposium]`
- `PluginSource::Crate` simplified to unit variant (no payload)
- `source.crate = { ... }` and `source.crate_path` are now parse errors
  with migration hints
- `load_crate_skills` reads metadata, follows redirects recursively with
  cycle detection (hyphen/underscore-normalized) and depth limit of 10
- Diamond redirects dedup via SkillOrigin, malformed metadata falls back
  to skills/, explicit `skills = []` opts out

Co-authored-by: Claude <claude@anthropic.com>
Comment thread src/skills.rs
Comment thread src/lib.rs Outdated
nikomatsakis and others added 2 commits June 2, 2026 17:30
Address review nit — this module is internal-only.

Co-authored-by: Claude <claude@anthropic.com>
These modules are only used internally — the binary accesses them via
the CLI dispatch layer, not directly.

Co-authored-by: Claude <claude@anthropic.com>
@nikomatsakis
Copy link
Copy Markdown
Member Author

This is a breaking change, but I'm inclined to just do it, update the recommendations repo, and encourage folks to upgrade.

@nikomatsakis nikomatsakis added this pull request to the merge queue Jun 3, 2026
Merged via the queue into symposium-dev:main with commit d7ec437 Jun 3, 2026
6 checks passed
@nikomatsakis nikomatsakis mentioned this pull request Jun 3, 2026
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.

2 participants