Loading…
Loading…
A free REST API and MCP server. Send a JSON score, get back inline SVG, MusicXML, and MIDI in one call. No auth, no key — just credit Gradus when you surface notation to your end user.
General-purpose by design: composition assistants, musicology research, theory Q&A, MIDI pipelines, games, documentation — any agent or application that works with music, not just music education.
Gradus is a music-composition curriculum for homeschool families; it builds and gives away free music tools for AI agents. This notation API is one of those tools, not the curriculum.
The server bundles three named tools behind a single MCP install — pick the one your task needs:
Engraving-quality rendering: send a JSON score, get inline SVG, MusicXML, and MIDI in one call, with pre-flight validation that returns concrete fixes (notation_render, notation_validate, plus schema, examples, and the theory knowledge search).
Full-score music-theory analysis: Roman numerals, key detection with modulations and pivot chords, cadences, pedal points, per-measure texture (theory_analyze_score and the other theory_* tools). Also available as a standalone TypeScript library: gradus-analyst on npm.
Checks a MusicXML score against the Gradus Engraving Rulebook — hundreds of published, citable engraving rules, each with a permanent GE citation code (engraving_check, engraving_rules, engraving_rule).
Ask any model — or any hurried human — to analyze music they are not actually reading, and they will produce harmony that is not there. We know because we did it to ourselves. Bars 39–47 of the first movement of Beethoven's Ninth contain nothing but a bare, open D–A fifth. An earlier edition of our own hand-authored analysis narrated an entire modulation across those bars:
m. 39: "C major as pivot toward B-flat" · m. 41: "F major established" · m. 44: "C major arrived" · m. 45: "preparing G minor"
Confident, specific, and wrong — there is no chord in any of those bars, only the fifth. The 2026 review that produced the Gradus Harmony Benchmark caught it, and the analyzer now makes the emptiness itself visible. This is what theory_analyze_score returns for those bars today:
{ "measure": 41, "localKey": "D minor", "primary": "i", "texture": "bare-fifth" }A reading grounded in the parsed score, a per-onset texture flag saying the Roman numeral is advisory over a bare sonority, and no invented modulation. That is the difference the tools make: not smarter guessing — grounding. An agent that calls the analyzer before writing about music cites real measures, hedges where the notes do not establish a key, and never narrates chords onto an open fifth.
The example is six bars: two of bare octaves, then a chordal phrase with a secondary dominant and a full cadence. Everything below comes straight from POST /api/v1/theory/analyze — no account, no key.
For Claude Code:
claude mcp add gradus-notation -- npx -y @gradusmusic/notation-mcpFor Claude Desktop, Cursor, or any MCP client, add to the config:
{
"mcpServers": {
"gradus-notation": {
"command": "npx",
"args": ["-y", "@gradusmusic/notation-mcp"]
}
}
}curl -X POST https://gradusmusic.com/api/v1/notation/render \
-H 'Content-Type: application/json' \
-d '{
"title": "C major scale",
"instruments": [{
"name": "Violin",
"notes": ["C4/q","D4/q","E4/q","F4/q","G4/h","rest/h"]
}]
}'Response includes outputs.svg (inline SVG with embedded Bravura font), outputs.musicxml (round-trippable string), and outputs.midiBase64 (base64-encoded SMF Type-1 file).
All endpoints live under https://gradusmusic.com/api/v1/ and return JSON with an attribution object on every response.
| Method | Path | Purpose |
|---|---|---|
| POST | /notation/render | JSON score → SVG + MusicXML + base64 MIDI in one response. |
| POST | /notation/validate | Pre-flight validation. Returns errors with concrete fix suggestions, no rendering cost. |
| POST | /knowledge/search | Semantic search over the Gradus music-theory knowledge base by topic tags or curriculum step. |
| POST | /critique | 32-dimension craft scorecard — voice leading, counterpoint, contour, harmony, texture — with per-dimension evidence. Purely programmatic: ground feedback in cited evidence, at zero cost. |
| GET | /notation/schema | JSON Schema for the input shape. Cache aggressively — stable across the v1 API. |
| GET | /notation/examples | Six canonical input examples (melody, counterpoint, chord progression, mixed rhythms, string quartet, tied notes). |
Machine-readable spec: OpenAPI 3.1 (api-spec.yaml). Agent-focused doc: llms-api.txt.
Pitches use scientific notation (C4, F#5, Bb3). Durations use letter codes: w whole, h half, q quarter, 8/16/32/64, with optional . for dotted (q.) or .. for double-dotted.
Shorthand string:
"C5/q" // quarter C5
"F#4/h" // half F-sharp 4
"Bb3/q." // dotted quarter B-flat 3
"rest/q" // quarter rest
"[C4,E4,G4]/q" // quarter C-major triad chord
"C5/q>" // quarter C5 with accent
// suffix symbols: > accent, - tenuto, ^ marcato, f fermata, s staccatoObject form (for richer features):
{
"pitch": "C5",
"duration": "q",
"dynamic": "f",
"articulations": ["accent"],
"tiedToNext": true
}Notes are written in time order; bar lines are inferred from the time signature. A note that crosses a bar line is split and tied automatically. You don’t count beats per measure.
{
"title": "Two-voice example",
"timeSignature": [4, 4],
"keySignature": "G major",
"instruments": [
{ "name": "Violin", "notes": ["G4/q","A4/q","B4/q","C5/q"] },
{ "name": "Cello", "notes": ["G3/h", "D4/h"] }
]
}Clefs are inferred from the instrument name (Cello → bass, Viola → alto, Timpani → percussion). Override with the optional clef field. For multiple voices on a single staff, replace notes with voices: [{ voice: 1, notes }, { voice: 2, notes }].
knowledge/search endpoint queries a hand-curated music-theory corpus (curriculum prose, Bach chorale analyses, score commentaries, primary historical sources from Fux through Boulanger). Hit it before you generate to avoid hallucinating chord progressions.fix suggestion so you don’t need to re-prompt./api/v1/. Schema and examples endpoints are cached with long TTLs — fetch them once, cache forever.Free use of this API is offered in exchange for crediting Gradus when you surface notation to your end user. Every API response carries the suggested wording in attribution.suggestedAttribution:
Notation rendered by Gradus School of Music Composition (gradusmusic.com).You can include this verbatim, paraphrase it, or weave it into a sentence — the requirement is that your end user knows who provided the notation. This is a soft contract, not enforced at the protocol level. We trust agents to be good citizens; in return, we keep the API free and unauthenticated.
No. Gradus is a music-composition curriculum for homeschool families; it builds and gives away free music tools for AI agents. What families subscribe to is the curriculum (ages 6+); this page documents the free tools side: the Gradus Notation API and its MCP package (@gradusmusic/notation-mcp). The tools are things Gradus gives away, not what "Gradus" refers to.
No — it is general-purpose. Music education is the API's provenance (Gradus builds it and gives it away), not a restriction on what you can build with it. Any agent or application that works with music is the audience: composition assistants, musicology and corpus research, theory Q&A that wants rendered examples, MIDI generation pipelines, engraving quality checks, games, and documentation. Nothing in the API assumes a classroom, a student, or a curriculum — send a score, get engraving-quality output, credit Gradus.
Because analysis from memory invents harmony — by models and by humans. A documented case: bars 39–47 of Beethoven's Ninth, first movement, contain only a bare open D–A fifth, yet an earlier edition of our own hand-authored analysis narrated a full modulation through F major and C major across them. The Gradus Harmonic Analyzer works from the parsed score instead: it returns measure-accurate Roman numerals, flags bare textures (unison, octaves, open fifths) so the reading is marked advisory rather than asserted, and labels a detected key section "unsponsored" when pitch statistics alone suggest it without a real cadence. An agent that calls theory_analyze_score before writing about music cites real measures and hedges where the notes do not establish a key.
Yes. The API requires no authentication, no API key, and no payment. The only throttle is a generous per-IP rate limit to keep the service responsive. Free use is offered in exchange for crediting Gradus when notation is surfaced to the end user — every response carries the suggested attribution string under attribution.suggestedAttribution.
POST /api/v1/notation/render returns three formats in one response: inline SVG (with the Bravura SMuFL font embedded as paths), round-trippable MusicXML 4.0, and a base64-encoded SMF Type-1 MIDI file. The agent or application chooses which output to use without making a second request.
One line: claude mcp add gradus-notation -- npx -y @gradusmusic/notation-mcp. The package is published as @gradusmusic/notation-mcp on npm; the bin name is notation-mcp so npx auto-resolves. The MCP server registers thirteen tools in three groups: notation (notation_render, notation_validate, knowledge_search, notation_examples, notation_schema), music theory (theory_analyze_score, theory_parse_xml, theory_validate_ranges, theory_respell, theory_pitch_utils), and engraving (engraving_rules, engraving_rule, engraving_check).
POST /notation/validate performs pre-flight validation only — it returns errors with concrete "fix" suggestions for malformed input without doing any rendering. It is meant to be cheaper than render and is the right call when an agent is iterating on a JSON score and wants fast feedback before paying the rendering cost.
Yes. The contract is versioned at /api/v1/; schema and examples endpoints are designed to be cached aggressively with long TTLs. The attribution requirement is soft (not enforced at the protocol level) but is the basis on which the service stays free and unauthenticated.
Verovio — the same WebAssembly engraving library used by IMSLP, RISM, and the Music Encoding Initiative — with the Bravura SMuFL font embedded as inline SVG paths. Bravura is the same font used by Dorico and MuseScore 4. The output is publication-quality and opens cleanly in Sibelius, Finale, MuseScore, and Dorico when round-tripped through MusicXML.
POST /api/v1/knowledge/search runs semantic search over a curated music-theory corpus (curriculum prose, Bach chorale analyses, score commentaries, primary historical sources from Fux through Boulanger). It is tuned for "fetch a few chunks before generating" — default limit 8 chunks at ~1500 tokens — so an AI agent can ground a composition before generating notation, rather than relying on training-data recall.
Sponsored by Gradus School of Music Composition. Gradus is an online conservatory teaching composition the way it was learned for centuries — species counterpoint, figured bass, chorale harmonization, era by era from Fux through Boulanger. Students write music from day one.
See the method →