skills/apm/SKILL.md
Create and manage APM (Agent Package Manager) projects — manifest authoring, dependency management, compilation, packaging, and distribution of AI agent configuration. Use when: initializing apm.yml, adding APM or MCP dependencies, compiling AGENTS.md/CLAUDE.md, building portable bundles, publishing packages, or auditing supply chain security.
npx skillsauth add congiuluc/my-awesome-copilot apmInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
apm init)apm.yml manifestsAGENTS.md or CLAUDE.mdWindows (PowerShell):
irm https://aka.ms/apm-windows | iex
macOS / Linux:
curl -sSL https://aka.ms/apm-unix | sh
Alternative installs:
# Homebrew (macOS/Linux)
brew install microsoft/apm/apm
# Scoop (Windows)
scoop bucket add apm https://github.com/microsoft/scoop-apm
scoop install apm
# pip (requires Python 3.10+)
pip install apm-cli
Verify:
apm --version
Create a new project or initialize inside an existing repo:
# New directory
apm init my-project && cd my-project
# Existing repo (interactive)
apm init
# Non-interactive with auto-detected defaults
apm init --yes
# Plugin authoring project
apm init my-plugin --plugin
This creates apm.yml — the dependency manifest for AI agent configuration:
name: my-project
version: 1.0.0
dependencies:
apm: []
Auto-detected fields: name from directory, author from git config user.name,
version defaults to 1.0.0.
apm.yml)A conforming manifest is a YAML 1.2 document with the following top-level fields:
name: <string> # REQUIRED — package identifier
version: <string> # REQUIRED — semver (^\d+\.\d+\.\d+)
description: <string> # OPTIONAL
author: <string> # OPTIONAL
license: <string> # OPTIONAL — SPDX identifier
target: <enum> # OPTIONAL — vscode | agents | claude | all
type: <enum> # OPTIONAL — instructions | skill | hybrid | prompts
scripts: <map<string, string>> # OPTIONAL — named commands via `apm run`
dependencies:
apm: <list<ApmDependency>> # OPTIONAL
mcp: <list<McpDependency>> # OPTIONAL
devDependencies:
apm: <list<ApmDependency>> # OPTIONAL
mcp: <list<McpDependency>> # OPTIONAL
compilation: <CompilationConfig> # OPTIONAL
target Enum| Value | Output |
|-----------|------------------------------------------------------------|
| vscode | Emits AGENTS.md at project root (+ per-directory files) |
| agents | Alias for vscode |
| claude | Emits CLAUDE.md at project root |
| all | Both vscode and claude targets |
Auto-detected when unset: vscode if .github/ exists, claude if .claude/ exists,
all if both, minimal if neither.
type Enum| Value | Behaviour |
|----------------|----------------------------------------------------|
| instructions | Compiled into AGENTS.md only |
| skill | Installed as a native skill only |
| hybrid | Both AGENTS.md compilation and skill installation|
| prompts | Commands/prompts only |
dependencies.apm)Each element is either a string shorthand or an object.
String form:
dependencies:
apm:
# GitHub shorthand (default host)
- microsoft/apm-sample-package # latest
- microsoft/apm-sample-package#v1.0.0 # pinned to tag
- microsoft/apm-sample-package#main # branch ref
# Non-GitHub hosts (FQDN preserved)
- gitlab.com/acme/coding-standards
- dev.azure.com/org/project/_git/repo
# Virtual packages (subdirectory or single file)
- ComposioHQ/awesome-claude-skills/brand-guidelines
- contoso/prompts/review.prompt.md
# Local path (development only)
- ./packages/my-shared-skills
Object form (required when shorthand is ambiguous):
dependencies:
apm:
- git: https://gitlab.com/acme/repo.git
path: instructions/security
ref: v2.0
alias: acme-sec
# Local path dependency
- path: ./packages/my-shared-skills
Object fields: git (clone URL), path (subdirectory or local path),
ref (branch/tag/SHA), alias (local name).
Virtual package classification rules:
| Type | Condition | Example |
|-----------------|-------------------------------------------------|----------------------------------------------|
| File | Ends in .prompt.md, .instructions.md, etc. | owner/repo/prompts/review.prompt.md |
| Collection dir | Contains /collections/ | owner/repo/collections/security |
| Collection file | Contains /collections/ + .collection.yml | owner/repo/collections/sec.collection.yml |
| Subdirectory | None of the above | owner/repo/skills/security |
Canonical normalisation: github.com is default host and MUST be stripped;
all other hosts are preserved as FQDN.
dependencies.mcp)String form — registry reference:
dependencies:
mcp:
- io.github.github/github-mcp-server
Object form — registry with overlays or self-defined:
dependencies:
mcp:
# Registry with overlays
- name: io.github.github/github-mcp-server
tools: ["repos", "issues"]
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
# Self-defined server (registry: false)
- name: my-private-server
registry: false
transport: stdio
command: ./bin/my-server
args: ["--port", "3000"]
env:
API_KEY: ${{ secrets.KEY }}
Object fields: name, transport (stdio | sse | http | streamable-http),
env, args, version, registry (bool or string), package (npm | pypi | oci),
headers, tools (default ["*"]), url, command.
Validation for self-defined servers (registry: false):
transport MUST be present.transport is stdio, command MUST be present.transport is http/sse/streamable-http, url MUST be present.Same structure as dependencies, placed under devDependencies. Installed locally
but excluded from apm pack --format plugin bundles.
devDependencies:
apm:
- owner/test-helpers
- owner/lint-rules#v2.0.0
Add with apm install --dev owner/test-helpers.
# Install all from apm.yml
apm install
# Install specific package (adds to apm.yml automatically)
apm install microsoft/apm-sample-package#v1.0.0
# Install from any git host
apm install gitlab.com/org/repo
apm install dev.azure.com/org/project/_git/repo
# Install only APM or only MCP
apm install --only=apm
apm install --only=mcp
# Update to latest versions
apm install --update
# Preview without installing
apm install --dry-run
# Install as dev dependency
apm install --dev owner/test-helpers
What happens on install:
apm_modules/ (like node_modules/)..github/instructions/, .github/prompts/, .github/agents/, .github/skills/.claude/commands/, .claude/agents/, .claude/skills/.cursor/rules/, .cursor/agents/, .cursor/skills/.opencode/agents/, .opencode/commands/, .opencode/skills/apm.lock.yaml written — pinning exact commit SHAs.Add apm_modules/ to .gitignore. Commit apm.yml, apm.lock.yaml, and
deployed .github/, .claude/, .cursor/ files.
Compile primitives into optimized output files:
# Auto-detect targets and compile
apm compile
# Target specific format
apm compile --target vscode # AGENTS.md + .github/
apm compile --target claude # CLAUDE.md + .claude/
apm compile --target all # All formats
# Watch mode (auto-recompile on changes)
apm compile --watch
# Preview without writing
apm compile --dry-run
# Validate primitives without compiling
apm compile --validate
Compilation config in apm.yml:
compilation:
target: all
strategy: distributed # distributed | single-file
source_attribution: true
resolve_links: true
exclude:
- "apm_modules/**"
- "tmp/**"
placement:
min_instructions_per_file: 1
| Setting | Default | Description |
|-------------------------|---------------|-------------------------------------------------|
| target | auto-detect | vscode, claude, all |
| strategy | distributed | distributed (per-dir) or single-file |
| source_attribution | true | Include source-file origin comments |
| resolve_links | true | Resolve relative Markdown links |
| exclude | [] | Glob patterns to skip during compilation |
APM manages seven primitive types:
| Primitive | Description | File Convention | Deploy Location |
|--------------|---------------------------------|----------------------------|-------------------------------------|
| Instructions | Coding standards and guardrails | .instructions.md | .github/instructions/ |
| Skills | Reusable AI capabilities | SKILL.md in folder | .github/skills/{name}/ |
| Prompts | Slash commands | .prompt.md | .github/prompts/ |
| Agents | Specialized AI personas | .agent.md | .github/agents/ |
| Hooks | Lifecycle event handlers | .json in hooks/ | .github/hooks/ |
| Plugins | Pre-packaged agent bundles | plugin.json | Varies |
| MCP Servers | External tool integrations | Declared in apm.yml | .vscode/mcp.json / IDE config |
Standard package directory layout:
my-package/
├── apm.yml # Package manifest
└── .apm/
├── instructions/ # .instructions.md files
├── prompts/ # .prompt.md files
├── skills/ # Folders with SKILL.md
├── agents/ # .agent.md files
└── hooks/ # .json hook definitions
apm.lock.yaml)The lock file records the exact resolved state of every dependency. It is
analogous to package-lock.json (npm) or .terraform.lock.hcl.
Structure:
lockfile_version: "1"
generated_at: "2026-03-09T14:00:00Z"
apm_version: "0.7.7"
dependencies:
- repo_url: https://github.com/acme-corp/security-baseline
resolved_commit: a1b2c3d4e5f6789012345678901234567890abcd
resolved_ref: v2.1.0
version: "2.1.0"
depth: 1
package_type: apm_package
content_hash: "sha256:9f86d081..."
deployed_files:
- .github/instructions/security.instructions.md
- .github/agents/security-auditor.agent.md
mcp_servers:
- security-scanner
Key fields per dependency entry:
| Field | Required | Description |
|--------------------|------------|-----------------------------------------------|
| repo_url | MUST | Source repository URL |
| resolved_commit | MUST (remote) | Full 40-char commit SHA |
| resolved_ref | MUST (remote) | Git ref that resolved to commit |
| depth | MUST | 1 = direct, 2+ = transitive |
| package_type | MUST | apm_package, plugin, virtual, etc. |
| deployed_files | MUST | Workspace-relative paths of installed files |
| content_hash | MAY | SHA-256 of package file tree |
| is_dev | MAY | true for devDependencies |
Resolver behaviour:
--update — re-resolve all refs, overwrite lock file.All deployed_files paths use forward slashes. The lock file MUST be
committed to version control. It MUST NOT be manually edited.
Create portable bundles for offline or CI distribution:
# Pack to ./build/<name>-<version>/
apm pack
# Pack as .tar.gz archive
apm pack --archive
# Pack only VS Code files
apm pack --target vscode
# Export as standalone plugin
apm pack --format plugin
# Preview what would be packed
apm pack --dry-run
Unpack in another project:
apm unpack ./build/my-pkg-1.0.0.tar.gz
apm unpack bundle.tar.gz --output /path/to/project
APM scans packages for hidden Unicode characters (supply chain attacks):
# Scan all installed packages
apm audit
# Scan a specific package
apm audit https://github.com/owner/repo
# Scan any file
apm audit --file .cursorrules
# Remove dangerous characters (preserves emoji)
apm audit --strip
# CI lockfile consistency gate
apm audit --ci
# CI gate with org policy checks
apm audit --ci --policy org
# SARIF output for GitHub Code Scanning
apm audit -f sarif -o report.sarif
Threat detection tiers:
| Severity | Characters | |----------|---------------------------------------------------------------| | Critical | Tag chars (U+E0001–E007F), bidi overrides, variation sel 17–256 | | Warning | Zero-width spaces/joiners, bidi marks, invisible operators | | Info | Non-breaking spaces, unusual whitespace, emoji presentation |
# List installed packages with primitive counts
apm deps list
# Show dependency tree
apm deps tree
# Show detailed info for a package
apm deps info compliance-rules
# Update all or specific dependencies
apm deps update
apm deps update compliance-rules
# Remove a package and its deployed files
apm uninstall microsoft/apm-sample-package
# Remove orphaned packages
apm prune
# Remove all dependencies
apm deps clean
Any git repository is a valid APM package. Publishing = pushing to a git remote:
git init
git add .
git commit -m "Initial APM package"
git remote add origin https://github.com/you/my-package.git
git push -u origin main
Consumers install with:
apm install you/my-package
# or pin a version
apm install you/my-package#v1.0.0
name: my-project
version: 1.0.0
description: AI-native web application
author: Contoso
license: MIT
target: all
type: hybrid
scripts:
review: "copilot -p 'code-review.prompt.md'"
impl: "copilot -p 'implement-feature.prompt.md'"
dependencies:
apm:
- microsoft/apm-sample-package#v1.0.0
- gitlab.com/acme/coding-standards#main
- git: https://gitlab.com/acme/repo.git
path: instructions/security
ref: v2.0
mcp:
- io.github.github/github-mcp-server
- name: my-private-server
registry: false
transport: stdio
command: ./bin/my-server
env:
API_KEY: ${{ secrets.KEY }}
devDependencies:
apm:
- owner/test-helpers
compilation:
target: all
strategy: distributed
exclude:
- "apm_modules/**"
placement:
min_instructions_per_file: 1
# New developer joins
git clone <org/repo> && cd <repo> && apm install
# Add a new dependency
apm install owner/package#v1.0.0
# Update dependencies
apm install --update
# Compile for Codex / Gemini
apm compile
# Audit supply chain
apm audit
# Package for distribution
apm pack --archive
# Check for CLI updates
apm update --check
name and version are the only REQUIRED fields in apm.yml.version MUST follow semver (^\d+\.\d+\.\d+); pre-release/build suffixes allowed.github.com is the default host — strip from canonical entries; preserve all other FQDNs.apm.lock.yaml MUST be committed; apm_modules/ MUST be in .gitignore.apm install, apm compile, and apm pack.devDependencies) are excluded from apm pack --format plugin bundles.apm.yml MUST be preserved on read/write for forward compatibility.tools
Build VS Code extensions with TypeScript. Covers extension anatomy, activation events, commands, tree views, webview panels, language features, testing, and publishing. Use when: creating a new VS Code extension, adding commands/views/providers, building webview UIs, implementing language server features, testing extensions, or packaging for the marketplace.
development
Track implementations, features, bugs, and releases in a versioning document. Use when: adding a commit, completing a feature, fixing a bug, or preparing a release. Automatically updates CHANGELOG.md following Keep a Changelog format and Semantic Versioning.
development
Write frontend tests using Vitest and React Testing Library. Use when: testing React components, hooks, user interactions, form submissions, accessibility assertions, or mocking API services.
development
Write Angular frontend tests using Jasmine, Karma, and Angular TestBed. Use when: testing Angular components, services, pipes, directives, user interactions, form submissions, accessibility assertions, or mocking HTTP services.