Instagram Reels API audio: AAC, 48 kHz max, mono or stereo
Meta's Reel spec asks for AAC audio, a sample rate of 48 kHz at most, 1 or 2 channels and 128 kbps. Check those fields with a Sume video inspect probe first.

For an Instagram Reel through the API, Meta's IG User Media reference lists the audio as AAC, 48 kHz sample rate maximum, 1 or 2 channels (mono or stereo), with an audio bitrate of 128 kbps (read 2026-10-02). Sume's video inspect probe returns audio_codec, audio_channels, audio_sample_rate and has_audio, which covers three of those four items before you create a container.
What does the Reel audio spec say?
The audio line sits next to the video requirements in the Reel specifications. Stories use the same audio line.
| Meta item | Value | Sume probe field |
|---|---|---|
| Audio codec | AAC | audio_codec |
| Sample rate | 48 kHz maximum | audio_sample_rate |
| Channels | 1 or 2 | audio_channels |
| Audio bitrate | 128 kbps | Not in the probe |
Which of these can I check with Sume?
Codec, channel count and sample rate. The probe schema has no audio bitrate field, so that item stays unchecked. Probe and stills are unbilled; with frames: false you get the probe alone.
A clip without sound reports has_audio: false and a null codec. The page does not say whether a Reel must have audio, so a silent clip is something to test, not to assume.
import hashlib, os, time, requests
BASE = "https://api.sume.com"
H = {"Authorization": f"Bearer {os.environ['SUME_API_KEY']}"}
def probe(video_url):
key = "probe-" + hashlib.sha256(video_url.encode()).hexdigest()[:24]
r = requests.post(f"{BASE}/v1/video-inspect", headers={**H, "Idempotency-Key": key},
json={"video_url": video_url, "frames": False}, timeout=60)
r.raise_for_status()
rid = r.json()["data"]["video_inspect_id"]
while True:
d = requests.get(f"{BASE}/v1/video-inspect/{rid}", headers=H, timeout=30).json()["data"]
if d["resource_status"] == "ready":
return d["probe"]
if d["resource_status"] in ("failed", "canceled"):
raise RuntimeError(d["error"])
time.sleep(2)
p = probe("https://media.sume.com/artifacts/artf_demo/talk.mp4")
problems = []
if not p["has_audio"]:
print("no audio track")
else:
if (p["audio_codec"] or "").lower() != "aac": problems.append(f"codec {p['audio_codec']}")
if (p["audio_sample_rate"] or 0) > 48000: problems.append(f"{p['audio_sample_rate']} Hz")
if p["audio_channels"] not in (1, 2): problems.append(f"{p['audio_channels']} channels")
print(problems or "audio fields within the listed limits")What if the audio is outside the limits?
Video trim with precision: exact re-encodes the clip and, per its docs, remuxes kept audio as AAC. That fixes a codec mismatch. The docs do not list a sample-rate or channel option on trim, so a 96 kHz or 6-channel source needs another route; regenerate the audio at a supported shape instead.
Trim's precision: keyframe is a stream copy, so it keeps the source audio unchanged.
What should I do?
Probe every file, fail on the three checkable fields, and keep the 128 kbps item as a manual check on a sample. The Facebook Reels audio spec is covered in its own post; this one is Instagram only.
Sources
Related posts
More in Integrations
- Instagram Reels API cover_url vs thumb_offset: which one wins?
If a Reel container sets both cover_url and thumb_offset, Meta uses cover_url and ignores thumb_offset. How each works, and how to pull a cover frame.
- Instagram Reels API: is_paid_partnership and sponsor IDs
The Instagram Content Publishing API takes is_paid_partnership and branded_content_sponsor_ids for Reels, sponsor ids need Facebook Login. Request-body example.
- Instagram Reels API share_to_feed: true does not guarantee Reels
share_to_feed=true lets a Reel appear in Feed and Reels; false limits it to Reels. Neither value guarantees placement. What Meta's page says, and what to prep.
- Instagram Reels API limits: 3 collaborators, no carousel, audio tags
Meta's Reels API allows up to 3 collaborators, keeps Reels out of carousels, and limits music tagging to original audio. The limits that shape a batch plan.
Written by Sume