# How to Create Custom Skills for Hermes Agent

Hermes Agent skills are reusable procedural knowledge documents that follow the agentskills.io open standard. This tutorial walks through creating a custom skill from scratch, covering the SKILL.md format, frontmatter configuration, progressive loading, local testing, and publishing to the Skills Hub where 672 skills already live across four registries.

Source: https://fast.io/resources/hermes-agent-skill-creation-tutorial/
Last reviewed: 2026-05-05

## What Hermes Agent Skills Are and Why They Matter

Nous Research Hermes Agent treats skills as on-demand knowledge documents loaded progressively to minimize token usage. Instead of stuffing every instruction into a system prompt, Hermes pulls skill content only when the agent actually needs it. This keeps context windows lean while giving the agent access to hundreds of specialized procedures.

Skills follow the [agentskills.io](https://agentskills.io/specification) open standard. A skill written for Hermes works in Claude Code, Cursor, or Codex CLI without modification. The format is portable because it is simple: a SKILL.md file with YAML frontmatter for metadata and markdown for instructions.

The Skills Hub currently holds 672 skills across four registries (built-in, official optional, community, and third-party). But none of those registries include a skill for your specific deployment, your team's coding standards, or your internal API quirks. That is where custom skills fill the gap.

Hermes stores skills in `~/.hermes/skills/` by default. The agent discovers them automatically through a three-level progressive loading system:

1. **Level 0** calls `skills_list()` and returns metadata for all available skills in roughly 3,000 tokens
2. **Level 1** calls `skill_view(name)` to load the full SKILL.md content for a single skill
3. **Level 2** calls `skill_view(name, path)` to fetch a specific reference file within that skill's directory

This means your custom skill shows up in the agent's skill index the moment you drop a SKILL.md file in the right directory. No registration, no build step, no restart.

## Step 1: Create the SKILL.md File

Every Hermes skill starts with a single file: SKILL.md. Create a directory under `~/.hermes/skills/` with a category and skill name, then add the file.

```bash
mkdir -p ~/.hermes/skills/devops/deploy-checker/
touch ~/.hermes/skills/devops/deploy-checker/SKILL.md
```

The SKILL.md file has two parts: YAML frontmatter for machine-readable metadata, and markdown body for the actual instructions the agent will follow.

### Frontmatter fields

Here is a complete frontmatter example with every supported field:

```yaml
---
name: deploy-checker
description: Verifies deployment health across staging and production environments
version: 1.0.0
author: your-name
license: MIT
platforms: [macos, linux]
metadata:
  hermes:
    tags: [devops, deployment, monitoring]
    category: devops
    requires_toolsets: [terminal]
    config:
      - key: deploy_checker.default_env
        default: "staging"
        prompt: "Which environment should be checked by default?"
required_environment_variables:
  - name: DEPLOY_API_KEY
    prompt: "Enter your deployment API key"
    help: "https://docs.example.com/api-keys"
    required_for: "Authenticating with the deployment service"
---
```

The required fields are `name` and `description`. Everything else is optional but improves the skill's usability:

- **platforms** restricts the skill to specific operating systems (`macos`, `linux`, `windows`). Omit this field to support all platforms. Skills with incompatible platforms hide from the agent automatically.
- **requires_toolsets** makes the skill visible only when certain toolsets are loaded. If you set `requires_toolsets: [web]`, the skill disappears when the web toolset is unavailable.
- **fallback_for_toolsets** works in reverse: `fallback_for_toolsets: [web]` hides the skill when the web toolset IS available, making it a fallback alternative.
- **config** defines non-secret preferences stored in `config.yaml` under `skills.config.<key>`. Run `hermes config migrate` to prompt for any unconfigured values.
- **required_environment_variables** declares API keys and tokens. When a skill that requires missing variables gets loaded, Hermes prompts for them securely. The values pass automatically to sandboxed code execution.

### Markdown body structure

The official developer guide recommends five sections in the markdown body:

```markdown
# Deploy Checker

Verifies deployment health by checking endpoint availability.
response codes, and error rates.

## When to Use

Use this skill when:
- Deploying a new release to staging or production
- Investigating a suspected deployment failure
- Running a pre-release health check

## Quick Reference

Common commands:
- `curl -s https://api.example.com/health | jq .status`
- `kubectl get pods -n production --field-selector=status.phase!=Running`

## Procedure

1. Identify the target environment from the user's request
2. Run health endpoint checks against all registered services
3. Parse response codes and flag any non-200 responses
4. Check error rate metrics for the last 15 minutes
5. Report findings with a clear pass/fail summary

## Pitfalls

- Health endpoints behind VPNs will timeout without network access
- Some services return 200 even during partial outages; check response body
- Rate limiting on monitoring APIs can cause false negatives

## Verification - All health endpoints return 200 with valid response bodies
- Error rates are below the threshold defined in config
- The user confirms the deployment matches expectations
```

The "When to Use" section is particularly important. It tells Hermes when to load this skill during progressive disclosure. Write specific trigger conditions rather than vague descriptions.

## Step 2: Add Supporting Files

A SKILL.md file is enough for simple skills. For complex workflows, add supporting directories that the agent can access through Level 2 progressive loading.

```
~/.hermes/skills/devops/deploy-checker/
├── SKILL.md
├── references/
│   ├── api-docs.md
│   └── error-codes.md
├── templates/
│   └── health-report.md
├── scripts/
│   └── check-endpoints.sh
└── assets/
    └── service-map.json
```

Each directory serves a different purpose:

- **references/** holds supplementary documentation. The agent loads these on demand with `skill_view("deploy-checker", "references/api-docs.md")` instead of cramming everything into the main SKILL.md. This keeps the Level 1 load lightweight.
- **templates/** stores output format templates. If your skill generates reports or config files, put the template here and reference it in the procedure.
- **scripts/** contains helper scripts for complex parsing or multi-step operations. Reference them in SKILL.md with the `${HERMES_SKILL_DIR}` template variable: `bash ${HERMES_SKILL_DIR}/scripts/check-endpoints.sh`.
- **assets/** holds static data files, JSON schemas, or anything else the skill needs.

Two built-in template variables work inside SKILL.md:

- `${HERMES_SKILL_DIR}` resolves to the absolute path of the skill directory
- `${HERMES_SESSION_ID}` resolves to the current session identifier

These let you write portable references that work regardless of where Hermes is installed. Prefer stdlib Python, curl, and existing Hermes tools in your scripts. For XML/JSON parsing or complex logic, a helper script in `scripts/` is cleaner than expecting the LLM to write parsers inline during execution.

## Step 3: Test the Skill Locally

Custom skills become available immediately without registration. Open a new chat session and verify the skill appears:

```bash
hermes chat --toolsets skills -q "What skills do you have?"
```

The agent should list your new skill alongside the built-in ones. To test it directly, use the slash command format:

```bash
/deploy-checker check staging health
```

Or reference it naturally in conversation:

```bash
hermes chat --toolsets skills -q "Use the deploy-checker skill to verify staging"
```

### Debugging common issues

**Skill does not appear in the list:**
- Confirm the file is at `~/.hermes/skills/[category]/[skill-name]/SKILL.md` with that exact filename
- Check the YAML frontmatter for syntax errors. A missing closing `---` or bad indentation will silently skip the file
- If you set `platforms`, verify your current OS matches one of the listed values
- If you set `requires_toolsets`, make sure those toolsets are loaded in the current session

**Skill loads but the agent ignores instructions:**
- The "When to Use" section may not match the user's request closely enough. Make trigger conditions explicit
- Long SKILL.md files can dilute the important steps. Move supplementary content to `references/` and keep the main file focused on the core procedure
- Check that numbered steps in the Procedure section are concrete actions, not abstract guidance

**Environment variables not available:**
- Variables declared in `required_environment_variables` are prompted only when the skill is actually loaded via `skill_view`. They are not prompted at discovery time
- Verify the variable name matches exactly between frontmatter and your script references

### External skill directories

If you maintain skills in a shared team repository instead of `~/.hermes/skills/`, configure additional directories in `config.yaml`:

```yaml
skills:
  external_dirs:
    - ~/team-skills
    - /home/shared/hermes-skills
    - ${SKILLS_REPO}/skills
```

External directories are read-only for discovery. When Hermes creates or edits skills through its own `skill_manage` tool, it always writes to `~/.hermes/skills/`. Local versions take precedence over external ones with the same name, so you can override a team skill with a personal variant.

## Step 4: Publish to the Skills Hub

Once a skill works locally, you can share it through the Skills Hub. The Hub supports several publishing targets.

### Publishing to GitHub

The most common path is pushing to a GitHub repository:

```bash
hermes skills publish skills/devops/deploy-checker --to github --repo your-org/hermes-skills
```

Other users install it with:

```bash
hermes skills install your-org/hermes-skills/devops/deploy-checker
```

### Other installation sources

The Hub supports multiple sources beyond GitHub repositories:

| Source | Install command | Use case |
|---|---|---|
| Official optional | `hermes skills install official/devops/deploy-checker` | Nous Research maintained |
| GitHub repo | `hermes skills install org/repo/path` | Team or community sharing |
| Direct URL | `hermes skills install https://example.com/SKILL.md --name deploy-checker` | Quick sharing without a repo |
| Well-known endpoint | `hermes skills install well-known:https://site/.well-known/skills/` | Organization-wide discovery |

### Security scanning

Every hub-installed skill goes through automated security scanning before it runs. The scanner checks for data exfiltration attempts, prompt injection, destructive commands, and supply-chain threats. Trust levels determine how strict the scanning is:

- **builtin** and **official** skills are trusted by default
- **trusted** skills come from established sources like Anthropic or Vercel
- **community** skills get the full scan. Non-dangerous policy blocks can be overridden with `--force` after manual review, but the scanner blocks anything flagged as genuinely dangerous

After installation, you can re-audit skills at any time:

```bash
hermes skills audit
hermes skills check    # check for upstream updates
hermes skills update   # reinstall updated skills
```

### Managing published skills

Track your skill versions with standard semver in the frontmatter. Users who installed your skill can run `hermes skills check` to see if an update is available, then `hermes skills update` to pull the latest version. If a user has modified their local copy, Hermes marks it as user-modified and skips automatic updates to avoid overwriting their changes.

## Letting Hermes Create Skills Automatically

You do not always need to write skills by hand. Hermes Agent can create procedural memory on its own through the `skill_manage` tool. After completing a complex task (typically 5 or more tool calls), finding a solution after encountering errors, or discovering a non-trivial workflow, the agent may offer to save the procedure as a new skill.

The `skill_manage` tool supports these actions:

| Action | What it does | Parameters |
|---|---|---|
| `create` | Creates a new skill | `name`, `content`, optional `category` |
| `patch` | Targeted fixes to an existing skill | `name`, `old_string`, `new_string` |
| `edit` | Full rewrite of a skill | `name`, `content` |
| `delete` | Removes a skill | `name` |
| `write_file` | Adds a supporting file | `name`, `file_path`, `file_content` |
| `remove_file` | Removes a supporting file | `name`, `file_path` |

The `patch` action is preferred over `edit` for incremental improvements because it preserves the rest of the file. Agent-created skills land in `~/.hermes/skills/` alongside your manually created ones and follow the same SKILL.md format.

This creates a feedback loop: you build a skill, the agent uses it, discovers edge cases, and patches the skill with updated pitfalls and verification steps. Over time, skills accumulate the kind of operational knowledge that usually lives in someone's head or gets lost in chat histories.

### Writing effective skills

Whether you write skills manually or let the agent generate them, the same principles apply:

- **Keep scope narrow.** A skill that covers "deploy and monitor and rollback and alert" is four skills pretending to be one. Focused skills are easier to trigger, test, and maintain.
- **Write concrete triggers.** "When to Use" should describe specific situations, not abstract categories. "When deploying a Node.js service to ECS" beats "When doing DevOps tasks."
- **Document failure modes.** The Pitfalls section is often more valuable than the Procedure section. Every time the skill fails in a new way, add the failure and its fix.
- **Include verification.** Without a Verification section, the agent has no way to confirm the task succeeded. Make success criteria observable and specific.

### Storing skill output with persistent storage

Skills that generate files, reports, or artifacts need somewhere to put the results. Local disk works for personal use, but teams working with Hermes across multiple machines or sharing output with non-technical stakeholders need persistent, shareable storage.

[Fastio](https://fast.io) provides persistent workspaces where Hermes can write skill output and hand it off to humans. The [Fastio MCP server](/storage-for-agents/) exposes a consolidated MCP toolset covering workspace management, file operations, and AI-powered search. A skill that generates deployment reports, for example, can upload them to a shared workspace where the rest of the team accesses them through a browser without needing Hermes installed.

Fastio offers a 14-day Business Trial requiring a credit card. Once Intelligence is enabled on a workspace, uploaded files are indexed for semantic search, so anyone on the team can ask questions about past skill output through [RAG-powered chat with citations](/product/ai/).

For teams that already use S3, Google Drive, or Dropbox for artifact storage, Fastio also supports [URL Import](/product/cloud-import/) to pull files from those services without local I/O. The difference is that Fastio workspaces are built for agent-to-human handoff: ownership transfer lets the agent build and organize a workspace, then transfer it to a human who takes over management through the web UI.

## Frequently asked questions

### How do I create a custom skill for Hermes Agent?

Create a directory under ~/.hermes/skills/ with a category and skill name, add a SKILL.md file with YAML frontmatter (name, description, version) and markdown body sections (When to Use, Procedure, Pitfalls, Verification), then start a new Hermes chat session. The skill appears automatically without registration.

### What is the SKILL.md format?

SKILL.md is a markdown file with YAML frontmatter that follows the agentskills.io open standard. The frontmatter contains metadata like name, description, version, platform restrictions, and environment variable declarations. The markdown body contains the actual instructions organized into sections like When to Use, Procedure, Pitfalls, and Verification.

### How do I publish a skill to the Hermes Skills Hub?

Run "hermes skills publish skills/category/skill-name --to github --repo your-org/repo-name" to push the skill to a GitHub repository. Other users can then install it with "hermes skills install your-org/repo-name/category/skill-name". The Hub also supports direct URL installation and well-known endpoint discovery for organization-wide distribution.

### Can Hermes Agent create its own skills automatically?

Yes. Hermes uses the skill_manage tool to create procedural memory after completing complex tasks, recovering from errors, or discovering non-trivial workflows. The agent writes these to ~/.hermes/skills/ in standard SKILL.md format. You can also ask Hermes to patch or edit existing skills incrementally using the same tool.

### What is progressive loading in the Hermes skills system?

Progressive loading is a three-level system that minimizes token usage. Level 0 returns a metadata list of all skills in about 3,000 tokens. Level 1 loads the full SKILL.md content for a specific skill. Level 2 fetches individual reference files from the skill's directory. The agent only advances to the next level when it genuinely needs the content.

### How do I restrict a skill to specific platforms or toolsets?

Add a platforms field to the YAML frontmatter with an array of supported systems (macos, linux, windows). For toolset-based activation, use requires_toolsets to show the skill only when certain toolsets are loaded, or fallback_for_toolsets to show it only when certain toolsets are missing. Skills that fail platform or toolset checks hide automatically.

## About Fast.io

Fast.io provides shared workspaces where people and AI agents work on the same files, with built-in semantic search and citation-backed chat over what they hold. Agents reach it through a remote MCP server at https://mcp.fast.io/mcp, a REST API at https://api.fast.io/current/, and a command line client published on npm as @vividengine/fastio-cli.
