13 KiB
Global Identities
GET /api/v1/identities
Auth: Required Scope: identity-level
List all registered identities with pagination.
Example
curl -s "$API/api/v1/identities?page=1&page_size=20" -H "X-API-Key: $KEY" | jq '{count, identities: [.identities[] | {name}]}'
GET /api/v1/identity/:identity_uuid
Auth: Required Scope: identity-level
Get detailed information for a specific identity, including metadata and TMDb references.
Example
curl -s "$API/api/v1/identity/$IDENTITY_UUID" -H "X-API-Key: $KEY"
Response (200)
{
"success": true,
"identity_uuid": "a9a901056d6b46ff92da0c3c1a57dff4",
"name": "Cary Grant",
"identity_type": "people",
"source": "tmdb",
"status": "confirmed",
"tmdb_id": 112,
"tmdb_profile": "{output}/identities/{identity_uuid}/profile.jpg",
"metadata": {},
"reference_data": {},
"created_at": "2026-05-16T12:00:00Z",
"updated_at": null
}
| Field | Type | Description |
|---|---|---|
identity_uuid |
string | Identity identifier |
name |
string | Identity name |
identity_type |
string | "people" or null |
source |
string | .json, auto, tmdb, user_defined, or merged |
status |
string | "confirmed", "pending", or "inactive" |
tmdb_id |
integer | TMDb person ID (only if source = tmdb) |
tmdb_profile |
string | Local profile image path ({output}/identities/{uuid}/profile.jpg) |
metadata |
object | Metadata JSON (tmdb_character, cast_order, etc.) |
created_at |
string | Creation timestamp |
DELETE /api/v1/identity/:identity_uuid
Auth: Required Scope: identity-level
Delete an identity permanently.
PATCH /api/v1/identity/:identity_uuid
Auth: Required Scope: identity-level
Partially update an identity. Only provided fields are modified. The name field is a display label and may repeat across identities. Aliases for multilingual display are stored in metadata.aliases (see BCP 47 reference below).
Request (JSON, all fields optional)
| Field | Type | Description |
|---|---|---|
name |
string | New display name |
metadata |
object | Merged into existing metadata. Use "aliases" key for locale-tagged names |
status |
string | "confirmed", "pending", or "skipped" |
identity_type |
string | "people", "brand", "object", "concept", etc. |
Example
curl -s -X PATCH "$API/api/v1/identity/$IDENTITY_UUID" \
-H "X-API-Key: $KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "John Smith",
"metadata": {
"aliases": [
{"locale": "en", "name": "John Smith"},
{"locale": "zh-TW", "name": "約翰·史密斯"},
{"locale": "ja", "name": "ジョン・スミス"}
]
}
}'
Response (200)
{
"success": true,
"identity_uuid": "a9a901056d6b46ff92da0c3c1a57dff4",
"updated_fields": ["name", "metadata"]
}
Error Responses
| HTTP | When |
|---|---|
400 |
No fields to update or invalid UUID format |
404 |
Identity not found |
GET /api/v1/identity/:identity_uuid/files
Auth: Required Scope: identity-level
Get all files where this identity appears. Returns per-file summary including face count, confidence, and appearance time range.
Example
curl -s "$API/api/v1/identity/$IDENTITY_UUID/files" -H "X-API-Key: $KEY"
Response (200)
{
"success": true,
"identity_uuid": "c3545906c82d4b66aa1d150bc02decce",
"total": 1,
"page": 1,
"page_size": 20,
"data": [
{
"file_uuid": "aeed71342a899fe4b4c57b7d41bcb692",
"file_name": "Charade (1963) Cary Grant & Audrey Hepburn.mp4",
"file_path": "/path/to/videos/Charade.mp4",
"status": "completed",
"face_count": 19695,
"speaker_count": 0,
"first_appearance": 206.76,
"last_appearance": 6756.68,
"confidence": 0.803
}
]
}
Response Fields
| Field | Type | Description |
|---|---|---|
file_uuid |
string | File identifier (full 32-char hex) |
file_name |
string | Video file name |
file_path |
string | Absolute path to video file |
status |
string | Video processing status ("completed", "processing", etc.) |
face_count |
int | Total face detections for this identity in this file |
speaker_count |
int | Speaker segments (reserved, always 0) |
first_appearance |
float | First appearance time in seconds (computed from frame_number / fps) |
last_appearance |
float | Last appearance time in seconds |
confidence |
float | Average detection confidence |
GET /api/v1/identity/:identity_uuid/faces
Auth: Required Scope: identity-level
Get all face detection records associated with this identity.
Example
curl -s "$API/api/v1/identity/$IDENTITY_UUID/faces?page=1&page_size=20" -H "X-API-Key: $KEY"
Response (200)
{
"success": true,
"identity_uuid": "c3545906c82d4b66aa1d150bc02decce",
"total": 19695,
"page": 1,
"page_size": 20,
"data": [
{
"id": 655704,
"file_uuid": "aeed71342a899fe4b4c57b7d41bcb692",
"frame_number": 5169,
"timestamp_secs": 206.76,
"face_id": "5169_0",
"bbox": {
"x": 706,
"y": 469,
"width": 618,
"height": 618
},
"confidence": 0.855
}
]
}
Response Fields
| Field | Type | Description |
|---|---|---|
id |
int64 | Face detection record ID |
file_uuid |
string | File where face was detected |
frame_number |
int64 | Frame number (primary coordinate) |
timestamp_secs |
float | Time in seconds (computed as frame_number / fps) |
face_id |
string | Face ID (format: {frame_number}_{detection_index}) |
bbox |
object | Bounding box |
bbox.x |
float | Left coordinate |
bbox.y |
float | Top coordinate |
bbox.width |
float | Width in pixels |
bbox.height |
float | Height in pixels |
confidence |
float | Detection confidence (0.0–1.0) |
GET /api/v1/identity/:identity_uuid/chunks
Auth: Required Scope: identity-level
Get all text chunks (sentences) spoken while this identity's face was on screen. Useful for finding what a person said.
Example
curl -s "$API/api/v1/identity/$IDENTITY_UUID/chunks" -H "X-API-Key: $KEY"
Response (200)
{
"success": true,
"identity_uuid": "a9a901056d6b46ff92da0c3c1a57dff4",
"data": [
{
"id": 0,
"file_uuid": "bd80fec92b0b6963d177a2c55bf713e2",
"chunk_id": "bd80fec92b0b6963d177a2c55bf713e2_2",
"chunk_type": "sentence",
"start_frame": 5103,
"end_frame": 5127,
"fps": 24.0,
"start_time": 212.64,
"end_time": 213.64,
"text_content": "[213s-214s] Cary Grant: \"Olá!\""
}
]
}
| Field | Type | Description |
|---|---|---|
file_uuid |
string | File identifier |
chunk_id |
string | Sentence chunk identifier |
start_frame |
integer | Frame-accurate start position |
end_frame |
integer | Frame-accurate end position |
fps |
float | Frames per second |
start_time |
float | Start time in seconds |
end_time |
float | End time in seconds |
text_content |
string | Spoken text content |
POST /api/v1/identity/:identity_uuid/bind
Auth: Required Scope: identity-level
Bind a face detection to an identity. Associates the face trace with the identity for future search and recognition.
Request Parameters
| Field | Type | Required | Description |
|---|---|---|---|
file_uuid |
string | Yes | File where face is detected |
face_id |
string | Yes | Face ID (format: {frame}_{idx}) |
Example
curl -s -X POST "$API/api/v1/identity/$IDENTITY_UUID/bind" \
-H "X-API-Key: $KEY" \
-H "Content-Type: application/json" \
-d '{"file_uuid": "'"$FILE_UUID"'", "face_id": "1_5"}'
POST /api/v1/identity/:identity_uuid/unbind
Auth: Required Scope: identity-level
Unbind a face detection from an identity. Removes the identity association from the face record.
GET /api/v1/identities/search
Auth: Required Scope: identity-level
Search identities by name (ILIKE search). Returns matching identity records.
Example
curl -s "$API/api/v1/identities/search?q=Cary" -H "X-API-Key: $KEY"
| Field | Type | Description |
|---|---|---|
name |
string | Identity name |
source |
string | Identity source |
tmdb_id |
integer | TMDb ID (if source = tmdb) |
file_uuid |
string | Associated file |
POST /api/v1/identity/upload
Auth: Required Scope: identity-level
Upload an identity.json file to create or update an identity. Accepts the same format as the identity.json files stored on disk.
If an identity with the same identity_uuid already exists, it will be updated with the new values.
Request
The request body is an IdentityFile object:
| Field | Type | Required | Description |
|---|---|---|---|
identity_uuid |
string | Yes | Identity identifier |
name |
string | Yes | Identity display name |
identity_type |
string | No | "people" or null |
source |
string | No | .json, auto, tmdb, user_defined, or merged |
status |
string | No | "confirmed", "pending", or "inactive" |
tmdb_id |
integer | No | TMDb person ID |
tmdb_profile |
string | No | TMDb profile image URL |
metadata |
object | No | Arbitrary metadata JSON |
file_bindings |
array | No | Array of { file_uuid, trace_ids, face_count } (informational) |
Example
curl -s -X POST "$API/api/v1/identity/upload" \
-H "X-API-Key: $KEY" \
-H "Content-Type: application/json" \
-d '{
"version": 1,
"identity_uuid": "a9a901056d6b46ff92da0c3c1a57dff4",
"name": "Cary Grant",
"identity_type": "people",
"source": ".json",
"status": "confirmed",
"metadata": {},
"file_bindings": []
}'
Response (200)
{
"success": true,
"identity_uuid": "a9a901056d6b46ff92da0c3c1a57dff4",
"name": "Cary Grant",
"message": "Identity uploaded successfully"
}
POST /api/v1/identity/:identity_uuid/profile-image
Auth: Required Scope: identity-level
Upload a profile image (JPEG or PNG) for an identity. The image is saved to {output}/identities/{uuid}/profile.{ext}.
Uses multipart/form-data with field name image.
Example
curl -s -X POST "$API/api/v1/identity/$IDENTITY_UUID/profile-image" \
-H "X-API-Key: $KEY" \
-F "image=@/path/to/photo.jpg"
Response (200)
{
"success": true,
"identity_uuid": "a9a901056d6b46ff92da0c3c1a57dff4",
"path": "/path/to/output/identities/.../profile.jpg",
"message": "Profile image saved: profile.jpg"
}
Error Responses
| HTTP | When |
|---|---|
400 |
Missing image field or unsupported format |
404 |
Identity not found |
415 |
Unsupported image type (use JPEG or PNG) |
GET /api/v1/identity/:identity_uuid/profile-image
Auth: Required Scope: identity-level
Retrieve the profile image for an identity. Returns the raw image data with appropriate Content-Type header.
curl -s "$API/api/v1/identity/$IDENTITY_UUID/profile-image" \
-H "X-API-Key: $KEY" -o profile.jpg
| Response Header | Value |
|---|---|
content-type |
image/jpeg or image/png |
Alias System (BCP 47 Locale Tags)
Identity aliases support multilingual display names. Aliases are stored in metadata.aliases as an array of {locale, name} objects.
BCP 47 Locale Tags Reference
| Locale | Tag | Example |
|---|---|---|
| English | en |
John Smith |
| Traditional Chinese | zh-TW |
約翰·史密斯 |
| Simplified Chinese | zh-CN |
约翰·史密斯 |
| Japanese | ja |
ジョン・スミス |
| Korean | ko |
존 스미스 |
| Cantonese | yue |
約翰·史密夫 |
| French | fr |
John Smith (French spelling) |
| Spanish | es |
Juan Smith |
| Arabic | ar |
جون سميث |
| Russian | ru |
Джон Смит |
| Thai | th |
จอห์น สมิธ |
BCP 47 is the IETF standard for language tags. Format: language (e.g. en, ja) or language-Region (e.g. zh-TW, zh-CN).
Frontend Display Logic
function getDisplayName(identity, preferredLocale) {
const match = identity.metadata?.aliases?.find(a => a.locale === preferredLocale);
if (match) return match.name;
const lang = preferredLocale.split('-')[0];
const langMatch = identity.metadata?.aliases?.find(a => a.locale.startsWith(lang));
if (langMatch) return langMatch.name;
return identity.name;
}
Updating Aliases via PATCH
PATCH /api/v1/identity/:identity_uuid
{
"metadata": {
"aliases": [
{"locale": "en", "name": "John Smith"},
{"locale": "zh-TW", "name": "約翰·史密斯"}
]
}
}
Updated: 2026-05-22