Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 12 additions & 4 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,22 @@ on:

jobs:
build:
name: Build and Test (Java ${{ matrix.java }})
runs-on: ubuntu-latest

strategy:
matrix:
java: ['11', '17']

steps:
- uses: actions/checkout@v3
- name: Set up JDK
uses: actions/setup-java@v3
- uses: actions/checkout@v4

- name: Set up JDK ${{ matrix.java }}
uses: actions/setup-java@v4
with:
java-version: '11'
java-version: ${{ matrix.java }}
distribution: 'temurin'
cache: 'maven'

- name: Build and test
run: mvn clean verify
92 changes: 92 additions & 0 deletions CLAUDE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
# CLAUDE.md

This file provides guidance for Claude Code when working in this repository.

## Repository overview

This is the **install-skill CLI** — a Java command-line tool (PicoCLI + embedded Maven) for installing AI assistant skills deployed with the skills-jar-maven-plugin. Skills are resolved from the [skills registry](https://github.com/webliteca/skills-registry) or by Maven coordinates.

## Key files

- `src/main/java/ca/weblite/installskill/InstallSkillCommand.java` — Main CLI entry point and command implementation. Handles single-skill install and batch install from `.skills-versions`.
- `src/main/java/ca/weblite/installskill/SkillCoordinates.java` — Immutable value class for resolved Maven coordinates (name, groupId, artifactId, version).
- `src/main/java/ca/weblite/installskill/SkillVersionsFile.java` — Parser for `.skills-versions` files.
- `src/main/java/ca/weblite/installskill/SkillLockFile.java` — Read/write for `.skills-versions.lock` (JSON). Includes resolution plan computation (comparing desired vs locked state).
- `pom.xml` — Maven build configuration. Java 11 target, PicoCLI + Maven Embedder dependencies.
- `package.json` — npm/jDeploy configuration for distribution as a native CLI.

## Architecture

### Two execution modes

1. **Single-skill mode** (`install-skill <skill>`): resolves one skill, creates a temp Maven project, runs `skills-jar-plugin:install`, copies result to target directory. No interaction with `.skills-versions` or lock files.

2. **Batch mode** (`install-skill` with no arguments): reads `.skills-versions` from the working directory, uses `.skills-versions.lock` for reproducible resolution, installs all listed skills sequentially.

### Key method flow in `InstallSkillCommand`

- `call()` — dispatcher: delegates to `installSingleSkill()` or `installFromVersionsFile()`
- `resolveSkillCoordinates(String)` — parses raw input (registry name, `name@version`, or Maven coords) into `SkillCoordinates`
- `resolveRegistryName(String, String)` — looks up a skill name in the XML registry
- `installResolved(String, String, String)` — creates temp Maven project and installs a single resolved skill
- `installFromVersionsFile()` — batch flow: parse versions file, compute resolution plan against lock, resolve new entries, install all, write lock

### Lock file resolution plan

`SkillLockFile.computeResolutionPlan()` compares `.skills-versions` entries against `.skills-versions.lock`:
- **Reusable**: entry exists in lock and `requestedVersion` matches — skip resolution
- **To resolve**: new entry or `requestedVersion` changed — needs fresh resolution
- **Removed**: in lock but not in `.skills-versions` — dropped from updated lock

## `.skills-versions` format

```
# Comment
skill-name@0.1.0
skill-name
com.example:my-lib@1.0
```

## `.skills-versions.lock` format (JSON)

```json
{
"lockVersion": 1,
"skills": {
"skill-name": {
"name": "skill-name",
"groupId": "com.example",
"artifactId": "my-lib",
"version": "0.1.0",
"requestedVersion": "0.1.0"
}
}
}
```

## Build and test commands

```bash
# Compile
mvn compile

# Run unit tests
mvn test

# Run integration tests (requires Maven on PATH)
mvn verify

# Package as shaded JAR
mvn package
```

## Testing patterns

- Unit tests (`*Test.java`): test parsing and logic in isolation using `@TempDir`.
- Integration tests (`*IT.java`): install a fixture skills JAR to the local Maven repo in `@BeforeAll`, then exercise the CLI via `new CommandLine(new InstallSkillCommand()).execute(...)`.
- For batch-mode tests, set `cmd.workingDirectory` to control where `.skills-versions` is looked up.
- For registry tests, set `System.setProperty("skills.registry.url", ...)` to a local file URI.

## Distribution

The CLI is distributed via npm/jDeploy as the `install-skill` package with native bundles for macOS, Windows, and Linux.
145 changes: 144 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1 +1,144 @@
# install-skill-cli
# install-skill-cli

A CLI tool for installing skills deployed with the [skills-jar-maven-plugin](https://github.com/webliteca/skills-jar-maven-plugin). Skills are AI assistant guidance bundles published as Maven artifacts.

## Installation

```bash
npm install -g install-skill
```

## Usage

### Install a single skill

By registry name:

```bash
install-skill teavm-lambda
```

By registry name with a specific version:

```bash
install-skill teavm-lambda@0.1.2
```

By Maven coordinates:

```bash
install-skill ca.weblite:teavm-lambda-parent:0.1.2
```

### Install from a `.skills-versions` file

When run with no arguments, `install-skill` reads a `.skills-versions` file from the current directory and installs all listed skills:

```bash
install-skill
```

This is the recommended way to manage skills for a project. Add `.skills-versions` to version control so all contributors share the same skill set.

## `.skills-versions` file

A plain text file listing skills to install, one per line:

```
# Skills for this project
teavm-lambda@0.1.2
my-other-skill@0.3.1
some-skill
```

Format rules:
- One entry per line: `name@version` or just `name` (latest version)
- Names can be registry skill names or Maven coordinates (`groupId:artifactId`)
- Lines starting with `#` are comments
- Blank lines are ignored

Examples of valid entries:

```
# Registry skill name with pinned version
teavm-lambda@0.1.2

# Registry skill name, latest version
teavm-lambda

# Maven coordinates with version
ca.weblite:teavm-lambda-parent@0.1.2

# Maven coordinates, latest version
ca.weblite:teavm-lambda-parent
```

## `.skills-versions.lock` file

After installing from `.skills-versions`, a `.skills-versions.lock` file is created. This JSON file records the resolved Maven coordinates for each skill, enabling reproducible installs across machines and CI.

The lock file behaves similarly to `composer.lock`:

- **First install**: resolves all versions from `.skills-versions` and creates the lock file.
- **Subsequent installs**: reuses locked versions for unchanged entries. Only new or changed entries are re-resolved.
- **Version changes**: if you modify a version in `.skills-versions`, that entry is re-resolved on the next install.
- **Force re-resolution**: use `--update` to ignore the lock file and re-resolve everything.

Add `.skills-versions.lock` to version control to ensure all contributors install the exact same resolved versions.

## Options

| Option | Description |
|--------|-------------|
| `-d <dir>` | Skills installation directory (overrides `--global`) |
| `-g, --global` | Install globally to `~/.claude/skills` (default is local: `./.claude/skills`) |
| `-r <repo>` | Repository URL with optional credentials: `[user:pass@]repositoryUrl` |
| `-u, --update` | Force re-resolution of all skill versions, ignoring the lock file |
| `-h, --help` | Show help message |
| `-V, --version` | Show version |

## Examples

Install all skills from `.skills-versions` to the default directory:

```bash
install-skill
```

Install all skills to a custom directory:

```bash
install-skill -d ./my-skills
```

Install all skills globally:

```bash
install-skill --global
```

Force re-resolution of all versions (like `composer update`):

```bash
install-skill --update
```

Install a single skill from a private repository:

```bash
install-skill my-skill@1.0.0 -r user:pass@https://maven.example.com/releases
```

## How it works

1. **Single-skill mode** (`install-skill <skill>`): resolves the skill from the [skills registry](https://github.com/webliteca/skills-registry) or by Maven coordinates, creates a temporary Maven project, runs the `skills-jar-plugin:install` goal, and copies the result to the target directory.

2. **Batch mode** (`install-skill` with no arguments): reads `.skills-versions`, checks `.skills-versions.lock` for previously resolved versions, resolves any new or changed entries, installs each skill, and updates the lock file.

## Skills registry

Skills are looked up by name in the [skills registry](https://github.com/webliteca/skills-registry). The registry maps human-readable skill names to Maven coordinates. To register a new skill, open a PR against that repository.

## License

Apache License 2.0
Loading
Loading