How CasaOS Uses the OpenAPI Specification for API Documentation

CasaOS embeds an OpenAPI (Swagger) description in its source tree and leverages the oapi-codegen toolchain to generate server code, request-validation middleware, and self-hosted documentation from that single source of truth.

The IceWhaleTech/CasaOS repository treats the OpenAPI specification as the canonical contract for its REST API. By generating Go types and server interfaces directly from the YAML definition, the project ensures that code, documentation, and runtime validation remain synchronized without manual duplication.

OpenAPI Specification as the Source of Truth

The API contract lives in a single YAML file that serves as the foundation for the entire v2 API surface.

The API Contract Location

All routes, parameters, and schemas are defined in api/casaos/openapi.yaml. This file is the authoritative source that both humans and machines read to understand the CasaOS API capabilities. Keeping the specification in version control alongside the implementation guarantees that documentation updates accompany code changes.

Code Generation with oapi-codegen

CasaOS uses the oapi-codegen tool to transform the static YAML file into runnable Go code, eliminating the need to manually write repetitive boilerplate.

The go:generate Directive

In main.go, a code generation directive triggers the build process. When you run go generate, the tool reads api/casaos/openapi.yaml and emits type-safe Go code:

// main.go
//go:generate bash -c "mkdir -p codegen && \
//   go run github.com/deepmap/oapi-codegen/cmd/oapi-codegen@v1.12.4 \
//   -generate types,server,spec -package codegen api/casaos/openapi.yaml \
//   > codegen/casaos_api.go"

This command produces three critical outputs: Go structs modeling request/response bodies, server interface stubs, and a helper function to parse the spec at runtime.

Generated Server Components

The resulting codegen/casaos_api.go file contains:

  • Go structs that map to OpenAPI schema definitions
  • GetSwagger() helper that returns an *openapi3.T object for runtime use
  • Server interface stubs that concrete handlers must implement

By deriving these from the OpenAPI specification, CasaOS ensures that any breaking change in the YAML causes a compilation error in the Go code, catching inconsistencies at build time rather than runtime.

Runtime Validation and Middleware

Once the application starts, CasaOS loads the OpenAPI specification to validate every incoming HTTP request against the defined contract.

Loading the OpenAPI Spec

In route/v2.go, the bootstrap code initializes the OpenAPI specification at startup:

// route/v2.go
swagger, err := codegen.GetSwagger()
if err != nil { panic(err) }
_swagger = swagger

The spec is stored in a package-level variable _swagger, making it available to validation middleware and documentation handlers throughout the application lifecycle.

Request Validation Middleware

The Echo framework attaches OapiRequestValidatorWithOptions from the github.com/deepmap/oapi-codegen/pkg/middleware package. This middleware compares every incoming request against the OpenAPI specification, automatically rejecting requests with incorrect paths, methods, or malformed bodies.

e.Use(middleware.OapiRequestValidatorWithOptions(_swagger, &middleware.Options{
    Skipper: func(c echo.Context) bool {
        return strings.Contains(c.Request().Header[echo.HeaderContentType][0],
                                "multipart/form-data")
    },
    Options: openapi3filter.Options{AuthenticationFunc: openapi3filter.NoopAuthenticationFunc},
}))

A custom skipper function bypasses validation for multipart file uploads, addressing a known limitation of the validator while enforcing strict validation for all other endpoints.

Serving Interactive API Documentation

CasaOS exposes both machine-readable and human-friendly versions of the OpenAPI specification through dedicated endpoints.

HTML UI and Raw Spec Endpoints

The InitV2DocRouter function in route/v2.go returns an HTTP handler that serves documentation at the /doc/ path:

// route/v2.go
func InitV2DocRouter(docHTML string, docYAML string) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        if r.URL.Path == V2DocPath {
            _, _ = w.Write([]byte(docHTML))
            return
        }
        if r.URL.Path == V2DocPath+"/openapi.yaml" {
            _, _ = w.Write([]byte(docYAML))
            return
        }
    })
}

