APIndex Documentation
Back to Home

Documentation

Everything you need to install, configure, and use APIndex in your organization.

Getting Started

APIndex is a self-hosted API catalog and management platform that helps teams discover, organize, test, and visualize their APIs in one place. It provides:

  • Centralized API Catalog — Register, tag, and organize all your APIs
  • Network Map — Interactive visualization of API dependencies
  • Environment Management — Manage dev, staging, and production environments with variables
  • Built-in API Tester — Test API endpoints directly from the UI
  • Role-Based Access Control — Fine-grained permissions with custom roles
  • Multi-Organization Support — Create and switch between organizations
  • LDAP/AD Integration — Enterprise authentication (Business plan)
  • Audit Logging — Track all changes (Business plan)

Prerequisites

  • Docker — version 20.10 or later
  • Docker Compose — version 2.0 or later
  • Network Access — outbound HTTPS to https://license.apindex.dev (for paid plans)

Installation

Get APIndex running in three steps using our official Docker images.

1. Create a project directory

mkdir apindex && cd apindex

2. Create docker-compose.yml

Copy the production Docker Compose configuration from the Docker Deployment section, or download it:

# Create docker-compose.yml with the configuration from the Docker Deployment section
# Then create your .env file:

cat > .env << 'EOF'
POSTGRES_PASSWORD=your-secure-db-password
SECRET_KEY=generate-with-openssl-rand-hex-32
FIRST_SUPERUSER_EMAIL=admin@yourcompany.com
FIRST_SUPERUSER_PASSWORD=change-this-password
PORT=8080
EOF

3. Start the services

docker compose up -d

Verify installation

# Check container status
docker compose ps

# API health check
curl http://localhost:8000/health

# Access the UI at http://localhost:8080

Default Credentials

On first startup, APIndex creates a superuser account using the credentials from your .env file. If not specified, defaults are:

  • Email: admin@apindex.local
  • Password: changeme

Configuration

APIndex is configured via environment variables. Create a .env file in your project directory with the following settings.

Database

Variable Description Default
POSTGRES_HOST Database hostname postgres
POSTGRES_PORT Database port 5432
POSTGRES_USER Database user apindex
POSTGRES_PASSWORD Database password (required)
POSTGRES_DB Database name apindex

Security

Variable Description Default
SECRET_KEY JWT signing key (generate with openssl rand -hex 32) (required)
DEBUG Enable debug mode false
FIRST_SUPERUSER_EMAIL Initial admin email admin@apindex.local
FIRST_SUPERUSER_PASSWORD Initial admin password changeme

License & Instance

Variable Description Default
LICENSE_KEY Your license key (auto-activates on startup)
INSTANCE_NAME License ID received with your license key (required for validation)

Licensing

APIndex uses a tier-based licensing system. The Community tier is free and works offline. Paid tiers require periodic license validation.

License Tiers

Tier Users Environments Key Features
Community 3 1 API Catalog, Network Map, API Tester, Import
Team 25 Unlimited + RBAC, Custom Roles
Business Unlimited Unlimited + LDAP/AD, Audit Log, Multi-tenant
Enterprise Unlimited Unlimited + SLA, Dedicated Support, Custom Integrations

How License Validation Works

When APIndex starts, it validates your license with our license server. Only two pieces of information are sent:

  • License Key — your unique license key
  • Instance Name (License ID) — the ID provided with your license

Privacy by design: No user data, API catalog data, usage analytics, or any other information from your instance is ever transmitted. The license server only verifies that your license key and ID are valid.

Network Requirements

Required for Paid Tiers

Your APIndex backend must be able to make outbound HTTPS requests to https://license.apindex.dev. Ensure your firewall and proxy settings allow this connection.

Offline / Grace Period

If the license server cannot be reached:

  • Cached token valid — Full functionality continues until token expires (7 days)
  • Token expired — Falls back to Community tier limits until connection is restored
  • Community tier — No license server required, works fully offline

Activating Your License

