Stage 3: Implement mci install command for project initialization#10
Stage 3: Implement mci install command for project initialization#10MaestroError merged 8 commits intomainfrom
mci install command for project initialization#10Conversation
Co-authored-by: MaestroError <46760939+MaestroError@users.noreply.github.com>
Co-authored-by: MaestroError <46760939+MaestroError@users.noreply.github.com>
Co-authored-by: MaestroError <46760939+MaestroError@users.noreply.github.com>
mci install command for project initialization
There was a problem hiding this comment.
Pull Request Overview
This PR implements the mci install command, which bootstraps a new MCI project by creating configuration files and directory structure. The implementation follows the project's testing strategy with unit tests, feature tests, and manual tests.
- Adds
installCLI command that createsmci.json(ormci.yamlwith--yamlflag),./mci/directory, example toolset, and.gitignoreconfiguration - Implements asset file copying from package resources using
importlib.resources - Ensures idempotent behavior by gracefully handling existing files without overwriting them
Reviewed Changes
Copilot reviewed 11 out of 11 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
| src/mci/cli/install.py | Core implementation of the install command with helper functions for file creation |
| src/mci/mci.py | Registers the install command to the main CLI group |
| src/mci/assets/mci.json | Template for JSON configuration file |
| src/mci/assets/mci.yaml | Template for YAML configuration file |
| src/mci/assets/gitignore | Template for .gitignore file in ./mci/ directory |
| src/mci/assets/example_toolset.mci.json | Example toolset demonstrating CLI tool usage |
| tests/unit/cli/test_install.py | Unit tests for individual functions in the install command |
| tests/test_install_command.py | Feature tests for end-to-end install workflow |
| testsManual/test_install.py | Manual test script for real-world install command verification |
| pyproject.toml | Adds force-include configuration for assets directory in wheel build |
| README.md | Documentation for the install command usage and examples |
Comments suppressed due to low confidence (1)
testsManual/test_install.py:16
- Import of 'shutil' is not used.
import shutil
|
@copilot There is only the |
Co-authored-by: MaestroError <46760939+MaestroError@users.noreply.github.com>
Added YAML example toolset file ( When running
Both JSON and YAML versions contain the same Implemented in commit dc902b6. |
Implements the
mci installCLI command to bootstrap MCI projects with starter configuration files and directory structure.Changes
Asset Templates
src/mci/assets/: Package-bundled templates for project initializationmci.json/mci.yaml: Main configuration with example echo toolexample_toolset.mci.json/example_toolset.mci.yaml: CLI tool example usinglscommand (both JSON and YAML formats)gitignore: Template for MCP server directory exclusionInstall Command
src/mci/cli/install.py: Install command implementationcopy_asset(): Zip-safe asset copying usingimportlib.resourcescreate_mci_file(): Creates JSON or YAML configuration (via--yamlflag)create_mci_directory(): Sets up./mci/with smart.gitignoremanagementcreate_example_toolset(): Copies example toolset in matching format (JSON or YAML based on--yamlflag)Integration
src/mci/mci.py: Registered install command with main CLI grouppyproject.toml: Force-include assets in wheel via[tool.hatch.build.targets.wheel.force-include]Tests
Usage
Generated files are valid MCI schemas that integrate with
mci-py'sMCIClient. Both JSON and YAML formats create matching example toolsets, ensuring consistency across different project setups.Original prompt
This section details on the original issue you should resolve
<issue_title>Stage 3: CLI Command —
mci install</issue_title><issue_description>## Goal
Implement the
installCLI command to initialize an MCI project structure. Provide a simple way for users to bootstrap a new MCI project with starter schema files and directory organization.Deliverables
uvx mci installwith optional--yamlflagmci.jsonormci.yaml) from package assets into project root (default: JSON; YAML if--yamlis passed)./mci/library directoryexample_toolset.mci.jsonfrom assets into./mci/./mci/.gitignorewithmcp/entry (append if not present)src/mci/assets/mci.jsonsrc/mci/assets/mci.yamlsrc/mci/assets/example_toolset.mci.jsonsrc/mci/assets/gitignore(containsmcp/)importlib.resourcesto access and copy assets (zip-safe, avoids hardcoded paths)pyproject.toml:[tool.hatch.build.targets.wheel]should force-includesrc/mci/assetsin the package wheeluv run mci installworksFiles to Create/Modify (from PLAN.md, updated for asset approach)
src/mci/cli/install.py— Install command implementationsrc/mci/assets/mci.json— Main template filesrc/mci/assets/mci.yaml— Main YAML template filesrc/mci/assets/example_toolset.mci.json— Example toolset filesrc/mci/assets/example_toolset.mci.yaml— Example toolset filesrc/mci/assets/gitignore— Template for .gitignoresrc/mci/mci.py— Register install command in Click grouppyproject.toml— Ensure asset inclusion in build configClasses/Functions
install_command(yaml: bool = False)— Click command formci installcopy_asset(package: str, resource_name: str, dest_path: Path, overwrite: bool = False)— Utility for copying assetscreate_mci_file(format: str) -> None— Copymci.jsonormci.yamlfrom assetscreate_mci_directory() -> None— Create ./mci directory and update .gitignorecreate_example_toolset() -> None— Copyexample.mci.jsonfrom assetsInitial MCI File Structure
The default JSON template (located at
src/mci/assets/mci.json) should create:{ "schemaVersion": "1.0", "metadata": { "name": "Example Project", "description": "Example MCI configuration" }, "tools": [ { "name": "echo_test", "description": "Simple echo test tool", "inputSchema": { "type": "object", "properties": { "message": { "type": "string", "description": "Message to echo" } }, "required": ["message"] }, "execution": { "type": "text", "text": "Echo: {{props.message}}" } } ], "toolsets": [], "mcp_servers": {} }YAML template should be equivalent and reside in
src/mci/assets/mci.yaml.Implementation Notes
importlib.resources.files()for zip-safe asset access and copying--forceis introducedlscommand to list directoryLS command example
{ "name": "list_files", "description": "List files in a directory", "inputSchema": { "type": "object", "properties": { "directory": { "type": "string" } } }, "execution": { "type": "cli", "command": "ls", "args": ["-la", "{{props.directory}}"] }, "enableAnyPaths": false, "directoryAllowList": [ "{{env.PROJECT_ROOT}}" ] }Tests
Unit Tests
tests/unit/cli/test_install.pytest_create_json_file()— Copies mci.json from assetstest_create_yaml_file()— Copies mci.yaml from assets with --yaml flagtest_file_already_exists()— Handles existing file gracefullytest_create_mci_directory()— Creates ./mci dirtest_create_gitignore()— Copies/updates .gitignoreFeature Tests
tests/test_install_command.py— Full install workflow in a temp directoryManual Tests
testsManual/test_install.py— Run install in a real directory; verify filesAcceptance Criteria
uvx mci installcopies mci.json with the specified structureuvx mci install --yamlcopies mci.yaml./mci/directory is created withexample.mci.json./mci/.gitignoreexists and includesmcp/mci install#9✨ Let Copilot coding agent set things up for you — coding agent works faster and does higher quality work when set up for your repo.