# Create embeddings

> Turns text into vectors, in the format of OpenAI's embeddings API (`client.embeddings.create` in the OpenAI SDKs). `qwen3-embedding-0.6b` (alias `qwen/qwen3-embedding-0.6b`) returns one vector of 1024 numbers per input, for at most 512 inputs per request.

Source: https://docs.serenityedge.ai/docs/api/edge/create-embedding/

`POST https://api.serenityedge.ai/v1/embeddings`

Turns text into vectors, in the format of OpenAI's embeddings API (`client.embeddings.create` in the OpenAI SDKs). `qwen3-embedding-0.6b` (alias `qwen/qwen3-embedding-0.6b`) returns one vector of 1024 numbers per input, for at most 512 inputs per request.

Billed on `usage.prompt_tokens`, the input tokens the model read, at the model's input price; output is not billed. `GET /v1/models?format=openai` lists the model with `endpoints: ["/v1/embeddings"]` and its price per million tokens. Only Serenity Edge API keys can use this route. See the [Embeddings, rerank and redaction guide](https://docs.serenityedge.ai/docs/embeddings-rerank-and-redaction#embeddings).

## Request body (`application/json`)

| Field | Type | Required | Description |
| --- | --- | --- | --- |
| `model` | string | yes | Id of the embeddings model: `qwen3-embedding-0.6b`, or its alias `qwen/qwen3-embedding-0.6b`. `GET /v1/models?format=openai` lists it with `endpoints: ["/v1/embeddings"]`. |
| `input` | one of string, array of string | yes | The text to embed: a non-empty string, or an array of at most 512 non-empty strings. Each input is read up to its first 8,192 tokens; the rest is ignored and not billed. At most about 300,000 tokens per request (a quarter of the characters). Token ids are refused with a 400: the model reads text through its own tokenizer, so send the strings themselves. |
| `encoding_format` | string | no | Accepted as in OpenAI's API, but vectors always come back as arrays of numbers, also for `base64`; the official OpenAI SDKs accept either form. `dimensions` is not supported: every vector has 1024 numbers. One of `float`, `base64`. |

Example:

```json
{
  "model": "qwen3-embedding-0.6b",
  "input": [
    "Refunds are issued within 5 working days.",
    "Orders ship from Valencia within 48 hours."
  ],
  "encoding_format": "float"
}
```

## Responses

### 200: One embedding per input, in input order, with the model id and the tokens the model read. The vectors of the example are shortened to four numbers; each has 1024.

Body (`application/json`): `EmbeddingList`

| Field | Type | Required | Description |
| --- | --- | --- | --- |
| `object` | string | yes | Always `list`. |
| `data` | array of Embedding (object) | yes | One embedding per input, in input order. |
| `data[].object` | string | yes | Always `embedding`. |
| `data[].index` | integer | yes | Position of the input in `input`. |
| `data[].embedding` | one of array of number, string | yes | The vector: 1024 numbers, or a base64 string with `encoding_format: base64`. |
| `model` | string | yes | `qwen3-embedding-0.6b`, also when the request named the alias. |
| `usage` | EmbeddingUsage (object) | no |  |
| `usage.prompt_tokens` | integer | yes | Input tokens the model read, billed at the model's input price: each input's own tokens, up to 8,192 per input, so a batch costs the same as its inputs sent one by one. If an answer ever comes without `usage`, the request is billed on an estimate instead: a quarter of the characters of each string, rounded up. |
| `usage.total_tokens` | integer | yes | Equal to `prompt_tokens`: output is not billed. |

### 400: The request was refused: a body that is not a JSON object, a missing or invalid `model`, `input` or `encoding_format`, more than 512 inputs, more than about 300,000 tokens (a quarter of the characters), a model served on another route (`The model 'qwen3-reranker-0.6b' is not served on /v1/embeddings.`), or a request the model server could not process (`The model server rejected the request. Check the input sizes and parameters.`). `param` names the field at fault when there is one.

Body (`application/json`): `ErrorResponse`

| Field | Type | Required | Description |
| --- | --- | --- | --- |
| `error` | Error (object) | yes | OpenAI-style error object. |
| `error.message` | string | yes | Human-readable description of the problem. |
| `error.type` | string | yes | Error category. One of `invalid_request_error`, `authentication_error`, `permission_error`, `not_found_error`, `rate_limit_error`, `server_error`. |
| `error.code` | string or null | no | Machine-readable error code, when available. |
| `error.param` | string or null | no | The request parameter the error refers to, when applicable. |

### 401: Missing or invalid API key.

Body (`application/json`): `ErrorResponse`, the same fields as under 400.

### 403: The key is valid but cannot use this route: only Serenity Edge API keys can. Any other key, such as a key from a Serenity Star account, gets `permission_denied` with a message that names the route's API (`embeddings`, `rerank` or `redact`).

Body (`application/json`): `ErrorResponse`, the same fields as under 400.

### 404: The model id is unknown, or it is a chat or decision model, which cannot be used on this route (`model_not_found`).

Body (`application/json`): `ErrorResponse`, the same fields as under 400.

### 413: The request body is larger than this route accepts (4 MB, `request_too_large`).

Body (`application/json`): `ErrorResponse`, the same fields as under 400.

### 429: Rate limit exceeded, or the service is temporarily at capacity for this model. Wait for the number of seconds in the `Retry-After` header before retrying.

Header `Retry-After`: Seconds to wait before retrying.

Body (`application/json`): `ErrorResponse`, the same fields as under 400.

### 500: Unexpected server error: the model service returned an unexpected response (`upstream_error`), the request got no answer within 600 seconds (`timeout`), or an error in the gateway. Retry with backoff.

Body (`application/json`): `ErrorResponse`, the same fields as under 400.

### 503: The model service is temporarily unavailable (`upstream_unavailable`). Retry later and check the status page at https://status.serenityedge.ai.

Body (`application/json`): `ErrorResponse`, the same fields as under 400.
