Skip to main content

openapi-spec

Write and update OpenAPI 3.0 specification files from REST API code. Use when: documenting REST endpoints, creating API specs, generating swagger.yaml, updating API documentation from implementation.

소스 정보

저장소
BlueAndi/Pixelix
최근 소스 활동
2026년 9월 8일 19:22
감지된 SKILL.md 언어
영어
스타
443
포크
74

설치 방법

기본적으로 소스를 먼저 확인하는 Prompt가 선택됩니다. 직접 명령으로 전환하거나 로컬 사본을 다운로드할 수도 있습니다.

소스 파일 검토

설치 여부를 결정하기 전에 SKILL.md와 SkillsMP에 표시된 보조 파일을 읽어 보세요.

파일 탐색기
2 개 파일

SKILL.md 표시 중

SKILL.md
소스 지침 · 읽기 전용 미리보기
name
openapi-spec
description
Write and update OpenAPI 3.0 specification files from REST API code. Use when: documenting REST endpoints, creating API specs, generating swagger.yaml, updating API documentation from implementation.
argument-hint
Describe the API endpoints to document or specify the code files containing REST handlers
# OpenAPI 3.0 Specification Writer ## When to Use Load this skill when asked to: - Create an OpenAPI/Swagger specification from existing REST API code - Document REST endpoints in OpenAPI 3.0 format - Update an existing `openapi.yaml` or `swagger.yaml` file - Generate API documentation that follows OpenAPI 3.0 standards - Extract endpoint definitions, parameters, and responses from code ## Ground Rules - Target specification: **OpenAPI 3.0.x** (not Swagger 2.0) - Output format: YAML (preferred) or JSON - Follow [OpenAPI 3.0 Specification](https://swagger.io/docs/specification/v3_0/about/) - Include examples for complex schemas - Document all response codes actually returned by the implementation ## Procedure ### 1. Analyze the REST API Code #### Static Route Registration Search for and identify: - HTTP request handlers and route definitions (e.g., `server.on()`, route arrays) - HTTP methods (GET, POST, PUT, PATCH, DELETE, OPTIONS) - Path patterns and parameters (`:id`, `{id}`, wildcards) - Query parameters from `request->getParam()` or equivalent - Request body parsing (JSON, form data, multipart) - Response codes and JSON structures - Authentication/authorization requirements - Error responses and status codes #### Dynamic Route Registration Some REST APIs use plugin or service architectures where endpoints are registered dynamically: **Common patterns to search for:** - `getTopics()` or `registerTopics()` methods in plugins/services - Topic handler or topic registration services - Topic constants (e.g., `TOPIC_CONFIG`, `TOPIC_STATUS`) - Dynamic endpoint builders that construct paths from entity IDs and topic names **Topic-based endpoint patterns:** - Plugin endpoints: `/api/v1/display/uid/{uid}/{topic}` or `/display/alias/{alias}/{topic}` - Service endpoints: `/api/v1/{entityId}/{topic}` - System endpoints: `/api/v1/{topic}` (empty entityId) - Indexed endpoints: `/api/v1/{entityId}/{index}/{topic}` **How to find dynamic endpoints:** 1. Search for `getTopics()` implementations - these list available topics 2. Find `getTopic()` and `setTopic()` methods - these handle GET/POST requests 3. Locate topic registration code - shows how topics become REST endpoints 4. Check for `TopicHandlerService` or similar dynamic registration systems 5. Look for topic constants defined in header or source files **Example (C++):** ```cpp // Plugin defines topics const char* TOPIC_CONFIG = "config"; const char* TOPIC_STATUS = "status"; void Plugin::getTopics(JsonArray& topics) const { topics.add(TOPIC_CONFIG); // Creates GET/POST /display/uid/{uid}/config topics.add(TOPIC_STATUS); // Creates GET/POST /display/uid/{uid}/status } bool Plugin::getTopic(const String& topic, JsonObject& value) const { if (topic.equals(TOPIC_CONFIG)) { // Handle GET request } } bool Plugin::setTopic(const String& topic, const JsonObjectConst& value) { if (topic.equals(TOPIC_CONFIG)) { // Handle POST request } } ``` ### 2. Discover All Endpoints **Critical**: Don't assume you've found all endpoints after discovering static routes. **Complete discovery workflow:** 1. **Static routes**: Find route registration arrays or explicit route handlers 2. **Plugin topics**: Search for classes implementing plugin interfaces - Look for `getTopics()` implementations - Each plugin may expose multiple topics as REST endpoints 3. **Service topics**: Search for service classes that register topics - Services often register multiple topics (e.g., files, upload, remove) 4. **Topic registration**: Find the topic handler or registration service - Understand how topics are converted to REST paths - Check for path prefix construction (e.g., base + entityId + topic) 5. **Validate completeness**: Cross-reference existing OpenAPI spec - Check for endpoints in old spec that might still exist - Verify each documented endpoint still exists in code - Add missing endpoints found in code **Search patterns:** ```bash # Find topic definitions grep -r "TOPIC_" --include="*.cpp" --include="*.h" # Find getTopics implementations grep -r "getTopics" --include="*.cpp" # Find topic handlers grep -r "getTopic\|setTopic" --include="*.cpp" # Find topic registration grep -r "registerTopic" --include="*.cpp" ``` ### 3. Build the OpenAPI Structure Start with the [base template](./references/openapi-template.yaml): ```yaml openapi: 3.0.3 info: title: [API Name] version: [Version from VERSION constant or git tag] description: [Brief API description] contact: name: [From LICENSE or README] email: [If available] servers: - url: http://{host}/rest/api/v1 description: REST API base path variables: host: default: localhost description: Device hostname or IP paths: # Endpoints go here components: schemas: # Reusable schemas responses: # Common responses securitySchemes: # Auth schemes ``` ### 4. Document Each Endpoint For each route/handler found: ```yaml /path/{param}: get: summary: [One-line description from code comments] description: [Detailed behavior from docstrings/comments] operationId: [camelCase unique identifier] tags: - [Logical grouping] parameters: - name: param in: path required: true schema: type: string description: [From parameter docs] - name: query in: query required: false schema: type: integer description: [From code inspection] responses: '200': description: Success content: application/json: schema: $ref: '#/components/schemas/SuccessResponse' example: status: "ok" data: {} '400': $ref: '#/components/responses/BadRequest' '404': $ref: '#/components/responses/NotFound' ``` ### 5. Extract Response Schemas From JSON response building code, create reusable schemas: ```yaml components: schemas: SuccessResponse: type: object required: - status - data properties: status: type: string enum: [ok] data: type: object description: Endpoint-specific response data ErrorResponse: type: object required: - status - msg properties: status: type: string enum: [error] msg: type: string description: Human-readable error message ``` ### 6. Document Authentication If authentication is present: ```yaml components: securitySchemes: basicAuth: type: http scheme: basic description: HTTP Basic Authentication # Then apply to protected endpoints: paths: /protected: get: security: - basicAuth: [] ``` ### 7. Validate and Refine - Check that all paths start with `/` - Verify all `$ref` references exist - Ensure required fields are present - Add examples for complex request/response bodies - Group related endpoints with `tags` - Document error responses consistently ## Output Format Save the specification as: - `docs/openapi.yaml` or `docs/swagger.yaml` (YAML preferred) - `docs/api-spec.yaml` (alternative naming) Include a comment header: ```yaml # OpenAPI 3.0.3 Specification # Generated from: [source files] # Last updated: [date] # See: https://swagger.io/docs/specification/v3_0/ ``` ## Common Patterns ### REST API with CRUD Operations ```yaml /items: get: summary: List all items responses: '200': description: Array of items post: summary: Create new item requestBody: required: true content: application/json: schema: $ref: '#/components/schemas/ItemCreate' responses: '201': description: Item created /items/{id}: get: summary: Get single item put: summary: Update item delete: summary: Delete item ``` ### Query Parameters ```yaml parameters: - name: limit in: query schema: type: integer minimum: 1 maximum: 100 default: 20 - name: offset in: query schema: type: integer minimum: 0 default: 0 ``` ### File Upload ```yaml requestBody: content: multipart/form-data: schema: type: object properties: file: type: string format: binary path: type: string ``` ## Common Pitfalls & Lessons Learned ### Missing Dynamic Endpoints **Issue**: Forgetting to document endpoints that are registered dynamically via plugin/service systems. **Solution**: 1. Don't rely only on static route definitions 2. Search for `getTopics()`, `registerTopics()`, or similar methods 3. Check for topic registration services that create REST endpoints 4. Look for topic handler implementations 5. Verify each plugin/service that registers topics **Example**: In Pixelix, sensor endpoints (`/sensors/{index}/{channelName}`) are created dynamically by `SensorDataProvider` registering topics via `TopicHandlerService`, not found in static route arrays. ### Path Pattern Consistency **Issue**: API paths may have multiple formats depending on registration method. **Check for**: - Service endpoints: `/{serviceId}/{topic}` - Plugin endpoints by UID: `/display/uid/{uid}/{topic}` - Plugin endpoints by alias: `/display/alias/{alias}/{topic}` - Indexed endpoints: `/{entityId}/{index}/{topic}` - System endpoints: `/{topic}` (no prefix) ### Parameter Types from Code **Issue**: Documentation doesn't match actual parameter types used in code. **Verify**: - Check actual JSON key names in `getTopic()`/`setTopic()` implementations - Confirm data types (string, number, boolean, array, object) - Note optional vs required parameters - Check for parameter validation rules (min/max, enums) ### Configuration vs Command Topics **Issue**: Some topics serve dual purposes. **Pattern**: - **Config topics**: GET returns current config, POST updates and persists config - **Command topics**: GET returns status, POST executes actions with `action` parameter - **Status topics**: GET only, returns current state **Example:** ```yaml # Command topic - action-based /display/uid/{uid}/playCtrl: post: parameters: - name: action schema: type: string enum: [next, previous, pause, continue] ``` ## Tips - **Use `$ref` for reusability**: Common responses and schemas should be defined once in `components` - **Include examples**: Especially for complex nested objects - **Document all response codes**: Even error cases (400, 401, 403, 404, 500) - **Add operation IDs**: Unique, descriptive `operationId` for code generation tools - **Group with tags**: Logical grouping improves generated documentation (e.g., by plugin name or service name) - **Version properly**: Use `info.version` matching your API versioning scheme - **Add curl examples**: Include practical curl command examples in endpoint descriptions to show authentication and parameter usage - **Consistency matters**: Keep response schemas, error formats, and authentication patterns consistent across all endpoints - **Trace the implementation**: Don't guess parameter types or structures - read the actual code that builds JSON responses ## Validation After generating the spec, validate it using: - [Swagger Editor](https://editor.swagger.io/) - paste YAML to check for errors - `swagger-cli validate openapi.yaml` - CLI validation - VS Code OpenAPI extensions for real-time validation ## References - [OpenAPI 3.0 Specification](https://swagger.io/docs/specification/v3_0/about/) - [OpenAPI Data Types](https://swagger.io/docs/specification/data-models/data-types/) - [Authentication](https://swagger.io/docs/specification/authentication/) - [Example template](./references/openapi-template.yaml)
GitHub에서 보기