Conversation
Write one JSON object for an installed pack: the list --json fields plus commands, templates and scripts arrays (and hooks for extensions) in place of the provides counts. Errors follow the list --json stderr contract. Part of github#4213. Assisted-by: Claude Code (model: Claude Opus 5.5, autonomous)
Contributor
There was a problem hiding this comment.
Copilot review overview
馃煛 Changes recommended
Direct preset handler calls incorrectly enter JSON mode because Typer鈥檚 default option object is truthy.
Review effort: Balanced
Findings: 1
Open (1)
What changed in this PR
Adds scoped JSON output for installed preset and extension detail commands.
Changes:
- Adds normalized per-contribution JSON helpers and CLI flags.
- Handles JSON errors, extension lookup, hooks, and option conflicts.
- Adds contract tests and reference documentation.
| File | Description |
|---|---|
src/鈥媠pecify_cli/鈥媉installed_info_json.py |
Builds detailed installed-pack JSON objects. |
src/鈥媠pecify_cli/鈥媝resets/鈥媍ommand_info.py |
Adds preset info --json. |
src/鈥媠pecify_cli/鈥媏xtensions/鈥媍ommand_info.py |
Adds extension info --json. |
tests/鈥媡est_installed_info_json.py |
Tests JSON output and errors. |
docs/鈥媟eference/鈥媝resets.md |
Documents preset JSON output. |
docs/鈥媟eference/鈥媏xtensions.md |
Documents extension JSON output. |
馃挕 Configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
| from ..extensions import normalize_priority | ||
| from . import PresetCatalog, PresetError, PresetManager | ||
|
|
||
| if json_output: |
Collaborator
|
Please address Copilot feedback and fix test & lint errors |
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.

Description
Part of #4213, following the scope in #4213 (comment).
Adds
--jsontospecify preset info <id>andspecify extension info <name>for installed packs. Each command writes one JSON object to stdout:id,name,description,version,author,priority,enabledandsourcecome frominstalled_list_item, the helper behindlist --json, so the two views share one definition. Theprovidescounts are replaced by arrays.commands,templatesandscriptsentries havename,description,sourceandsourcePath(the manifestfile). Preset entries addstrategyas the manifest validates it (lowercased, defaultreplace). Extension entries have nostrategy, since extension-provided files always replace. Extension scripts addruntimeswhen the manifest declares them.hooksentries havetrigger,targetCommand,optionalandpriority, with the defaults hook registration applies (trueand10). If an event declares the same command twice, the last declaration wins, as it does inHookExecutorregistration.list --jsoncontract: one{"error": "..."}object on stderr. A pack that is not installed, an ambiguous name or a missing project exits 1; parse errors keep their exit code throughInstalledListJSONCommand.extension info --json --versionsexits 2.The new helpers are in
src/specify_cli/_installed_info_json.py, next to_installed_list_json.py. Without--json, both commands behave as before. The CLI reference pages for presets and extensions describe the new output.With the bundled
gitextension andleanpreset installed through--dev:Not in this PR
These are the open questions from the scope comment, left for follow-ups:
id: [Feature]: Add deterministic contribution IDs and stack lookup IDs for resolved artifacts聽#4210 tracks ids for these surfaces.artifact,optionalandhandoffson commands: they depend on [Feature]: Add artifact, optional, and handoffs to the command manifest schema聽#4209.runtimeson preset scripts: this needs a preset manifest schema change.strategy. The loader does not readreplaces:(used inpresets/lean/preset.yml), soleanreports the defaultreplace. Mappingreplaces/wraps/prepends/appendswould change the loader, which seems better as its own PR.--jsonreturns the not-installed error instead of catalog metadata.Hook entries have no
sourcePath, because a hook can target a core command or a command from another pack, and then there is no file in this pack to point to.#4776 also changes
presets/command_info.py; I'll rebase on whichever lands first.Testing
The agent ran these on macOS with Python 3.12:
uv run pytest tests/test_installed_info_json.py: 12 passed. The same file againstmain(ae5ade7): 12 failed withNo such option: --json.uv sync --extra test, thenuv run pytest -n 4(pytest-xdist added to the local venv only): 9312 passed, 264 skipped.uvx ruff@0.15.0 check src tests: all checks passed.specify preset info --helpandspecify extension info --helplist--json; the sample-project commands above were run as shown.Tested locally with
uv run specify --helpRan existing tests with
uv sync && uv run pytestTested with a sample project (if applicable)
AI Disclosure
AI disclosure: Opened by @nefayran. Implemented with Claude Code (model: Claude Opus 5.5, max reasoning effort) in autonomous mode: the agent wrote the code, tests, docs and this description, and ran the checks listed above. The commit carries an
Assisted-bytrailer.