Generate AI-powered academic research reports via the Scholar API (scholar.x49.ai). Creates comprehensive literature review reports with inline citations, pa...
Generate AI-powered academic research reports via the Scholar API at https://scholar.x49.ai.
Reports are comprehensive literature reviews with inline citations, paper evidence, and downloadable Markdown output. The process is asynchronous: create a report, poll its progress, then download the result.
Use this skill when the user needs to:
Consider using scholar-search first to validate the topic and refine the query before generating a full report. Searching first helps confirm the right direction and filters before committing to a longer report generation.
The API base URL is https://scholar.x49.ai/api/v1.
Authentication uses a Bearer token. Resolve the key in this order:
SCHOLAR_API_KEYpsk_tLzPCmJdUw5oAHGeXL2H_fMrDdSyiF_SBJfn2p5uCO4Users can get their own higher-quota key at: https://scholar.x49.ai/docs?section=api-keys
Always construct API calls like this:
bash
SCHOLAR_KEY="${SCHOLAR_API_KEY:-psk_tLzPCmJdUw5oAHGeXL2H_fMrDdSyiF_SBJfn2p5uCO4}"
BASE="https://scholar.x49.ai/api/v1"
POST /reports — Start an asynchronous report generation job.
bash
SCHOLAR_KEY="${SCHOLAR_API_KEY:-psk_tLzPCmJdUw5oAHGeXL2H_fMrDdSyiF_SBJfn2p5uCO4}"
curl -s "https://scholar.x49.ai/api/v1/reports" \
-H "Authorization: Bearer ${SCHOLAR_KEY}" \
-H "Content-Type: application/json" \
-d '{
"query": "What are the latest advances in transformer attention mechanisms for NLP?",
"target_language": "en",
"include_papers": true,
"filters": {
"year_from": 2020,
"year_to": 2025
}
}'
Request body fields:
FieldTypeRequiredMeaningquerystringYesThe report topic. Write it as a research question or tasktarget_languagestringNoOutput language: en (English) or zh (Chinese), etc.include_papersbooleanNoWhether to include paper-level evidence in the resultfilters.year_fromintegerNoRestrict to papers published from this yearfilters.year_tointegerNoRestrict to papers published up to this yearfilters.paper_typesstring[]Noe.g. ["article", "review"]
Optional: Idempotency-Key header — For safe retries. If the client may retry the same create request, include Idempotency-Key: <unique-key> header. The API replays the same report_id on duplicate requests.
Response: Returns HTTP 202 with:
json
{
"data": {
"report_id": "fdaca9e7-b1cc-4286-a7fc-8c466d8e8554",
"status": "pending",
"stage": "queued",
"progress": 0
}
}
Save the report_id immediately — you need it for polling and downloading.
GET /reports/{report_id} — Check progress until status=completed.
bash
curl -s "${BASE}/reports/${REPORT_ID}" \
-H "Authorization: Bearer ${KEY}"
Key response fields:
FieldMeaningstatus``pending, running, or completed``stageCurrent stage: queued, searching, retrieving, deduplicating, summarizing``progress0 to 100messageHuman-readable progress messagetiming.running_secondsTime spent so farresult.summaryReport summary (only when completed)result.artifacts.markdown_availableWhether markdown is ready to downloadresult.papersPaper evidence (when include_papers=true)result.referencesReference entriesresult.directionsResearch directions covered
Polling strategy: Poll every 15 seconds until status=completed. Reports typically take 2-5 minutes.
bash
REPORT_ID="fdaca9e7-b1cc-4286-a7fc-8c466d8e8554"
SCHOLAR_KEY="${SCHOLAR_API_KEY:-psk_tLzPCmJdUw5oAHGeXL2H_fMrDdSyiF_SBJfn2p5uCO4}"
while true; do
STATUS=$(curl -s "https://scholar.x49.ai/api/v1/reports/${REPORT_ID}" \
-H "Authorization: Bearer ${SCHOLAR_KEY}")
echo "$STATUS" | python3 -c "
import sys, json
d = json.load(sys.stdin)['data']
print(f'Status: {d[\"status\"]} | Stage: {d[\"stage\"]} | Progress: {d[\"progress\"]}% | Message: {d.get(\"message\",\"\")}')
"
if echo "$STATUS" | python3 -c "import sys,json; sys.exit(0 if json.load(sys.stdin)['data']['status']=='completed' else 1)"; then
break
fi
sleep 15
done
GET /reports/{report_id}/markdown — Download the final report as Markdown text.
bash
curl -s "${BASE}/reports/${REPORT_ID}/markdown" \
-H "Authorization: Bearer ${KEY}"
This endpoint returns raw Markdown text, not a JSON envelope. The markdown content includes:
[(Author et al., Year)](#ref-REF_001)User asks: "Generate a report on recent advances in CRISPR gene therapy"
scholar-search first to validate the query returns good resultsPOST /reports with the queryUser asks: "Create a Chinese-language report on LLM safety from 2023-2025, only articles and reviews"
Build the request: json
{
"query": "What are the safety challenges and solutions for large language models?",
"target_language": "zh",
"include_papers": true,
"filters": {
"year_from": 2023,
"year_to": 2025,
"paper_types": ["article", "review"]
}
}
Create, poll, download as usual
User asks: "I need a report with supporting papers included"
Set include_papers: true in the create request
The completed report's result.papers array will contain paper cards with:
summary_snippet — relevant excerptevidence.matched_questions — how many directions this paper supportsmetrics.citation_count and metrics.relevanceDownload the markdown for the full synthesized report
User asks: "Create that report again" or client may retry
Use the Idempotency-Key header:
bash
curl -s "${BASE}/reports" \
-H "Authorization: Bearer ${KEY}" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: my-unique-key-123" \
-d '{"query": "..."}'
Duplicate requests with the same key return the same report_id
Check response header Idempotency-Replayed: true to know it was a replay
StageWhat happensTypical durationqueuedJob received, waiting to start< 1 secondsearchingSearching paper databases10-30 secondsretrievingFetching paper metadata and full text20-60 secondsdeduplicatingRemoving duplicate papers5-10 secondssummarizingAI synthesizing the report60-180 secondscompletedReport ready for download—
Note: The summarizing stage takes the longest. Progress may stay at 82% for a while during this stage — this is normal.
When a report completes, present it to the user in this format:
text
## Report Complete
- **Report ID**: fdaca9e7-b1cc-4286-a7fc-8c466d8e8554
- **Papers retrieved**: 100 | **Deduplicated**: 53 | **Matched**: 50
- **Generation time**: ~3 minutes
### Summary Preview
[First few paragraphs of the report summary]
The full report is available as Markdown. Would you like me to save it to a file?
ScenarioWhat to doHTTP 401Check API key — verify SCHOLAR_API_KEY env var or use the built-in keyHTTP 429Rate limited — wait and retry. Reports have separate rate limits from searchesReport stuck (progress unchanged for 5+ minutes)The data.error field may contain details. Report the issue to the userMarkdown download returns emptyCheck result.artifacts.markdown_available is true before downloadingstatus remains pending for > 2 minutesThe job queue may be busy. Continue polling.
These two skills work together naturally:
scholar-search to explore a topic and confirm it has enough literatureauthor_refs in report filters if neededscholar-search to find more papers on specific subtopics from the reportresult.papers[].author_ref may be null in report results — use scholar-search for full author details