~/docs cat create-detection.md
Create a detection
POST /v1/detections runs a detection on one file or link. The server infers image, video, audio or document, runs the right detectors, and answers with one envelope. Synchronous: every call is one run, and a retried call is a second run and a second charge.
Request (multipart/form-data):
request fields
file binary the media. image ≤ 10 MB, video ≤ 100 MB,
document ≤ 50 MB, audio ≤ 50 MB
url string a link to the media, as an alternative to file
save string "true" | "false". persist history + file (default "true")
thumbnails string "true" | "false". video only: include a small base64 JPEG
of each scored frame as frames[].thumbnail_b64
(default "false")curl
curl -X POST "https://api.scam.ai/v1/detections" \ -H "x-api-key: <YOUR_API_KEY>" \ -F "file=@/path/to/media.mp4"
response fields
id string detection id, always present
status string always "completed"
created_at string RFC 3339 timestamp, millisecond precision, Z
media object { type: "image" | "video" | "document" | "audio",
filename, mime_type, bytes }
model string the public model name, "Eva V1.6"
verdict string "LIKELY_REAL" | "ALERT" | "LIKELY_AI"
score float probability the media is manipulated, 0 to 1.
null when nothing scored
summary string one sentence a person can read
credits_used number what was debited for this run. 0 on a free run, with
zero_charge_reason: "sandbox" | "duplicate"ALERT means we detected some AI-related signals, but the result is not conclusive. It can occur on images, documents and videos. Audio is judged on one line, so it answers LIKELY_REAL or LIKELY_AI.
Video, audio and links add their own fields on top of the base above:
video adds
threshold_used number the line the verdict was decided against
frames array per-frame, the whole clip:
[{ index, timestamp_s, score, cause?, thumbnail_b64? }]
score is null, never 0, for a frame that was not
scored, and cause says why. thumbnail_b64 is present
only when the request sent thumbnails="true"audio adds
duration_ms number clip length. audio is billed by length
segments array per-window [{ start_ms, end_ms, value, status }]
value = P(synthetic), null for a window with no speechlink adds
source object only when the media came from a link:
{ url, canonical_url, platform, title, uploader,
duration_s, truncated, analyzed_duration_s }
truncated is true when only a prefix was scored;
analyzed_duration_s is the length that was scoredverdict uses the same three words for every media type.