Skip to content

Create a skill

A skill is a folder. Inside it is one file named SKILL.md, and the folder name is the skill’s identity — so a skill for the audit-event convention lives at a directory like audit-event/, with audit-event/SKILL.md inside.

Copilot discovers skills from a set of known locations. For a skill you want the whole team to share — which is exactly what the audit-event convention is — put it in the repository so it’s committed alongside the code:

  • .github/skills/
  • .claude/skills/
  • .agents/skills/

Any of the three works; Copilot reads all of them. (Those last two names are not accidental — hold that thought; it’s the payoff of the last lesson in this chapter.) For something personal that follows you across every project rather than living in one repo, there are user-level locations instead — ~/.copilot/skills or ~/.agents/skills — but a team convention belongs in the repo, where review and version control apply.

Since both shared-lib and orders-service need this procedure, you commit it into each repo’s .github/skills/ — or, once you reach the MCP and automation chapters and your tooling spans repos, into a shared location both can reach.

A SKILL.md is YAML frontmatter followed by the procedure in plain markdown. Two fields are required:

  • name — lowercase, hyphen-separated, and it must match the directory name. Folder audit-event/ means name: audit-event.
  • description — a single line stating when Copilot should use this skill. This is the load-bearing field, and the next lesson is entirely about getting it right. For now, write it as a trigger condition, not a summary.

Here’s the audit-event skill. The body is just the team’s convention written down as steps:

---
name: audit-event
description: Use when recording a significant event through shared-lib's
audit helper — e.g. approval requested or granted. Ensures every audit
call follows the team's required shape, fields, and naming.
---
# Recording an audit event
Every significant event in our services is recorded through shared-lib's
audit helper, the same way in every repo. Follow these steps.
1. Import the audit helper from shared-lib. Do not write events directly to
a log or the database — they must go through the helper so the schema and
redaction rules apply.
2. Name the event in dotted form, lowercase: `<domain>.<action>`. Examples:
`approval.requested`, `approval.granted`.
3. Pass the required fields: the actor (who triggered it), the subject (what
the event is about, e.g. the order id), and a timestamp. Never include raw
secrets or full payloads in the event body.
4. Record the event *after* the action it describes has succeeded, never
before — an audit trail must reflect what actually happened.
5. If the action can fail partway, record a corresponding failure event using
the same naming so the trail stays complete.

That’s a complete skill. Nothing else is required.

The procedure above is pure instruction, but a skill can carry more than prose. Alongside SKILL.md in the same folder you can bundle scripts, examples, or other resources the procedure needs — a small script that validates an event payload, a reference example of a correct call, a fixture file. Copilot can reach for those bundled pieces when it applies the skill, so the skill becomes self-contained: not just what to do, but the tools and samples to do it well.

For the audit-event skill you might later add a examples/ file showing one correct approval.requested call end to end, so Copilot has a concrete pattern to match rather than reconstructing it from the steps each time. Start with the prose; add resources when you notice Copilot getting the shape almost right.

You’ve written a correct skill — but writing it isn’t enough to make Copilot use it. The whole mechanism that decides whether this folder ever gets pulled into a task hangs on one line you wrote almost in passing: the description. Next: the description does the triggering.