Invalid fileSize: send a JSON number
Why fileSize must be a JSON number (bytes), not a string—and how to fix 400 Invalid fileSize errors
Invalid fileSize: send a JSON number
For POST /v1/upload/presigned-url and POST /v1/upload/confirm, the fileSize field must be a JSON number: the size of the file in bytes, with no quotes around it.
What you'll see
Invalid fileSize. Must be a positive number in bytes (not a formatted string like '1.46mbs')This is different from a file size mismatch after upload, where the file exists but the byte count you declared does not match what was stored.
Common mistakes
Quoted size in JSON ("1024" is a string)
{ "filename": "video.mp4", "contentType": "video/mp4", "fileSize": "1024" }
The value must be unquoted:
{ "filename": "video.mp4", "contentType": "video/mp4", "fileSize": 1024 }
Human-readable sizes
Values like "1.5MB", "1.46mbs", or "1,460,000 bytes" are not accepted. Compute the size in bytes (e.g. in JavaScript use file.size from a File object) and send that integer.
Building the body in JavaScript
JSON.stringify will serialize a number correctly as long as the value is actually a number:
const file = document.querySelector('input[type=file]').files[0]
await fetch('https://api.ffmpeg-micro.com/v1/upload/presigned-url', {
method: 'POST',
headers: {
Authorization: 'Bearer YOUR_API_KEY',
'Content-Type': 'application/json',
},
body: JSON.stringify({
filename: file.name,
contentType: file.type,
fileSize: file.size, // number — do not use String(file.size)
}),
})
Use the same numeric byte value (and the filename returned from presign) when you call /v1/upload/confirm.
cURL
Use a numeric literal inside the JSON (no quotes around the digits):
curl -X POST "https://api.ffmpeg-micro.com/v1/upload/presigned-url" \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{"filename":"video.mp4","contentType":"video/mp4","fileSize":12345678}'
How to get file size in bytes
You need the exact byte length of the payload you will PUT to the presigned URL (same bytes at confirm). The API does not parse human strings like "2 MB"; your runtime must produce an integer.
Browser (file input) — File objects expose size in bytes:
const bytes = document.querySelector('input[type=file]').files[0].size
Node.js — length of the buffer you upload, or filesystem metadata:
import fs from 'fs'
const bytes = (await fs.promises.stat('/path/to/video.mp4')).size
// or: Buffer.byteLength(buf) if you already have the file in memory
Python
import os
bytes_count = os.path.getsize("/path/to/video.mp4")
macOS / Linux (terminal) — examples (flags differ by OS):
# macOS
stat -f%z /path/to/video.mp4
# Linux (GNU stat)
stat -c%s /path/to/video.mp4
n8n — See How to use ffmpeg with n8n cloud for downloadable workflows. The Extract Metadata sub-workflow sets fileSizeBytes from the binary buffer (buffer.length after this.helpers.getBinaryDataBuffer(...)), then passes that numeric field into the presign and confirm JSON bodies (unquoted). Import those workflows or copy the same pattern for your binary property.
Other stacks (Go os.Stat, .NET FileInfo.Length, etc.) follow the same idea: use the language’s file or buffer size in bytes, then put that value in JSON as a number.
Rules at a glance
| Requirement | Valid | Invalid |
|---|---|---|
| JSON type | number | string, object, array |
| Value | finite, > 0, whole-byte count | 0, negative, Infinity (not representable as JSON anyway) |
| Meaning | size in bytes | "2MB", "1024" as text |
More help
Related Articles
Can't find what you're looking for?