List Developer Keys
curl --request GET \
--url https://api.devkit4ai.com/api/v1/auth/developer-keys \
--header 'Authorization: Bearer <token>'import requests
url = "https://api.devkit4ai.com/api/v1/auth/developer-keys"
headers = {"Authorization": "Bearer <token>"}
response = requests.get(url, headers=headers)
print(response.text)const options = {method: 'GET', headers: {Authorization: 'Bearer <token>'}};
fetch('https://api.devkit4ai.com/api/v1/auth/developer-keys', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.devkit4ai.com/api/v1/auth/developer-keys",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "GET",
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"net/http"
"io"
)
func main() {
url := "https://api.devkit4ai.com/api/v1/auth/developer-keys"
req, _ := http.NewRequest("GET", url, nil)
req.Header.Add("Authorization", "Bearer <token>")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.get("https://api.devkit4ai.com/api/v1/auth/developer-keys")
.header("Authorization", "Bearer <token>")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.devkit4ai.com/api/v1/auth/developer-keys")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Get.new(url)
request["Authorization"] = 'Bearer <token>'
response = http.request(request)
puts response.read_body[
{
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"name": "<string>",
"key_prefix": "<string>",
"is_active": true,
"last_used_at": "2023-11-07T05:31:56Z",
"created_at": "2023-11-07T05:31:56Z"
}
]Authentication
List Developer Keys
List all developer keys for the current developer user.
GET
/
api
/
v1
/
auth
/
developer-keys
List Developer Keys
curl --request GET \
--url https://api.devkit4ai.com/api/v1/auth/developer-keys \
--header 'Authorization: Bearer <token>'import requests
url = "https://api.devkit4ai.com/api/v1/auth/developer-keys"
headers = {"Authorization": "Bearer <token>"}
response = requests.get(url, headers=headers)
print(response.text)const options = {method: 'GET', headers: {Authorization: 'Bearer <token>'}};
fetch('https://api.devkit4ai.com/api/v1/auth/developer-keys', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://api.devkit4ai.com/api/v1/auth/developer-keys",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "GET",
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"net/http"
"io"
)
func main() {
url := "https://api.devkit4ai.com/api/v1/auth/developer-keys"
req, _ := http.NewRequest("GET", url, nil)
req.Header.Add("Authorization", "Bearer <token>")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.get("https://api.devkit4ai.com/api/v1/auth/developer-keys")
.header("Authorization", "Bearer <token>")
.asString();require 'uri'
require 'net/http'
url = URI("https://api.devkit4ai.com/api/v1/auth/developer-keys")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Get.new(url)
request["Authorization"] = 'Bearer <token>'
response = http.request(request)
puts response.read_body[
{
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"name": "<string>",
"key_prefix": "<string>",
"is_active": true,
"last_used_at": "2023-11-07T05:31:56Z",
"created_at": "2023-11-07T05:31:56Z"
}
]Retrieve all active developer keys for the authenticated developer account. This endpoint returns key metadata including usage timestamps and identification prefixes, but never returns the full key values.
(((REPLACE_THIS_WITH_IMAGE: cloud-admin-developer-keys-list.png: Cloud Admin console showing list of developer keys with names, prefixes, last used timestamps, and action buttons)))
Missing or invalid JWT token.
User role is not
Authentication
Requires valid JWT token withdeveloper role and an active developer key.
Headers
string
required
Bearer JWT access token obtained from login
string
required
Must be set to
developerstring
required
Active developer key for authentication (format:
ak_ + 32 characters)Response
Returns an array of developer key objects without the full key values.string
Unique identifier (UUID) for the developer key
string
Descriptive name assigned to the key (e.g., “Production API”, “Staging Environment”)
string
First 8 characters of the key for identification (e.g.,
ak_abc12)boolean
Key status - only active keys are returned by this endpoint
string
ISO 8601 timestamp of the most recent API request using this key. Returns
null if the key has never been used.string
ISO 8601 timestamp when the key was created
Example Request
curl -X GET https://api.vibecoding.ad/api/v1/auth/developer-keys \
-H "Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9..." \
-H "X-User-Role: developer" \
-H "X-Developer-Key: ak_abc123XYZ-_789def456ghi012jkl345"
Example Response
[
{
"id": "550e8400-e29b-41d4-a716-446655440000",
"name": "Production API",
"key_prefix": "ak_abc12",
"is_active": true,
"last_used_at": "2025-12-07T09:15:00Z",
"created_at": "2025-12-01T10:30:00Z"
},
{
"id": "660e8400-e29b-41d4-a716-446655440001",
"name": "Staging Environment",
"key_prefix": "ak_xyz78",
"is_active": true,
"last_used_at": null,
"created_at": "2025-12-05T14:20:00Z"
},
{
"id": "770e8400-e29b-41d4-a716-446655440002",
"name": "Development Key",
"key_prefix": "ak_dev99",
"is_active": true,
"last_used_at": "2025-12-08T14:30:00Z",
"created_at": "2025-11-15T08:00:00Z"
}
]
Use Cases
Key Management Dashboard
Display all developer keys with usage statistics:async function fetchDeveloperKeys(
jwtToken: string,
developerKey: string
): Promise<DeveloperKey[]> {
const response = await fetch(
'https://api.vibecoding.ad/api/v1/auth/developer-keys',
{
headers: {
'Authorization': `Bearer ${jwtToken}`,
'X-User-Role': 'developer',
'X-Developer-Key': developerKey
}
}
);
if (!response.ok) {
throw new Error('Failed to fetch developer keys');
}
return response.json();
}
Identify Unused Keys
Find keys that haven’t been used recently for rotation:function getUnusedKeys(keys: DeveloperKey[], daysSinceUse: number = 90) {
const cutoffDate = new Date();
cutoffDate.setDate(cutoffDate.getDate() - daysSinceUse);
return keys.filter(key => {
if (!key.last_used_at) return true; // Never used
return new Date(key.last_used_at) < cutoffDate;
});
}
Key Rotation Workflow
Implement automated key rotation:async function rotateOldKeys(
jwtToken: string,
developerKey: string,
maxAgeDays: number = 90
) {
// List all keys
const keys = await fetchDeveloperKeys(jwtToken, developerKey);
// Find keys older than maxAgeDays
const oldKeys = keys.filter(key => {
const created = new Date(key.created_at);
const age = Date.now() - created.getTime();
return age > maxAgeDays * 24 * 60 * 60 * 1000;
});
// Create new keys and revoke old ones
for (const oldKey of oldKeys) {
console.log(`Key ${oldKey.key_prefix} is ${Math.floor((Date.now() - new Date(oldKey.created_at).getTime()) / (24 * 60 * 60 * 1000))} days old`);
// Implementation continues with create and revoke...
}
}
Security Considerations
The
last_used_at timestamp is updated asynchronously and may have a delay of up to 1 minute. Use this for monitoring and auditing, not for real-time access control.Best Practices
- Regular Audits: Review keys monthly to identify unused or unnecessary keys
- Monitor Usage: Track
last_used_atto detect suspicious activity or compromised keys - Name Convention: Use consistent naming (e.g., “Production”, “Staging”, “CI/CD Pipeline”)
- Limit Active Keys: Keep only necessary keys active to minimize attack surface
Error Responses
Unauthorized (401)
{
"detail": "Could not validate credentials"
}
Forbidden (403)
{
"detail": "Insufficient permissions"
}
developer or developer key is invalid.
Related Pages
Create Developer Key
Generate new developer keys
Revoke Developer Key
Deactivate compromised or unused keys
Key Management Guide
Cloud Admin UI workflow
Security Best Practices
Key rotation and security guidelines
Authorizations
The access token received from the authorization server in the OAuth 2.0 flow.

