Material Embedding
Material embedding (embed) is a synchronous API: send text / images (base64, mixed batches allowed) and get back full 1024-dimensional normalized vectors in the same semantic space as the cloud material matrix — vectors search across text and images, matching runs on your machine, and the cloud only produces the vectors.
Typical uses: building a vector index over your own materials, semantic dedup / clustering, or embedding query text to match against your local index. It is the sibling capability of Video Material Search: that endpoint takes keywords and returns matched materials directly from the cloud; this one takes text / images and returns only vectors — the matching is yours to do.
💡 For bulk indexing, use the gtrk CLI (session-based metering, settled precisely by actual usage).
Embedding
Basics
| Item | Value |
|---|---|
| Method | POST |
| Path | /task/material_embed |
| Content-Type | application/json |
| Auth | Authorization header (raw API Key) |
| Response Mode | Synchronous (not an asynchronous task) |
| Billing | Images 0.1 credits each (settled per request, rounded half up, minimum 1 credit when images are present); text free |
Request Body
| Field | Type | Required | Default | Description |
|---|---|---|---|---|
input | array | Yes | — | Mixed-batch input array; each item is {"text": "..."}, {"image": "<base64>"}, or {"file_id": "<uploaded file id>"} (exactly one of the three — multiple keys or none is a parameter error). The response aligns with the input item by item via index. Per-request limits: 16 images (image and file_id forms counted together) or 64 texts — exceeding a limit rejects the whole request with the limit stated, no partial processing |
normalized | boolean | No | true | Only true is supported (an explicit false is rejected); responses are always normalized vectors |
task | string | No | — | Optional task prefix for the text side, same convention as cloud search (pass retrieval.query for search query text); ignored for images; length ≤ 64 |
input[] element (text / image / file_id — exactly one, mutually exclusive)
| Field | Type | Description |
|---|---|---|
text | string | Text to embed (non-empty string) |
image | string | Base64 of the image file bytes (data URI form also accepted), ≤ 1MB after decoding; we recommend downscaling images to 512px before sending |
file_id | string | ID of an image file previously stored via File Upload — no need to send the bytes again as base64. The file must be uploaded by you and of an image type (jpg / jpeg / png / bmp / webp): missing or not-yours returns 6004 (one shared code, existence not disclosed), non-image types return 6014. Single image ≤ 10MB (no transfer cost when reading from storage, so this limit is separate from the 1MB base64 limit); the resulting vector is identical to sending the same image as base64 |
Request Example
curl -X POST https://api.ai-mcn.tv:10000/task/material_embed \
-H "Authorization: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"input": [
{"text": "aerial night view of a city"},
{"image": "iVBORw0KGgoAAAANSUhEUgAA..."},
{"file_id": "1954167xxxxxxxxxxxx"}
],
"normalized": true
}'
Success Response
{
"code": 200,
"msg": "success",
"data": {
"data": [
{"index": 0, "embedding": [0.0123, -0.0456, 0.0789]},
{"index": 1, "embedding": [0.0234, 0.0567, -0.0891]},
{"index": 2, "embedding": [-0.0142, 0.0378, 0.0655]}
],
"usage": {"texts": 1, "images": 2, "total": 3}
}
}
ℹ️ Note:
embeddingis truncated in the example; the actual value is a full 1024-dimensional float array. Images referenced viafile_idcount towardusage.imagesjust like base64 images.
Response Fields
| Field | Type | Description |
|---|---|---|
data | array | Vector array aligned with the input item by item |
data[].index | integer | Index of the corresponding input item |
data[].embedding | array | 1024-dimensional normalized float vector, same semantic space as the cloud material matrix |
usage.texts | integer | Number of texts in this request |
usage.images | integer | Number of images in this request (successfully delivered images are what gets billed) |
usage.total | integer | Total item count |
⚠️ Warning: The model is lazily loaded and evicted when idle — the first request after eviction can be slow (cold start on the order of minutes). Set your client timeout to ≥ 180 seconds; with continuous requests only the first batch is slow.
Billing
- Images: 0.1 credits each, settled per request — each request is charged
image count × 0.1credits rounded half up to an integer, with a minimum of 1 credit whenever the request contains images. Billing counts only successfully delivered images; failed requests are not charged. Images sent asimage(base64) and referenced viafile_idare billed identically per image. - Text: free — text-only requests cost zero credits.
- Gitruck Cloud internal member exemption: accounts with
gc_member_typeofinternal(see User Management) are not billed. - Insufficient balance / quota fails the request outright (HTTP
402) — no partial charge is left behind. - Bulk indexing produces many small requests, and per-request rounding amplifies the billing error — for that workload, switch to the gtrk CLI (session-based metering, settled precisely by actual usage).
Error Codes
| Code | HTTP | Description | Resolution |
|---|---|---|---|
6013 | 400 | Missing required parameter (input) | Provide the required parameter |
6016 | 400 | Invalid business parameter (input item not exactly one of the three forms, explicit normalized: false, task too long, etc.) | Fix per the parameter spec |
6004 | 404 | The file_id does not exist or does not belong to you (one shared code — existence is not disclosed) | Make sure the file_id comes from your own upload records and has not expired |
6014 | 400 | The file behind file_id is not an image | Only image files can be referenced (jpg / jpeg / png / bmp / webp) |
6030 | 400 | Per-request input limit exceeded (more than 16 images or 64 texts); the whole request is rejected | Split into smaller batches |
6031 | 413 | A single image exceeds its size limit: image form > 1MB after decoding, or file_id form > 10MB (separate limits; the error message states which form) | Compress / downscale and resend (512px recommended) |
6032 | 429 | Per-key rate limit hit (60 requests/minute, configurable) | Slow down and retry later |
6201 | 402 | Insufficient quota | Buy a quota package or top up |
6202 | 402 | Insufficient balance | Top up in the dashboard |
6502 | 401 | Authentication failed | Check the Authorization header |
6401 | 500 | Upstream model service unavailable | Retry later |
6402 | 500 | Upstream model service timeout (including cold start overrun) | Retry later; set client timeout to ≥ 180 seconds |
Limits
- Per request: up to 16 images (
imageandfile_idforms counted together) or 64 texts; 60 requests/minute per key (all values configurable). - Single-image size limits are separate per form:
image(base64) ≤ 1MB after decoding;file_id≤ 10MB (it references an already-uploaded file, so there is no transfer cost and the limit is wider). file_idcan only reference files uploaded by you, of an image type (jpg / jpeg / png / bmp / webp), and not expired.normalizedonly supportstrue; responses are always normalized vectors.- Lazy model loading: the first request after idle eviction may cold-start on the order of minutes — set client timeout to ≥ 180 seconds.