← Back to Skills Marketplace
charlie-morrison

Api Changelog Generator

by charlie-morrison · GitHub ↗ · v1.0.0 · MIT-0
cross-platform ⚠ suspicious
41
Downloads
0
Stars
0
Active Installs
1
Versions
Install in OpenClaw
/install api-changelog-generator
Description
Generate and maintain API changelogs from OpenAPI/Swagger specs — track endpoints added, removed, deprecated, or modified between versions. Detect breaking c...
README (SKILL.md)

API Changelog Generator

Track API changes across versions automatically. Compare OpenAPI specs to detect what changed, classify changes as breaking/non-breaking, and generate professional changelogs and migration guides for API consumers.

Use when: "generate API changelog", "what changed in the API", "API release notes", "breaking changes since v1", "API migration guide", "track API changes", or maintaining public API documentation.

Commands

1. diff — Compare Two API Versions

Compare two OpenAPI/Swagger spec files and produce a structured diff.

OLD_SPEC="${1:?Usage: diff \x3Cold-spec> \x3Cnew-spec>}"
NEW_SPEC="${2:?Usage: diff \x3Cold-spec> \x3Cnew-spec>}"

python3 -c "
import json, sys, os

def load_spec(path):
    with open(path) as f:
        if path.endswith(('.yml', '.yaml')):
            try:
                import yaml
                return yaml.safe_load(f)
            except ImportError:
                print(f'Warning: PyYAML not installed, trying JSON parse')
                return json.load(f)
        return json.load(f)

old = load_spec('$OLD_SPEC')
new = load_spec('$NEW_SPEC')

# Extract paths (endpoints)
old_paths = set()
new_paths = set()
for path, methods in old.get('paths', {}).items():
    for method in methods:
        if method in ('get','post','put','patch','delete','options','head'):
            old_paths.add(f'{method.upper()} {path}')
for path, methods in new.get('paths', {}).items():
    for method in methods:
        if method in ('get','post','put','patch','delete','options','head'):
            new_paths.add(f'{method.upper()} {path}')

added = sorted(new_paths - old_paths)
removed = sorted(old_paths - new_paths)
common = sorted(old_paths & new_paths)

print('=== Endpoint Changes ===')
print(f'Added: {len(added)}, Removed: {len(removed)}, Modified: (checking...)')
print()

if added:
    print('🟢 New Endpoints:')
    for ep in added:
        print(f'  + {ep}')
    print()

if removed:
    print('🔴 Removed Endpoints (BREAKING):')
    for ep in removed:
        print(f'  - {ep}')
    print()

# Check for parameter changes in common endpoints
print('🟡 Modified Endpoints:')
for ep in common:
    method, path = ep.split(' ', 1)
    old_op = old['paths'].get(path, {}).get(method.lower(), {})
    new_op = new['paths'].get(path, {}).get(method.lower(), {})

    changes = []

    # Parameter changes
    old_params = {p.get('name',''): p for p in old_op.get('parameters', [])}
    new_params = {p.get('name',''): p for p in new_op.get('parameters', [])}

    for name in set(new_params) - set(old_params):
        req = new_params[name].get('required', False)
        changes.append(f'  + param: {name} ({\"required\" if req else \"optional\"}){\" (BREAKING)\" if req else \"\"}')
    for name in set(old_params) - set(new_params):
        changes.append(f'  - param: {name} (removed, BREAKING)')
    for name in set(old_params) & set(new_params):
        if old_params[name].get('required') != new_params[name].get('required'):
            if new_params[name].get('required'):
                changes.append(f'  ~ param: {name} now required (BREAKING)')
            else:
                changes.append(f'  ~ param: {name} now optional')

    # Response changes
    old_resps = set(old_op.get('responses', {}).keys())
    new_resps = set(new_op.get('responses', {}).keys())
    for code in new_resps - old_resps:
        changes.append(f'  + response: {code}')
    for code in old_resps - new_resps:
        changes.append(f'  - response: {code} (removed)')

    # Deprecation
    if new_op.get('deprecated') and not old_op.get('deprecated'):
        changes.append(f'  ⚠️  DEPRECATED')

    if changes:
        print(f'  {ep}:')
        for c in changes:
            print(f'    {c}')

# Schema changes
print()
print('=== Schema Changes ===')
old_schemas = old.get('components', old.get('definitions', {})).get('schemas', {})
new_schemas = new.get('components', new.get('definitions', {})).get('schemas', {})

for name in sorted(set(new_schemas) - set(old_schemas)):
    print(f'  + New schema: {name}')
