315 lines
7.6 KiB
Markdown
315 lines
7.6 KiB
Markdown
# Advoware API Proxy Steps
|
|
|
|
Dieser Ordner enthält die API-Proxy-Steps für die Advoware-Integration. Jeder Step implementiert eine HTTP-Methode als universellen Proxy zur Advoware-API mit **Motia III v1.0-RC**.
|
|
|
|
## Übersicht
|
|
|
|
Die Proxy-Steps fungieren als transparente Schnittstelle zwischen Clients und der Advoware-API. Sie handhaben Authentifizierung, Fehlerbehandlung und Logging automatisch.
|
|
|
|
## Steps
|
|
|
|
### 1. GET Proxy (`advoware_api_proxy_get_step.py`)
|
|
|
|
**Zweck:** Universeller Proxy für GET-Requests an die Advoware-API.
|
|
|
|
**Konfiguration:**
|
|
```python
|
|
config = {
|
|
'name': 'Advoware Proxy GET',
|
|
'flows': ['advoware'],
|
|
'triggers': [
|
|
http('GET', '/advoware/proxy')
|
|
],
|
|
'enqueues': []
|
|
}
|
|
```
|
|
|
|
**Funktionalität:**
|
|
- Extrahiert den Ziel-Endpoint aus Query-Parametern (`endpoint`)
|
|
- Übergibt alle anderen Query-Parameter als API-Parameter
|
|
- Gibt das Ergebnis als JSON zurück
|
|
|
|
**Beispiel Request:**
|
|
```bash
|
|
GET /advoware/proxy?endpoint=employees&limit=10&offset=0
|
|
```
|
|
|
|
**Response:**
|
|
```json
|
|
{
|
|
"result": {
|
|
"data": [...],
|
|
"total": 100
|
|
}
|
|
}
|
|
```
|
|
|
|
### 2. POST Proxy (`advoware_api_proxy_post_step.py`)
|
|
|
|
**Zweck:** Universeller Proxy für POST-Requests an die Advoware-API.
|
|
|
|
**Konfiguration:**
|
|
```python
|
|
config = {
|
|
'name': 'Advoware Proxy POST',
|
|
'flows': ['advoware'],
|
|
'triggers': [
|
|
http('POST', '/advoware/proxy')
|
|
],
|
|
'enqueues': []
|
|
}
|
|
```
|
|
|
|
**Funktionalität:**
|
|
- Extrahiert den Ziel-Endpoint aus Query-Parametern (`endpoint`)
|
|
- Verwendet den Request-Body als JSON-Daten für die API
|
|
- Erstellt neue Ressourcen in Advoware
|
|
|
|
**Beispiel Request:**
|
|
```bash
|
|
POST /advoware/proxy?endpoint=employees
|
|
Content-Type: application/json
|
|
|
|
{
|
|
"name": "John Doe",
|
|
"email": "john@example.com"
|
|
}
|
|
```
|
|
|
|
### 3. PUT Proxy (`advoware_api_proxy_put_step.py`)
|
|
|
|
**Zweck:** Universeller Proxy für PUT-Requests an die Advoware-API.
|
|
|
|
**Konfiguration:**
|
|
```python
|
|
config = {
|
|
'name': 'Advoware Proxy PUT',
|
|
'flows': ['advoware'],
|
|
'triggers': [
|
|
http('PUT', '/advoware/proxy')
|
|
],
|
|
'enqueues': []
|
|
}
|
|
```
|
|
|
|
**Funktionalität:**
|
|
- Extrahiert den Ziel-Endpoint aus Query-Parametern (`endpoint`)
|
|
- Verwendet den Request-Body als JSON-Daten für Updates
|
|
- Aktualisiert bestehende Ressourcen in Advoware
|
|
|
|
**Beispiel Request:**
|
|
```bash
|
|
PUT /advoware/proxy?endpoint=employees/123
|
|
Content-Type: application/json
|
|
|
|
{
|
|
"name": "John Smith",
|
|
"email": "johnsmith@example.com"
|
|
}
|
|
```
|
|
|
|
### 4. DELETE Proxy (`advoware_api_proxy_delete_step.py`)
|
|
|
|
**Zweck:** Universeller Proxy für DELETE-Requests an die Advoware-API.
|
|
|
|
**Konfiguration:**
|
|
```python
|
|
config = {
|
|
'name': 'Advoware Proxy DELETE',
|
|
'flows': ['advoware'],
|
|
'triggers': [
|
|
http('DELETE', '/advoware/proxy')
|
|
],
|
|
'enqueues': []
|
|
}
|
|
```
|
|
|
|
**Funktionalität:**
|
|
- Extrahiert den Ziel-Endpoint aus Query-Parametern (`endpoint`)
|
|
- Löscht Ressourcen in Advoware
|
|
|
|
**Beispiel Request:**
|
|
```bash
|
|
DELETE /advoware/proxy?endpoint=employees/123
|
|
```
|
|
|
|
## Gemeinsame Features
|
|
|
|
### Authentifizierung
|
|
Alle Steps verwenden den `AdvowareService` für automatische Token-Verwaltung und Authentifizierung:
|
|
- HMAC-512 basierte Signatur
|
|
- Token-Caching in Redis (55 Minuten Lifetime)
|
|
- Automatischer Token-Refresh bei 401-Errors
|
|
|
|
### Fehlerbehandling
|
|
- **400 Bad Request:** Fehlender `endpoint` Parameter
|
|
- **500 Internal Server Error:** API-Fehler oder Exceptions
|
|
- **401 Unauthorized:** Automatischer Token-Refresh und Retry
|
|
|
|
### Logging
|
|
Detaillierte Logs via `ctx.logger` für:
|
|
- Eingehende Requests
|
|
- API-Calls an Advoware
|
|
- Fehler und Exceptions
|
|
- Token-Management
|
|
|
|
Alle Logs sind in der **iii Console** sichtbar.
|
|
|
|
### Sicherheit
|
|
- Keine direkte Weitergabe sensibler Daten
|
|
- Authentifizierung über Service-Layer
|
|
- Input-Validation für erforderliche Parameter
|
|
- HMAC-512 Signatur für alle API-Requests
|
|
|
|
## Handler-Struktur (Motia III)
|
|
|
|
Alle Steps folgen dem gleichen Pattern:
|
|
|
|
```python
|
|
from motia import http, ApiRequest, ApiResponse, FlowContext
|
|
from services.advoware_service import AdvowareService
|
|
|
|
config = {
|
|
'name': 'Advoware Proxy {METHOD}',
|
|
'flows': ['advoware'],
|
|
'triggers': [
|
|
http('{METHOD}', '/advoware/proxy')
|
|
],
|
|
'enqueues': []
|
|
}
|
|
|
|
async def handler(request: ApiRequest, ctx: FlowContext) -> ApiResponse:
|
|
# Extract endpoint from query params
|
|
endpoint = request.query_params.get('endpoint')
|
|
|
|
if not endpoint:
|
|
return ApiResponse(
|
|
status=400,
|
|
body={'error': 'Missing required query parameter: endpoint'}
|
|
)
|
|
|
|
# Call Advoware API
|
|
advoware_service = AdvowareService()
|
|
result = await advoware_service.{method}(endpoint, **params)
|
|
|
|
return ApiResponse(status=200, body={'result': result})
|
|
```
|
|
|
|
## Testing
|
|
|
|
### Unit Tests
|
|
```bash
|
|
# Test GET Proxy
|
|
curl -X GET "http://localhost:3111/advoware/proxy?endpoint=employees"
|
|
|
|
# Test POST Proxy
|
|
curl -X POST "http://localhost:3111/advoware/proxy?endpoint=employees" \
|
|
-H "Content-Type: application/json" \
|
|
-d '{"name": "Test Employee"}'
|
|
|
|
# Test PUT Proxy
|
|
curl -X PUT "http://localhost:3111/advoware/proxy?endpoint=employees/1" \
|
|
-H "Content-Type: application/json" \
|
|
-d '{"name": "Updated Employee"}'
|
|
|
|
# Test DELETE Proxy
|
|
curl -X DELETE "http://localhost:3111/advoware/proxy?endpoint=employees/1"
|
|
```
|
|
|
|
### Integration Tests
|
|
Überprüfen Sie die Logs in der iii Console:
|
|
```bash
|
|
# Check logs
|
|
curl http://localhost:3111/_console/logs
|
|
```
|
|
|
|
## Konfiguration
|
|
|
|
### Umgebungsvariablen
|
|
Stellen Sie sicher, dass folgende Variablen gesetzt sind:
|
|
```env
|
|
ADVOWARE_API_BASE_URL=https://www2.advo-net.net:90/
|
|
ADVOWARE_PRODUCT_ID=64
|
|
ADVOWARE_APP_ID=your_app_id
|
|
ADVOWARE_API_KEY=your_api_key
|
|
ADVOWARE_KANZLEI=your_kanzlei
|
|
ADVOWARE_DATABASE=your_database
|
|
ADVOWARE_USER=your_user
|
|
ADVOWARE_ROLE=2
|
|
ADVOWARE_PASSWORD=your_password
|
|
ADVOWARE_TOKEN_LIFETIME_MINUTES=55
|
|
ADVOWARE_API_TIMEOUT_SECONDS=30
|
|
|
|
# Redis (für Token-Caching)
|
|
REDIS_HOST=localhost
|
|
REDIS_PORT=6379
|
|
REDIS_DB=0
|
|
```
|
|
|
|
### Dependencies
|
|
- `services/advoware_service.py` - Advoware API Client mit HMAC Auth
|
|
- `config.py` - Konfigurationsmanagement
|
|
- `motia` - Motia III Python SDK
|
|
- `asyncpg` - PostgreSQL Client
|
|
- `redis` - Redis Client für Token-Caching
|
|
|
|
## Erweiterungen
|
|
|
|
### Geplante Features
|
|
- Request/Response Caching für häufige Queries
|
|
- Rate Limiting pro Client
|
|
- Request Validation Schemas mit Pydantic
|
|
- Batch-Operations Support
|
|
|
|
### Custom Endpoints
|
|
Für spezifische Endpoints können zusätzliche Steps erstellt werden, die direkt auf bestimmte Ressourcen zugreifen und erweiterte Validierung/Transformation bieten.
|
|
|
|
## Architektur
|
|
|
|
```
|
|
Client Request
|
|
│
|
|
▼
|
|
HTTP Trigger (http('METHOD', '/advoware/proxy'))
|
|
│
|
|
▼
|
|
Handler (ApiRequest → ApiResponse)
|
|
│
|
|
├─► Extract 'endpoint' from query params
|
|
├─► Extract other params/body
|
|
│
|
|
▼
|
|
AdvowareService
|
|
│
|
|
├─► Check Redis for valid token
|
|
├─► If expired: Get new token (HMAC-512 auth)
|
|
├─► Build HTTP request
|
|
│
|
|
▼
|
|
Advoware API
|
|
│
|
|
▼
|
|
Response → Transform → Return ApiResponse
|
|
```
|
|
|
|
## Migration Notes
|
|
|
|
Dieses System wurde von **Motia v0.17** nach **Motia III v1.0-RC** migriert:
|
|
|
|
### Wichtige Änderungen:
|
|
- ✅ `type: 'api'` → `triggers: [http('METHOD', 'path')]`
|
|
- ✅ `ApiRouteConfig` → `StepConfig` mit `as const satisfies`
|
|
- ✅ `Handlers['StepName']` → `Handlers<typeof config>`
|
|
- ✅ `context` → `ctx`
|
|
- ✅ `req` dict → `ApiRequest` typed object
|
|
- ✅ Return dict → `ApiResponse` typed object
|
|
- ✅ `method`, `path` moved into trigger
|
|
- ✅ Motia Workbench → iii Console
|
|
|
|
### Kompatibilität:
|
|
- ✅ Alle 4 Proxy Steps vollständig migriert
|
|
- ✅ AdvowareService kompatibel (keine Änderungen)
|
|
- ✅ Redis Token-Caching unverändert
|
|
- ✅ HMAC-512 Auth unverändert
|
|
- ✅ API-Endpoints identisch
|