Some_claude_skills openapi-spec-writer
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
install
source · Clone the upstream repo
git clone https://github.com/curiositech/some_claude_skills
Claude Code · Install into ~/.claude/skills/
T=$(mktemp -d) && git clone --depth=1 https://github.com/curiositech/some_claude_skills "$T" && mkdir -p ~/.claude/skills && cp -r "$T/.claude/skills/openapi-spec-writer" ~/.claude/skills/curiositech-some-claude-skills-openapi-spec-writer && rm -rf "$T"
manifest:
.claude/skills/openapi-spec-writer/SKILL.mdsource content
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 design patternsapi-architect
- RESTful conventionsrest-api-design
- Generated client typestypescript-pro
- CI validationgithub-actions-pipeline-builder
Examples
Complete OpenAPI 3.1 Spec
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)
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
# .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
- Use components - Extract reusable schemas, parameters, responses
- Provide examples - Real-world examples for every schema
- Meaningful descriptions - Markdown-formatted, explain business context
- Consistent naming - kebab-case paths, camelCase properties
- Version your API - Include version in URL or header
- Document errors - Define all error responses with examples
- Use operationId - Unique, descriptive IDs for SDK generation
- Validate with linting - Use Spectral to enforce standards
- 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