{"openapi":"3.0.3","info":{"title":"API Test Lab REST API","version":"1.0.0","description":"Official OpenAPI 3.0 specification for API Test Lab. Includes endpoints for automated REST/GraphQL testing, load simulation, uptime monitoring, AI error analysis, and API key management.","contact":{"name":"API Test Lab Support","url":"https://www.apitestlab.org/contact","email":"hi@apitestlab.org"},"license":{"name":"Proprietary","url":"https://www.apitestlab.org/terms"}},"servers":[{"url":"https://api.apitestlab.org","description":"Production API Server"},{"url":"http://127.0.0.1:8000","description":"Local Development Server"}],"tags":[{"name":"Authentication","description":"User login, signup, OTP verification, password resets, and session tokens"},{"name":"API Keys","description":"Self-serve API key creation, listing, and revocation for CI/CD automation"},{"name":"Tests & Execution","description":"Ad-hoc REST testing, script execution, and AI analysis"},{"name":"Saved Requests & Collections","description":"Manage saved request templates, folders, workflows, and collection runs"},{"name":"Load Testing","description":"Simulate concurrent user traffic, monitor real-time test progress, and view performance percentiles"},{"name":"Uptime Monitors","description":"Configure automated endpoint health checks, interval schedules, and alerts"},{"name":"GraphQL","description":"Schema introspection, GraphQL query execution, and saved query library"},{"name":"Web Analysis & Scanner","description":"Security, performance, and header analysis of web endpoints"},{"name":"Traffic Monitoring","description":"Real-time telemetry, response trends, and recorded anomaly statistics"},{"name":"User Profile & Usage","description":"Account settings, tier quota usage, and notification preferences"}],"paths":{"/api/auth/login":{"post":{"tags":["Authentication"],"summary":"Authenticate user with email and password","description":"Authenticates a user using credentials and returns JWT access and refresh tokens.","operationId":"loginUser","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["email","password"],"properties":{"email":{"type":"string","format":"email","example":"developer@example.com"},"password":{"type":"string","format":"password","example":"SecurePassword123!"}}}}}},"responses":{"200":{"description":"Authentication successful","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthResponse"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"429":{"$ref":"#/components/responses/TooManyRequests"}}}},"/api/auth/signup":{"post":{"tags":["Authentication"],"summary":"Create a new user account","description":"Registers a new user on the Free tier without requiring a credit card.","operationId":"signupUser","requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["email","password"],"properties":{"email":{"type":"string","format":"email","example":"newuser@example.com"},"password":{"type":"string","format":"password","example":"SecretP@ss123"},"name":{"type":"string","example":"Jane Dev"}}}}}},"responses":{"201":{"description":"Account created successfully","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthResponse"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"429":{"$ref":"#/components/responses/TooManyRequests"}}}},"/api/api-keys":{"get":{"tags":["API Keys"],"summary":"List user API keys","description":"Retrieves all active API keys created by the authenticated user, including key prefixes and last used timestamps.","operationId":"listApiKeys","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"responses":{"200":{"description":"List of API keys","content":{"application/json":{"schema":{"type":"object","properties":{"keys":{"type":"array","items":{"$ref":"#/components/schemas/ApiKeyItem"}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}},"post":{"tags":["API Keys"],"summary":"Generate a new API key","description":"Self-serve generation of an API key for CI/CD and automation. The raw secret key is returned only once.","operationId":"createApiKey","security":[{"BearerAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"name":{"type":"string","example":"GitHub Actions CI","description":"Label identifying where this key is used"}}}}}},"responses":{"201":{"description":"API key generated successfully","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","example":"key_9823abf"},"name":{"type":"string","example":"GitHub Actions CI"},"api_key":{"type":"string","example":"apt_live_98371bd9823abf89234710293847"},"key_prefix":{"type":"string","example":"apt_live_98"},"created_at":{"type":"string","format":"date-time"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/api/api-keys/{id}":{"delete":{"tags":["API Keys"],"summary":"Revoke an API key","description":"Permanently deletes and revokes an API key by ID.","operationId":"revokeApiKey","security":[{"BearerAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"},"description":"The unique ID of the API key to revoke"}],"responses":{"200":{"description":"API key revoked successfully","content":{"application/json":{"schema":{"type":"object","properties":{"success":{"type":"boolean","example":true},"message":{"type":"string","example":"API key revoked"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/api/tests/run":{"post":{"tags":["Tests & Execution"],"summary":"Execute an ad-hoc API test","description":"Sends an HTTP request to the target URL, verifies assertions, and measures response latency.","operationId":"runApiTest","security":[{"ApiKeyAuth":[]},{"BearerAuth":[]},{}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TestRunRequest"}}}},"responses":{"200":{"description":"Test executed successfully","content":{"application/json":{"schema":{"$ref":"#/components/schemas/TestRunResult"}}}},"400":{"$ref":"#/components/responses/BadRequest"},"429":{"$ref":"#/components/responses/TooManyRequests"}}}},"/api/tests/ai-explain":{"post":{"tags":["Tests & Execution"],"summary":"Get AI diagnosis of an API test error","description":"Provides plain-English explanation and fix recommendations for failed test responses.","operationId":"explainTestWithAI","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","required":["status_code","response_body"],"properties":{"status_code":{"type":"integer","example":502},"response_body":{"type":"string","example":"{\"error\":\"Bad Gateway\",\"details\":\"Connection reset\"}"},"request_url":{"type":"string","example":"https://api.example.com/checkout"}}}}}},"responses":{"200":{"description":"AI explanation generated","content":{"application/json":{"schema":{"type":"object","properties":{"explanation":{"type":"string"},"root_cause":{"type":"string"},"suggested_fix":{"type":"string"}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/api/requests/list":{"get":{"tags":["Saved Requests & Collections"],"summary":"List saved requests and collections","description":"Retrieves the folder tree, saved requests, and environment presets for the authenticated user.","operationId":"listSavedRequests","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Saved requests and collections retrieved","content":{"application/json":{"schema":{"type":"object","properties":{"requests":{"type":"array","items":{"$ref":"#/components/schemas/SavedRequest"}},"folders":{"type":"array","items":{"type":"object"}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/api/requests/create":{"post":{"tags":["Saved Requests & Collections"],"summary":"Save a request to collection","description":"Creates a new saved request template with headers, params, and assertions in a collection folder.","operationId":"createSavedRequest","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/SavedRequestInput"}}}},"responses":{"201":{"description":"Request saved successfully","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SavedRequest"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/api/load-tester/create":{"post":{"tags":["Load Testing"],"summary":"Create and launch a load test simulation","description":"Initializes a load testing job simulating concurrent virtual users against target endpoints.","operationId":"createLoadTest","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LoadTestConfig"}}}},"responses":{"201":{"description":"Load test created and started","content":{"application/json":{"schema":{"type":"object","properties":{"id":{"type":"string","example":"load_8372109"},"status":{"type":"string","example":"running"},"ws_url":{"type":"string","example":"/api/load-tester/ws/monitor/load_8372109"}}}}}},"400":{"$ref":"#/components/responses/BadRequest"},"401":{"$ref":"#/components/responses/Unauthorized"},"429":{"$ref":"#/components/responses/TooManyRequests"}}}},"/api/load-tester/{id}":{"get":{"tags":["Load Testing"],"summary":"Get load test metrics and progress","description":"Retrieves current status, p50/p95/p99 latencies, requests per second, and error count.","operationId":"getLoadTestStatus","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"},"description":"The unique ID of the load test"}],"responses":{"200":{"description":"Load test metrics retrieved","content":{"application/json":{"schema":{"$ref":"#/components/schemas/LoadTestStatus"}}}},"401":{"$ref":"#/components/responses/Unauthorized"},"404":{"$ref":"#/components/responses/NotFound"}}}},"/api/uptime/monitors":{"get":{"tags":["Uptime Monitors"],"summary":"List uptime monitors","description":"Retrieves all configured uptime monitors and their latest status.","operationId":"listUptimeMonitors","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"responses":{"200":{"description":"List of uptime monitors","content":{"application/json":{"schema":{"type":"object","properties":{"monitors":{"type":"array","items":{"$ref":"#/components/schemas/UptimeMonitorItem"}}}}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}},"post":{"tags":["Uptime Monitors"],"summary":"Create an uptime monitor","description":"Creates a new automated periodic health check against an endpoint.","operationId":"createUptimeMonitor","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UptimeMonitorInput"}}}},"responses":{"201":{"description":"Uptime monitor created","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UptimeMonitorItem"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}},"/api/users/me":{"get":{"tags":["User Profile & Usage"],"summary":"Get current user profile and plan limits","description":"Returns authenticated user details, plan tier (free, pro, max), and monthly quota usage.","operationId":"getCurrentUser","security":[{"BearerAuth":[]},{"ApiKeyAuth":[]}],"responses":{"200":{"description":"Current user profile retrieved","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UserProfile"}}}},"401":{"$ref":"#/components/responses/Unauthorized"}}}}},"components":{"securitySchemes":{"ApiKeyAuth":{"type":"apiKey","in":"header","name":"X-API-Key","description":"Self-serve user API key generated from Account Settings. Grants account-level access to execute tests, trigger load runs, and manage collections in CI/CD."},"BearerAuth":{"type":"http","scheme":"bearer","bearerFormat":"JWT","description":"JWT session access token obtained from /api/auth/login or /api/auth/signup."}},"schemas":{"AuthResponse":{"type":"object","properties":{"token":{"type":"string","description":"JWT access token"},"refresh_token":{"type":"string","description":"JWT refresh token"},"expires_in":{"type":"integer","example":3600},"user":{"$ref":"#/components/schemas/UserProfile"}}},"UserProfile":{"type":"object","properties":{"id":{"type":"string","example":"usr_8923ab"},"email":{"type":"string","format":"email","example":"developer@example.com"},"name":{"type":"string","example":"Jane Dev"},"plan":{"type":"string","enum":["free","pro","max"],"example":"free"},"tests_used":{"type":"integer","example":12},"tests_limit":{"type":"integer","example":100}}},"ApiKeyItem":{"type":"object","properties":{"id":{"type":"string","example":"key_1928374"},"name":{"type":"string","example":"GitHub Actions"},"key_prefix":{"type":"string","example":"apt_live_4a"},"created_at":{"type":"string","format":"date-time"},"last_used_at":{"type":"string","format":"date-time","nullable":true}}},"TestRunRequest":{"type":"object","required":["url","method"],"properties":{"url":{"type":"string","example":"https://httpbin.org/get"},"method":{"type":"string","enum":["GET","POST","PUT","DELETE","PATCH","HEAD","OPTIONS"],"example":"GET"},"headers":{"type":"object","additionalProperties":{"type":"string"},"example":{"Accept":"application/json"}},"params":{"type":"object","additionalProperties":{"type":"string"}},"body":{"type":"string","example":"{\"query\": \"data\"}"},"timeout_ms":{"type":"integer","example":10000}}},"TestRunResult":{"type":"object","properties":{"status":{"type":"integer","example":200},"status_text":{"type":"string","example":"OK"},"latency_ms":{"type":"number","example":142.5},"headers":{"type":"object","additionalProperties":{"type":"string"}},"body":{"type":"string"},"size_bytes":{"type":"integer","example":450},"passed_assertions":{"type":"integer","example":3},"total_assertions":{"type":"integer","example":3}}},"SavedRequestInput":{"type":"object","required":["name","url","method"],"properties":{"name":{"type":"string","example":"Get User Profile"},"url":{"type":"string","example":"https://api.example.com/v1/users/me"},"method":{"type":"string","example":"GET"},"folder_id":{"type":"string","nullable":true},"headers":{"type":"object","additionalProperties":{"type":"string"}},"body":{"type":"string"}}},"SavedRequest":{"type":"object","properties":{"id":{"type":"string","example":"req_81923"},"name":{"type":"string","example":"Get User Profile"},"url":{"type":"string","example":"https://api.example.com/v1/users/me"},"method":{"type":"string","example":"GET"},"folder_id":{"type":"string","nullable":true},"created_at":{"type":"string","format":"date-time"},"updated_at":{"type":"string","format":"date-time"}}},"LoadTestConfig":{"type":"object","required":["target_url","method","concurrency","duration_seconds"],"properties":{"name":{"type":"string","example":"Checkout Load Test"},"target_url":{"type":"string","example":"https://api.example.com/v1/checkout"},"method":{"type":"string","example":"POST"},"concurrency":{"type":"integer","minimum":1,"maximum":500,"example":50},"duration_seconds":{"type":"integer","minimum":5,"maximum":86400,"example":60},"headers":{"type":"object","additionalProperties":{"type":"string"}},"body":{"type":"string"}}},"LoadTestStatus":{"type":"object","properties":{"id":{"type":"string","example":"load_8372109"},"status":{"type":"string","enum":["pending","running","completed","failed","stopped"],"example":"completed"},"total_requests":{"type":"integer","example":12450},"success_rate":{"type":"number","example":99.8},"rps":{"type":"number","example":207.5},"latency_p50":{"type":"number","example":45.2},"latency_p95":{"type":"number","example":110.6},"latency_p99":{"type":"number","example":195}}},"UptimeMonitorInput":{"type":"object","required":["name","url","interval_minutes"],"properties":{"name":{"type":"string","example":"Primary API Gateway"},"url":{"type":"string","example":"https://api.example.com/health"},"interval_minutes":{"type":"integer","enum":[5,10,15,30,60],"example":5},"expected_status":{"type":"integer","example":200}}},"UptimeMonitorItem":{"type":"object","properties":{"id":{"type":"string","example":"mon_98312"},"name":{"type":"string","example":"Primary API Gateway"},"url":{"type":"string","example":"https://api.example.com/health"},"status":{"type":"string","enum":["up","down","paused"],"example":"up"},"uptime_percentage_30d":{"type":"number","example":99.98},"last_check_at":{"type":"string","format":"date-time"}}},"ErrorResponse":{"type":"object","properties":{"error":{"type":"string","example":"Bad Request"},"message":{"type":"string","example":"Invalid parameter provided"}}}},"responses":{"BadRequest":{"description":"Invalid input parameters or request body","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}},"Unauthorized":{"description":"Missing, expired, or invalid authentication credentials","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}},"NotFound":{"description":"The specified resource was not found","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}},"TooManyRequests":{"description":"Rate limit or plan tier quota exceeded","headers":{"Retry-After":{"schema":{"type":"integer"},"description":"Number of seconds to wait before retrying"},"RateLimit-Limit":{"schema":{"type":"integer"},"description":"The maximum number of requests allowed in the current time window"},"RateLimit-Remaining":{"schema":{"type":"integer"},"description":"The number of remaining requests allowed in the current time window"},"RateLimit-Reset":{"schema":{"type":"integer"},"description":"Seconds remaining until the current rate limit window resets"}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}}