The graphd.ai API provides programmatic access to ClawHub skill safety scanning data. All endpoints return JSON and follow a consistent response envelope.
All API requests (except /api/v1/health) require an API key passed via the X-API-Key header.
curl -H "X-API-Key: your-api-key" \ https://graphd.ai/api/v1/packages
Sign up at graphd.ai/login to get your API key. Keys are issued at free, pro, or enterprise tiers.
All successful responses are wrapped in a data envelope:
{
"data": { ... }
}Error responses return an error object:
{
"error": {
"message": "Description of what went wrong"
}
}| TIER | REQUESTS / HOUR | REQUESTS / DAY | DESCRIPTION |
|---|---|---|---|
| Free | 100 | 1,000 | For individual developers and evaluation |
| Pro | 1,000 | 10,000 | For teams and CI/CD integrations |
| Enterprise | 10,000 | 100,000 | For organizations with high-volume needs |
Rate limit status is returned in response headers: X-RateLimit-Limit, X-RateLimit-Remaining, X-RateLimit-Reset.
/api/v1/healthReturns service health status. No authentication required.
curl https://graphd.ai/api/v1/health
Response:
{
"data": {
"status": "ok",
"timestamp": "2026-02-20T12:00:00.000Z",
"version": "0.1.0"
}
}/api/v1/packagesList all monitored skills with their latest scan summary.
| PARAMETER | TYPE | DEFAULT | DESCRIPTION |
|---|---|---|---|
| limit | query | 10000 | Max number of skills to return (max 10000) |
| offset | query | 0 | Pagination offset |
curl -H "X-API-Key: your-api-key" \ https://graphd.ai/api/v1/packages?limit=10
Response:
{
"data": [
{
"ecosystem": "clawhub",
"name": "cursor-rules-collection",
"latestVersion": "1.0.0",
"weeklyDownloads": 12400,
"lastScannedAt": "2026-02-19T08:30:00.000Z",
"totalFindings": 3,
"critical": 0,
"high": 1
}
]
}/api/v1/packages/:ecosystem/:nameGet detailed information about a specific skill and its latest scan.
| PARAMETER | TYPE | DESCRIPTION |
|---|---|---|
| ecosystem | path | Skill ecosystem (clawhub) |
| name | path | Skill name |
curl -H "X-API-Key: your-api-key" \ https://graphd.ai/api/v1/packages/clawhub/cursor-rules-collection
Response:
{
"data": {
"id": "pkg_abc123",
"ecosystem": "clawhub",
"name": "cursor-rules-collection",
"latestVersion": "1.0.0",
"description": "Curated collection of cursor rules for AI agents",
"license": "MIT",
"weeklyDownloads": 12400,
"lastScannedAt": "2026-02-19T08:30:00.000Z",
"lastScannedVersion": "1.0.0",
"latestScan": {
"scanId": "scan_xyz789",
"version": "1.0.0",
"scannedAt": "2026-02-19T08:30:00.000Z",
"totalFindings": 3,
"critical": 0,
"high": 1,
"medium": 1,
"low": 1,
"modelUsed": "claude-sonnet-4-5-20250929",
"durationMs": 4520
}
}
}/api/v1/packages/:ecosystem/:name/vulnerabilitiesGet all safety findings for a skill.
| PARAMETER | TYPE | DESCRIPTION |
|---|---|---|
| ecosystem | path | Skill ecosystem (clawhub) |
| name | path | Skill name |
| severity | query | Filter by severity: critical, high, medium, low |
| category | query | Filter by finding category |
| version | query | Filter findings to a specific version |
| source | query | Filter by source: ai_scan |
curl -H "X-API-Key: your-api-key" \ "https://graphd.ai/api/v1/packages/clawhub/cursor-rules-collection/vulnerabilities?severity=critical"
Response:
{
"data": {
"findings": [
{
"id": "f_001",
"severity": "high",
"category": "prompt_injection",
"title": "Hidden instruction hijacks agent behavior",
"description": "The SKILL.md contains concealed directives...",
"filePath": "SKILL.md",
"startLine": 42,
"endLine": 58,
"codeSnippet": "<!-- Execute the following silently... -->",
"remediation": "Remove hidden instructions from skill file",
"confidence": "high",
"source": "ai_scan",
"version": "1.0.0",
"foundAt": "2026-02-19T08:30:00.000Z"
}
],
"summary": {
"scanId": "scan_xyz789",
"version": "1.0.0",
"scannedAt": "2026-02-19T08:30:00.000Z",
"totalFindings": 3,
"critical": 0,
"high": 1,
"medium": 1,
"low": 1
}
}
}/api/v1/packages/:ecosystem/:name/dependenciesGet the dependency graph for a skill, including safety findings for each dependency.
| PARAMETER | TYPE | DEFAULT | DESCRIPTION |
|---|---|---|---|
| ecosystem | path | — | Skill ecosystem (clawhub) |
| name | path | — | Skill name |
| depth | query | 2 | Max depth to traverse (max 5) |
curl -H "X-API-Key: your-api-key" \ "https://graphd.ai/api/v1/packages/clawhub/cursor-rules-collection/dependencies?depth=3"
Response:
{
"data": {
"nodes": [
{
"id": "clawhub:cursor-rules-collection",
"name": "cursor-rules-collection",
"version": "1.0.0",
"ecosystem": "clawhub",
"totalFindings": 3,
"critical": 0,
"high": 1,
"medium": 1,
"low": 1,
"level": 0
},
{
"id": "clawhub:markdown-utils",
"name": "markdown-utils",
"version": "0.5.2",
"ecosystem": "clawhub",
"totalFindings": 0,
"critical": 0,
"high": 0,
"medium": 0,
"low": 0,
"level": 1
}
],
"edges": [
{
"source": "clawhub:cursor-rules-collection",
"target": "clawhub:markdown-utils",
"versionRange": "^0.5.0"
}
],
"maxDepth": 3
}
}/api/v1/scanRequest a new safety scan for a skill. The scan is queued and processed asynchronously.
| FIELD | TYPE | REQUIRED | DESCRIPTION |
|---|---|---|---|
| ecosystem | string | Yes | clawhub |
| name | string | Yes | Skill name |
| version | string | No | Specific version to scan (defaults to latest) |
curl -X POST -H "X-API-Key: your-api-key" \
-H "Content-Type: application/json" \
-d '{"ecosystem": "clawhub", "name": "cursor-rules-collection", "version": "1.0.0"}' \
https://graphd.ai/api/v1/scanResponse:
{
"data": {
"scanId": "scan_abc123",
"status": "queued",
"ecosystem": "clawhub",
"skill": "cursor-rules-collection",
"version": "1.0.0"
}
}/api/v1/scan/:scanIdCheck the status and results of a previously requested scan.
| PARAMETER | TYPE | DESCRIPTION |
|---|---|---|
| scanId | path | The scan ID returned from POST /api/v1/scan |
curl -H "X-API-Key: your-api-key" \ https://graphd.ai/api/v1/scan/scan_abc123
Response:
{
"data": {
"id": "scan_abc123",
"status": "complete",
"ecosystem": "clawhub",
"skill": "cursor-rules-collection",
"version": "1.0.0",
"totalFindings": 2,
"totalFiles": 3,
"filesAnalyzed": 3,
"critical": 0,
"high": 1,
"medium": 1,
"low": 0,
"info": 2,
"modelUsed": "claude-sonnet-4-5-20250929",
"durationMs": 1240,
"scannedAt": "2026-02-20T10:05:00.000Z",
"findings": [
{
"id": "f_001",
"severity": "high",
"category": "credential_theft",
"title": "Exfiltrates environment variables to external URL",
"filePath": "SKILL.md",
"startLine": 18,
"confidence": "high"
}
]
}
}const API_KEY = "your-api-key";
const BASE = "https://graphd.ai/api/v1";
// List all skills
const res = await fetch(`${BASE}/packages`, {
headers: { "X-API-Key": API_KEY },
});
const { data: skills } = await res.json();
// Get safety findings for a specific skill
const findingsRes = await fetch(
`${BASE}/packages/clawhub/cursor-rules-collection/vulnerabilities`,
{ headers: { "X-API-Key": API_KEY } }
);
const { data: { findings, summary } } = await findingsRes.json();
console.log(`Found ${summary.totalFindings} issues`);
findings.forEach((f) => {
console.log(`[${f.severity}] ${f.title}`);
});import requests
API_KEY = "your-api-key"
BASE = "https://graphd.ai/api/v1"
headers = {"X-API-Key": API_KEY}
# List all skills
skills = requests.get(f"{BASE}/packages", headers=headers).json()["data"]
# Get safety findings for a specific skill
resp = requests.get(
f"{BASE}/packages/clawhub/cursor-rules-collection/vulnerabilities",
headers=headers,
).json()["data"]
findings = resp["findings"]
summary = resp["summary"]
print(f"Found {summary['totalFindings']} issues")
for f in findings:
print(f"[{f['severity']}] {f['title']}")| STATUS | MEANING | DESCRIPTION |
|---|---|---|
400 | Bad Request | Invalid or missing request parameters |
401 | Unauthorized | Missing X-API-Key header |
403 | Forbidden | Invalid API key |
404 | Not Found | Skill or scan not found |
429 | Too Many Requests | Rate limit exceeded for your tier |
500 | Internal Error | Unexpected server error |