Skip to main content

Skill Development

Skills extend agent capabilities with domain-specific knowledge and tools. OpenFang supports four skill types: Python, WASM, Node.js, and Prompt-Only.

Skill Types

Python Skills

Execute Python code with full package ecosystem

WASM Skills

Sandboxed WebAssembly modules with strict limits

Node.js Skills

JavaScript/TypeScript execution (OpenClaw compatibility)

Prompt-Only

Inject expert knowledge into system prompts

Creating a Skill

1

Initialize skill structure

openfang skill create my-skill
cd my-skill
Creates:
my-skill/
├── skill.toml        # Manifest
├── skill.py          # Python implementation (optional)
├── SKILL.md          # Prompt-only content (optional)
└── README.md
2

Define the manifest

Edit skill.toml:
name = "my-skill"
version = "0.1.0"
description = "My custom skill"
author = "your-name"
runtime = "python"  # python, wasm, nodejs, or prompt

[tools]
my_tool = { description = "Does something useful" }

[requirements]
python_packages = ["requests", "beautifulsoup4"]
3

Implement the skill

For Python skills, edit skill.py:
# skill.py
import json

def my_tool(input_data):
    """Tool implementation"""
    # Your logic here
    return {"result": "success", "data": "..."}

if __name__ == "__main__":
    # Read input from stdin
    input_json = input()
    input_data = json.loads(input_json)
    
    # Route to the right tool
    tool_name = input_data["tool"]
    tool_input = input_data["input"]
    
    if tool_name == "my_tool":
        result = my_tool(tool_input)
    else:
        result = {"error": f"Unknown tool: {tool_name}"}
    
    # Write output to stdout
    print(json.dumps(result))
4

Test the skill

# Test locally
echo '{"tool":"my_tool","input":{}}' | python skill.py

# Install in OpenFang
openfang skill install .

# Activate for an agent
# Edit agent.toml:
# [capabilities]
# tools = ["my_tool"]

Prompt-Only Skills

The simplest skill type injects expert knowledge without code execution:
---
name: github-expert
version: 1.0.0
runtime: prompt
---

# GitHub Expert Knowledge

You are an expert in GitHub workflows and best practices.

## Common Tasks

### Creating a Pull Request
1. Fork the repository
2. Create a feature branch
3. Make your changes and commit
4. Push to your fork
5. Open a PR with a clear description

### CI/CD Best Practices
- Use GitHub Actions for automation
- Run tests on every push
- Require reviews before merging
...
This content is injected into the agent’s system prompt when the skill is activated.

Python Skills

Protocol

Python skills communicate via stdin/stdout JSON: Input (from OpenFang):
{
  "tool": "my_tool",
  "input": {"param1": "value1"}
}
Output (to OpenFang):
{
  "result": "success",
  "output": "Tool output here"
}

Dependencies

Declare Python packages in skill.toml:
[requirements]
python_packages = ["requests>=2.28", "pandas", "numpy"]
OpenFang installs these in an isolated virtual environment.

Example: Web Scraper Skill

# skill.py
import json
import requests
from bs4 import BeautifulSoup

def scrape_page(input_data):
    url = input_data.get("url")
    if not url:
        return {"error": "Missing url parameter"}
    
    try:
        response = requests.get(url, timeout=10)
        soup = BeautifulSoup(response.text, 'html.parser')
        
        return {
            "title": soup.title.string if soup.title else None,
            "links": [a['href'] for a in soup.find_all('a', href=True)][:10],
            "text": soup.get_text()[:500]
        }
    except Exception as e:
        return {"error": str(e)}

if __name__ == "__main__":
    input_json = input()
    data = json.loads(input_json)
    result = scrape_page(data["input"])
    print(json.dumps(result))

WASM Skills

WebAssembly skills run in a sandboxed environment with:
  • Fuel metering - CPU instruction limits
  • Epoch interruption - Wall-clock timeout
  • No network access - Air-gapped execution
  • Memory limits - 64MB default
Build from Rust:
# Install toolchain
rustup target add wasm32-wasi

# Build skill
cargo build --target wasm32-wasi --release

# skill.toml
[runtime]
type = "wasm"
module = "target/wasm32-wasi/release/my_skill.wasm"

Publishing to FangHub

1

Test thoroughly

openfang skill test my-skill
2

Add metadata

Update skill.toml:
category = "web"  # web, data, security, etc.
tags = ["scraping", "html"]
license = "MIT"
homepage = "https://github.com/..."
3

Publish

openfang skill publish my-skill
Requires FangHub account (free).

Security

Automatic Scanning

All skills are scanned for:
  • Prompt injection attempts
  • Data exfiltration patterns
  • Shell command injection
  • Hardcoded secrets

Subprocess Isolation

Python/Node.js skills run with:
  • env_clear() - No inherited environment
  • Selective variable injection
  • Process tree isolation
  • Timeout enforcement (60s default)

Best Practices

Never trust input from agents. Validate types, ranges, and formats.
Explicitly allow known-good patterns rather than blocking known-bad ones.
Use environment variables or the credential vault, never hardcode API keys.
If your skill doesn’t need network access, don’t request it.

Next Steps

Browse Skills

Explore 60+ bundled skills and community contributions

OpenClaw Compatibility

Convert OpenClaw skills to OpenFang format

Build docs developers (and LLMs) love