When you purchase a license, you receive two values: a License Key and a License ID. Configure both in your environment:

# .env file
LICENSE_KEY=apx_live_xxxxxxxxxxxxxxxxxxxx
INSTANCE_NAME=550e8400-e29b-41d4-a716-446655440000

On startup, APIndex automatically activates the license if the LICENSE_KEY environment variable is set. The INSTANCE_NAME must match the License ID exactly for validation to succeed.

Community Plan

The Community plan is free forever and includes core API catalog features, OpenAPI import, basic testing, and Docker deployment for up to 3 users. No license key is required for the Community plan.

Architecture

APIndex consists of three main services:

Backend (FastAPI)

Python REST API with async support, JWT authentication, RBAC, and LDAP integration.

Frontend (React)

React + TypeScript SPA with Vite, shadcn/ui components, and TailwindCSS.

Database (PostgreSQL)

PostgreSQL 16 for persistent storage with SQLAlchemy ORM and Alembic migrations.

Default Ports

Port Service Description
8000 Backend API FastAPI application
5173 Frontend (dev) Vite development server
8080 Frontend (prod) nginx with API proxy
5432 PostgreSQL Internal only (not exposed)

API Catalog

The API Catalog is the central registry for all your APIs. Organize them with collections, tags, and detailed metadata.

Creating an API

Click Add API and provide:

  • Name — Display name for the API
  • Slug — URL-friendly identifier (auto-generated)
  • Description — What the API does
  • Type — REST, GraphQL, gRPC, SOAP, or WebSocket
  • Base URL — The API's base endpoint
  • Tags — For filtering and organization
  • Collection — Group related APIs together

Importing APIs

APIndex supports importing OpenAPI 3.x, Swagger 2.0, and WSDL specifications:

  • Upload a file (JSON, YAML, or XML)
  • Paste spec content directly
  • Import from URL

Endpoints, schemas, and authentication requirements are automatically parsed.

API Versions

Each API can have multiple versions. Mark versions as published or deprecated. Only one version can be the "current" version displayed by default.

Upstream & Downstream Connections

Define relationships between APIs to build the network map. Each API can specify:

  • Upstream connections — APIs that this service depends on (services it calls)
  • Downstream connections — APIs that depend on this service (services that call it)

These connections power the Network Map visualization and help teams understand service dependencies at a glance.

Upstream Resources

Upstream Resources represent the backend systems, databases, and services that your APIs depend on. By mapping these dependencies, APIndex gives your team full visibility into the infrastructure landscape behind your API catalog.

What Are Upstream Resources?

While APIs define the contracts your consumers interact with, Upstream Resources capture what those APIs connect to on the backend. Examples include:

  • Databases — PostgreSQL clusters, Redis caches, Elasticsearch indexes
  • Core Systems — Core Banking System, ERP, CRM platforms
  • Third-Party Services — Payment gateways, SMS providers, identity platforms
  • Internal Services — Message queues, shared microservices, data pipelines

Creating an Upstream Resource

Navigate to Upstream Resources in the sidebar and click Add Resource. Provide:

  • Name — A clear identifier (e.g., "Customer Database", "Payment Gateway")
  • Type — Database, Service, Queue, Cache, or External
  • Description — What this resource provides and any relevant context

Linking APIs to Upstream Resources

Each API version can be linked to one or more Upstream Resources, creating a dependency map between your API layer and its underlying infrastructure. To link an API:

  • Open an API version and navigate to the Upstream Resources tab
  • Select existing resources or create new ones inline
  • The connection is automatically reflected in the Network Map

Use Cases

Impact Analysis

When a backend system experiences issues or planned downtime, instantly identify every API that depends on it. Understand the blast radius before it affects consumers.

Dependency Tracking

Maintain an accurate map of which APIs rely on which systems. Prevent surprises during migrations, upgrades, or decommissions.

Infrastructure Documentation

Give platform teams and API architects a single view that bridges API contracts and the infrastructure powering them — no more tribal knowledge.

Visualization

Upstream Resources appear as distinct nodes in the Network Map, visually differentiated from API nodes. This gives teams a complete picture — from consumer-facing APIs down to the backend systems they depend on.

Network Map

The Network Map provides an interactive force-directed graph visualization showing how your APIs connect to each other and external services.

Features

  • Interactive Graph — Drag nodes, zoom, and pan
  • Dependency Lines — Arrows show data flow direction
  • Click to Navigate — Click any API node to view details
  • Connection Types — Visual distinction for internal vs external

Adding Connections

Edit any API and add upstream URLs in the "Connections" section. For each connection, specify:

  • Name — Display name for the connection
  • URL — Target endpoint (matched to other APIs if internal)
  • Type — Internal API or External service
  • Direction — Upstream (this API calls it) or Downstream (it calls this API)

Environments

Environments let you manage different configurations for development, staging, and production.

Environment Variables

Each environment can store key-value pairs that are substituted in API requests:

  • Regular Variables — Visible to all users with access
  • Secret Variables — Hidden after creation, only values are used

Use variables in API Tester with {{ variable_name }} syntax.

Testing Control

Enable or disable the "Allow Testing" flag per environment to control which environments can be used in the API Tester.

Limits

Community: 1 environment • Team/Business: Unlimited

API Testing

The built-in API Tester lets you make HTTP requests directly from the UI without external tools.

Features

  • All HTTP Methods — GET, POST, PUT, PATCH, DELETE, etc.
  • Custom Headers — Add any headers including Authorization
  • Request Body — JSON, form data, or raw text
  • Environment Variables — Select environment and use variables
  • Response Viewer — Formatted JSON, headers, status, timing
  • SSL Verification — Toggle SSL certificate verification

Request History

All requests are saved to history. View your recent requests or browse organization-wide history (with permission).

User Management

APIndex includes role-based access control (RBAC) with predefined and custom roles.

Default Roles

Role Permissions
Superuser Bypasses all permission checks. Can only be granted by another superuser. The initial account created during setup is automatically a superuser.
Owner Full access including billing and organization settings
Admin Manage users, roles, APIs, and settings
Editor Create and edit APIs, environments, collections
Viewer Read-only access to APIs and network map

Superuser Access

The superuser role is a special elevated privilege that bypasses all permission checks. Key points:

  • The first account created during initial setup is automatically granted superuser status
  • Superuser status can only be granted by another superuser
  • Superusers can access all organizations, workspaces, and APIs regardless of role assignments
  • Use sparingly — prefer standard roles for day-to-day operations

Custom Roles (Team+)

Create custom roles with specific permission combinations for your organization's needs.

User Limits

Community: 3 users • Team: 25 users • Business: Unlimited

Organizations

Users can belong to multiple organizations and switch between them. Each organization has its own:

  • API catalog and collections
  • Environments and variables
  • Users and roles
  • License and billing
  • Audit log (Business plan)

Creating Organizations

Click the organization switcher in the sidebar and select "Create Organization". You become the owner of any organization you create.

Switching Organizations

Use the organization switcher to move between organizations. Your permissions may differ per organization based on your assigned roles.

LDAP / Active Directory

Business Plan — APIndex supports LDAP and Active Directory for enterprise authentication.

Configuration

Navigate to LDAP Settings in the sidebar and configure:

  • Server URL — e.g., ldaps://ldap.example.com:636
  • Bind DN — Service account DN for searches
  • Bind Password — Service account password
  • User Search Base — e.g., ou=People,dc=example,dc=com
  • User Search Filter — e.g., (uid={username})

Group-to-Role Mapping

Map LDAP groups to APIndex roles. Users are automatically assigned roles based on their group membership.

Audit Log

Business Plan — Track all changes made in your organization.

Tracked Events

  • API created, updated, deleted
  • User created, updated, deleted
  • Role created, updated, deleted
  • Environment changes
  • Collection changes
  • API imports

Log Details

Each log entry includes:

  • Timestamp
  • User who performed the action (name and email preserved even if user is deleted)
  • Action type (create, update, delete)
  • Entity type and ID
  • Changes made (before/after for updates)

MCP Integration

APIndex exposes an MCP server that allows AI agents (Claude Desktop, Cursor, Windsurf, custom agents, etc.) to interact with your API catalog programmatically — searching APIs, reading specs, running tests, importing specs, and managing mocks.

How it works

The MCP server is built with FastMCP and mounted at /mcp on the APIndex backend. It uses the Streamable HTTP transport.

  • Org-scoped — Each API key is bound to an organization. Tools only return data from that org.
  • Permission-based — Each API key has granular permissions. Tools check permissions before executing.
  • Stateless auth — Authentication via X-API-Key header on every request.
┌─────────────────┐       ┌──────────────────────────────────┐
│   AI Agent       │       │         APIndex                  │
│  (Claude, etc.)  │──────▶│  nginx (/mcp) ──▶ FastAPI (/mcp)│
│                  │       │                    │             │
│  X-API-Key: ...  │       │          MCPAPIKeyMiddleware     │
│                  │       │                    │             │
│  JSON-RPC/HTTP   │       │          FastMCP Server          │
│                  │       │          (12 tools)              │
└─────────────────┘       └──────────────────────────────────┘

Prerequisites

  • APIndex instance running (v1.0.0+ with migration 017 applied)
  • A user with Owner or Admin role (required to manage MCP keys)
  • An MCP-compatible AI client

1. Create an MCP API Key

Via the UI:

  1. Log in to APIndex as an Owner or Admin
  2. Navigate to Settings > MCP Keys (in the sidebar under Admin)
  3. Click New API Key
  4. Enter a name (e.g., "Claude Desktop", "Cursor", "CI Agent")
  5. Select the permissions you want to grant
  6. Click Create Key
  7. Copy the key immediately — it will not be shown again

Via the API:

# Login to get a JWT token
TOKEN=$(curl -s https://your-apindex.com/api/v1/auth/login \
  -H 'Content-Type: application/json' \
  -d '{"email":"admin@admin.com","password":"your-password"}' \
  | jq -r '.access_token')

# Create an MCP key with all permissions
curl -s https://your-apindex.com/api/v1/mcp-keys \
  -H "Authorization: Bearer $TOKEN" \
  -H 'Content-Type: application/json' \
  -d '{
    "name": "Claude Desktop",
    "permissions": [
      "api:read",
      "api:import",
      "collection:read",
      "environment:read",
      "test:execute",
      "mock:read",
      "mock:manage"
    ]
  }' | jq .

The response includes a raw_key field (e.g., apx_praOAemR...) — save this securely.

2. Configure Your AI Client

Point your MCP client to:

Setting Value
URL https://your-apindex.com/mcp
Transport Streamable HTTP
Auth Header X-API-Key: apx_your_key_here

Available Tools

The MCP server exposes 12 tools organized by category:

Catalog (read & import)

Tool Description Permission
search_apis Search and list APIs with text search, tag filtering, and collection filtering api:read
get_api_details Get full details for an API including all versions and endpoints api:read
get_api_spec Get the raw OpenAPI/Swagger spec for an API version api:read
list_tags List all unique tags used across APIs in the catalog api:read
get_catalog_stats Get catalog statistics: total API count and breakdown by type api:read
import_openapi_spec Import an OpenAPI/Swagger spec into the catalog api:import

Collections & Environments

Tool Description Permission
get_collection_tree Get the hierarchical collection tree with API counts collection:read
list_environments List all environments with variables (secrets masked) and mock server status environment:read

Testing

Tool Description Permission
execute_api_test Execute an HTTP request for API testing with environment variable substitution test:execute
list_saved_test_examples List all saved test examples (pre-configured requests) test:execute

Mocks

Tool Description Permission
list_mock_projects List mock projects from the Mocktail server attached to an environment mock:read
generate_mocks Generate mock rules from an API spec on the Mocktail server mock:manage

Permissions

MCP API keys use a granular permission system, separate from user RBAC roles:

Permission What it allows
api:read Search APIs, get details, read specs, list tags, get stats
api:import Import OpenAPI/Swagger specs into the catalog
collection:read Read the collection tree
environment:read List environments (secrets are always masked)
test:execute Execute HTTP requests and list saved test examples
mock:read List mock projects from connected Mocktail servers
mock:manage Generate mocks from API specs

Recommended permission sets:

  • Read-only agentapi:read, collection:read, environment:read
  • Developer agent — all of the above + api:import, test:execute, mock:read
  • Full access agent — all permissions

Authentication

Every request to the MCP server must include the API key in the X-API-Key header.

  • Missing key401 {"detail": "Missing X-API-Key header"}
  • Invalid/revoked key401 {"detail": "Invalid or revoked API key"}
  • Missing permission — Tool returns a PermissionError in the MCP response

Keys can be disabled (without deleting) via the UI or API — useful for temporary revocation. The last_used_at timestamp is updated on every authenticated request.

Client Configuration Examples

Claude Desktop

Add to ~/Library/Application Support/Claude/claude_desktop_config.json (macOS):

{
  "mcpServers": {
    "apindex": {
      "url": "https://your-apindex.com/mcp",
      "headers": {
        "X-API-Key": "apx_your_key_here"
      }
    }
  }
}

Cursor

Add to .cursor/mcp.json in your project or global config:

{
  "mcpServers": {
    "apindex": {
      "url": "https://your-apindex.com/mcp",
      "headers": {
        "X-API-Key": "apx_your_key_here"
      }
    }
  }
}

Claude Code (CLI)

Add to your project's .mcp.json:

{
  "mcpServers": {
    "apindex": {
      "type": "url",
      "url": "https://your-apindex.com/mcp",
      "headers": {
        "X-API-Key": "apx_your_key_here"
      }
    }
  }
}

Custom Python Client

Click to expand Python example
import httpx
import json

MCP_URL = "https://your-apindex.com/mcp/"
API_KEY = "apx_your_key_here"

headers = {
    "X-API-Key": API_KEY,
    "Content-Type": "application/json",
    "Accept": "application/json, text/event-stream",
}

def mcp_request(method, params=None, req_id=1, session_id=None):
    payload = {"jsonrpc": "2.0", "id": req_id, "method": method, "params": params or {}}
    h = {**headers}
    if session_id:
        h["Mcp-Session-Id"] = session_id
    return httpx.post(MCP_URL, json=payload, headers=h, timeout=30)

# Initialize
resp = mcp_request("initialize", {
    "protocolVersion": "2024-11-05",
    "capabilities": {},
    "clientInfo": {"name": "python-client", "version": "1.0"},
})
session_id = resp.headers.get("mcp-session-id")

# Send initialized notification
httpx.post(MCP_URL, json={
    "jsonrpc": "2.0",
    "method": "notifications/initialized",
    "params": {},
}, headers={**headers, "Mcp-Session-Id": session_id}, timeout=10)

# Call a tool
resp = mcp_request("tools/call", {
    "name": "search_apis",
    "arguments": {"query": "pet"},
}, req_id=2, session_id=session_id)

for line in resp.text.strip().split("\n"):
    if line.startswith("data: "):
        print(json.dumps(json.loads(line[6:]), indent=2))

Testing the MCP Server

Quick smoke test to verify the endpoint is reachable and auth works:

# Should return 401 (no key)
curl -s https://your-apindex.com/mcp/

# Should return a JSON-RPC response (with key)
curl -s -X POST https://your-apindex.com/mcp/ \
  -H "X-API-Key: apx_your_key_here" \
  -H "Content-Type: application/json" \
  -H "Accept: application/json, text/event-stream" \
  -d '{
    "jsonrpc": "2.0",
    "id": 1,
    "method": "initialize",
    "params": {
      "protocolVersion": "2024-11-05",
      "capabilities": {},
      "clientInfo": {"name": "curl-test", "version": "1.0"}
    }
  }'

Key Management API

# List all keys
GET /api/v1/mcp-keys

# Create a key (returns raw_key once)
POST /api/v1/mcp-keys
{"name": "...", "permissions": ["api:read", ...]}

# Update a key (name, permissions, or active status)
PATCH /api/v1/mcp-keys/{key_id}
{"name": "new name", "permissions": [...], "is_active": false}

# Delete a key permanently
DELETE /api/v1/mcp-keys/{key_id}

All key management endpoints require the mcp:manage permission (Owner and Admin roles have this by default).

Troubleshooting

"Missing X-API-Key header" even though you're sending it

If you access APIndex through a reverse proxy (nginx, Caddy, etc.), make sure the proxy forwards the X-API-Key header to the backend.

"Not Acceptable: Client must accept text/event-stream"

Your request is missing the Accept: application/json, text/event-stream header. MCP Streamable HTTP requires the client to accept SSE responses.

"Bad Request: Missing session ID"

After the initial initialize call, all subsequent requests must include the Mcp-Session-Id header from the initialize response.

Tool returns "Missing permission: xxx"

The API key doesn't have the required permission. Edit the key in Settings > MCP Keys to add the missing permission.

Connection timeout / SSE not working

If behind a reverse proxy, ensure: proxy_buffering off, proxy_read_timeout 300s, and chunked_transfer_encoding off are set for the /mcp location.

Docker Deployment

The recommended way to deploy APIndex in production using Docker Compose.

docker-compose.prod.yml

version: '3.8'

services:
  postgres:
    image: postgres:16-alpine
    container_name: apindex-db
    environment:
      POSTGRES_USER: ${POSTGRES_USER:-apindex}
      POSTGRES_PASSWORD: ${POSTGRES_PASSWORD:?Set POSTGRES_PASSWORD}
      POSTGRES_DB: ${POSTGRES_DB:-apindex}
    volumes:
      - postgres_data:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER:-apindex} -d ${POSTGRES_DB:-apindex}"]
      interval: 10s
      timeout: 5s
      retries: 5
    restart: unless-stopped

  backend:
    image: apindex/backend:${APINDEX_VERSION:-latest}
    container_name: apindex-backend
    environment:
      - POSTGRES_HOST=postgres
      - POSTGRES_PORT=5432
      - POSTGRES_USER=${POSTGRES_USER:-apindex}
      - POSTGRES_PASSWORD=${POSTGRES_PASSWORD:?Set POSTGRES_PASSWORD}
      - POSTGRES_DB=${POSTGRES_DB:-apindex}
      - SECRET_KEY=${SECRET_KEY:?Set SECRET_KEY}
      - DEBUG=false
      - INSTANCE_NAME=${INSTANCE_NAME:-default}
      - FIRST_SUPERUSER_EMAIL=${FIRST_SUPERUSER_EMAIL:-admin@apindex.local}
      - FIRST_SUPERUSER_PASSWORD=${FIRST_SUPERUSER_PASSWORD:-changeme}
    depends_on:
      postgres:
        condition: service_healthy
    restart: unless-stopped

  frontend:
    image: apindex/frontend:${APINDEX_VERSION:-latest}
    container_name: apindex-frontend
    environment:
      - BACKEND_URL=http://backend:8000
    ports:
      - "${PORT:-8080}:80"
    depends_on:
      - backend
    restart: unless-stopped

volumes:
  postgres_data:

Deployment Steps

# 1. Create .env file
cat > .env << 'EOF'
POSTGRES_PASSWORD=your-secure-password
SECRET_KEY=$(openssl rand -hex 32)
FIRST_SUPERUSER_EMAIL=admin@yourcompany.com
FIRST_SUPERUSER_PASSWORD=change-this-password
PORT=8080
EOF

# 2. Start services
docker compose -f docker-compose.prod.yml up -d

# 3. Check status
docker compose -f docker-compose.prod.yml ps

# 4. View logs
docker compose -f docker-compose.prod.yml logs -f

Reverse Proxy (nginx)

server {
    listen 443 ssl http2;
    server_name apindex.yourcompany.com;

    ssl_certificate /etc/ssl/certs/apindex.crt;
    ssl_certificate_key /etc/ssl/private/apindex.key;

    location / {
        proxy_pass http://localhost:8080;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}

Kubernetes Deployment

Deploy APIndex on Kubernetes using the manifest below. Includes ConfigMap, Secret, Deployments, Services, and Ingress.

Quick Start

# 1. Download the manifest
curl -O https://docs.apindex.dev/k8s/apindex.yaml

# 2. Edit the ConfigMap and Secret values
# IMPORTANT: Change all default passwords and secrets!

# 3. Apply the manifest
kubectl apply -f apindex.yaml

# 4. Check deployment status
kubectl -n apindex get pods

# 5. Get the ingress IP/hostname
kubectl -n apindex get ingress

Full Manifest (apindex.yaml)

Click to expand full Kubernetes manifest
# APIndex Kubernetes Deployment
# Apply with: kubectl apply -f apindex.yaml

---
# Namespace
apiVersion: v1
kind: Namespace
metadata:
  name: apindex
  labels:
    app.kubernetes.io/name: apindex

---
# ConfigMap - Non-sensitive configuration
apiVersion: v1
kind: ConfigMap
metadata:
  name: apindex-config
  namespace: apindex
data:
  POSTGRES_HOST: "postgres"
  POSTGRES_PORT: "5432"
  POSTGRES_DB: "apindex"
  POSTGRES_USER: "apindex"
  DEBUG: "false"
  INSTANCE_NAME: "default"
  BACKEND_URL: "http://backend:8000"

---
# Secret - CHANGE THESE VALUES!
# Generate base64: echo -n 'your-value' | base64
apiVersion: v1
kind: Secret
metadata:
  name: apindex-secrets
  namespace: apindex
type: Opaque
data:
  POSTGRES_PASSWORD: Y2hhbmdlbWU=  # changeme
  SECRET_KEY: Y2hhbmdlLXRoaXMtdG8tYS1zZWN1cmUtcmFuZG9tLXN0cmluZw==
  FIRST_SUPERUSER_EMAIL: YWRtaW5AYXBpbmRleC5sb2NhbA==
  FIRST_SUPERUSER_PASSWORD: Y2hhbmdlbWU=

---
# PostgreSQL PVC
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: postgres-pvc
  namespace: apindex
spec:
  accessModes: [ReadWriteOnce]
  resources:
    requests:
      storage: 10Gi

---
# PostgreSQL Deployment
apiVersion: apps/v1
kind: Deployment
metadata:
  name: postgres
  namespace: apindex
spec:
  replicas: 1
  selector:
    matchLabels:
      app.kubernetes.io/component: database
  template:
    metadata:
      labels:
        app.kubernetes.io/component: database
    spec:
      containers:
        - name: postgres
          image: postgres:16-alpine
          ports: [{containerPort: 5432}]
          env:
            - name: POSTGRES_USER
              valueFrom: {configMapKeyRef: {name: apindex-config, key: POSTGRES_USER}}
            - name: POSTGRES_DB
              valueFrom: {configMapKeyRef: {name: apindex-config, key: POSTGRES_DB}}
            - name: POSTGRES_PASSWORD
              valueFrom: {secretKeyRef: {name: apindex-secrets, key: POSTGRES_PASSWORD}}
          volumeMounts:
            - name: postgres-data
              mountPath: /var/lib/postgresql/data
          resources:
            requests: {memory: "256Mi", cpu: "100m"}
            limits: {memory: "1Gi", cpu: "500m"}
      volumes:
        - name: postgres-data
          persistentVolumeClaim: {claimName: postgres-pvc}

---
# PostgreSQL Service
apiVersion: v1
kind: Service
metadata:
  name: postgres
  namespace: apindex
spec:
  ports: [{port: 5432}]
  selector:
    app.kubernetes.io/component: database

---
# Backend Deployment
apiVersion: apps/v1
kind: Deployment
metadata:
  name: backend
  namespace: apindex
spec:
  replicas: 2
  selector:
    matchLabels:
      app.kubernetes.io/component: backend
  template:
    metadata:
      labels:
        app.kubernetes.io/component: backend
    spec:
      containers:
        - name: backend
          image: apindex/backend:latest
          ports: [{containerPort: 8000}]
          env:
            - name: POSTGRES_HOST
              valueFrom: {configMapKeyRef: {name: apindex-config, key: POSTGRES_HOST}}
            - name: POSTGRES_PORT
              valueFrom: {configMapKeyRef: {name: apindex-config, key: POSTGRES_PORT}}
            - name: POSTGRES_USER
              valueFrom: {configMapKeyRef: {name: apindex-config, key: POSTGRES_USER}}
            - name: POSTGRES_DB
              valueFrom: {configMapKeyRef: {name: apindex-config, key: POSTGRES_DB}}
            - name: POSTGRES_PASSWORD
              valueFrom: {secretKeyRef: {name: apindex-secrets, key: POSTGRES_PASSWORD}}
            - name: SECRET_KEY
              valueFrom: {secretKeyRef: {name: apindex-secrets, key: SECRET_KEY}}
            - name: DEBUG
              valueFrom: {configMapKeyRef: {name: apindex-config, key: DEBUG}}
            - name: INSTANCE_NAME
              valueFrom: {configMapKeyRef: {name: apindex-config, key: INSTANCE_NAME}}
            - name: FIRST_SUPERUSER_EMAIL
              valueFrom: {secretKeyRef: {name: apindex-secrets, key: FIRST_SUPERUSER_EMAIL}}
            - name: FIRST_SUPERUSER_PASSWORD
              valueFrom: {secretKeyRef: {name: apindex-secrets, key: FIRST_SUPERUSER_PASSWORD}}
          livenessProbe:
            httpGet: {path: /health, port: 8000}
            initialDelaySeconds: 30
          readinessProbe:
            httpGet: {path: /health, port: 8000}
            initialDelaySeconds: 10
          resources:
            requests: {memory: "256Mi", cpu: "100m"}
            limits: {memory: "1Gi", cpu: "1000m"}

---
# Backend Service
apiVersion: v1
kind: Service
metadata:
  name: backend
  namespace: apindex
spec:
  ports: [{port: 8000}]
  selector:
    app.kubernetes.io/component: backend

---
# Frontend Deployment
apiVersion: apps/v1
kind: Deployment
metadata:
  name: frontend
  namespace: apindex
spec:
  replicas: 2
  selector:
    matchLabels:
      app.kubernetes.io/component: frontend
  template:
    metadata:
      labels:
        app.kubernetes.io/component: frontend
    spec:
      containers:
        - name: frontend
          image: apindex/frontend:latest
          ports: [{containerPort: 80}]
          env:
            - name: BACKEND_URL
              valueFrom: {configMapKeyRef: {name: apindex-config, key: BACKEND_URL}}
          resources:
            requests: {memory: "64Mi", cpu: "50m"}
            limits: {memory: "256Mi", cpu: "200m"}

---
# Frontend Service
apiVersion: v1
kind: Service
metadata:
  name: frontend
  namespace: apindex
spec:
  ports: [{port: 80}]
  selector:
    app.kubernetes.io/component: frontend

---
# Ingress
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: apindex-ingress
  namespace: apindex
spec:
  rules:
    - host: apindex.example.com  # Change this!
      http:
        paths:
          - path: /
            pathType: Prefix
            backend:
              service:
                name: frontend
                port: {number: 80}

Customization

  • Change apindex.example.com to your domain in the Ingress
  • Update Secret values (generate new base64 values)
  • Adjust resource limits based on your cluster capacity
  • Add TLS configuration to Ingress for HTTPS
  • Configure a StorageClass for the PVC if needed