Remote Work Tools

API documentation that drifts from the actual API is worse than no documentation — it creates false confidence and wastes engineering hours debugging. The tools in this guide all start from your OpenAPI spec (the source of truth), rendering documentation that’s always accurate and shareable without manual updates.


OpenAPI Spec as the Foundation

Every tool in this guide consumes an OpenAPI spec. Write one if you don’t have one:

# openapi.yaml
openapi: "3.1.0"
info:
  title: Payments API
  version: "2.0.0"
  description: |
    Process payments, manage subscriptions, and handle refunds.

    ## Authentication
    All endpoints require `Bearer` token authentication.

servers:
  - url: https://api.yourcompany.com/v2
    description: Production
  - url: https://staging-api.yourcompany.com/v2
    description: Staging

security:
  - bearerAuth: []

paths:
  /payments:
    post:
      operationId: createPayment
      summary: Create a payment
      tags: [Payments]
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/CreatePaymentRequest'
            examples:
              basic:
                summary: Basic card payment
                value:
                  amount: 2999
                  currency: usd
                  source: tok_visa
      responses:
        "201":
          description: Payment created
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Payment'
        "402":
          description: Payment failed
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PaymentError'

components:
  schemas:
    CreatePaymentRequest:
      type: object
      required: [amount, currency, source]
      properties:
        amount:
          type: integer
          description: Amount in smallest currency unit (cents for USD)
          example: 2999
        currency:
          type: string
          enum: [usd, eur, gbp]
          example: usd
        source:
          type: string
          description: Stripe payment token or customer ID
          example: tok_visa

  securitySchemes:
    bearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT

Stoplight (Collaboration-First)

Stoplight Studio is the most complete API design and documentation platform. Teams edit the OpenAPI spec in a visual editor, publish docs to a branded portal, and mock the API from the same spec.

Host the published docs as a static site:

# Install Stoplight CLI
npm install -g @stoplight/cli

# Validate your spec
stoplight lint openapi.yaml

# Push to Stoplight Platform
stoplight push --ci-token $STOPLIGHT_CI_TOKEN openapi.yaml

# Build static docs site
stoplight export --format html --output ./docs/api

Serve the static output:

server {
    listen 443 ssl http2;
    server_name docs.yourcompany.com;
    root /var/www/api-docs;
    index index.html;
    location / { try_files $uri $uri/ /index.html; }
}

Integrate into CI to publish on every spec change:

# .github/workflows/docs.yml
name: Publish API Docs
on:
  push:
    paths:
      - 'openapi.yaml'
    branches: [main]
jobs:
  publish:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - name: Install Stoplight CLI
        run: npm install -g @stoplight/cli
      - name: Publish docs
        run: stoplight push --ci-token ${{ secrets.STOPLIGHT_TOKEN }} openapi.yaml

Scalar (Modern, Self-Hosted)

Scalar is an open-source API reference documentation UI with a clean, modern design and built-in API client (send requests directly from the docs). It replaces Swagger UI for teams who want something better looking.

Serve as a Docker container:

# docker-compose.yml
services:
  api-docs:
    image: scalar/api-reference:latest
    ports:
      - "3000:3000"
    volumes:
      - ./openapi.yaml:/app/openapi.yaml:ro
    environment:
      - SCALAR_CONFIG_FILE=/app/openapi.yaml
      - SCALAR_BASE_PATH=/

Or embed in your existing API server (Node.js/Express):

// server.js
import express from 'express';
import { apiReference } from '@scalar/express-api-reference';
import { readFileSync } from 'fs';

const app = express();

const spec = readFileSync('./openapi.yaml', 'utf-8');

app.use('/docs', apiReference({
  spec: { content: spec },
  theme: 'default',
  // Show "Try It" button using your staging server
  defaultHttpClient: { targetKey: 'node', clientKey: 'axios' },
  servers: [{ url: 'https://staging-api.yourcompany.com/v2' }],
}));

Embed in Go with chi:

import (
    "github.com/scalar/scalar/packages/go-scalar"
    "github.com/go-chi/chi/v5"
)

r := chi.NewRouter()
r.Get("/docs", scalar.Handler(scalar.Options{
    SpecURL:  "/openapi.yaml",
    Title:    "Payments API Reference",
}))
r.Get("/openapi.yaml", func(w http.ResponseWriter, r *http.Request) {
    http.ServeFile(w, r, "./openapi.yaml")
})

Redoc (Embeddable, Clean)

Redoc is the standard self-hosted OpenAPI renderer. It’s fast, well-maintained, and integrates into any HTML page.

Static HTML deployment:

<!-- docs/index.html -->
<!DOCTYPE html>
<html>
<head>
  <title>API Reference</title>
  <meta charset="utf-8"/>
  <meta name="viewport" content="width=device-width, initial-scale=1">
  <link href="https://fonts.googleapis.com/css?family=Montserrat:300,400,700|Roboto:300,400,700" rel="stylesheet">
  <style>
    body { margin: 0; padding: 0; }
  </style>
</head>
<body>
  <redoc spec-url='./openapi.yaml'></redoc>
  <script src="https://cdn.redoc.ly/redoc/latest/bundles/redoc.standalone.js"></script>
</body>
</html>

Build a static bundle with redocly CLI:

npm install -g @redocly/cli

# Validate spec
redocly lint openapi.yaml

# Bundle into single HTML file (no CDN dependency)
redocly build-docs openapi.yaml --output docs/index.html

# Preview locally
redocly preview-docs openapi.yaml

Split large specs into multiple files (better for team editing):

# openapi.yaml can reference other files
paths:
  /payments:
    $ref: './paths/payments.yaml'
  /users:
    $ref: './paths/users.yaml'

# Bundle into one file
redocly bundle openapi.yaml --output openapi-bundled.yaml

Keep Docs in Sync with Code

Generate OpenAPI specs from code annotations to prevent drift:

Go (swaggo):

// @Summary Create a payment
// @Tags Payments
// @Accept json
// @Produce json
// @Param request body CreatePaymentRequest true "Payment details"
// @Success 201 {object} Payment
// @Failure 402 {object} PaymentError
// @Router /payments [post]
func CreatePayment(w http.ResponseWriter, r *http.Request) {
    // ...
}
swag init -g cmd/api/main.go --output ./docs/swagger

Python FastAPI (auto-generated):

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI(title="Payments API", version="2.0.0")

class PaymentRequest(BaseModel):
    amount: int
    currency: str
    source: str

@app.post("/payments", status_code=201)
async def create_payment(request: PaymentRequest) -> Payment:
    """Create a new payment."""
    # FastAPI generates OpenAPI spec automatically
    ...

# Docs available at /docs and /redoc
# Export spec: GET /openapi.json

Tool Comparison

Tool Hosting Try It API Cost Best For
Stoplight SaaS/self Via Stoplight Free tier + paid Design-first teams
Scalar Self-hosted Built-in Free (OSS) Modern UI, embedded
Redoc Self-hosted No Free (OSS) Clean, lightweight
Swagger UI Self-hosted Built-in Free (OSS) Maximum compatibility

For most remote teams: use Scalar for external developer-facing docs, Redoc for internal API references, and Stoplight when your team does API-first design.



Built by theluckystrike — More at zovo.one