for name in sorted(set(old_schemas) - set(new_schemas)):
    print(f'  - Removed schema: {name} (BREAKING if referenced)')
for name in sorted(set(old_schemas) & set(new_schemas)):
    old_props = set(old_schemas[name].get('properties', {}).keys())
    new_props = set(new_schemas[name].get('properties', {}).keys())
    old_req = set(old_schemas[name].get('required', []))
    new_req = set(new_schemas[name].get('required', []))

    added_props = new_props - old_props
    removed_props = old_props - new_props
    new_required = new_req - old_req

    if added_props or removed_props or new_required:
        print(f'  ~ {name}:')
        for p in sorted(added_props):
            brk = ' (BREAKING)' if p in new_req else ''
            print(f'      + property: {p}{brk}')
        for p in sorted(removed_props):
            print(f'      - property: {p} (BREAKING)')
        for p in sorted(new_required - added_props):
            print(f'      ~ property: {p} now required (BREAKING)')
" 2>/dev/null

2. changelog — Generate Formatted Changelog

Produce a consumer-facing changelog from the diff:

# API Changelog

## v2.1.0 (2026-04-28)

### New Endpoints
- `POST /api/v2/webhooks` — Register webhook subscriptions
- `GET /api/v2/webhooks/{id}` — Get webhook details

### Breaking Changes
- `DELETE /api/v1/legacy-auth` — Removed (use `/api/v2/auth` instead)
- `POST /api/v2/users` — `email` parameter is now required
- Schema `UserResponse` — removed `legacy_id` property

### Deprecated
- `GET /api/v2/users/search` — Use `GET /api/v2/users?q=` instead (removal in v3.0)

### Non-Breaking Changes
- `GET /api/v2/users/{id}` — Added optional `include` parameter
- Schema `UserResponse` — Added `avatar_url` property
- `POST /api/v2/orders` — New response code `429` for rate limiting

### Migration Guide
1. Replace calls to `/api/v1/legacy-auth` with `/api/v2/auth`
2. Ensure `email` is included in `POST /api/v2/users` requests
3. Update response parsing to handle missing `legacy_id` in `UserResponse`

3. breaking — Breaking Changes Only

Filter the diff to show only breaking changes:

  • Removed endpoints
  • Removed parameters or schema properties
  • Parameters changed from optional to required
  • Response schema type changes
  • Changed authentication requirements

Categorize severity:

  • Critical: Endpoint removed, auth changed
  • High: Required parameter added, response property removed
  • Medium: Parameter type changed, new validation rules
  • Low: Deprecation warnings

4. migration — Generate Migration Guide

For each breaking change, generate specific consumer migration instructions:

## Migration Guide: v2.0 → v2.1

### 1. Removed: POST /api/v1/legacy-auth
**Impact:** All clients using v1 auth will get 404
**Action:**
- Replace `POST /api/v1/legacy-auth` with `POST /api/v2/auth`
- Update request body: `{username, password}` → `{email, password}`
- Response format changed: `{token}` → `{access_token, refresh_token, expires_in}`

### 2. Required param: POST /api/v2/users — email
**Impact:** Requests without `email` will get 422
**Action:**
- Add `email` field to all user creation requests
- Validate email format client-side before sending

5. track — Maintain Changelog History

Append new diff results to a running API-CHANGELOG.md file:

CHANGELOG="${1:-API-CHANGELOG.md}"

# If changelog exists, prepend new entry
if [ -f "$CHANGELOG" ]; then
  echo "Prepending to existing changelog: $CHANGELOG"
else
  echo "Creating new changelog: $CHANGELOG"
fi

Format: newest version at the top, Keep a Changelog compatible.

6. consumers — Estimate Consumer Impact

Scan the codebase for API calls that would be affected by breaking changes:

echo "=== Consumer Impact Analysis ==="

# Find API calls in the codebase
rg -n "(fetch|axios|http|request)\(['\"].*(/api/|/v[0-9])" \
  -g '*.{ts,js,py,go,java}' -g '!node_modules' -g '!vendor' 2>/dev/null | head -30

# For each breaking change endpoint, find matching calls
# (Use the removed/changed endpoints from diff output)

Output Formats

  • text (default): Human-readable changelog
  • json: {version, date, breaking: [], deprecated: [], added: [], modified: [], migration: []}
  • markdown: Consumer-facing changelog document
  • rss: RSS/Atom feed format for API changelog subscriptions

