Files
geutebruck-api/docs/architecture.md
Geutebruck API Developer 733b3b924a Phase 1 Complete: Project Setup & Configuration
Completed Tasks (T001-T010):
-  Project structure created (src/, tests/, docs/, scripts/)
-  Python dependencies defined (requirements.txt)
-  C# SDK Bridge project initialized (.csproj)
-  Configuration template (.env.example)
-  Database migration config (alembic.ini)
-  Code quality tools (pyproject.toml with ruff, black, mypy)
-  Development setup script (setup_dev_environment.ps1)
-  Service startup script (start_services.ps1)
-  Architecture documentation (docs/architecture.md)
-  Revised MVP tasks (tasks-revised-mvp.md - 84 tasks focused on cross-switching)

MVP Scope Refined:
- Focus: Cross-switching control for GSCView viewers
- NO recordings, NO analytics, NO LPR in MVP
- REST API only, no UI needed
- Phase 2: GeViSet configuration management

Ready for Phase 2: SDK Bridge Foundation

🤖 Generated with Claude Code (https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2025-12-09 08:25:26 +01:00

498 lines
13 KiB
Markdown

# Geutebruck Cross-Switching API - Architecture
**Version**: 1.0.0 (MVP)
**Last Updated**: 2025-12-08
**Status**: In Development
---
## Overview
The Geutebruck Cross-Switching API provides a modern REST API for controlling video routing between cameras (video inputs) and monitors/viewers (video outputs) in Geutebruck surveillance systems. The system acts as a bridge between the native GeViScope/GeViSoft SDK and modern web/mobile applications.
**Core Functionality**:
- 🔐 User authentication with JWT tokens
- 📹 Camera discovery and management
- 🖥️ Monitor/viewer discovery and status
- 🔀 Cross-switching operations (route camera to monitor)
- 📊 Routing state tracking and audit logging
---
## System Architecture
### High-Level Architecture
```
┌─────────────────┐
│ Client Apps │ (Postman, curl, custom apps)
└────────┬────────┘
│ HTTP/REST
┌─────────────────┐
│ FastAPI Server │ (Python 3.11)
│ Port: 8000 │
└────────┬────────┘
┌────┴────┬───────────┬──────────┐
│ │ │ │
▼ ▼ ▼ ▼
┌────────┐ ┌────────┐ ┌────────┐ ┌─────────┐
│ PostgreSQL│ │ Redis │ │SDK Bridge│ │Auth/JWT │
│ Port:5432│ │Port:6379│ │Port:50051│ │ Service │
└─────────┘ └────────┘ └────┬───┘ └─────────┘
│ gRPC
┌──────────────┐
│ GeViScope │
│ SDK (.NET) │
└──────┬───────┘
│ TCP/IP
┌──────────────┐
│ GeViServer │
│ Port: 7700+ │
└──────┬───────┘
┌────────┴────────┐
▼ ▼
┌──────────┐ ┌──────────┐
│ Cameras │ │ GSCView │
│ (Inputs) │ │ Viewers │
└──────────┘ └──────────┘
```
---
## Component Details
### 1. FastAPI Server (Python)
**Purpose**: REST API layer handling HTTP requests, authentication, and business logic
**Technology Stack**:
- Python 3.11+
- FastAPI (web framework)
- SQLAlchemy (ORM)
- Pydantic (validation)
- PyJWT (authentication)
**Key Responsibilities**:
- Accept HTTP REST requests from clients
- Authenticate users and generate JWT tokens
- Validate request data
- Communicate with SDK Bridge via gRPC
- Store routing state in PostgreSQL
- Cache camera/monitor lists in Redis
- Audit log all operations
- Return HTTP responses to clients
**Port**: 8000
---
### 2. SDK Bridge (C# .NET 8.0)
**Purpose**: gRPC service that wraps the GeViScope SDK, translating between modern gRPC and legacy SDK
**Technology Stack**:
- C# .NET 8.0
- Grpc.AspNetCore
- GeViScope SDK (.NET Framework 4.8 DLL)
- Serilog (logging)
**Key Responsibilities**:
- Connect to GeViServer using GeViScope SDK
- Enumerate cameras (GetFirstVideoInput / GetNextVideoInput)
- Enumerate monitors (GetFirstVideoOutput / GetNextVideoOutput)
- Execute cross-switching (CrossSwitch action)
- Clear monitors (ClearVideoOutput action)
- Translate SDK errors to gRPC status codes
- Maintain connection health with retry logic
**Why Separate Service?**:
- ✅ Isolates SDK crashes from Python API
- ✅ Enables independent scaling
- ✅ Clear separation of concerns (SDK complexity vs API logic)
- ✅ Type-safe gRPC communication
- ✅ Can run on different machines if needed
**Port**: 50051 (gRPC)
---
### 3. PostgreSQL Database
**Purpose**: Persistent storage for users, routing state, and audit logs
**Schema**:
```sql
users:
- id (UUID, primary key)
- username (unique)
- password_hash (bcrypt)
- role (viewer, operator, administrator)
- created_at, updated_at
crossswitch_routes:
- id (UUID, primary key)
- camera_id (int)
- monitor_id (int)
- switched_at (timestamp)
- switched_by_user_id (UUID, FK to users)
audit_logs:
- id (UUID, primary key)
- user_id (UUID, FK to users)
- action (string)
- target (string)
- timestamp (timestamp)
- details (JSON)
```
**Port**: 5432
---
### 4. Redis
**Purpose**: Session storage, caching, and future pub/sub for events
**Usage**:
- **Session Storage**: JWT tokens and user sessions
- **Caching**: Camera list (60s TTL), monitor list (60s TTL)
- **Future**: Pub/sub for real-time routing updates
**Port**: 6379
---
### 5. GeViScope SDK & GeViServer
**GeViServer**:
- Backend service managing surveillance system
- Handles actual video routing
- Controls GSCView viewers
- Manages camera inputs and outputs
**GeViScope SDK**:
- .NET Framework 4.8 DLL (GeViProcAPINET_4_0.dll)
- Provides C# wrapper for GeViServer communication
- Uses action-based message passing
- State query pattern for enumeration
**Ports**: 7700, 7701, 7703
---
## Data Flow
### 1. Authentication Flow
```
Client → POST /api/v1/auth/login
{ username: "admin", password: "secret" }
FastAPI validates credentials
Hash password with bcrypt
Query PostgreSQL for user
Generate JWT token (1hr expiry)
Store session in Redis
Client ← { access_token: "eyJ...", token_type: "bearer" }
```
### 2. Camera Discovery Flow
```
Client → GET /api/v1/cameras
Header: Authorization: Bearer eyJ...
FastAPI validates JWT
Check Redis cache for camera list
↓ (cache miss)
gRPC call to SDK Bridge: ListCameras()
SDK Bridge → GeViScope SDK
→ CSQGetFirstVideoInput()
→ CSQGetNextVideoInput() (loop)
SDK Bridge ← Camera list
FastAPI ← gRPC response
Store in Redis (60s TTL)
Client ← { cameras: [
{ id: 1, name: "Camera 1", has_ptz: false },
{ id: 2, name: "Front Gate", has_ptz: true }
]}
```
### 3. Cross-Switching Flow
```
Client → POST /api/v1/crossswitch
{ camera_id: 7, monitor_id: 3, mode: 0 }
FastAPI validates JWT (requires operator role)
Validate camera_id and monitor_id exist
gRPC call to SDK Bridge: ExecuteCrossSwitch(7, 3, 0)
SDK Bridge → GeViScope SDK
→ SendMessage("CrossSwitch(7, 3, 0)")
GeViServer executes cross-switch
SDK Bridge ← Success confirmation
FastAPI stores route in PostgreSQL
FastAPI logs to audit_logs table
Client ← { success: true, message: "Camera 7 routed to monitor 3" }
```
---
## Security Architecture
### Authentication & Authorization
**Authentication**: JWT (JSON Web Tokens)
- Access tokens: 1 hour lifetime
- Refresh tokens: 7 days lifetime (future)
- Tokens stored in Redis for quick invalidation
- Bcrypt password hashing (cost factor: 12)
**Authorization**: Role-Based Access Control (RBAC)
| Role | Permissions |
|------|------------|
| **Viewer** | Read cameras, Read monitors, Read routing state |
| **Operator** | Viewer + Execute cross-switch, Clear monitors |
| **Administrator** | Operator + User management, Configuration |
### API Security
- ✅ HTTPS enforced in production (TLS 1.2+)
- ✅ CORS configured for allowed origins
- ✅ Rate limiting (60 requests/minute per IP)
- ✅ JWT secret key from environment (not hardcoded)
- ✅ Database credentials in environment variables
- ✅ No stack traces exposed to clients
- ✅ Audit logging for all operations
---
## Scalability Considerations
### Current Architecture (MVP)
- Single FastAPI instance
- Single SDK Bridge instance
- Single GeViServer connection
### Future Horizontal Scaling
**FastAPI Layer**:
- ✅ Stateless design enables multiple instances
- ✅ Load balancer in front (nginx/HAProxy)
- ✅ Shared PostgreSQL and Redis
**SDK Bridge Layer**:
- ⚠️ Limited by GeViServer connection capacity
- Consider: Connection pooling pattern
- Consider: Multiple SDK Bridge instances if needed
**Database Layer**:
- PostgreSQL read replicas for camera/monitor queries
- Redis Cluster for high availability
---
## Error Handling
### SDK Bridge Error Translation
| SDK Error | gRPC Status | HTTP Status |
|-----------|-------------|-------------|
| Connection Failed | UNAVAILABLE | 503 Service Unavailable |
| Invalid Channel | INVALID_ARGUMENT | 400 Bad Request |
| Permission Denied | PERMISSION_DENIED | 403 Forbidden |
| Timeout | DEADLINE_EXCEEDED | 504 Gateway Timeout |
| Unknown | INTERNAL | 500 Internal Server Error |
### Retry Logic
- SDK Bridge connection: 3 attempts with exponential backoff
- gRPC calls from FastAPI: 2 attempts with 1s delay
- Transient errors logged but not exposed to client
---
## Monitoring & Observability
### Logging
**FastAPI**:
- Structured JSON logs (Structlog)
- Log levels: DEBUG, INFO, WARNING, ERROR
- Correlation IDs for request tracing
**SDK Bridge**:
- Serilog with file and console sinks
- Separate logs for SDK communication
### Metrics (Future)
**Prometheus Endpoint**: `/metrics`
- Request count by endpoint
- Request latency (p50, p95, p99)
- Active cross-switch operations
- gRPC call success/failure rates
- Cache hit/miss rates
### Health Checks
**Endpoint**: `GET /api/v1/health`
Returns:
```json
{
"status": "healthy",
"components": {
"database": "up",
"redis": "up",
"sdk_bridge": "up"
},
"timestamp": "2025-12-08T15:30:00Z"
}
```
---
## Deployment Architecture
### Development Environment
```
Localhost:
- PostgreSQL (Docker or native)
- Redis (Docker or native)
- SDK Bridge (.NET)
- FastAPI (uvicorn --reload)
- GeViServer (C:\GEVISOFT\GeViServer.exe)
```
### Production Environment (Windows Server)
```
Windows Server 2016+:
- GeViServer (native Windows service)
- SDK Bridge (Windows service via NSSM)
- PostgreSQL (Docker or native)
- Redis (Docker or native)
- FastAPI (Docker or uvicorn behind nginx)
- Nginx (reverse proxy with SSL termination)
```
### Network Requirements
- Port 8000: FastAPI (HTTPS in production)
- Port 50051: SDK Bridge gRPC (internal only)
- Port 5432: PostgreSQL (internal only)
- Port 6379: Redis (internal only)
- Port 7700-7703: GeViServer (internal only)
---
## Technology Choices Rationale
### Why Python FastAPI?
- ✅ Modern async Python framework
- ✅ Automatic OpenAPI documentation
- ✅ Fast development cycle
- ✅ Rich ecosystem (SQLAlchemy, Pydantic)
- ✅ Easy to expand with new features
### Why C# SDK Bridge?
- ✅ GeViScope SDK is .NET Framework 4.8
- ✅ gRPC provides type-safe communication
- ✅ Isolates SDK complexity
- ✅ Can run on separate machine if needed
### Why PostgreSQL?
- ✅ Mature, reliable, ACID compliant
- ✅ JSON support for flexible audit logs
- ✅ Good performance for relational data
### Why Redis?
- ✅ Fast in-memory caching
- ✅ Session storage
- ✅ Future: pub/sub for events
### Why gRPC (not REST for SDK Bridge)?
- ✅ Type-safe protocol buffers
- ✅ Efficient binary protocol
- ✅ Streaming support (future)
- ✅ Language-agnostic
---
## Future Enhancements (Phase 2)
1. **GeViSet Configuration Management**
- Retrieve action mappings from GeViServer
- Modify configurations via API
- Export/import to CSV
- Push configurations back to server
2. **Real-Time Event Stream**
- WebSocket endpoint for routing changes
- Redis pub/sub for event distribution
- Monitor status change notifications
3. **PTZ Camera Control**
- Pan/tilt/zoom commands
- Preset positions
- Tour sequences
4. **Multi-Tenancy**
- Organization/tenant isolation
- Per-tenant GeViServer connections
5. **Advanced Analytics**
- Routing history reports
- Usage patterns
- Performance metrics
---
## Development Workflow
1. **Setup**: `.\scripts\setup_dev_environment.ps1`
2. **Start Services**: `.\scripts\start_services.ps1`
3. **Database Migrations**: `alembic upgrade head`
4. **Run Tests**: `pytest tests/ -v`
5. **Code Quality**: `ruff check src/api` + `black src/api`
6. **API Docs**: http://localhost:8000/docs
---
## References
- **FastAPI Documentation**: https://fastapi.tiangolo.com
- **gRPC .NET**: https://grpc.io/docs/languages/csharp/
- **GeViScope SDK**: See `docs/SDK_INTEGRATION_LESSONS.md`
- **SQLAlchemy**: https://docs.sqlalchemy.org
- **Pydantic**: https://docs.pydantic.dev
---
**Document Version**: 1.0
**Architecture Status**: ✅ Defined, 🔄 In Development
**Last Review**: 2025-12-08