API Key Management
The API Key Management system allows users to securely store and manage their external service API keys. Keys are encrypted at rest and can be used by the AI agents for enhanced functionality.
Base URL
All API key management endpoints are prefixed with:
Authentication
All API key endpoints require authentication. Include the Bearer token in the Authorization header:
Supported API Key Types
Type | Description | Used For |
---|---|---|
google_api |
Google AI Studio API Key | Gemini AI models and agent functionality |
news_api |
NewsAPI Key | Financial news aggregation and analysis |
Note: Yahoo Finance requires no API key. Finnhub and FMP keys can be stored as general purpose keys.
Data Models
API Key Response
{
"id": 1,
"key_type": "news_api",
"key_name": "My News API Key",
"is_active": true,
"masked_key": "****abcd",
"created_at": "2025-01-15T10:30:00Z",
"updated_at": "2025-01-15T10:30:00Z",
"last_used_at": "2025-01-15T12:00:00Z"
}
API Key Creation
API Key Update
Endpoints
Create API Key
Create a new API key for external service integration.
Request Body
Response
Status Code: 201 Created
{
"id": 1,
"key_type": "news_api",
"key_name": "My News API Key",
"is_active": true,
"masked_key": "****abcd",
"created_at": "2025-01-15T10:30:00Z",
"updated_at": null,
"last_used_at": null
}
Error Responses
400 Bad Request - Invalid data or duplicate key type
Get All API Keys
Retrieve all API keys for the current user.
Query Parameters
Parameter | Type | Required | Description |
---|---|---|---|
include_inactive |
boolean | No | Include inactive keys (default: false) |
Response
Status Code: 200 OK
[
{
"id": 1,
"key_type": "news_api",
"key_name": "My News API Key",
"is_active": true,
"masked_key": "****abcd",
"created_at": "2025-01-15T10:30:00Z",
"updated_at": null,
"last_used_at": "2025-01-15T12:00:00Z"
},
{
"id": 2,
"key_type": "google_api",
"key_name": "Google AI Key",
"is_active": true,
"masked_key": "****xyz9",
"created_at": "2025-01-15T11:00:00Z",
"updated_at": null,
"last_used_at": null
}
]
Get Specific API Key
Retrieve a specific API key by ID.
Path Parameters
Parameter | Type | Description |
---|---|---|
key_id |
integer | ID of the API key to retrieve |
Response
Status Code: 200 OK
{
"id": 1,
"key_type": "news_api",
"key_name": "My News API Key",
"is_active": true,
"masked_key": "****abcd",
"created_at": "2025-01-15T10:30:00Z",
"updated_at": null,
"last_used_at": "2025-01-15T12:00:00Z"
}
Error Responses
404 Not Found
Update API Key
Update an existing API key (name or active status only - not the key value).
Path Parameters
Parameter | Type | Description |
---|---|---|
key_id |
integer | ID of the API key to update |
Request Body
Response
Status Code: 200 OK
{
"id": 1,
"key_type": "news_api",
"key_name": "Updated Key Name",
"is_active": false,
"masked_key": "****abcd",
"created_at": "2025-01-15T10:30:00Z",
"updated_at": "2025-01-15T14:30:00Z",
"last_used_at": "2025-01-15T12:00:00Z"
}
Delete API Key
Delete an API key (soft delete - marks as inactive).
Path Parameters
Parameter | Type | Description |
---|---|---|
key_id |
integer | ID of the API key to delete |
Response
Status Code: 204 No Content
Test API Key by ID
Test the functionality of a stored API key.
Path Parameters
Parameter | Type | Description |
---|---|---|
key_id |
integer | ID of the API key to test |
Response
Status Code: 200 OK
{
"status": "success",
"service": "news_api",
"message": "API key is valid and working",
"response_time_ms": 245,
"tested_at": "2025-01-15T15:00:00Z"
}
Failed Test Response:
{
"status": "error",
"service": "news_api",
"message": "Invalid API key or service unavailable",
"error_code": "UNAUTHORIZED",
"tested_at": "2025-01-15T15:00:00Z"
}
Test API Key by Type
Test the functionality of an API key by service type.
Path Parameters
Parameter | Type | Description |
---|---|---|
key_type |
string | Type of API key to test (google_api , news_api ) |
Response
Status Code: 200 OK
{
"status": "success",
"service": "news_api",
"message": "API key is valid and working",
"response_time_ms": 245,
"tested_at": "2025-01-15T15:00:00Z"
}
Security Features
Encryption
- All API keys are encrypted at rest using symmetric encryption
- Keys are never stored in plain text
- Only the last 4 characters are shown in responses (masked)
Access Control
- Users can only access their own API keys
- Full authentication required for all operations
- Proper authorization checks on all endpoints
Key Testing
- Built-in functionality to test API key validity
- Tests make actual calls to external services
- Results include response time and status information
Usage in AI Agents
When you store API keys, they become available to the AI agents:
- News API: Used by News Analyst agent for real-time financial news
- Google API: Used by all agents for Gemini AI model access
- System Fallbacks: If no user key is provided, system defaults are used (when available)
Examples
Complete API Key Workflow
1. Create a News API Key
curl -X POST "http://localhost:8000/api/v1/api-keys/" \
-H "Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9..." \
-H "Content-Type: application/json" \
-d '{
"key_type": "news_api",
"api_key": "your-news-api-key-here",
"key_name": "My Primary News Key"
}'
2. Test the API Key
curl -X POST "http://localhost:8000/api/v1/api-keys/test-by-type/news_api" \
-H "Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9..."
3. Get All Your Keys
curl -X GET "http://localhost:8000/api/v1/api-keys/" \
-H "Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9..."
JavaScript/TypeScript Examples
// Create API key service
class APIKeyService {
constructor(baseURL, token) {
this.baseURL = baseURL;
this.token = token;
}
async createAPIKey(keyType, apiKey, keyName) {
const response = await fetch(`${this.baseURL}/api/v1/api-keys/`, {
method: 'POST',
headers: {
'Authorization': `Bearer ${this.token}`,
'Content-Type': 'application/json'
},
body: JSON.stringify({
key_type: keyType,
api_key: apiKey,
key_name: keyName
})
});
return await response.json();
}
async testAPIKey(keyType) {
const response = await fetch(`${this.baseURL}/api/v1/api-keys/test-by-type/${keyType}`, {
method: 'POST',
headers: {
'Authorization': `Bearer ${this.token}`
}
});
return await response.json();
}
async getAllAPIKeys(includeInactive = false) {
const response = await fetch(`${this.baseURL}/api/v1/api-keys/?include_inactive=${includeInactive}`, {
headers: {
'Authorization': `Bearer ${this.token}`
}
});
return await response.json();
}
}
// Usage
const apiKeyService = new APIKeyService('http://localhost:8000', 'your-jwt-token');
// Create a new API key
const newKey = await apiKeyService.createAPIKey('news_api', 'your-api-key', 'My News Key');
// Test the key
const testResult = await apiKeyService.testAPIKey('news_api');
// Get all keys
const allKeys = await apiKeyService.getAllAPIKeys();
Related APIs
- Authentication API - User authentication and token management
- Market Data API - Market data endpoints that use these keys
- Chat API - AI chat that leverages stored API keys
- Users API - User management and preferences
Best Practices
- Key Naming: Use descriptive names for your API keys
- Testing: Regularly test your API keys to ensure they're still valid
- Rotation: Update API keys periodically for security
- Monitoring: Check the
last_used_at
field to monitor key usage - Cleanup: Remove or deactivate unused API keys