Ce que fait l’API
La famille /mastering de l’API REST de Jam Jam rend un fichier audio avec un préréglage : elle équilibre le ton, calme les sifflantes, règle la largeur stéréo et amène le niveau à une cible de volume (streaming, Apple Music, Deezer, podcast ou club), avec les réglages de l’outil web sur jam-jam.org/app/mastering. Le contrat OpenAPI 3.1 est sur jam-jam.org/api/v1/openapi.json et la référence sur jam-jam.org/developers. Un fichier fait 200 Mo et 10 minutes au plus, mono ou stéréo (au-delà de deux canaux, les deux premiers sont utilisés), et il est traité à 48 kHz. La sortie est un WAV 16 bits (wav-pcm16, par défaut) ou 32 bits flottant (wav-f32) ; l’API ne propose pas le 24 bits. Le fichier source est supprimé dès qu’il est décodé et le résultat est gardé 24 heures. Un rendu serveur est reproductible (même fichier, mêmes réglages, même engineVersion), mais pas garanti identique à l’export du navigateur au bit près.
Obtenir une clé et vérifier ton accès
Crée un compte sur jam-jam.org, ouvre Paramètres puis Clés API (jam-jam.org/app/prefs/api-keys) et crée une clé avec les portées mastering:read et mastering:write. La clé commence par jj_live_, n’est affichée qu’une fois, et un compte peut en garder cinq. Garde-la dans la variable d’environnement JAM_JAM_API_KEY, jamais dans un dépôt ni sur une ligne de commande partagée. Le rendu d’un fichier par l’API (POST /mastering/jobs) est ouvert à tout compte : 3 rendus par semaine ISO avec un compte gratuit, sur le même compteur que l’outil web, sans plafond avec Premium. Lire le contrat et lister ou enregistrer des préréglages est aussi ouvert à tout compte.
Lire le contrat vivant
GET /mastering/capabilities ne demande aucune clé. Il renvoie la version du moteur, la plage et le pas de chaque réglage, les cibles de volume, les préréglages intégrés et les limites, et avec une clé il ajoute renderAllowed et le solde de ton compteur. Lis-le plutôt que de coder les bornes en dur. Cinq préréglages intégrés sont en lecture seule et s’utilisent en preset=builtin:<id> : builtin:balanced, builtin:warm, builtin:bright, builtin:punchy et builtin:crushed. Tu peux aussi enregistrer jusqu’à 50 préréglages à toi (un nom de 60 caractères au plus) avec POST /mastering/presets et les appeler par leur identifiant.
Lire le contrat (aucune clé requise)
curl https://jam-jam.org/api/v1/mastering/capabilities Rendre un fichier avec curl
Le déroulé est celui de tous les travaux Jam Jam : un POST qui répond 202, une interrogation jusqu’à la fin, puis le téléchargement. L’en-tête Idempotency-Key (16 à 80 caractères parmi A-Z, a-z, 0-9, _ et -) est obligatoire sur chaque écriture : rejouer la même clé avec le même corps rend le même travail sans second débit. Le travail passe par queued, decoding, analyzing et rendering, puis finit en done, failed, cancelled ou expired, et une fois terminé il porte un report avec le volume intégré (LUFS) et la crête réelle (dBTP) avant et après. Un compte a un rendu actif et trois en attente au plus. Le dépôt d’exemples livre les mêmes étapes en scripts numérotés, de curl/09-mastering-capabilities.sh à curl/14-mastering-delete.sh.
Rendre avec un préréglage intégré, suivre le travail, télécharger le WAV
# 1. Upload the file with a built-in preset (Idempotency-Key is required)
curl -X POST https://jam-jam.org/api/v1/mastering/jobs \
-H "Authorization: Bearer $JAM_JAM_API_KEY" \
-H "Idempotency-Key: $(uuidgen)" \
-F [email protected] -F preset=builtin:warm -F format=wav-pcm16
# The 202 answer carries the job "id": JOB_ID=<that id>
# 2. Follow the job, honouring Retry-After, until "status" is "done"
curl https://jam-jam.org/api/v1/mastering/jobs/$JOB_ID \
-H "Authorization: Bearer $JAM_JAM_API_KEY"
# 3. Download the mastered WAV
curl -o mix-master.wav https://jam-jam.org/api/v1/mastering/jobs/$JOB_ID/result \
-H "Authorization: Bearer $JAM_JAM_API_KEY" Python et Node
Ces deux extraits condensent python/mastering_lib.py et javascript/mastering-lib.mjs du dépôt d’exemples github.com/titouannwtt/jam-jam-api-examples (licence MIT) : Python 3.10 ou plus avec requests, Node 20 ou plus sans dépendance. Les scripts complets ajoutent un message lisible pour chaque code HTTP et se lancent avec python mastering.py master mix.wav --preset builtin:warm ou node mastering.mjs master mix.wav --preset builtin:warm.
Python (3.10 ou plus, requests)
import os, time, uuid, requests
API = "https://jam-jam.org/api/v1"
HEADERS = {"Authorization": f"Bearer {os.environ['JAM_JAM_API_KEY']}"}
FINAL = ("done", "failed", "cancelled", "expired")
# 1. Upload the file with a built-in preset. Idempotency-Key is required.
with open("mix.wav", "rb") as audio:
res = requests.post(
f"{API}/mastering/jobs",
headers={**HEADERS, "Idempotency-Key": str(uuid.uuid4())},
data={"preset": "builtin:warm", "format": "wav-pcm16"},
files={"file": ("mix.wav", audio)},
)
res.raise_for_status()
job = res.json()
# 2. Poll, waiting as long as the server asks.
while job["status"] not in FINAL:
time.sleep(int(res.headers.get("Retry-After") or 2))
res = requests.get(f"{API}/mastering/jobs/{job['id']}", headers=HEADERS)
res.raise_for_status()
job = res.json()
if job["status"] != "done":
raise SystemExit(f"mastering {job['status']}: {job.get('error')}")
before, after = job["report"]["before"], job["report"]["after"]
print(f"LUFS {before['integratedLufs']} -> {after['integratedLufs']}")
# 3. Download the mastered WAV.
audio = requests.get(f"{API}/mastering/jobs/{job['id']}/result", headers=HEADERS)
audio.raise_for_status()
with open("mix-master.wav", "wb") as out:
out.write(audio.content) Node (20 ou plus, sans dépendance)
import { openAsBlob } from 'node:fs';
import { writeFile } from 'node:fs/promises';
const API = 'https://jam-jam.org/api/v1';
const headers = { Authorization: `Bearer ${process.env.JAM_JAM_API_KEY}` };
const FINAL = ['done', 'failed', 'cancelled', 'expired'];
// 1. Upload the file with a built-in preset. Idempotency-Key is required.
const body = new FormData();
body.append('file', await openAsBlob('mix.wav'), 'mix.wav');
body.append('preset', 'builtin:warm');
body.append('format', 'wav-pcm16');
let res = await fetch(`${API}/mastering/jobs`, {
method: 'POST',
headers: { ...headers, 'Idempotency-Key': crypto.randomUUID() },
body,
});
if (!res.ok) throw new Error(`${res.status} ${await res.text()}`);
let job = await res.json();
// 2. Poll, waiting as long as the server asks.
while (!FINAL.includes(job.status)) {
await new Promise((r) => setTimeout(r, (Number(res.headers.get('retry-after')) || 2) * 1000));
res = await fetch(`${API}/mastering/jobs/${job.id}`, { headers });
if (!res.ok) throw new Error(`${res.status} ${await res.text()}`);
job = await res.json();
}
if (job.status !== 'done') throw new Error(`mastering ${job.status}: ${JSON.stringify(job.error)}`);
const { before, after } = job.report;
console.log(`LUFS ${before.integratedLufs} -> ${after.integratedLufs}`);
// 3. Download the mastered WAV.
res = await fetch(`${API}/mastering/jobs/${job.id}/result`, { headers });
if (!res.ok) throw new Error(`${res.status} ${await res.text()}`);
await writeFile('mix-master.wav', Buffer.from(await res.arrayBuffer())); Tes propres réglages
À la place d’un préréglage, envoie les réglages en JSON dans le champ settings : exactement un des deux, preset ou settings. Le format (MasteringSettingsV1) contient huit modules, chacun avec une value et un drapeau enabled, une cible de volume (streaming, apple, deezer, podcast ou club) et normalize. Les réglages de tonalité sont en décibels et les autres en pourcentage, jusqu’à 150 ; une valeur hors de sa plage ou hors de son pas répond 422 invalid-settings avec une entrée par problème. Pour réutiliser un jeu de réglages, enregistre-le avec POST /mastering/presets et passe son identifiant dans preset. Les réglages sont copiés à l’envoi : modifier le préréglage ensuite ne change pas un travail déjà lancé.
Envoyer tes propres réglages
{
"modules": {
"autoEq": { "value": 50, "enabled": true },
"lows": { "value": 2, "enabled": true },
"mids": { "value": -0.5, "enabled": true },
"highs": { "value": -1.5, "enabled": true },
"deEss": { "value": 40, "enabled": true },
"width": { "value": 10, "enabled": true },
"loudness": { "value": 45, "enabled": true },
"destruct": { "value": 0, "enabled": false }
},
"target": "streaming",
"normalize": false
} Envoyer tes propres réglages
curl -X POST https://jam-jam.org/api/v1/mastering/jobs \
-H "Authorization: Bearer $JAM_JAM_API_KEY" -H "Idempotency-Key: $(uuidgen)" \
-F [email protected] -F "settings=<samples/mastering-settings.json" -F format=wav-pcm16 Masteriser tout un dossier par lots
Le dépôt contient deux scripts de lots, python/mastering_batch.py et javascript/mastering-batch.mjs, qui masterisent un dossier avec un préréglage, un fichier après l’autre. Trois choix valent d’être repris. Les fichiers partent un par un, car un compte accepte un rendu actif et trois en attente. Un fichier dont le nom-master.wav existe déjà est ignoré, donc tu peux relancer après une interruption. Sur un 429 avec une courte attente (cinq minutes au plus), le script attend Retry-After et rejoue le même fichier avec la même clé d’idempotence, et il s’arrête sur un 403 ou sur un long 429, car les fichiers suivants échoueraient pareil.
Masteriser un dossier, un fichier à la fois
python mastering_batch.py ~/Music/mixes --preset builtin:balanced --out masters
node mastering-batch.mjs ~/Music/mixes --preset builtin:balanced --out masters Erreurs et quotas
Chaque erreur est un application/problem+json avec un code stable à tester, et les réponses de rendu portent les en-têtes X-Mastering-Quota-Limit, X-Mastering-Quota-Remaining et X-Mastering-Quota-Reset. Les comptes Premium n’ont aucun plafond de rendus. Sur un compte gratuit, un 429 de code quota-exhausted dit que les rendus de la semaine sont épuisés ; tout autre 429 signale une limite de débit ou une file occupée. Un rendu échoué ou annulé n’est pas compté. Le rendu d’un fichier par l’API (POST /mastering/jobs) est ouvert à tout compte : 3 rendus par semaine ISO avec un compte gratuit, sur le même compteur que l’outil web, sans plafond avec Premium. Lire le contrat et lister ou enregistrer des préréglages est aussi ouvert à tout compte.
| Statut | Code | Signification |
|---|---|---|
| 401 | Clé absente ou invalide. | |
| 403 | insufficient-scope | La clé n’a pas la portée mastering:read ou mastering:write. |
| 403 | premium-required | Le rendu n’est pas ouvert à ton offre (voir renderAllowed dans GET /mastering/capabilities). |
| 409 | not-ready | Résultat demandé avant la fin du rendu. |
| 410 | expired | Les 24 heures sont passées : refais le rendu. |
| 413, 415, 422 | Fichier trop gros, format non pris en charge, audio de plus de 10 minutes ou réglages invalides (lis errors[]). | |
| 429 | rate-limited | Trop de requêtes, ou un rendu déjà en cours et trois en attente (client-quota), ou file pleine (queue-full) : attends Retry-After secondes et ne boucle pas. |
Le serveur MCP pour les assistants
Le serveur MCP officiel @jam-jam/convert-mcp offre le Mastering à Claude Desktop, Claude Code, Cursor et aux autres clients Model Context Protocol, et n’affiche que les outils que les portées de ta clé permettent. Six outils couvrent le Mastering : jj_mastering_capabilities (sans portée), jj_list_mastering_presets, jj_create_mastering_preset, jj_master_audio, jj_mastering_get_job et jj_mastering_cancel_job. jj_master_audio envoie un fichier local avec un préréglage ou des réglages en ligne et, avec maxWaitMs, attend et télécharge le résultat. Tu peux alors demander à ton assistant de masteriser un fichier avec le préréglage warm et de te dire le volume avant et après. Mets la clé dans l’environnement, jamais sur une ligne de commande.
Configuration d’un client MCP
{
"mcpServers": {
"jam-jam": {
"command": "npx",
"args": ["-y", "@jam-jam/convert-mcp"],
"env": { "JAM_JAM_API_KEY": "jj_live_..." }
}
}
} Pour comprendre ce que font les réglages et quel volume viser, lis notre guide pour masteriser un morceau gratuitement.
Questions fréquentes sur l’API de mastering
L’API de mastering de Jam Jam est-elle gratuite ?
Oui. Avec un compte gratuit, POST /mastering/jobs rend 3 fichiers par semaine ISO, sur le même compteur que l’outil web ; un rendu échoué ou annulé est remboursé. Premium lève le plafond. Lire le contrat vivant et gérer tes préréglages ne coûte rien.
Quelles sont les limites de fichier ?
200 Mo et 10 minutes au plus, mono ou stéréo. Le résultat est un WAV 48 kHz, 16 bits, 24 bits ou 32 bits flottant, gardé 24 heures.
Le résultat est-il identique à celui du navigateur ?
Il est reproductible sur le serveur (même fichier, mêmes réglages, même engineVersion) mais pas garanti identique à l’export du navigateur au bit près. Les réglages sont les mêmes.
Peut-on envoyer plusieurs fichiers à la fois ?
Un compte a un rendu actif et trois en attente. Pour un dossier, envoie les fichiers un par un avec les scripts de lots du dépôt d’exemples.
Comment l’utiliser avec un assistant IA ?
Avec le serveur MCP @jam-jam/convert-mcp : l’outil jj_master_audio masterise un fichier local et jj_mastering_get_job lit le volume avant et après.
Le même moteur s’essaie gratuitement dans ton navigateur, avec ton fichier qui reste sur ton appareil.