feat(#93): implement agent spawn via federation
Implements FED-010: Agent Spawn via Federation feature that enables spawning and managing Claude agents on remote federated Mosaic Stack instances via COMMAND message type. Features: - Federation agent command types (spawn, status, kill) - FederationAgentService for handling agent operations - Integration with orchestrator's agent spawner/lifecycle services - API endpoints for spawning, querying status, and killing agents - Full command routing through federation COMMAND infrastructure - Comprehensive test coverage (12/12 tests passing) Architecture: - Hub → Spoke: Spawn agents on remote instances - Command flow: FederationController → FederationAgentService → CommandService → Remote Orchestrator - Response handling: Remote orchestrator returns agent status/results - Security: Connection validation, signature verification Files created: - apps/api/src/federation/types/federation-agent.types.ts - apps/api/src/federation/federation-agent.service.ts - apps/api/src/federation/federation-agent.service.spec.ts Files modified: - apps/api/src/federation/command.service.ts (agent command routing) - apps/api/src/federation/federation.controller.ts (agent endpoints) - apps/api/src/federation/federation.module.ts (service registration) - apps/orchestrator/src/api/agents/agents.controller.ts (status endpoint) - apps/orchestrator/src/api/agents/agents.module.ts (lifecycle integration) Testing: - 12/12 tests passing for FederationAgentService - All command service tests passing - TypeScript compilation successful - Linting passed Refs #93 Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -1,11 +1,13 @@
|
||||
# Issue #199: Implement rate limiting on webhook endpoints
|
||||
|
||||
## Objective
|
||||
|
||||
Implement rate limiting on webhook and public-facing API endpoints to prevent DoS attacks and ensure system stability under high load conditions.
|
||||
|
||||
## Approach
|
||||
|
||||
### TDD Implementation Plan
|
||||
|
||||
1. **RED**: Write failing tests for rate limiting
|
||||
- Test rate limit enforcement (429 status)
|
||||
- Test Retry-After header inclusion
|
||||
@@ -30,10 +32,12 @@ Implement rate limiting on webhook and public-facing API endpoints to prevent Do
|
||||
### Identified Webhook Endpoints
|
||||
|
||||
**Stitcher Module** (`apps/api/src/stitcher/stitcher.controller.ts`):
|
||||
|
||||
- `POST /stitcher/webhook` - Webhook endpoint for @mosaic bot
|
||||
- `POST /stitcher/dispatch` - Manual job dispatch endpoint
|
||||
|
||||
**Coordinator Integration Module** (`apps/api/src/coordinator-integration/coordinator-integration.controller.ts`):
|
||||
|
||||
- `POST /coordinator/jobs` - Create a job from coordinator
|
||||
- `PATCH /coordinator/jobs/:id/status` - Update job status
|
||||
- `PATCH /coordinator/jobs/:id/progress` - Update job progress
|
||||
@@ -45,6 +49,7 @@ Implement rate limiting on webhook and public-facing API endpoints to prevent Do
|
||||
### Rate Limit Configuration
|
||||
|
||||
**Proposed limits**:
|
||||
|
||||
- Global default: 100 requests per minute
|
||||
- Webhook endpoints: 60 requests per minute per IP
|
||||
- Coordinator endpoints: 100 requests per minute per API key
|
||||
@@ -53,11 +58,13 @@ Implement rate limiting on webhook and public-facing API endpoints to prevent Do
|
||||
**Storage**: Use Valkey (Redis-compatible) for distributed rate limiting across multiple API instances.
|
||||
|
||||
### Technology Stack
|
||||
|
||||
- `@nestjs/throttler` - NestJS rate limiting module
|
||||
- Valkey (already in project) - Redis-compatible cache for distributed rate limiting
|
||||
- Custom guards for per-API-key limiting
|
||||
|
||||
## Progress
|
||||
|
||||
- [x] Create scratchpad
|
||||
- [x] Identify webhook endpoints requiring rate limiting
|
||||
- [x] Define rate limit configuration strategy
|
||||
@@ -75,6 +82,7 @@ Implement rate limiting on webhook and public-facing API endpoints to prevent Do
|
||||
## Testing Plan
|
||||
|
||||
### Unit Tests
|
||||
|
||||
1. **Rate limit enforcement**
|
||||
- Verify 429 status code after exceeding limit
|
||||
- Verify requests within limit are allowed
|
||||
@@ -96,6 +104,7 @@ Implement rate limiting on webhook and public-facing API endpoints to prevent Do
|
||||
- Verify fallback to in-memory if Redis unavailable
|
||||
|
||||
### Integration Tests
|
||||
|
||||
1. **E2E rate limiting**
|
||||
- Test actual HTTP requests hitting rate limits
|
||||
- Test rate limits reset after time window
|
||||
@@ -115,6 +124,7 @@ RATE_LIMIT_STORAGE=redis # redis or memory
|
||||
## Implementation Summary
|
||||
|
||||
### Files Created
|
||||
|
||||
1. `/home/localadmin/src/mosaic-stack/apps/api/src/common/throttler/throttler-api-key.guard.ts` - Custom guard for API-key based rate limiting
|
||||
2. `/home/localadmin/src/mosaic-stack/apps/api/src/common/throttler/throttler-storage.service.ts` - Valkey/Redis storage for distributed rate limiting
|
||||
3. `/home/localadmin/src/mosaic-stack/apps/api/src/common/throttler/index.ts` - Export barrel file
|
||||
@@ -122,6 +132,7 @@ RATE_LIMIT_STORAGE=redis # redis or memory
|
||||
5. `/home/localadmin/src/mosaic-stack/apps/api/src/coordinator-integration/coordinator-integration.rate-limit.spec.ts` - Rate limiting tests for coordinator endpoints (8 tests)
|
||||
|
||||
### Files Modified
|
||||
|
||||
1. `/home/localadmin/src/mosaic-stack/apps/api/src/app.module.ts` - Added ThrottlerModule and ThrottlerApiKeyGuard
|
||||
2. `/home/localadmin/src/mosaic-stack/apps/api/src/stitcher/stitcher.controller.ts` - Added @Throttle decorators (60 req/min)
|
||||
3. `/home/localadmin/src/mosaic-stack/apps/api/src/coordinator-integration/coordinator-integration.controller.ts` - Added @Throttle decorators (100 req/min, health: 300 req/min)
|
||||
@@ -130,11 +141,13 @@ RATE_LIMIT_STORAGE=redis # redis or memory
|
||||
6. `/home/localadmin/src/mosaic-stack/apps/api/package.json` - Added @nestjs/throttler dependency
|
||||
|
||||
### Test Results
|
||||
|
||||
- All 14 rate limiting tests pass (6 stitcher + 8 coordinator)
|
||||
- Tests verify: rate limit enforcement, Retry-After headers, per-API-key limiting, independent API key tracking
|
||||
- TDD approach followed: RED (failing tests) → GREEN (implementation) → REFACTOR
|
||||
|
||||
### Rate Limits Configured
|
||||
|
||||
- Stitcher endpoints: 60 requests/minute per API key
|
||||
- Coordinator endpoints: 100 requests/minute per API key
|
||||
- Health endpoint: 300 requests/minute per API key (higher for monitoring)
|
||||
@@ -143,6 +156,7 @@ RATE_LIMIT_STORAGE=redis # redis or memory
|
||||
## Notes
|
||||
|
||||
### Why @nestjs/throttler?
|
||||
|
||||
- Official NestJS package with good TypeScript support
|
||||
- Supports Redis for distributed rate limiting
|
||||
- Flexible per-route configuration
|
||||
@@ -150,6 +164,7 @@ RATE_LIMIT_STORAGE=redis # redis or memory
|
||||
- Active maintenance
|
||||
|
||||
### Security Considerations
|
||||
|
||||
- Rate limiting by IP can be bypassed by rotating IPs
|
||||
- Implement per-API-key limiting as primary defense
|
||||
- Log rate limit violations for monitoring
|
||||
@@ -157,11 +172,13 @@ RATE_LIMIT_STORAGE=redis # redis or memory
|
||||
- Ensure rate limiting doesn't block legitimate traffic
|
||||
|
||||
### Implementation Details
|
||||
|
||||
- Use `@Throttle()` decorator for per-endpoint limits
|
||||
- Use `@SkipThrottle()` to exclude specific endpoints
|
||||
- Custom ThrottlerGuard to extract API key from X-API-Key header
|
||||
- Use Valkey connection from existing ValkeyModule
|
||||
|
||||
## References
|
||||
|
||||
- [NestJS Throttler Documentation](https://docs.nestjs.com/security/rate-limiting)
|
||||
- [OWASP Rate Limiting Cheat Sheet](https://cheatsheetseries.owasp.org/cheatsheets/Denial_of_Service_Cheat_Sheet.html)
|
||||
|
||||
Reference in New Issue
Block a user