Notes

  • Supports OpenAPI 3.x and Swagger 2.0 specifications
  • YAML specs require PyYAML (falls back to JSON parsing)
  • Breaking change classification follows semantic versioning conventions
  • Schema diff handles nested objects and $ref resolution
  • For best results, version your API specs in git and compare between tags
  • Works alongside api-diff skill (which focuses on spec comparison; this focuses on changelog generation and consumer communication)
Usage Guidance
This skill is coherent and low-risk for its stated purpose, but review these points before installing: - The SKILL.md runs an inline python3 command; ensure python3 is available in the agent environment (and install PyYAML if you need YAML input). The registry metadata did not list python3 as a required binary, so verify the runtime environment manually. - The script reads the two spec files you pass it — do not feed it files containing sensitive secrets or credentials embedded in examples unless you trust the environment. It does not perform network calls, but it will process whatever file contents you provide. - Because the skill is instruction-only, there is no packaged code to inspect beyond SKILL.md; if you allow autonomous invocation, the agent could execute the python command with files it chooses to use. If you want to be extra cautious, run the command locally first or restrict agent invocation. - If you rely on YAML parsing, ensure PyYAML is installed; otherwise the script will try to parse YAML as JSON and may fail. If you need stronger isolation, run the tool in a container or ephemeral environment.
Capability Analysis
Type: OpenClaw Skill Name: api-changelog-generator Version: 1.0.0 The skill contains a critical command injection vulnerability in the `diff` command within `SKILL.md`. It embeds shell variables (`$OLD_SPEC` and `$NEW_SPEC`) directly into a Python script string executed via `python3 -c`, which allows for arbitrary code execution if a user provides a crafted filename. While the tool's logic for comparing OpenAPI specs appears functionally aligned with its stated purpose and lacks evidence of intentional malice or data exfiltration, the insecure implementation poses a high risk.
Capability Assessment
Purpose & Capability
The name/description (API changelog generation from OpenAPI/Swagger specs) matches the instructions: a Python-based diff of two spec files and markdown changelog generation. Nothing requested or shown is unrelated to that purpose.
Instruction Scope
Runtime instructions operate only on the two spec file paths provided as arguments and produce diffs and example markdown. The script reads only the given files and does not reference other system paths, extra environment variables, or external endpoints.
Install Mechanism
The skill is instruction-only (no install spec). However, SKILL.md invokes python3 (and optionally PyYAML). The registry metadata listed no required binaries; that is a small mismatch — python3 (and PyYAML to parse YAML) are practical runtime dependencies even though not declared.
Credentials
The skill declares no credentials, config paths, or environment variables and the instructions do not access secrets or unrelated env vars. Required inputs are file paths to OpenAPI/Swagger specs only.
Persistence & Privilege
No install, no always:true, and no modifications to other skills or system-wide settings. The skill can be invoked autonomously per platform default, which is expected for a utility skill; this is not combined with other concerning privileges.
How to Use
  1. Make sure OpenClaw is installed (local or Docker)
  2. Run the install command in chat: /install api-changelog-generator
  3. After installation, invoke the skill by name or use /api-changelog-generator
  4. Provide required inputs per the skill's parameter spec and get structured output
Version History
v1.0.0
Initial release of api-changelog-generator — automate API changelogs, breaking change detection, and migration guide generation. - Compare two OpenAPI/Swagger specs to list added, removed, and modified endpoints and schemas. - Detect and highlight breaking changes (e.g., removed endpoints, required parameter changes). - Generate professional, consumer-facing changelogs and migration guides from API diffs. - Filter and categorize breaking changes by severity for easier migration planning. - Maintain historical changelog files with automatic updates after each API version change.
Metadata
Slug api-changelog-generator
Version 1.0.0
License MIT-0
All-time Installs 0
Active Installs 0
Total Versions 1
Frequently Asked Questions

What is Api Changelog Generator?

Generate and maintain API changelogs from OpenAPI/Swagger specs — track endpoints added, removed, deprecated, or modified between versions. Detect breaking c... It is an AI Agent Skill for Claude Code / OpenClaw, with 41 downloads so far.

How do I install Api Changelog Generator?

Run "/install api-changelog-generator" in the OpenClaw or Claude Code chat to install it in one step — no extra setup required.

Is Api Changelog Generator free?

Yes, Api Changelog Generator is completely free, licensed under MIT-0. You can download, install and use it at no cost.

Which platforms does Api Changelog Generator support?

Api Changelog Generator is cross-platform and runs anywhere OpenClaw / Claude Code is available (cross-platform).

Who created Api Changelog Generator?

It is built and maintained by charlie-morrison (@charlie-morrison); the current version is v1.0.0.

💬 Comments