# Test API Server A mock REST API server for testing the Daily Notification Plugin's network functionality, ETag support, and error handling capabilities. ## Features - **Content Endpoints**: Generate mock notification content for different time slots - **ETag Support**: Full HTTP caching with conditional requests (304 Not Modified) - **Error Simulation**: Test various error scenarios (timeout, server error, rate limiting) - **Metrics**: Monitor API usage and performance - **CORS Enabled**: Cross-origin requests supported for web testing ## Quick Start ```bash # Install dependencies npm install # Start server npm start # Development mode with auto-restart npm run dev ``` ## API Endpoints ### Health Check ```http GET /health ``` **Response:** ```json { "status": "healthy", "timestamp": 1703123456789, "version": "1.0.0", "endpoints": { "content": "/api/content/:slotId", "health": "/health", "metrics": "/api/metrics", "error": "/api/error/:type" } } ``` ### Get Notification Content ```http GET /api/content/:slotId ``` **Parameters:** - `slotId`: Slot identifier in format `slot-HH:MM` (e.g., `slot-08:00`) **Headers:** - `If-None-Match`: ETag for conditional requests **Response (200 OK):** ```json { "id": "abc12345", "slotId": "slot-08:00", "title": "Daily Update - 08:00", "body": "Your personalized content for 08:00. Content ID: abc12345", "timestamp": 1703123456789, "priority": "high", "category": "daily", "actions": [ { "id": "view", "title": "View Details" }, { "id": "dismiss", "title": "Dismiss" } ], "metadata": { "source": "test-api", "version": "1.0.0", "generated": "2023-12-21T08:00:00.000Z" } } ``` **Response (304 Not Modified):** When `If-None-Match` header matches current ETag. ### Update Content ```http PUT /api/content/:slotId ``` **Body:** ```json { "content": { "title": "Custom Title", "body": "Custom body content" } } ``` ### Clear All Content ```http DELETE /api/content ``` ### Simulate Errors ```http GET /api/error/:type ``` **Error Types:** - `timeout` - Simulates request timeout (15 seconds) - `server-error` - Returns 500 Internal Server Error - `not-found` - Returns 404 Not Found - `rate-limit` - Returns 429 Rate Limit Exceeded - `unauthorized` - Returns 401 Unauthorized ### API Metrics ```http GET /api/metrics ``` **Response:** ```json { "timestamp": 1703123456789, "contentStore": { "size": 5, "slots": ["slot-08:00", "slot-12:00", "slot-18:00"] }, "etagStore": { "size": 5, "etags": [["slot-08:00", "\"abc123\""]] }, "uptime": 3600, "memory": { "rss": 50331648, "heapTotal": 20971520, "heapUsed": 15728640, "external": 1048576 } } ``` ## Usage Examples ### Basic Content Fetch ```bash curl http://localhost:3001/api/content/slot-08:00 ``` ### ETag Conditional Request ```bash # First request curl -v http://localhost:3001/api/content/slot-08:00 # Second request with ETag (should return 304) curl -v -H "If-None-Match: \"abc123\"" http://localhost:3001/api/content/slot-08:00 ``` ### Error Testing ```bash # Test timeout curl http://localhost:3001/api/error/timeout # Test server error curl http://localhost:3001/api/error/server-error # Test rate limiting curl http://localhost:3001/api/error/rate-limit ``` ## Integration with Test Apps ### Android Test App ```typescript // In your Android test app const API_BASE_URL = 'http://10.0.2.2:3001'; // Android emulator localhost const fetchContent = async (slotId: string) => { const response = await fetch(`${API_BASE_URL}/api/content/${slotId}`); return response.json(); }; ``` ### iOS Test App ```typescript // In your iOS test app const API_BASE_URL = 'http://localhost:3001'; // iOS simulator localhost const fetchContent = async (slotId: string) => { const response = await fetch(`${API_BASE_URL}/api/content/${slotId}`); return response.json(); }; ``` ### Electron Test App ```typescript // In your Electron test app const API_BASE_URL = 'http://localhost:3001'; const fetchContent = async (slotId: string) => { const response = await fetch(`${API_BASE_URL}/api/content/${slotId}`); return response.json(); }; ``` ## Configuration ### Environment Variables - `PORT`: Server port (default: 3001) - `NODE_ENV`: Environment mode (development/production) ### CORS Configuration The server is configured to allow cross-origin requests from any origin for testing purposes. ## Testing Scenarios ### 1. Basic Content Fetching - Test successful content retrieval - Verify content structure and format - Check timestamp accuracy ### 2. ETag Caching - Test conditional requests with `If-None-Match` - Verify 304 Not Modified responses - Test cache invalidation ### 3. Error Handling - Test timeout scenarios - Test server error responses - Test rate limiting behavior - Test network failure simulation ### 4. Performance Testing - Test concurrent requests - Monitor memory usage - Test long-running scenarios ## Development ### Running in Development Mode ```bash npm run dev ``` This uses `nodemon` for automatic server restart on file changes. ### Adding New Endpoints 1. Add route handler in `server.js` 2. Update health check endpoint list 3. Add documentation to this README 4. Add test cases if applicable ### Testing ```bash npm test ``` ## Troubleshooting ### Common Issues 1. **Port Already in Use** ```bash # Kill process using port 3001 lsof -ti:3001 | xargs kill -9 ``` 2. **CORS Issues** - Server is configured to allow all origins - Check browser console for CORS errors 3. **Network Connectivity** - Android emulator: Use `10.0.2.2` instead of `localhost` - iOS simulator: Use `localhost` or `127.0.0.1` - Physical devices: Use your computer's IP address ### Logs The server logs all requests with timestamps and response codes for debugging. ## License MIT License - See LICENSE file for details.