Server-Side Integration
Use ADN's API directly to store tracks and manage playback. Build fully custom experiences without ADN components.
Best For
Playing Tracks
Create play sessions and fetch track URLs from your server.
Use ADN's API directly from your server to create play sessions and fetch track URLs. Build completely custom playback experiences — no ADN web components involved.
1. Create an API Key
Go to Settings → API Keys and create an API Access key.
2. Create a Play Session
const response = await fetch('https://api.audiodelivery.net/v1/play_session/collection', {
method: 'POST',
headers: {
'Authorization': 'Bearer YOUR_API_KEY',
'Content-Type': 'application/json'
},
body: JSON.stringify({
collection_id,
variants: ['preview'],
is_downloadable: false,
expires_in: 3600 // session duration in seconds (default: 3600, min: 60, max: 86400)
})
});
const { play_session_id, tracks } = await response.json(); This is where you apply business logic — check subscriptions, verify purchases, or enforce access rules before creating the session.
3. Fetch Track Data
const { id: track_id } = tracks[0];
// No auth needed - the session ID acts as a bearer token
const response = await fetch(`https://api.audiodelivery.net/v1/play/${play_session_id}/${track_id}`);
const { variants } = await response.json();
const preview = variants.find(v => v.variant.index === 'preview');
console.log(`Play Audio File: ${preview.url}`); 4. Custom Playback
Use the returned URL in your own audio player implementation. Works with any player library or native mobile audio APIs.
Waveform Data
levels field in the track response contains the data — use it to render waveforms
in your own player, or generate custom waveforms via the Audio Analysis variant type.
Cover Images & Theme Colors
cover_image
in the track response (in icon/small/regular/large sizes). You can also upload a cover image
separately via the API. When a cover image is present, ADN extracts a palette of colors
and selects a primary player_color — use these to style your player UI. Alongside it,
responses include player_color_light and player_color_dark, contrast-adjusted
variants for drawing the color on light and dark backgrounds respectively. The full
theme array contains all extracted colors with hex values, area, lightness, and saturation data.
Public tracks? Skip the session
Uploading Tracks
Use ADN's API to manage the entire upload flow from your server.
Use ADN's API directly from your server to create upload sessions, store tracks, and manage the entire upload flow. Build fully custom upload interfaces — no ADN web components involved.
1. Create an API Key
Go to Settings → API Keys and create an API Access key.
2. Create an Upload Session
const response = await fetch('https://api.audiodelivery.net/v1/upload_session', {
method: 'POST',
headers: {
'Authorization': 'Bearer YOUR_API_KEY',
'Content-Type': 'application/json'
},
body: JSON.stringify({
collection_id: 'COLLECTION-ID',
expires_in: 3600 // session duration in seconds (default: 3600, min: 60, max: 86400)
})
});
const { upload_session } = await response.json(); 3. Create Tracks Within the Session
const { id: upload_session_id } = upload_session;
// One request per file. No Authorization header needed here — the
// upload session ID authorizes track creation.
const response = await fetch(`https://api.audiodelivery.net/v1/upload/${upload_session_id}/track`, {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({ file_name: 'song.wav' })
});
const { track_id, track_upload } = await response.json();
const { method, upload_url, expires_at } = track_upload; 4. Upload Files
const file = document.querySelector('input[type="file"]').files[0];
await fetch(upload_url, {
method,
headers: { 'Content-Type': file.type },
body: file
});
Repeat steps 3 and 4 for each file you want to add to the session — every track needs its own POST /v1/upload/:upload_session_id/track request and its own signed upload URL.
5. Wait Until the Track Is Ready
Processing starts automatically once the file lands in storage. Wait until the track's status is ready before creating a play session or signing delivery URLs — either by polling or with a webhook.
// Processing runs automatically after the upload. Poll the track until it is
// ready, or configure a webhook (below) to be notified instead of polling.
let track;
do {
await new Promise((r) => setTimeout(r, 5000));
const res = await fetch(`https://api.audiodelivery.net/v1/track/${track_id}`, {
headers: { 'Authorization': 'Bearer YOUR_API_KEY' }
});
({ track } = await res.json());
} while (track.track_status_id !== 'ready');
// The track is now ready — create a play session or sign a delivery URL. 6. Optional: Webhooks
Instead of polling, enable a webhook under Settings → Webhook to be notified when a track reaches a terminal outcome (ready, incomplete, error, or init_error) and when its full file set is complete. See the Track Processing webhook docs.
Cover Images
theme)
that can be used to style your player UI.
Generating Keys
Mint scoped Client-Side keys from your server.
Once you have an API Access key, you can generate player and
uploader keys programmatically — for example, a per-customer player key scoped to a single collection.
Inline Share and URL Signing keys are not created through the API; provision them from Settings → API Keys in the dashboard.
See the API Keys reference for all parameters.
Create a Scoped Key
// Use your API Access key to mint a scoped Client-Side Player key.
const response = await fetch('https://api.audiodelivery.net/v1/api_key', {
method: 'POST',
headers: {
'Authorization': 'Bearer YOUR_API_ACCESS_KEY',
'Content-Type': 'application/json'
},
body: JSON.stringify({
title: 'Customer Player Key',
api_key_type_id: 'player', // 'player' | 'uploader' (share & signing keys are dashboard-only)
collection_id: 'COLLECTION_ID' // optional: limit the key to one collection
// expires_at is optional via the API — omit for a key that never expires
})
});
// The full key is returned once — store it securely, it cannot be retrieved again.
const { api_key } = await response.json();
Via the API, expires_at is optional for both key types — omit it for a key that never expires by time.
API Access, Inline Share, and URL Signing keys must be created in the dashboard.