Skip to content
Back to skills

Openapi Spec Writer

ASecurity

Expert in writing OpenAPI 3.0/3.1 specifications for REST APIs. Specializes in schema design, documentation best practices, API-first development, and tooling integration. Generates comprehensive

  • 208 stars
  • 0 votes
  • 0 copies
  • 1 view
  • Added May 29, 2026
businesstypescriptgogitapisecuritydocumentation

Works with

  • cli
  • api

Security analysis

A100/100

Scanned May 29, 2026

npx -y skills add curiositech/some_claude_skills --skill openapi-spec-writer --agent claude-code

Installs into .claude/skills of the current project.

Are you the author of Openapi Spec Writer?

Add the live security badge to your README. It updates with every re-scan.

Security grade badge for Openapi Spec Writer
[![Security: A — Skills Directory](https://www.skillsdirectory.com/api/skills/curiositech-openapi-spec-writer/badge)](https://www.skillsdirectory.com/skills/curiositech-openapi-spec-writer)

More formats (shields.io, HTML) on the badges page. Keep it an A: scan every change in CI with Pro.

Download with Pro
SKILL.md
---
name: openapi-spec-writer
description: Expert in writing OpenAPI 3.0/3.1 specifications for REST APIs. Specializes in schema design, documentation best practices, API-first development, and tooling integration. Generates comprehensive
  API documentation that serves as both documentation and contract.
version: 1.0.0
metadata:
  category: documentation
  tags:
  - openapi
  - swagger
  - api-documentation
  - rest
  - api-design
  pairs-with:
  - skill: api-architect
    reason: API design decisions are formalized and documented through OpenAPI specifications
  - skill: rest-api-design
    reason: REST endpoint design and OpenAPI documentation are tightly coupled deliverables
  - skill: technical-writer
    reason: API documentation quality depends on technical writing clarity and completeness
---

# OpenAPI Spec Writer

## Overview

Expert in writing OpenAPI 3.0/3.1 specifications for REST APIs. Specializes in schema design, documentation best practices, API-first development, and tooling integration. Generates comprehensive API documentation that serves as both documentation and contract.

## When to Use

- Creating OpenAPI specifications for new APIs
- Documenting existing REST APIs
- Designing API contracts before implementation
- Generating client SDKs from specs
- Setting up interactive API documentation (Swagger UI, Redoc)
- Validating API responses against schemas
- Migrating from OpenAPI 2.0 (Swagger) to 3.x

## Capabilities

### Specification Writing
- OpenAPI 3.0 and 3.1 syntax
- Path and operation definitions
- Request/response schemas
- Authentication schemes
- Server configurations

### Schema Design
- JSON Schema with OpenAPI extensions
- Reusable component schemas
- Discriminators for polymorphism
- oneOf, anyOf, allOf composition
- Nullable types and defaults

### Documentation Quality
- Meaningful descriptions and examples
- Markdown in descriptions
- Request/response examples
- Error response documentation
- Deprecation notices

### Tooling Integration
- Swagger UI configuration
- Redoc customization
- Spectral linting rules
- SDK generation setup
- Mock server configuration

## Dependencies

Works well with:
- `api-architect` - API design patterns
- `rest-api-design` - RESTful conventions
- `typescript-pro` - Generated client types
- `github-actions-pipeline-builder` - CI validation

## Examples

### Complete OpenAPI 3.1 Spec
```yaml
openapi: 3.1.0
info:
  title: Task Management API
  description: |
    RESTful API for managing tasks and projects.

    ## Authentication
    All endpoints require a Bearer token in the Authorization header.

    ## Rate Limiting
    - 1000 requests per hour per API key
    - Rate limit headers included in all responses
  version: 1.0.0
  contact:
    name: API Support
    email: api@example.com
    url: https://docs.example.com
  license:
    name: MIT
    url: https://opensource.org/licenses/MIT

servers:
  - url: https://api.example.com/v1
    description: Production server
  - url: https://staging-api.example.com/v1
    description: Staging server
  - url: http://localhost:3000/v1
    description: Local development

tags:
  - name: Tasks
    description: Task management operations
  - name: Projects
    description: Project management operations

paths:
  /tasks:
    get:
      operationId: listTasks
      summary: List all tasks
      description: Returns a paginated list of tasks with optional filtering.
      tags:
        - Tasks
      parameters:
        - $ref: '#/components/parameters/PageParam'
        - $ref: '#/components/parameters/LimitParam'
        - name: status
          in: query
          description: Filter by task status
          schema:
            $ref: '#/components/schemas/TaskStatus'
        - name: project_id
          in: query
          description: Filter by project ID
          schema:
            type: string
            format: uuid
      responses:
        '200':
          description: Successful response
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TaskListResponse'
              examples:
                default:
                  $ref: '#/components/examples/TaskListExample'
          headers:
            X-Total-Count:
              schema:
                type: integer
              description: Total number of tasks matching the query
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'

    post:
      operationId: createTask
      summary: Create a new task
      description: Creates a new task and returns the created resource.
      tags:
        - Tasks
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/CreateTaskRequest'
            examples:
              minimal:
                summary: Minimal task
                value:
                  title: "Complete documentation"
              full:
                summary: Full task with all fields
                value:
                  title: "Complete documentation"
                  description: "Write API docs for v1.0"
                  project_id: "550e8400-e29b-41d4-a716-446655440000"
                  due_date: "2024-12-31"
                  priority: "high"
      responses:
        '201':
          description: Task created successfully
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Task'
          headers:
            Location:
              schema:
                type: string
                format: uri
              description: URL of the created resource
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '422':
          $ref: '#/components/responses/ValidationError'

  /tasks/{taskId}:
    parameters:
      - $ref: '#/components/parameters/TaskIdParam'

    get:
      operationId: getTask
      summary: Get a task by ID
      tags:
        - Tasks
      responses:
        '200':
          description: Successful response
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Task'
        '404':
          $ref: '#/components/responses/NotFound'

    patch:
      operationId: updateTask
      summary: Update a task
      description: Partially updates a task. Only provided fields are updated.
      tags:
        - Tasks
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/UpdateTaskRequest'
      responses:
        '200':
          description: Task updated successfully
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Task'
        '404':
          $ref: '#/components/responses/NotFound'
        '422':
          $ref: '#/components/responses/ValidationError'

    delete:
      operationId: deleteTask
      summary: Delete a task
      tags:
        - Tasks
      responses:
        '204':
          description: Task deleted successfully
        '404':
          $ref: '#/components/responses/NotFound'

components:
  securitySchemes:
    bearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
      description: JWT token obtained from /auth/login

  parameters:
    TaskIdParam:
      name: taskId
      in: path
      required: true
      description: Unique task identifier
      schema:
        type: string
        format: uuid
      example: "550e8400-e29b-41d4-a716-446655440000"

    PageParam:
      name: page
      in: query
      description: Page number for pagination (1-indexed)
      schema:
        type: integer
        minimum: 1
        default: 1

    LimitParam:
      name: limit
      in: query
      description: Number of items per page
      schema:
        type: integer
        minimum: 1
        maximum: 100
        default: 20

  schemas:
    Task:
      type: object
      required:
        - id
        - title
        - status
        - created_at
        - updated_at
      properties:
        id:
          type: string
          format: uuid
          description: Unique identifier
          readOnly: true
        title:
          type: string
          minLength: 1
          maxLength: 200
          description: Task title
        description:
          type: string
          maxLength: 5000
          description: Detailed task description (supports Markdown)
        status:
          $ref: '#/components/schemas/TaskStatus'
        priority:
          $ref: '#/components/schemas/Priority'
        project_id:
          type: string
          format: uuid
          description: Associated project ID
        due_date:
          type: string
          format: date
          description: Due date (ISO 8601)
        created_at:
          type: string
          format: date-time
          readOnly: true
        updated_at:
          type: string
          format: date-time
          readOnly: true

    TaskStatus:
      type: string
      enum:
        - pending
        - in_progress
        - completed
        - cancelled
      description: Current task status
      default: pending

    Priority:
      type: string
      enum:
        - low
        - medium
        - high
        - urgent
      default: medium

    CreateTaskRequest:
      type: object
      required:
        - title
      properties:
        title:
          type: string
          minLength: 1
          maxLength: 200
        description:
          type: string
          maxLength: 5000
        project_id:
          type: string
          format: uuid
        due_date:
          type: string
          format: date
        priority:
          $ref: '#/components/schemas/Priority'

    UpdateTaskRequest:
      type: object
      minProperties: 1
      properties:
        title:
          type: string
          minLength: 1
          maxLength: 200
        description:
          type: string
          maxLength: 5000
        status:
          $ref: '#/components/schemas/TaskStatus'
        priority:
          $ref: '#/components/schemas/Priority'
        due_date:
          type: string
          format: date

    TaskListResponse:
      type: object
      required:
        - data
        - pagination
      properties:
        data:
          type: array
          items:
            $ref: '#/components/schemas/Task'
        pagination:
          $ref: '#/components/schemas/Pagination'

    Pagination:
      type: object
      required:
        - page
        - limit
        - total
        - total_pages
      properties:
        page:
          type: integer
        limit:
          type: integer
        total:
          type: integer
        total_pages:
          type: integer
        has_next:
          type: boolean
        has_prev:
          type: boolean

    Error:
      type: object
      required:
        - code
        - message
      properties:
        code:
          type: string
          description: Machine-readable error code
        message:
          type: string
          description: Human-readable error message
        details:
          type: object
          additionalProperties: true
          description: Additional error details

    ValidationError:
      allOf:
        - $ref: '#/components/schemas/Error'
        - type: object
          properties:
            errors:
              type: array
              items:
                type: object
                properties:
                  field:
                    type: string
                  message:
                    type: string

  responses:
    BadRequest:
      description: Bad request - invalid parameters
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          example:
            code: "BAD_REQUEST"
            message: "Invalid query parameters"

    Unauthorized:
      description: Authentication required
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          example:
            code: "UNAUTHORIZED"
            message: "Invalid or expired token"

    NotFound:
      description: Resource not found
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/Error'
          example:
            code: "NOT_FOUND"
            message: "Task not found"

    ValidationError:
      description: Validation failed
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ValidationError'
          example:
            code: "VALIDATION_ERROR"
            message: "Request validation failed"
            errors:
              - field: "title"
                message: "Title is required"

  examples:
    TaskListExample:
      value:
        data:
          - id: "550e8400-e29b-41d4-a716-446655440000"
            title: "Complete documentation"
            status: "in_progress"
            priority: "high"
            created_at: "2024-01-15T10:30:00Z"
            updated_at: "2024-01-15T10:30:00Z"
        pagination:
          page: 1
          limit: 20
          total: 42
          total_pages: 3
          has_next: true
          has_prev: false

security:
  - bearerAuth: []
```

### Polymorphic Schemas (Discriminator)
```yaml
components:
  schemas:
    Notification:
      type: object
      required:
        - id
        - type
        - created_at
      discriminator:
        propertyName: type
        mapping:
          email: '#/components/schemas/EmailNotification'
          sms: '#/components/schemas/SmsNotification'
          push: '#/components/schemas/PushNotification'
      properties:
        id:
          type: string
          format: uuid
        type:
          type: string
          enum: [email, sms, push]
        created_at:
          type: string
          format: date-time

    EmailNotification:
      allOf:
        - $ref: '#/components/schemas/Notification'
        - type: object
          required:
            - to
            - subject
          properties:
            to:
              type: string
              format: email
            subject:
              type: string
            body:
              type: string

    SmsNotification:
      allOf:
        - $ref: '#/components/schemas/Notification'
        - type: object
          required:
            - phone_number
            - message
          properties:
            phone_number:
              type: string
              pattern: '^\+[1-9]\d{1,14}$'
            message:
              type: string
              maxLength: 160
```

### Spectral Linting Rules
```yaml
# .spectral.yaml
extends: ["spectral:oas"]

rules:
  # Enforce operation IDs
  operation-operationId: error

  # Require descriptions
  operation-description: error
  oas3-schema-description: warn

  # Naming conventions
  path-casing:
    given: "$.paths[*]~"
    then:
      function: casing
      functionOptions:
        type: kebab

  # Security requirements
  operation-security-defined: error

  # Response codes
  operation-success-response: error

  # Custom: require examples
  require-examples:
    message: "Responses should have examples"
    given: "$.paths.*.*.responses.*.content.*.schema"
    then:
      field: example
      function: truthy
```

## Best Practices

1. **Use components** - Extract reusable schemas, parameters, responses
2. **Provide examples** - Real-world examples for every schema
3. **Meaningful descriptions** - Markdown-formatted, explain business context
4. **Consistent naming** - kebab-case paths, camelCase properties
5. **Version your API** - Include version in URL or header
6. **Document errors** - Define all error responses with examples
7. **Use operationId** - Unique, descriptive IDs for SDK generation
8. **Validate with linting** - Use Spectral to enforce standards
9. **Keep spec in sync** - Automate validation in CI

## Common Pitfalls

- **Missing required fields** - Forgetting to mark fields as required
- **Inconsistent naming** - Mixing snake_case and camelCase
- **Generic descriptions** - "Returns data" instead of specific details
- **No examples** - Makes spec hard to understand
- **Outdated spec** - Spec doesn't match implementation
- **Overusing anyOf** - Makes schemas hard to understand
- **Missing error responses** - Only documenting happy path
- **No pagination** - List endpoints without pagination info

Attribution

Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.

Comments

Loading comments…