Programmatic access to Axiomo analysis
Axiomo provides a JSON API for programmatic PR analysis. Use it to integrate Axiomo into your CI/CD pipelines, bots, or custom tooling.
The API supports two authentication methods:
For programmatic access, use API keys. Get yours from Settings.
Include your API key in the Authorization header:
Authorization: Bearer ax_your_key_here
API keys use your connected provider tokens, so they work with private repositories you have access to.
You can also pass a provider token directly in the request body:
{
"url": "https://github.com/owner/private-repo/pull/123",
"access_token": "ghp_xxxxxxxxxxxx"
}
Note: Never expose tokens in client-side code. Use API keys with server-side requests.
No authentication is required for public repositories, but you'll be subject to lower rate limits.
Analyze a pull request and generate an Axiomo Signal.
Content-Type: application/json
You can provide either a PR URL or explicit parameters:
{
"url": "https://github.com/owner/repo/pull/123",
"access_token": "ghp_xxxxxxxxxxxx" // optional
}
{
"provider": "github",
"owner": "owner",
"repo": "repo",
"pr_number": 123,
"access_token": "ghp_xxxxxxxxxxxx" // optional
}
| Field | Type | Required | Description |
|---|---|---|---|
url |
string | * | Full PR URL (e.g., https://github.com/owner/repo/pull/123) |
provider |
string | * | Git provider: "github" (more coming soon) |
owner |
string | * | Repository owner/organization |
repo |
string | * | Repository name |
pr_number |
integer | * | Pull request number |
access_token |
string | No | GitHub personal access token for private repos |
* Either url OR all of provider, owner, repo, pr_number are required.
Success (200):
{
"signal_id": "ax-owner-repo-123-a1b2c3d4",
"signal_url": "https://axiomo.app/s/ax-owner-repo-123-a1b2c3d4",
"signal": {
"version": "axiomo.signal.v1",
"signal_id": "ax-owner-repo-123-a1b2c3d4",
"pr": { ... },
"risk": { ... },
"contributors": [ ... ],
"evidence": { ... },
"supply_chain": { ... },
"focus": { ... },
"triage": { ... },
"review": { ... },
"meta": { ... }
}
}
Bad Request (400):
{
"error": "Invalid PR URL. Supported: GitHub PR URLs"
}
Server Error (500):
{
"error": "Analysis failed: ...",
"detail": "Error details"
}
Retrieve a previously generated signal by its scan ID.
No request body required. Authentication is optional (scan IDs are unguessable).
GET /api/scans/scan-a1b2c3d4e5f6
Success (200):
{
"signal_id": "ax-owner-repo-123-a1b2c3d4",
"scan_id": "scan-a1b2c3d4e5f6",
"signal": { ... },
"created_at": "2024-01-26T12:00:00Z"
}
Not Found (404):
{
"detail": "Scan not found"
}
The signal object contains the full analysis. Key sections:
PR metadata: provider, owner, repo, number, title, author, branches, timestamps.
Risk assessment with level (low/medium/high/critical), score (0-1), and drivers explaining why.
Array of contributor profiles with trust levels, account age, prior PRs, and context.
CI/test signals with completeness score and individual check statuses.
Dependency and CI config changes: new dependencies, lockfile mods, CI file changes.
Prioritized list of files to review, ranked by importance.
Review effort estimate, staleness risk, and recommendations.
Suggested action (approve/comment/request_changes/needs_discussion) with rationale and draft comments.
See the main documentation for detailed explanations of each section.
API rate limits depend on your authentication:
Rate limit headers are included in all responses:
X-RateLimit-Limit: Maximum requests allowedX-RateLimit-Remaining: Requests remainingX-RateLimit-Reset: Unix timestamp when limit resets# Public PR (no auth)
curl -X POST https://axiomo.app/api/analyze \
-H "Content-Type: application/json" \
-d '{"url": "https://github.com/facebook/react/pull/28000"}'
# Private PR (with API key)
curl -X POST https://axiomo.app/api/analyze \
-H "Content-Type: application/json" \
-H "Authorization: Bearer ax_your_key_here" \
-d '{"url": "https://github.com/your-org/private-repo/pull/42"}'
import requests
# With API key for private repos
response = requests.post(
"https://axiomo.app/api/analyze",
headers={"Authorization": "Bearer ax_your_key_here"},
json={"url": "https://github.com/your-org/private-repo/pull/42"}
)
signal = response.json()["signal"]
print(f"Risk: {signal['risk']['level']} ({signal['risk']['score']})")
// With API key for private repos
const response = await fetch("https://axiomo.app/api/analyze", {
method: "POST",
headers: {
"Content-Type": "application/json",
"Authorization": "Bearer ax_your_key_here"
},
body: JSON.stringify({
url: "https://github.com/your-org/private-repo/pull/42"
})
});
const { signal } = await response.json();
console.log(`Risk: ${signal.risk.level}`);