Users can browse an interactive HTML page (typically rendered by Redoc) at /doc, or download the raw OpenAPI specification at /doc/openapi.yaml for client generation or offline reference.

Implementing API Handlers

Concrete implementations of the API logic connect to the generated interfaces through a type-safe registration process.

Registering Routes with Generated Interfaces

After setting up middleware, the application registers concrete handlers using the generated RegisterHandlersWithBaseURL function:

codegen.RegisterHandlersWithBaseURL(e, appManagement, V2APIPath)

This call wires the implementation found in route/v2 files to the Echo router, automatically applying the base path derived from the OpenAPI specification's server URL. Because the handlers implement interfaces generated from the OpenAPI specification, the compiler enforces that all required methods are present and correctly typed.

Practical Examples

Fetching the OpenAPI Specification

Retrieve the raw YAML specification for use with external tools like Postman or Swagger UI:


# Retrieve the raw OpenAPI definition

curl -s http://<casa-os-host>/doc/openapi.yaml

Browsing the Documentation UI

Open a browser and navigate to:


http://<casa-os-host>/doc

The HTML page served by the InitV2DocRouter handler provides interactive documentation where you can explore endpoints and view schema definitions without reading the source code.

Using the Generated Client

The oapi-codegen output includes a client package that provides type-safe API access. After running go generate, you can import the generated client and call endpoints with full IDE support:

import "github.com/IceWhaleTech/CasaOS/codegen"

func main() {
    cfg := codegen.NewConfiguration()
    cfg.Host = "casaos.local"
    client := codegen.NewAPIClient(cfg)

    // Example: list installed apps (endpoint defined in the spec)
    resp, err := client.AppApi.GetApps(context.Background())
    if err != nil {
        log.Fatalf("API error: %v", err)
    }
    fmt.Println("Installed apps:", resp)
}

Adding New Endpoints

To extend the CasaOS API, modify the OpenAPI specification and regenerate the code:

  1. Edit api/casaos/openapi.yaml to describe the new path, methods, and request/response schemas.
  2. Run go generate ./... to update codegen/casaos_api.go with new types and interface methods.
  3. Implement the handler in the appropriate route/v2 file and register it via codegen.RegisterHandlersWithBaseURL.

This workflow ensures that your new endpoint is automatically documented, validated, and type-checked against the OpenAPI specification.

Summary

CasaOS implements a spec-first API strategy using the OpenAPI specification to automate documentation and validation:

  • The canonical contract resides in api/casaos/openapi.yaml
  • oapi-codegen generates Go types, server interfaces, and a spec loader from the YAML
  • Runtime validation middleware enforces the OpenAPI contract on every request
  • Interactive documentation is served from the same specification used for code generation
  • Developers add features by editing the spec first, ensuring documentation never diverges from implementation

Frequently Asked Questions

Where is the OpenAPI specification file located in the CasaOS repository?

The OpenAPI specification is located at api/casaos/openapi.yaml in the IceWhaleTech/CasaOS repository. This YAML file serves as the single source of truth for all API routes, request schemas, and response models used by the v2 API.

How does CasaOS validate incoming requests against the OpenAPI specification?

CasaOS uses the OapiRequestValidatorWithOptions middleware from the github.com/deepmap/oapi-codegen package. This middleware loads the parsed OpenAPI specification at startup and validates every incoming request against the defined paths, methods, and schemas, automatically rejecting requests that violate the contract.

Can I generate a Go client for the CasaOS API using the OpenAPI specification?

Yes. The oapi-codegen tool generates a complete client package in codegen/casaos_api.go that includes type-safe methods for every endpoint defined in the specification. You can import this package and use codegen.NewAPIClient() to interact with the CasaOS API with full IDE autocompletion and compile-time type safety.

What happens when developers add new endpoints to the CasaOS API?

Developers edit api/casaos/openapi.yaml to define the new endpoint, then run go generate to update the generated code. This process automatically creates the necessary Go structs and interface methods. The developer then implements the handler in the route/v2 directory and registers it using codegen.RegisterHandlersWithBaseURL, ensuring the new endpoint is immediately documented and validated.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →