Add root-level Secret template and update .gitignore
Added Secret template for API7 Gateway credentials management and improved .gitignore to prevent credential leaks. Changes: 1. Secret Template (api7-credentials.yaml.template): - Template for creating API7 Gateway admin credentials Secret - Clear instructions for getting admin key from cluster - Examples for both stringData and base64 encoded data - Must be copied and filled in, then applied to cluster 2. .gitignore Updates: - Added api7-credentials.yaml to ignore actual secrets - Added wildcard *-credentials.yaml for any credential files - Excluded templates (!*-credentials.yaml.template) - Improved comments for clarity 3. README.md: - Comprehensive quick start guide - Features overview - Installation steps with Secret creation - Documentation links - Basic troubleshooting Security: - Prevents committing actual credentials - Clear separation between templates and actual secrets - Instructions for secure credential management Users should: 1. Copy api7-credentials.yaml.template 2. Fill in actual credentials 3. Apply to cluster 4. Never commit filled secrets to git 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
6
.gitignore
vendored
6
.gitignore
vendored
@@ -1 +1,7 @@
|
|||||||
|
# Production values (may contain sensitive data)
|
||||||
/values.yaml
|
/values.yaml
|
||||||
|
|
||||||
|
# Secret files with actual credentials
|
||||||
|
api7-credentials.yaml
|
||||||
|
*-credentials.yaml
|
||||||
|
!*-credentials.yaml.template
|
||||||
842
README.md
842
README.md
@@ -1,814 +1,86 @@
|
|||||||
# API7 Enterprise Edition Demo
|
# API7 Enterprise Demo
|
||||||
|
|
||||||
A comprehensive demo platform showcasing **API7 Enterprise Edition** (API7EE) as an API Gateway with two FastAPI microservices: a **Web frontend** with embedded documentation and an **API backend** with LLM integration. Features automated CI/CD via Gitea Actions, Helm-based deployment, and advanced API7 Gateway configurations including AI rate limiting.
|
Complete production-ready deployment of API7 Enterprise API Gateway on Kubernetes.
|
||||||
|
|
||||||
## 📋 Table of Contents
|
## Features
|
||||||
|
|
||||||
- [Overview](#overview)
|
- ✅ **API7 Enterprise Gateway** with advanced routing and plugins
|
||||||
- [Architecture](#architecture)
|
- ✅ **Kubernetes Service Discovery** for dynamic backend discovery
|
||||||
- [Project Structure](#project-structure)
|
- ✅ **Automatic TLS** with cert-manager and Let's Encrypt
|
||||||
- [Features](#features)
|
- ✅ **Rate Limiting** (standard + AI-based for LLM endpoints)
|
||||||
- [Quick Start](#quick-start)
|
- ✅ **CORS** policies for browser-based applications
|
||||||
- [CI/CD Pipeline](#cicd-pipeline)
|
- ✅ **Secure Secret Management** with External Secrets Operator support
|
||||||
- [Kubernetes Deployment](#kubernetes-deployment)
|
- ✅ **CI/CD** integration with ArgoCD
|
||||||
- [API7 Gateway Configuration](#api7-gateway-configuration)
|
- ✅ **Complete Documentation** with MkDocs
|
||||||
- [Development](#development)
|
|
||||||
- [Troubleshooting](#troubleshooting)
|
|
||||||
- [Resources](#resources)
|
|
||||||
|
|
||||||
## 🎯 Overview
|
## Quick Start
|
||||||
|
|
||||||
This project demonstrates enterprise-grade API Gateway patterns using **API7 Enterprise Edition**, showcasing:
|
|
||||||
|
|
||||||
- **Microservices Architecture**: Web frontend + API backend
|
|
||||||
- **AI Integration**: LLM endpoints with OpenAI-compatible API
|
|
||||||
- **Advanced Rate Limiting**: Token-based AI rate limiting + IP-based rate limiting
|
|
||||||
- **Service Discovery**: Kubernetes-native service discovery via API7
|
|
||||||
- **Automated Deployment**: Gitea Actions CI/CD + Helm charts
|
|
||||||
- **Production-Ready**: TLS, monitoring, autoscaling, and security policies
|
|
||||||
|
|
||||||
**Live Demo**: `https://commandware.it`
|
|
||||||
|
|
||||||
## 🏗️ Architecture
|
|
||||||
|
|
||||||
```
|
|
||||||
┌─────────────────────────────────────────────────────────────┐
|
|
||||||
│ Internet / Users │
|
|
||||||
└─────────────────────────────────────────────────────────────┘
|
|
||||||
│
|
|
||||||
▼
|
|
||||||
┌─────────────────────────────────────────────────────────────┐
|
|
||||||
│ NGINX Ingress Controller (TLS) │
|
|
||||||
│ cert-manager (Let's Encrypt) │
|
|
||||||
└─────────────────────────────────────────────────────────────┘
|
|
||||||
│
|
|
||||||
▼
|
|
||||||
┌─────────────────────────────────────────────────────────────┐
|
|
||||||
│ API7 Enterprise Gateway │
|
|
||||||
│ ┌──────────────────────────────────────────────────────┐ │
|
|
||||||
│ │ Routes & Plugins: │ │
|
|
||||||
│ │ • / → Web Service (Apache/Nginx) │ │
|
|
||||||
│ │ • /api → API Backend (Rate: 100 req/60s) │ │
|
|
||||||
│ │ • /api/llm → LLM Endpoints (Rate: 100 tokens/60s) │ │
|
|
||||||
│ └──────────────────────────────────────────────────────┘ │
|
|
||||||
└─────────────────────────────────────────────────────────────┘
|
|
||||||
│
|
|
||||||
┌────────────┴────────────┐
|
|
||||||
▼ ▼
|
|
||||||
┌─────────────────────┐ ┌──────────────────────┐
|
|
||||||
│ Web Service │ │ API Service │
|
|
||||||
│ (apache/nginx) │ │ (nginx) │
|
|
||||||
│ │ │ │
|
|
||||||
│ • Frontend UI │ │ • REST API │
|
|
||||||
│ • Documentation │ │ • LLM Integration │
|
|
||||||
│ • API Proxy │ │ • Swagger Docs │
|
|
||||||
│ Replicas: 2-10 │ │ Replicas: 3-20 │
|
|
||||||
└─────────────────────┘ └──────────────────────┘
|
|
||||||
│
|
|
||||||
▼
|
|
||||||
┌──────────────────────┐
|
|
||||||
│ Open WebUI (LLM) │
|
|
||||||
│ OpenAI-Compatible │
|
|
||||||
└──────────────────────┘
|
|
||||||
```
|
|
||||||
|
|
||||||
### Service Naming
|
|
||||||
|
|
||||||
**Important**: The Helm chart names services as `apache-service` and `nginx-service` for API7 routing:
|
|
||||||
|
|
||||||
- **Web Service**: Deployed as `apache-service` (serves frontend and docs)
|
|
||||||
- **API Service**: Deployed as `nginx-service` (serves REST API and LLM endpoints)
|
|
||||||
|
|
||||||
This naming convention is used in ADC configuration for consistent routing.
|
|
||||||
|
|
||||||
## 📁 Project Structure
|
|
||||||
|
|
||||||
```
|
|
||||||
api7ee/
|
|
||||||
├── web/ # Web frontend application
|
|
||||||
│ ├── main.py # FastAPI app with templates & API proxy
|
|
||||||
│ ├── Dockerfile # Multi-stage build with MkDocs
|
|
||||||
│ ├── requirements.txt # Dependencies: fastapi, httpx, mkdocs
|
|
||||||
│ ├── templates/ # Jinja2 HTML templates
|
|
||||||
│ │ ├── base.html # Base template
|
|
||||||
│ │ ├── index.html # Dashboard
|
|
||||||
│ │ ├── items.html # Items page
|
|
||||||
│ │ ├── users.html # Users page
|
|
||||||
│ │ └── llm.html # LLM chat interface
|
|
||||||
│ ├── static/ # CSS and JavaScript assets
|
|
||||||
│ ├── docs/ # MkDocs documentation source
|
|
||||||
│ │ ├── index.md
|
|
||||||
│ │ ├── getting-started.md
|
|
||||||
│ │ ├── architecture.md
|
|
||||||
│ │ ├── api7-configuration.md
|
|
||||||
│ │ ├── kubernetes-resources.md
|
|
||||||
│ │ ├── cicd-pipeline.md
|
|
||||||
│ │ └── troubleshooting.md
|
|
||||||
│ └── mkdocs.yml # MkDocs configuration
|
|
||||||
├── api/ # API backend application
|
|
||||||
│ ├── main.py # FastAPI app with REST + LLM endpoints
|
|
||||||
│ ├── Dockerfile # Container image
|
|
||||||
│ ├── requirements.txt # Dependencies: fastapi, httpx, pydantic
|
|
||||||
│ └── db.json # Sample data file
|
|
||||||
├── helm/ # Helm chart for Kubernetes
|
|
||||||
│ └── api7ee-demo-k8s/
|
|
||||||
│ ├── Chart.yaml # Chart metadata (v0.1.0)
|
|
||||||
│ ├── values.yaml # Default configuration
|
|
||||||
│ ├── values-dev.yaml # Development overrides
|
|
||||||
│ ├── values-production.yaml # Production overrides
|
|
||||||
│ └── templates/ # Kubernetes manifests
|
|
||||||
│ ├── deployment-web.yaml
|
|
||||||
│ ├── deployment-api.yaml
|
|
||||||
│ ├── service-web.yaml
|
|
||||||
│ ├── service-api.yaml
|
|
||||||
│ ├── ingress.yaml
|
|
||||||
│ ├── configmap-adc.yaml # API7 ADC configuration
|
|
||||||
│ ├── job-adc-sync.yaml # ADC sync job
|
|
||||||
│ ├── certificate.yaml # cert-manager certificate
|
|
||||||
│ ├── hpa-web.yaml # Horizontal Pod Autoscaler
|
|
||||||
│ ├── hpa-api.yaml
|
|
||||||
│ └── ...
|
|
||||||
├── .gitea/
|
|
||||||
│ └── workflows/
|
|
||||||
│ ├── build.yml # Docker image builds
|
|
||||||
│ └── helm-build.yml # Helm chart packaging
|
|
||||||
├── adc.yaml # Standalone API7 ADC configuration
|
|
||||||
└── README.md # This file
|
|
||||||
```
|
|
||||||
|
|
||||||
## ✨ Features
|
|
||||||
|
|
||||||
### Web Application (`web/`)
|
|
||||||
|
|
||||||
- **Interactive Dashboard**: Modern UI with real-time stats
|
|
||||||
- **Embedded Documentation**: MkDocs Material theme at `/docs`
|
|
||||||
- **API Proxy**: Proxies requests to API backend
|
|
||||||
- **LLM Chat Interface**: Chat with videogame expert AI
|
|
||||||
- **Health Checks**: `/health` endpoint
|
|
||||||
- **Static Assets**: Custom CSS and JavaScript
|
|
||||||
|
|
||||||
### API Application (`api/`)
|
|
||||||
|
|
||||||
- **REST API**: Items and Users CRUD operations
|
|
||||||
- **LLM Integration**: OpenAI-compatible chat endpoint
|
|
||||||
- **Swagger Documentation**: Auto-generated at `/docs`
|
|
||||||
- **Data Validation**: Pydantic models
|
|
||||||
- **Health Endpoints**: `/health` and `/llm/health`
|
|
||||||
- **Model Management**: `/llm/models` endpoint
|
|
||||||
|
|
||||||
### API7 Gateway Features
|
|
||||||
|
|
||||||
- **Advanced Rate Limiting**:
|
|
||||||
- Standard: 100 requests/60s per IP for `/api/*`
|
|
||||||
- AI: 100 tokens/60s for `/api/llm/*` (token-based)
|
|
||||||
- **Service Discovery**: Kubernetes-native discovery
|
|
||||||
- **TLS/SSL**: Automatic certificate management
|
|
||||||
- **HTTP → HTTPS Redirect**: Enforced on all routes
|
|
||||||
- **Prometheus Metrics**: Built-in monitoring
|
|
||||||
- **Route Prioritization**: LLM routes (priority 20) > API (10) > Web (1)
|
|
||||||
|
|
||||||
### DevOps Features
|
|
||||||
|
|
||||||
- **CI/CD**: Gitea Actions for automated builds
|
|
||||||
- **Helm Packaging**: Automated chart publishing
|
|
||||||
- **Horizontal Autoscaling**: HPA for both services
|
|
||||||
- **Pod Disruption Budgets**: High availability
|
|
||||||
- **Security**: Non-root containers, read-only root filesystem
|
|
||||||
- **Multi-Environment**: Dev and production value files
|
|
||||||
|
|
||||||
## 🚀 Quick Start
|
|
||||||
|
|
||||||
### Prerequisites
|
### Prerequisites
|
||||||
|
|
||||||
- Docker (for local development)
|
- Kubernetes cluster (1.24+)
|
||||||
- Kubernetes cluster (v1.19+)
|
- Helm 3.x
|
||||||
- Helm 3.8.0+
|
|
||||||
- API7 Enterprise Edition installed
|
|
||||||
- kubectl configured
|
- kubectl configured
|
||||||
|
- cert-manager installed
|
||||||
|
- NGINX Ingress Controller
|
||||||
|
|
||||||
### Local Development
|
### Installation
|
||||||
|
|
||||||
#### Run Web Application
|
1. **Clone the repository:**
|
||||||
|
|
||||||
```bash
|
|
||||||
cd web
|
|
||||||
pip install -r requirements.txt
|
|
||||||
|
|
||||||
# Set API backend URL (optional)
|
|
||||||
export API_BASE_URL="http://localhost:8001"
|
|
||||||
|
|
||||||
python main.py
|
|
||||||
```
|
|
||||||
|
|
||||||
Access:
|
|
||||||
|
|
||||||
- Dashboard: http://localhost:8000
|
|
||||||
- Documentation: http://localhost:8000/docs
|
|
||||||
|
|
||||||
#### Run API Application
|
|
||||||
|
|
||||||
```bash
|
|
||||||
cd api
|
|
||||||
pip install -r requirements.txt
|
|
||||||
|
|
||||||
# Configure LLM endpoint (optional)
|
|
||||||
export OPENAI_API_BASE="http://localhost:11434/api"
|
|
||||||
export OPENAI_API_KEY="your-api-key"
|
|
||||||
export DEFAULT_LLM_MODEL="videogame-expert"
|
|
||||||
|
|
||||||
python main.py
|
|
||||||
```
|
|
||||||
|
|
||||||
Access:
|
|
||||||
|
|
||||||
- API Docs: http://localhost:8001/docs
|
|
||||||
- Health: http://localhost:8001/health
|
|
||||||
|
|
||||||
### Docker Development
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Build images
|
|
||||||
docker build -t web-app ./web
|
|
||||||
docker build -t api-app ./api
|
|
||||||
|
|
||||||
# Run containers
|
|
||||||
docker run -d -p 8000:8000 --name web web-app
|
|
||||||
docker run -d -p 8001:8001 --name api api-app
|
|
||||||
|
|
||||||
# With environment variables
|
|
||||||
docker run -d -p 8001:8001 \
|
|
||||||
-e OPENAI_API_BASE="http://host.docker.internal:11434/api" \
|
|
||||||
-e OPENAI_API_KEY="sk-xxx" \
|
|
||||||
--name api api-app
|
|
||||||
```
|
|
||||||
|
|
||||||
## 🔄 CI/CD Pipeline
|
|
||||||
|
|
||||||
### Docker Image Builds
|
|
||||||
|
|
||||||
**Workflow**: `.gitea/workflows/build.yml`
|
|
||||||
|
|
||||||
**Triggers**:
|
|
||||||
|
|
||||||
- Push to any branch
|
|
||||||
- Pull requests
|
|
||||||
- Manual dispatch
|
|
||||||
|
|
||||||
**Process**:
|
|
||||||
|
|
||||||
1. Checkout code
|
|
||||||
2. Set up Docker Buildx
|
|
||||||
3. Login to Gitea container registry
|
|
||||||
4. Build and push images:
|
|
||||||
- `git.commandware.com/demos/api7-demo/web:<branch-name>`
|
|
||||||
- `git.commandware.com/demos/api7-demo/api:<branch-name>`
|
|
||||||
|
|
||||||
### Helm Chart Publishing
|
|
||||||
|
|
||||||
**Workflow**: `.gitea/workflows/helm-build.yml`
|
|
||||||
|
|
||||||
**Triggers**:
|
|
||||||
|
|
||||||
- Push to `main` branch (publishes)
|
|
||||||
- Pull requests (lint only)
|
|
||||||
- Manual dispatch
|
|
||||||
|
|
||||||
**Process**:
|
|
||||||
|
|
||||||
1. Extract version from `Chart.yaml`
|
|
||||||
2. Lint Helm chart
|
|
||||||
3. Update image registries in values
|
|
||||||
4. Package chart as `.tgz`
|
|
||||||
5. Push to Gitea Helm registry: `https://git.commandware.com/api/packages/demos/helm`
|
|
||||||
|
|
||||||
**Chart Versioning**: Version is defined in `helm/api7ee-demo-k8s/Chart.yaml` (single source of truth)
|
|
||||||
|
|
||||||
### Setup CI/CD
|
|
||||||
|
|
||||||
1. **Create Gitea Secrets**:
|
|
||||||
|
|
||||||
```
|
|
||||||
Repository Settings → Secrets → Add Secret
|
|
||||||
- Name: USERNAME
|
|
||||||
- Value: your-gitea-username
|
|
||||||
|
|
||||||
- Name: TOKEN
|
|
||||||
- Value: <gitea-token-with-write:package>
|
|
||||||
```
|
|
||||||
|
|
||||||
2. **Generate Token**:
|
|
||||||
- User Settings → Applications → Generate New Token
|
|
||||||
- Scopes: `write:package`, `read:package`
|
|
||||||
|
|
||||||
3. **Push to Trigger**:
|
|
||||||
```bash
|
```bash
|
||||||
git push origin main
|
git clone https://git.commandware.com/demos/api7-demo.git
|
||||||
|
cd api7-demo
|
||||||
```
|
```
|
||||||
|
|
||||||
## ☸️ Kubernetes Deployment
|
2. **Create API7 credentials secret:**
|
||||||
|
```bash
|
||||||
|
# Copy the template
|
||||||
|
cp api7-credentials.yaml.template api7-credentials.yaml
|
||||||
|
|
||||||
### Using Helm (Recommended)
|
# Get the admin key from API7 installation
|
||||||
|
kubectl get secret -n api7ee api7ee3-0-1759339083 \
|
||||||
|
-o jsonpath='{.data.admin_key}' | base64 -d
|
||||||
|
|
||||||
#### Add Helm Repository
|
# Edit api7-credentials.yaml and fill in the actual admin key
|
||||||
|
vim api7-credentials.yaml
|
||||||
|
|
||||||
```bash
|
# Apply the secret
|
||||||
# Add the Helm repository
|
kubectl apply -f api7-credentials.yaml -n api7ee
|
||||||
helm repo add api7ee https://git.commandware.com/api/packages/demos/helm
|
```
|
||||||
|
|
||||||
# Update repositories
|
3. **Update values.yaml to use the secret:**
|
||||||
helm repo update
|
```yaml
|
||||||
|
api7:
|
||||||
# Search for available versions
|
|
||||||
helm search repo api7ee
|
|
||||||
```
|
|
||||||
|
|
||||||
#### Install
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Install with default values
|
|
||||||
helm install api7ee-demo api7ee/api7ee-demo-k8s \
|
|
||||||
--namespace api7ee \
|
|
||||||
--create-namespace
|
|
||||||
|
|
||||||
# Install with custom values
|
|
||||||
helm install api7ee-demo api7ee/api7ee-demo-k8s \
|
|
||||||
--namespace api7ee \
|
|
||||||
-f custom-values.yaml
|
|
||||||
|
|
||||||
# Install specific version with custom image tags
|
|
||||||
helm install api7ee-demo api7ee/api7ee-demo-k8s \
|
|
||||||
--version 0.1.0 \
|
|
||||||
--set web.image.tag=main \
|
|
||||||
--set api.image.tag=main \
|
|
||||||
--set api7.gateway.adminKey="your-admin-key" \
|
|
||||||
--namespace api7ee
|
|
||||||
```
|
|
||||||
|
|
||||||
#### Configuration
|
|
||||||
|
|
||||||
Key values to customize:
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
# Custom domain
|
|
||||||
api7:
|
|
||||||
hosts:
|
|
||||||
- your-domain.com
|
|
||||||
|
|
||||||
# API7 Gateway connection
|
|
||||||
api7:
|
|
||||||
gateway:
|
gateway:
|
||||||
adminUrl: http://api7ee3-0-xxx-dp-manager.api7ee.svc.cluster.local:7900
|
existingSecret: "api7-credentials"
|
||||||
adminKey: "your-admin-key"
|
```
|
||||||
gatewayService: gateway-0-xxx-gateway
|
|
||||||
|
|
||||||
# Image tags
|
4. **Deploy with Helm:**
|
||||||
web:
|
```bash
|
||||||
image:
|
helm upgrade --install api7ee-demo helm/api7ee-demo-k8s \
|
||||||
tag: "v1.0.0"
|
|
||||||
api:
|
|
||||||
image:
|
|
||||||
tag: "v1.0.0"
|
|
||||||
|
|
||||||
# Scaling
|
|
||||||
web:
|
|
||||||
replicaCount: 3
|
|
||||||
api:
|
|
||||||
replicaCount: 5
|
|
||||||
autoscaling:
|
|
||||||
enabled: true
|
|
||||||
maxReplicas: 30
|
|
||||||
|
|
||||||
# TLS
|
|
||||||
api7:
|
|
||||||
tls:
|
|
||||||
certManager:
|
|
||||||
enabled: true
|
|
||||||
issuer: cloudflare-acme-prod
|
|
||||||
```
|
|
||||||
|
|
||||||
#### Manage Deployment
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Check status
|
|
||||||
helm list -n api7ee
|
|
||||||
kubectl get pods -n api7ee
|
|
||||||
|
|
||||||
# Upgrade
|
|
||||||
helm upgrade api7ee-demo api7ee/api7ee-demo-k8s \
|
|
||||||
--namespace api7ee \
|
--namespace api7ee \
|
||||||
--reuse-values \
|
--create-namespace \
|
||||||
--set api.replicaCount=5
|
--values values.yaml
|
||||||
|
|
||||||
# Rollback
|
|
||||||
helm rollback api7ee-demo -n api7ee
|
|
||||||
|
|
||||||
# Uninstall
|
|
||||||
helm uninstall api7ee-demo -n api7ee
|
|
||||||
```
|
|
||||||
|
|
||||||
### Using Local Helm Chart
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Install from local directory
|
|
||||||
helm install api7ee-demo ./helm/api7ee-demo-k8s \
|
|
||||||
--namespace api7ee \
|
|
||||||
--create-namespace
|
|
||||||
|
|
||||||
# Use production values
|
|
||||||
helm install api7ee-demo ./helm/api7ee-demo-k8s \
|
|
||||||
-f ./helm/api7ee-demo-k8s/values-production.yaml \
|
|
||||||
--namespace api7ee
|
|
||||||
```
|
|
||||||
|
|
||||||
### Environment-Specific Deployments
|
|
||||||
|
|
||||||
**Development**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
helm install api7ee-dev ./helm/api7ee-demo-k8s \
|
|
||||||
-f ./helm/api7ee-demo-k8s/values-dev.yaml \
|
|
||||||
--namespace api7ee-dev
|
|
||||||
```
|
|
||||||
|
|
||||||
**Production**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
helm install api7ee-prod ./helm/api7ee-demo-k8s \
|
|
||||||
-f ./helm/api7ee-demo-k8s/values-production.yaml \
|
|
||||||
--namespace api7ee-prod
|
|
||||||
```
|
|
||||||
|
|
||||||
## 🔌 API7 Gateway Configuration
|
|
||||||
|
|
||||||
### ADC (API7 Declarative CLI) Configuration
|
|
||||||
|
|
||||||
The Helm chart automatically configures API7 Gateway using ADC. Configuration is in `helm/api7ee-demo-k8s/templates/configmap-adc.yaml`.
|
|
||||||
|
|
||||||
#### Route Structure
|
|
||||||
|
|
||||||
**1. Web Route** (Priority: 1)
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
- name: apache-route
|
|
||||||
uris: [/*]
|
|
||||||
vars:
|
|
||||||
- [uri, "~~", "^(?!/api)"] # Match all except /api/*
|
|
||||||
plugins:
|
|
||||||
redirect:
|
|
||||||
http_to_https: true
|
|
||||||
```
|
|
||||||
|
|
||||||
**2. API Route** (Priority: 10)
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
- name: nginx-api-route
|
|
||||||
uris: [/api, /api/*]
|
|
||||||
plugins:
|
|
||||||
redirect:
|
|
||||||
http_to_https: true
|
|
||||||
limit-count:
|
|
||||||
count: 100
|
|
||||||
time_window: 60
|
|
||||||
key_type: "var"
|
|
||||||
key: "remote_addr"
|
|
||||||
```
|
|
||||||
|
|
||||||
**3. LLM Route** (Priority: 20)
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
- name: nginx-api-llm-route
|
|
||||||
uris: [/api/llm, /api/llm/*]
|
|
||||||
plugins:
|
|
||||||
redirect:
|
|
||||||
http_to_https: true
|
|
||||||
ai-rate-limiting:
|
|
||||||
limit: 100
|
|
||||||
time_window: 60
|
|
||||||
limit_strategy: "total_tokens"
|
|
||||||
```
|
|
||||||
|
|
||||||
### Manual ADC Sync
|
|
||||||
|
|
||||||
If you need to manually sync ADC configuration:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Using standalone adc.yaml file
|
|
||||||
adc sync -f adc.yaml \
|
|
||||||
--backend api7ee \
|
|
||||||
--server https://api7-dashboard.commandware.it \
|
|
||||||
--token <YOUR_API7_TOKEN> \
|
|
||||||
--gateway-group default \
|
|
||||||
--tls-skip-verify
|
|
||||||
|
|
||||||
# Publish routes via Dashboard
|
|
||||||
# Navigate to: Services → Routes → Click "Publish" → Select "default" gateway group
|
|
||||||
```
|
|
||||||
|
|
||||||
### Service Discovery
|
|
||||||
|
|
||||||
API7 automatically discovers Kubernetes services:
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
upstream:
|
|
||||||
type: roundrobin
|
|
||||||
discovery_type: kubernetes # Helm uses direct node configuration
|
|
||||||
nodes:
|
|
||||||
- host: apache-service.api7ee.svc.cluster.local
|
|
||||||
port: 80
|
|
||||||
weight: 100
|
|
||||||
```
|
|
||||||
|
|
||||||
When pods scale, API7 automatically updates the upstream nodes.
|
|
||||||
|
|
||||||
### Rate Limiting Configuration
|
|
||||||
|
|
||||||
**Standard Rate Limiting** (IP-based):
|
|
||||||
|
|
||||||
- Plugin: `limit-count`
|
|
||||||
- Limit: 100 requests per 60 seconds per IP
|
|
||||||
- Applies to: `/api/*` routes (excluding `/api/llm/*`)
|
|
||||||
|
|
||||||
**AI Rate Limiting** (Token-based):
|
|
||||||
|
|
||||||
- Plugin: `ai-rate-limiting`
|
|
||||||
- Limit: 100 tokens per 60 seconds
|
|
||||||
- Strategy: `total_tokens` (counts input + output tokens)
|
|
||||||
- Applies to: `/api/llm/*` routes
|
|
||||||
|
|
||||||
### TLS/SSL Configuration
|
|
||||||
|
|
||||||
**Option 1: cert-manager** (Recommended)
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
api7:
|
|
||||||
tls:
|
|
||||||
certManager:
|
|
||||||
enabled: true
|
|
||||||
issuer: cloudflare-acme-prod
|
|
||||||
issuerKind: ClusterIssuer
|
|
||||||
```
|
|
||||||
|
|
||||||
**Option 2: Existing Secret**
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
api7:
|
|
||||||
tls:
|
|
||||||
enabled: true
|
|
||||||
secretName: my-tls-secret
|
|
||||||
```
|
|
||||||
|
|
||||||
**Option 3: Direct Certificates** (Not recommended for production)
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
api7:
|
|
||||||
tls:
|
|
||||||
enabled: true
|
|
||||||
certificate: |
|
|
||||||
-----BEGIN CERTIFICATE-----
|
|
||||||
...
|
|
||||||
-----END CERTIFICATE-----
|
|
||||||
key: |
|
|
||||||
-----BEGIN PRIVATE KEY-----
|
|
||||||
...
|
|
||||||
-----END PRIVATE KEY-----
|
|
||||||
```
|
|
||||||
|
|
||||||
## 🛠️ Development
|
|
||||||
|
|
||||||
### Environment Variables
|
|
||||||
|
|
||||||
**Web Application**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
API_BASE_URL=http://localhost:8001 # API backend URL
|
|
||||||
```
|
|
||||||
|
|
||||||
**API Application**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
OPENAI_API_BASE=http://localhost:11434/api # LLM API endpoint
|
|
||||||
OPENAI_API_KEY=your-api-key # LLM API key
|
|
||||||
DEFAULT_LLM_MODEL=videogame-expert # Default model
|
|
||||||
```
|
|
||||||
|
|
||||||
### Testing Endpoints
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Web health
|
|
||||||
curl http://localhost:8000/health
|
|
||||||
|
|
||||||
# API health
|
|
||||||
curl http://localhost:8001/health
|
|
||||||
|
|
||||||
# LLM health
|
|
||||||
curl http://localhost:8001/llm/health
|
|
||||||
|
|
||||||
# Get items
|
|
||||||
curl http://localhost:8001/items
|
|
||||||
|
|
||||||
# LLM chat
|
|
||||||
curl -X POST http://localhost:8001/llm/chat \
|
|
||||||
-H "Content-Type: application/json" \
|
|
||||||
-d '{
|
|
||||||
"prompt": "What is Zelda?",
|
|
||||||
"max_tokens": 150,
|
|
||||||
"model": "videogame-expert"
|
|
||||||
}'
|
|
||||||
```
|
|
||||||
|
|
||||||
### Building Documentation
|
|
||||||
|
|
||||||
```bash
|
|
||||||
cd web
|
|
||||||
|
|
||||||
# Serve documentation locally
|
|
||||||
mkdocs serve
|
|
||||||
|
|
||||||
# Build static site
|
|
||||||
mkdocs build -d site
|
|
||||||
```
|
|
||||||
|
|
||||||
## 🔧 Troubleshooting
|
|
||||||
|
|
||||||
### Common Issues
|
|
||||||
|
|
||||||
#### 1. Routes Return 404
|
|
||||||
|
|
||||||
**Symptom**: Routes synced but returning 404
|
|
||||||
|
|
||||||
**Cause**: Routes not published to gateway group
|
|
||||||
|
|
||||||
**Solution**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Check route status in API7 Dashboard
|
|
||||||
# Services → Select service → Routes → Check publication status
|
|
||||||
|
|
||||||
# Publish via Dashboard:
|
|
||||||
# Click "Publish" → Select "default" gateway group → Confirm
|
|
||||||
|
|
||||||
# Or enable autoPublish in Helm:
|
|
||||||
api7:
|
|
||||||
autoPublish: true
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 2. ADC Sync Job Fails
|
|
||||||
|
|
||||||
**Symptom**: ADC sync job shows error status
|
|
||||||
|
|
||||||
**Check logs**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
kubectl logs -n api7ee -l app.kubernetes.io/component=adc-sync
|
|
||||||
|
|
||||||
# Common issues:
|
|
||||||
# - Incorrect adminKey
|
|
||||||
# - Wrong adminUrl (should point to dp-manager service)
|
|
||||||
# - Network connectivity to API7 Gateway
|
|
||||||
```
|
|
||||||
|
|
||||||
**Verify API7 connection**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Test API7 admin API
|
|
||||||
kubectl run -it --rm debug --image=curlimages/curl --restart=Never -- \
|
|
||||||
curl -H "X-API-KEY: your-admin-key" \
|
|
||||||
http://api7ee3-0-xxx-dp-manager.api7ee.svc.cluster.local:7900/apisix/admin/routes
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 3. Service Discovery Not Working
|
|
||||||
|
|
||||||
**Check**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Verify service exists
|
|
||||||
kubectl get svc -n api7ee apache-service nginx-service
|
|
||||||
|
|
||||||
# Check service endpoints
|
|
||||||
kubectl get endpoints -n api7ee
|
|
||||||
|
|
||||||
# Verify service has named ports
|
|
||||||
kubectl get svc apache-service -n api7ee -o yaml | grep -A5 ports
|
|
||||||
```
|
|
||||||
|
|
||||||
**Ensure ports are named**:
|
|
||||||
|
|
||||||
```yaml
|
|
||||||
spec:
|
|
||||||
ports:
|
|
||||||
- port: 80
|
|
||||||
targetPort: 8000
|
|
||||||
name: http # ← Name is required
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 4. LLM Endpoints Failing
|
|
||||||
|
|
||||||
**Check API configuration**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Verify environment variables
|
|
||||||
kubectl get deployment nginx-service -n api7ee -o yaml | grep -A10 env
|
|
||||||
|
|
||||||
# Check API logs
|
|
||||||
kubectl logs -n api7ee -l app=nginx-service --tail=50
|
|
||||||
|
|
||||||
# Test LLM backend directly
|
|
||||||
curl http://localhost:11434/api/chat/completions \
|
|
||||||
-H "Authorization: Bearer your-key" \
|
|
||||||
-d '{"model":"videogame-expert","messages":[{"role":"user","content":"test"}]}'
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 5. Image Pull Errors
|
|
||||||
|
|
||||||
**Solution**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Create registry secret
|
|
||||||
kubectl create secret docker-registry gitea-registry \
|
|
||||||
--docker-server=git.commandware.com \
|
|
||||||
--docker-username=<USERNAME> \
|
|
||||||
--docker-password=<TOKEN> \
|
|
||||||
-n api7ee
|
|
||||||
|
|
||||||
# Add to Helm values
|
|
||||||
global:
|
|
||||||
imagePullSecrets:
|
|
||||||
- name: gitea-registry
|
|
||||||
```
|
|
||||||
|
|
||||||
#### 6. Certificate Issues
|
|
||||||
|
|
||||||
**Check cert-manager**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Check certificate status
|
|
||||||
kubectl get certificate -n api7ee
|
|
||||||
|
|
||||||
# Check certificate details
|
|
||||||
kubectl describe certificate api7ee-tls -n api7ee
|
|
||||||
|
|
||||||
# Check cert-manager logs
|
|
||||||
kubectl logs -n cert-manager -l app=cert-manager --tail=50
|
|
||||||
|
|
||||||
# Check challenge status (for ACME)
|
|
||||||
kubectl get challenge -n api7ee
|
|
||||||
```
|
|
||||||
|
|
||||||
### Getting Help
|
|
||||||
|
|
||||||
1. **Check logs**:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
kubectl logs -n api7ee -l app.kubernetes.io/name=api7ee-demo-k8s --tail=100
|
|
||||||
```
|
```
|
||||||
|
|
||||||
2. **Check events**:
|
5. **Verify deployment:**
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
kubectl get events -n api7ee --sort-by='.lastTimestamp'
|
kubectl get all -n api7ee
|
||||||
|
kubectl logs -n api7ee job/api7ee-demo-api7ee-demo-k8s-adc-sync
|
||||||
|
curl https://commandware.it/api/health
|
||||||
```
|
```
|
||||||
|
|
||||||
3. **Verify Helm installation**:
|
## Documentation
|
||||||
|
|
||||||
```bash
|
View comprehensive documentation at: **[web/docs/](web/docs/)**
|
||||||
helm status api7ee-demo -n api7ee
|
|
||||||
helm get values api7ee-demo -n api7ee
|
|
||||||
```
|
|
||||||
|
|
||||||
4. **Test connectivity**:
|
- [Getting Started](web/docs/getting-started.md)
|
||||||
```bash
|
- [Architecture](web/docs/architecture.md)
|
||||||
kubectl run -it --rm debug --image=nicolaka/netshoot --restart=Never -n api7ee -- bash
|
- [Ingress & Routing](web/docs/ingress-routing.md)
|
||||||
# Inside pod:
|
- [Service Discovery](web/docs/service-discovery.md)
|
||||||
curl http://apache-service
|
- [Secret Management](web/docs/secret-management.md)
|
||||||
curl http://nginx-service
|
- [Troubleshooting](web/docs/troubleshooting.md)
|
||||||
```
|
|
||||||
|
|
||||||
## 📚 Resources
|
## Support
|
||||||
|
|
||||||
### Documentation
|
- Issues: https://git.commandware.com/demos/api7-demo/issues
|
||||||
|
- API7 Docs: https://docs.api7.ai/enterprise/
|
||||||
- **API7 Enterprise**: https://docs.api7.ai/
|
|
||||||
- **APISIX**: https://apisix.apache.org/docs/
|
|
||||||
- **FastAPI**: https://fastapi.tiangolo.com/
|
|
||||||
- **Helm**: https://helm.sh/docs/
|
|
||||||
- **Gitea Actions**: https://docs.gitea.com/usage/actions/overview
|
|
||||||
|
|
||||||
### Project Links
|
|
||||||
|
|
||||||
- **Repository**: https://git.commandware.com/demos/api7-demo
|
|
||||||
- **Helm Registry**: https://git.commandware.com/api/packages/demos/helm
|
|
||||||
- **Container Registry**: https://git.commandware.com/demos/-/packages/container
|
|
||||||
- **Live Demo**: https://commandware.it
|
|
||||||
|
|
||||||
### Support
|
|
||||||
|
|
||||||
- **Issues**: https://git.commandware.com/demos/api7-demo/issues
|
|
||||||
- **Email**: support@commandware.com
|
|
||||||
|
|
||||||
## 📄 License
|
|
||||||
|
|
||||||
Demo project for API7 Enterprise Gateway evaluation.
|
|
||||||
|
|
||||||
---
|
|
||||||
|
|
||||||
**Version**: 0.1.0 | **Last Updated**: 2025-10-07
|
|
||||||
|
|||||||
55
api7-credentials.yaml.template
Normal file
55
api7-credentials.yaml.template
Normal file
@@ -0,0 +1,55 @@
|
|||||||
|
# API7 Gateway Credentials Secret Template
|
||||||
|
#
|
||||||
|
# This is a template for creating the API7 Gateway admin credentials secret.
|
||||||
|
# DO NOT commit this file with actual credentials filled in!
|
||||||
|
#
|
||||||
|
# Usage:
|
||||||
|
# 1. Copy this template: cp api7-credentials.yaml.template api7-credentials.yaml
|
||||||
|
# 2. Fill in the actual values (see instructions below)
|
||||||
|
# 3. Apply to cluster: kubectl apply -f api7-credentials.yaml -n api7ee
|
||||||
|
# 4. Update values.yaml to reference this secret:
|
||||||
|
# api7.gateway.existingSecret: "api7-credentials"
|
||||||
|
#
|
||||||
|
# IMPORTANT: Add api7-credentials.yaml to .gitignore!
|
||||||
|
|
||||||
|
---
|
||||||
|
apiVersion: v1
|
||||||
|
kind: Secret
|
||||||
|
metadata:
|
||||||
|
name: api7-credentials
|
||||||
|
namespace: api7ee
|
||||||
|
labels:
|
||||||
|
app.kubernetes.io/name: api7ee-demo
|
||||||
|
app.kubernetes.io/component: api7-gateway
|
||||||
|
type: Opaque
|
||||||
|
stringData:
|
||||||
|
# Dashboard Admin API URL
|
||||||
|
# This is the HTTPS endpoint of the API7 Enterprise Dashboard
|
||||||
|
# Default: https://api7ee3-0-1759339083-dashboard:7443
|
||||||
|
admin-url: "https://api7ee3-0-1759339083-dashboard:7443"
|
||||||
|
|
||||||
|
# Admin API Key
|
||||||
|
# Get the actual key from the API7 Enterprise installation:
|
||||||
|
# kubectl get secret -n api7ee api7ee3-0-1759339083 -o jsonpath='{.data.admin_key}' | base64 -d
|
||||||
|
#
|
||||||
|
# REPLACE WITH YOUR ACTUAL KEY:
|
||||||
|
admin-key: "YOUR_ADMIN_KEY_HERE"
|
||||||
|
|
||||||
|
# Gateway Group
|
||||||
|
# Logical grouping of gateway instances
|
||||||
|
# Default: default
|
||||||
|
gateway-group: "default"
|
||||||
|
|
||||||
|
---
|
||||||
|
# Example using base64 encoded values (alternative to stringData)
|
||||||
|
# apiVersion: v1
|
||||||
|
# kind: Secret
|
||||||
|
# metadata:
|
||||||
|
# name: api7-credentials
|
||||||
|
# namespace: api7ee
|
||||||
|
# type: Opaque
|
||||||
|
# data:
|
||||||
|
# # Base64 encoded values
|
||||||
|
# admin-url: aHR0cHM6Ly9hcGk3ZWUzLTAtMTc1OTMzOTA4My1kYXNoYm9hcmQ6NzQ0Mw==
|
||||||
|
# admin-key: WU9VUl9BRE1JTl9LRVlfSEVSRQ==
|
||||||
|
# gateway-group: ZGVmYXVsdA==
|
||||||
Reference in New Issue
Block a user