Build on the
MegaExams question bank.
A simple REST API to read and create questions, list and inspect exams, pull published results, and browse the library - all scoped to your organization, all over plain JSON.
https://megaexams.com/api/v1
{ "data": ..., "meta": ... }
Authentication
One Bearer key per organization
Create a key in the admin panel under Settings > API access. This card is visible to the organization owner only.
Name the key, pick its scopes, and create it. The full key is shown once - copy it immediately. We store only a hash, so it can never be shown again. You can revoke a key at any time.
Send it as a Bearer token on every request:
A request without the required scope returns 403 insufficient_scope. Keys only ever see their own organization's data.
# Set your key and base URL KEY="mx_live_your_key_here" BASE="https://megaexams.com/api/v1" # Every request carries the Bearer token curl -s "$BASE/questions?per_page=3" \ -H "Authorization: Bearer $KEY"
Every authenticated response includes X-RateLimit-Limit and X-RateLimit-Remaining headers. Over the limit returns 429 rate_limited.
Endpoint reference
Eight endpoints, one bank
/questions
scope: questions:read
List the organization's question bank. Filter by type, difficulty, grade, subject_id, chapter_id, topic_id, tag, q (text search), and language. Paginate with page and per_page.
curl -s "$BASE/questions?type=mcq&per_page=3" \ -H "Authorization: Bearer $KEY"
{
"data": [
{
"id": "f17c4bc1-3e16-476a-aa48-1b91b0739aae",
"type": "mcq",
"difficulty": "easy",
"language": "en",
"question_text": "What is 2+2?",
"points": 1,
"negative_marks": 0,
"curriculum": { "subject": "Mathematics", "chapter": "Arithmetic", "topic": "Addition" },
"tags": ["api-test", "math"],
"created_at": "2026-06-11T15:11:17Z"
}
],
"meta": { "page": 1, "per_page": 3, "total": 8, "total_pages": 3 }
}
/questions/{id}
scope: questions:read
Fetch a single question with its type-specific fields: options for MCQ, accepted_answers for fill_blank, and rubric / model_answer / word_limit for essay.
curl -s "$BASE/questions/f17c4bc1-3e16-476a-aa48-1b91b0739aae" \ -H "Authorization: Bearer $KEY"
{
"data": {
"id": "f17c4bc1-3e16-476a-aa48-1b91b0739aae",
"type": "mcq",
"question_text": "What is 2+2?",
"points": 1,
"options": [
{ "id": "a90fe079-...", "option_text": "4", "is_correct": true, "sort_order": 0 },
{ "id": "451e807d-...", "option_text": "5", "is_correct": false, "sort_order": 1 }
],
"images": []
}
}
/questions
scope: questions:write
Create a question in your bank. category_path resolves a "Subject > Chapter > Topic" path. MCQ needs at least 2 options with at least 1 correct. Returns 201 with the created question.
curl -s -X POST "$BASE/questions" \
-H "Authorization: Bearer $KEY" \
-H "Content-Type: application/json" \
-d '{
"type": "mcq",
"question_text": "Which planet is known as the Red Planet?",
"difficulty": "easy",
"category_path": "Physics > Laws of Motion > Newton's First Law",
"tags": ["astronomy"],
"options": [
{ "option_text": "Mars", "is_correct": true },
{ "option_text": "Venus", "is_correct": false }
]
}'
{
"data": {
"id": "86b9e62e-80ca-421c-b4ff-5a6703d13768",
"type": "mcq",
"question_text": "Which planet is known as the Red Planet?",
"curriculum": { "subject": "Physics", "chapter": "Laws of Motion", "topic": "Newton's First Law" },
"tags": ["api-docs", "astronomy"],
"options": [
{ "id": "5534564f-...", "option_text": "Mars", "is_correct": true, "sort_order": 0 }
],
"images": []
}
}
/taxonomy
scope: questions:read
Your full Subject > Chapter > Topic tree.
curl -s "$BASE/taxonomy" -H "Authorization: Bearer $KEY"
{
"data": [
{
"id": "e081ee4e-...",
"name": "Mathematics",
"chapters": [
{
"id": "24b941c7-...",
"name": "Arithmetic",
"topics": [ { "id": "a1fac685-...", "name": "Addition" } ]
}
]
}
]
}
/exams
scope: exams:read
List the organization's exams. Filter by status (draft | active | inactive). Paginate with page and per_page.
curl -s "$BASE/exams?status=active&per_page=2" \ -H "Authorization: Bearer $KEY"
{
"data": [
{
"id": "315c41d9-b4f5-4590-80d6-d4c9b0159115",
"title": "PlayerTest IBPS Fast",
"slug": "ptst01",
"status": "active",
"visibility": "link",
"question_count": 4,
"negative_marking": true,
"shuffle_scope": "section",
"share_url": "https://megaexams.com/e/ptst01",
"created_at": "2026-06-11T14:39:09Z"
}
],
"meta": { "page": 1, "per_page": 2, "total": 10, "total_pages": 5 }
}
/exams/{id}
scope: exams:read
Fetch an exam with its sections and questions. Option is_correct is included only if the key also holds questions:read.
curl -s "$BASE/exams/315c41d9-b4f5-4590-80d6-d4c9b0159115" \ -H "Authorization: Bearer $KEY"
{
"data": {
"id": "315c41d9-...",
"title": "PlayerTest IBPS Fast",
"status": "active",
"sections": [
{ "id": "05064e13-...", "name": "Reasoning", "sort_order": 0, "time_limit_mins": 1, "instructions": "Answer all questions in order." }
],
"questions": [
{
"id": "b0845d82-...",
"type": "mcq",
"question_text": "Which number completes the series 2, 4, 8, 16, ?",
"points": 2,
"section_id": "05064e13-...",
"sort_order": 0,
"options": [
{ "id": "20761d38-...", "option_text": "32", "sort_order": 1, "is_correct": true }
]
}
]
}
}
/exams/{id}/results
scope: results:read
Published, ranked results for an exam, including per-student scores and section breakdowns. Paginate with page and per_page.
curl -s "$BASE/exams/315c41d9-b4f5-4590-80d6-d4c9b0159115/results?per_page=5" \ -H "Authorization: Bearer $KEY"
{
"data": [
{
"id": "17475d85-...",
"student": { "name": "Ravi Tester", "city": "Chennai", "class_grade": "9", "institution": "Demo Public School" },
"marks_obtained": 0,
"total_marks": 10,
"percentage": 0,
"correct": 0,
"incorrect": 0,
"unanswered": 4,
"rank_overall": 1,
"total_time_secs": 121,
"submitted_at": "2026-06-11T14:44:41Z",
"section_scores": [
{ "section_name": "Quant", "marks_obtained": 0, "total_marks": 7 }
]
}
],
"meta": { "page": 1, "per_page": 5, "total": 1, "total_pages": 1 }
}
/library
scope: exams:read
Pre-made papers visible to your organization (platform papers and parent-organization shares).
curl -s "$BASE/library" -H "Authorization: Bearer $KEY"
{
"data": [
{
"id": "add7bcee-...",
"title": "Class 9 Physics - Laws of Motion (Unit Test)",
"source": "platform",
"question_count": 3,
"total_points": 7,
"time_limit_mins": 20,
"language": "en"
}
],
"meta": { "page": 1, "per_page": 1, "total": 1, "total_pages": 1 }
}
Error codes
Predictable, machine-readable errors
Errors always use the envelope { "error": { "code", "message" } } with the matching HTTP status.
| HTTP | code | When |
|---|---|---|
| 400 | invalid_request | The POST body is not a JSON object |
| 401 | invalid_api_key | Missing, malformed, unknown, or revoked key |
| 403 | insufficient_scope | The key lacks the required scope |
| 404 | not_found | Resource not in the key's org, or unknown endpoint |
| 405 | method_not_allowed | Wrong HTTP method on a known path |
| 422 | validation_failed | The question payload failed validation |
| 422 | plan_limit_reached | The org is at its question-bank limit |
| 429 | rate_limited | More than 120 requests per minute for the key |
| 500 | server_error | Unexpected failure |
Ready to build?
Create an API key in Settings > API access, grab the OpenAPI spec, and start in minutes.