E2E Integration Validation Skill
Guidelines for validating cross-container communication and infrastructure connectivity in the local development environment.
Purpose
This skill provides guidance on:
- •Validating frontend → backend communication
- •Validating backend → infrastructure connectivity
- •Validating service → service communication
- •Testing real data flow (CRUD operations)
- •Identifying integration blockers
When to Use This Skill
Use this skill when:
- •Running the
/validate-e2e-integrationcommand - •Acting as
e2e-integration-validatoragent - •Acting as
e2e-integration-fixeragent - •Diagnosing cross-container communication issues
Key Concepts
1. Communication Categories
| Category | Source | Target | Validation Method |
|---|---|---|---|
| Frontend → Backend | web-app, frontend | api, backend | HTTP requests, CORS check |
| Backend → Infrastructure | api, services | mongodb, redis, azurite | Log inspection, CRUD test |
| Service → Service | api | processing, worker | HTTP requests, log correlation |
2. LOCAL_RUN Mode
All validation occurs with LOCAL_RUN=true:
- •Authentication is bypassed
- •Local Docker infrastructure is used
- •Data is persisted to local services
- •Real effects occur (not mocked)
3. Evidence Requirements
Every validation must include evidence:
| Evidence Type | Source | Example |
|---|---|---|
| HTTP Response | curl output | HTTP 200 OK, response body |
| Connection Log | container logs | Connected to mongodb:27017 |
| Data Persistence | CRUD test | Create → Read → matches |
| Error Details | logs/response | Stack trace, error message |
Validation Patterns
Pattern 1: Health Check
# Check if endpoint is reachable
curl -s -o /dev/null -w "%{http_code}" http://localhost:{port}/health
# Expected: 200
Pattern 2: CORS Validation
# Check CORS headers
curl -s -I -X OPTIONS http://localhost:{api-port}/api/v1/items \
-H "Origin: http://localhost:{frontend-port}" \
-H "Access-Control-Request-Method: GET" \
| grep -i "access-control"
# Expected: Access-Control-Allow-Origin header present
Pattern 3: Connection Log Check
# Look for connection evidence
grep -i "connected\|ready\|established" .local-logs/{container}/combined.log
# Expected: Connection success messages
Pattern 4: CRUD Test
# Create
CREATE_RESPONSE=$(curl -s -X POST http://localhost:{port}/api/v1/items \
-H "Content-Type: application/json" \
-d '{"name": "test-'$(date +%s)'"}')
ID=$(echo $CREATE_RESPONSE | jq -r '.id // ._id // .data.id')
# Read
READ_RESPONSE=$(curl -s http://localhost:{port}/api/v1/items/$ID)
# Verify
echo $READ_RESPONSE | jq -e '.name'
# Expected: Name matches what was created
# Cleanup
curl -s -X DELETE http://localhost:{port}/api/v1/items/$ID
Pattern 5: Error Search
# Search for errors in logs
grep -i "error\|exception\|failed" .local-logs/{container}/combined.log | tail -n 10
# Expected: No critical errors
Common Integration Issues
Issue: CORS Errors
Symptoms:
- •Browser console shows CORS error
- •Preflight OPTIONS request fails
- •
Access-Control-Allow-Originmissing
Diagnosis:
# Check if CORS middleware exists
grep -r "cors\|CORS" {backend}/src/
# Check allowed origins
grep -r "allow.*origin\|allowedOrigins" {backend}/src/
Fix Pattern:
# Python/FastAPI
from fastapi.middleware.cors import CORSMiddleware
app.add_middleware(
CORSMiddleware,
allow_origins=["*"] if os.getenv("LOCAL_RUN") == "true" else [os.getenv("FRONTEND_URL")],
allow_credentials=True,
allow_methods=["*"],
allow_headers=["*"],
)
Issue: Connection Refused
Symptoms:
- •
ECONNREFUSEDin logs - •Service unreachable from another container
- •Health check fails
Diagnosis:
# Check if service is binding to correct interface
grep -r "listen\|bind\|host" {container}/src/
# Check if using localhost (wrong) or 0.0.0.0 (correct)
grep -r "localhost\|127.0.0.1\|0.0.0.0" {container}/src/
Fix Pattern:
// Node.js - bind to 0.0.0.0, not localhost
app.listen(PORT, '0.0.0.0', () => {
console.log(`Server running on port ${PORT}`);
});
Issue: Database Connection Failed
Symptoms:
- •
MongoNetworkErroror similar in logs - •
Connection refusedto database port - •Application fails to start
Diagnosis:
# Check database service is running
docker ps | grep -i mongo
# Check connection string
grep -r "DATABASE_URL\|MONGO_URI\|mongodb://" {container}/
# Check container logs for connection attempts
grep -i "mongo\|database\|connection" .local-logs/{container}/combined.log
Fix Pattern:
# .env.example - use localhost for LOCAL_RUN DATABASE_URL=mongodb://localhost:27017/mydb
Issue: Service-to-Service Communication Failed
Symptoms:
- •One service can't reach another
- •Async processing doesn't complete
- •Events don't propagate
Diagnosis:
# Check both services are running
./scripts/local-status.sh
# Check source service logs for outbound calls
grep -i "calling\|request\|POST\|GET" .local-logs/{source}/combined.log
# Check target service logs for received requests
grep -i "received\|handling\|incoming" .local-logs/{target}/combined.log
Fix Pattern:
# Ensure service URLs are configured correctly
# In source service .env.example:
PROCESSING_SERVICE_URL=http://localhost:8001
# In startup script:
export PROCESSING_SERVICE_URL=${PROCESSING_SERVICE_URL:-http://localhost:8001}
Log Inspection Commands
View Container Logs
# View recent logs
tail -n 50 .local-logs/{container}/combined.log
# Follow logs in real-time
tail -f .local-logs/{container}/combined.log
# View only errors
tail -n 100 .local-logs/{container}/stderr.log
Search Across Containers
# Find errors across all containers
grep -r "error\|Error\|ERROR" .local-logs/*/combined.log
# Find specific pattern
grep -r "mongodb\|database" .local-logs/*/combined.log
# Count errors by container
for dir in .local-logs/*/; do
echo "$dir: $(grep -c 'error' ${dir}combined.log 2>/dev/null || echo 0) errors"
done
Check Infrastructure Logs
# Docker compose logs
docker-compose -f {container}/docker-compose.local.yml logs --tail=50
# Specific service logs
docker logs $(docker ps -qf "name=mongodb") --tail=50
Validation Report Format
Successful Validation
VALIDATION RESULT: PASS ## Summary | Validation | Status | Evidence | |------------|--------|----------| | Health Check | ✓ PASS | HTTP 200 | | CORS | ✓ PASS | Headers present | | Database | ✓ PASS | Connection established | | CRUD | ✓ PASS | Data persisted | ## Log Evidence
[timestamp] Connected to mongodb:27017 [timestamp] Server listening on 0.0.0.0:8000
## HTTP Evidence
GET /health HTTP/1.1 200 OK {"status": "healthy"}
Failed Validation
VALIDATION RESULT: FAIL ## Summary | Validation | Status | Issue | |------------|--------|-------| | Health Check | ✓ PASS | - | | CORS | ✗ FAIL | Missing headers | | Database | ✓ PASS | - | ## Failed: CORS **Expected**: Access-Control-Allow-Origin header present **Actual**: No CORS headers in response **Error**:
Access to fetch at 'http://localhost:8000/api/v1/items' from origin 'http://localhost:3000' has been blocked by CORS policy
**Container**: api **Log Context**:
[timestamp] WARN No CORS middleware configured
**Possible Cause**: CORS middleware not added to application **Impact**: Frontend cannot make API calls
Fix Report Format
FIX RESULT: APPLIED ## Issue Fixed **Category**: Frontend → Backend **Root Cause**: CORS middleware not configured **Impact**: Frontend API calls blocked ## Changes Made ### File: api/src/app.py **Change Type**: Code **Before**: ```python app = FastAPI()
After:
from fastapi.middleware.cors import CORSMiddleware
app = FastAPI()
app.add_middleware(
CORSMiddleware,
allow_origins=["http://localhost:3000"],
allow_credentials=True,
allow_methods=["*"],
allow_headers=["*"],
)
Reason: Added CORS middleware to allow frontend requests
Verification Needed
- •Restart api container
- •Re-run Frontend → Backend validation
---
## Docker Compose Patterns
### Basic Infrastructure
```yaml
# docker-compose.local.yml
version: '3.8'
services:
mongodb:
image: mongo:6
ports:
- "27017:27017"
healthcheck:
test: echo 'db.runCommand("ping").ok' | mongosh localhost:27017/test --quiet
interval: 10s
timeout: 10s
retries: 5
volumes:
- mongodb_data:/data/db
redis:
image: redis:7-alpine
ports:
- "6379:6379"
healthcheck:
test: ["CMD", "redis-cli", "ping"]
interval: 10s
timeout: 5s
retries: 5
volumes:
mongodb_data:
With Azurite (Azure Storage Emulator)
azurite:
image: mcr.microsoft.com/azure-storage/azurite
ports:
- "10000:10000" # Blob
- "10001:10001" # Queue
- "10002:10002" # Table
healthcheck:
test: nc -z localhost 10000
interval: 10s
timeout: 5s
retries: 5
With MailHog (Email Capture)
mailhog:
image: mailhog/mailhog
ports:
- "1025:1025" # SMTP
- "8025:8025" # Web UI
Environment Variable Patterns
Database Connection
# .env.example # For LOCAL_RUN=true (connecting to docker-compose services) DATABASE_URL=mongodb://localhost:27017/myapp # Connection options DATABASE_NAME=myapp DATABASE_HOST=localhost DATABASE_PORT=27017
Service URLs
# .env.example # API Service API_URL=http://localhost:8000 # Processing Service PROCESSING_SERVICE_URL=http://localhost:8001 # Frontend FRONTEND_URL=http://localhost:3000
Feature Flags
# .env.example # Local development mode LOCAL_RUN=true # Enable/disable features ENABLE_ASYNC_PROCESSING=true ENABLE_EMAIL_NOTIFICATIONS=true
Checklist for Validators
Before Validation
- • Solution is running (
./scripts/local-status.sh) - • All containers show as healthy
- • Docker infrastructure is up
- • Logs are accessible
During Validation
- • Each step has explicit evidence
- • HTTP responses captured
- • Log entries referenced
- • Errors fully documented
After Validation
- • Clear PASS/FAIL result
- • All evidence included
- • Blockers identified (if FAIL)
- • Next steps documented
Checklist for Fixers
Before Fixing
- • Root cause clearly identified
- • Validation failure report read
- • Container logs inspected
- • Fix scope is minimal
During Fixing
- • Only necessary changes made
- • Production behavior preserved
- • LOCAL_RUN conditional used if needed
- • Syntax verified
After Fixing
- • All changes documented
- • Before/after code shown
- • Verification steps provided
- • No scope creep