> ## Documentation Index
> Fetch the complete documentation index at: https://docs.mka1.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Vector stores

> Index files and retrieve relevant document chunks.

Vector stores are reusable retrieval resources. This guide covers their lifecycle and direct search; pass retrieved context into a [Response](/docs/responses) when building an answer grounded in your files.

First [upload your files](/docs/files). Keep their file IDs for the examples below.

## Create a vector store

Create a vector store and attach one or more uploaded file IDs.

<CodeGroup>
  ```ts TypeScript SDK theme={null}
  import { SDK } from '@meetkai/mka1';

  const sdk = new SDK({ bearerAuth: 'Bearer <mka1-api-key>' });

  const vectorStore = await sdk.llm.vectorStores.create({
    xOnBehalfOf: '<end-user-id>',
    createVectorStoreRequest: {
      name: 'Support knowledge base',
      description: 'Indexed support manuals and help center docs',
      fileIds: ['file-abc123'],
      expiresAfter: { anchor: 'last_active_at', days: 30 },
    },
  });
  ```

  ```ts OpenAI SDK theme={null}
  import OpenAI from 'openai';

  const openai = new OpenAI({
    apiKey: '<mka1-api-key>',
    baseURL: 'https://apigw.mka1.com/api/v1/llm/',
    defaultHeaders: { 'X-On-Behalf-Of': '<end-user-id>' },
  });

  const vectorStore = await openai.vectorStores.create({
    name: 'Support knowledge base',
    description: 'Indexed support manuals and help center docs',
    file_ids: ['file-abc123'],
    expires_after: { anchor: 'last_active_at', days: 30 },
  });
  ```

  ```python Python SDK theme={null}
  from meetkai_mka1 import SDK

  sdk = SDK(bearer_auth="Bearer <mka1-api-key>")

  vector_store = sdk.llm.vector_stores.create(
      name="Support knowledge base",
      description="Indexed support manuals and help center docs",
  )
  ```

  ```csharp C# SDK theme={null}
  using MeetKai.MKA1;
  using MeetKai.MKA1.Types.Components;
  using MeetKai.MKA1.Types.Requests;

  var sdk = new SDK(bearerAuth: "Bearer <mka1-api-key>");

  var vs = await sdk.Llm.VectorStores.CreateAsync(new MeetKai.MKA1.Types.Components.CreateVectorStoreRequest()
  {
      Name = "Support knowledge base",
      Description = "Indexed support manuals and help center docs",
  });
  ```

  ```bash CLI theme={null}
  mka1 llm vector-stores create --body '{
    "name": "Support knowledge base",
    "description": "Indexed support manuals and help center docs",
    "file_ids": ["file-abc123"],
    "expires_after": { "anchor": "last_active_at", "days": 30 }
  }'
  ```

  ```bash Bash theme={null}
  curl https://apigw.mka1.com/api/v1/llm/vector_stores \
    --request POST \
    --header 'Content-Type: application/json' \
    --header 'Authorization: Bearer <mka1-api-key>' \
    --header 'X-On-Behalf-Of: <end-user-id>' \
    --data '{
      "name": "Support knowledge base",
      "description": "Indexed support manuals and help center docs",
      "file_ids": [
        "file-abc123"
      ],
      "expires_after": {
        "anchor": "last_active_at",
        "days": 30
      }
    }'
  ```
</CodeGroup>

This response returns a vector store ID such as `vs_abc123`.

## Add more files later

You can add more files to an existing vector store without recreating it.

<CodeGroup>
  ```ts TypeScript SDK theme={null}
  const vsFile = await sdk.llm.vectorStores.createFile({
    vectorStoreId: 'vs_abc123',
    xOnBehalfOf: '<end-user-id>',
    createVectorStoreFileRequest: {
      fileId: 'file-def456',
      attributes: { category: 'manual', version: '2.0' },
    },
  });
  ```

  ```ts OpenAI SDK theme={null}
  const vsFile = await openai.vectorStores.files.create('vs_abc123', {
    file_id: 'file-def456',
  });
  ```

  ```python Python SDK theme={null}
  vs_file = sdk.llm.vector_stores.create_file(
      vector_store_id="vs_abc123",
      file_id="file-def456",
  )
  ```

  ```csharp C# SDK theme={null}
  // Adding files to an existing vector store is done via the
  // VectorStores.CreateFile or VectorStores.Files API methods.
  // Refer to the API reference for the full method signature.
  ```

  ```bash CLI theme={null}
  mka1 llm vector-stores create-file \
    --vector-store-id vs_abc123 \
    --file-id file-def456 \
    --attributes '{"category":"manual","version":"2.0"}'
  ```

  ```bash Bash theme={null}
  curl https://apigw.mka1.com/api/v1/llm/vector_stores/vs_abc123/files \
    --request POST \
    --header 'Content-Type: application/json' \
    --header 'Authorization: Bearer <mka1-api-key>' \
    --header 'X-On-Behalf-Of: <end-user-id>' \
    --data '{
      "file_id": "file-def456",
      "attributes": {
        "category": "manual",
        "version": "2.0"
      }
    }'
  ```
</CodeGroup>

The vector store file can return `status: "in_progress"` while indexing runs.
A file is not searchable until its status reaches `"completed"` — searching before then
succeeds but omits the file, so poll for `"completed"` rather than assuming a fixed wait.
Indexing usually finishes in seconds, but latency varies with file size and load.
Check the Files and Vector Stores endpoints in the API Reference for the polling endpoint (for example, `GET /vector_stores/{vector_store_id}/files/{file_id}`).

## Search the vector store

Use semantic search to retrieve the most relevant chunks for a user question.

<CodeGroup>
  ```ts TypeScript SDK theme={null}
  const results = await sdk.llm.vectorStores.search({
    vectorStoreId: 'vs_abc123',
    xOnBehalfOf: '<end-user-id>',
    searchVectorStoreRequest: {
      query: 'How do I reset my password?',
      maxNumResults: 5,
    },
  });
  ```

  ```ts OpenAI SDK theme={null}
  const results = await openai.vectorStores.search('vs_abc123', {
    query: 'How do I reset my password?',
    max_num_results: 5,
  });
  ```

  ```python Python SDK theme={null}
  results = sdk.llm.vector_stores.search(
      vector_store_id="vs_abc123",
      query="How do I reset my password?",
  )
  ```

  ```csharp C# SDK theme={null}
  // Search is available via the VectorStores.Search method.
  // Refer to the API reference for the full method signature.
  ```

  ```bash CLI theme={null}
  mka1 llm vector-stores search \
    --vector-store-id vs_abc123 \
    --body '{
      "query": "How do I reset my password?",
      "max_num_results": 5
    }'
  ```

  ```bash Bash theme={null}
  curl https://apigw.mka1.com/api/v1/llm/vector_stores/vs_abc123/search \
    --request POST \
    --header 'Content-Type: application/json' \
    --header 'Authorization: Bearer <mka1-api-key>' \
    --header 'X-On-Behalf-Of: <end-user-id>' \
    --data '{
      "query": "How do I reset my password?",
      "max_num_results": 5
    }'
  ```
</CodeGroup>

The response returns ranked matches with `file_id`, `filename`, score data, chunk content, and the file's current `attributes`.

## Filter search by file attributes

Attributes are file-level key-value metadata — string, number, or boolean values — set when you attach a file (see [Add more files later](#add-more-files-later)).
You can change them after ingest with the update-file endpoint (`POST /vector_stores/{vector_store_id}/files/{file_id}`); search always evaluates the current values.

Pass `filters` in the search request to restrict results to files whose attributes match.
A filter is either a comparison — `eq`, `ne`, `gt`, `gte`, `lt`, `lte`, `in`, `nin` — or an `and`/`or` compound of nested filters.

<CodeGroup>
  ```ts TypeScript SDK theme={null}
  const results = await sdk.llm.vectorStores.search({
    vectorStoreId: 'vs_abc123',
    xOnBehalfOf: '<end-user-id>',
    searchVectorStoreRequest: {
      query: 'How do I reset my password?',
      maxNumResults: 5,
      filters: {
        type: 'and',
        filters: [
          { type: 'eq', key: 'category', value: 'manual' },
          { type: 'ne', key: 'version', value: '1.0' },
        ],
      },
    },
  });
  ```

  ```ts OpenAI SDK theme={null}
  const results = await openai.vectorStores.search('vs_abc123', {
    query: 'How do I reset my password?',
    max_num_results: 5,
    filters: {
      type: 'and',
      filters: [
        { type: 'eq', key: 'category', value: 'manual' },
        { type: 'ne', key: 'version', value: '1.0' },
      ],
    },
  });
  ```

  ```python Python SDK theme={null}
  results = sdk.llm.vector_stores.search(
      vector_store_id="vs_abc123",
      query="How do I reset my password?",
      filters={
          "type": "and",
          "filters": [
              {"type": "eq", "key": "category", "value": "manual"},
              {"type": "ne", "key": "version", "value": "1.0"},
          ],
      },
  )
  ```

  ```csharp C# SDK theme={null}
  // Filtered search is available via the VectorStores.Search method's Filters
  // parameter (ComparisonFilter / CompoundFilter).
  // Refer to the API reference for the full method signature.
  ```

  ```bash CLI theme={null}
  mka1 llm vector-stores search \
    --vector-store-id vs_abc123 \
    --body '{
      "query": "How do I reset my password?",
      "max_num_results": 5,
      "filters": {
        "type": "and",
        "filters": [
          { "type": "eq", "key": "category", "value": "manual" },
          { "type": "ne", "key": "version", "value": "1.0" }
        ]
      }
    }'
  ```

  ```bash Bash theme={null}
  curl https://apigw.mka1.com/api/v1/llm/vector_stores/vs_abc123/search \
    --request POST \
    --header 'Content-Type: application/json' \
    --header 'Authorization: Bearer <mka1-api-key>' \
    --header 'X-On-Behalf-Of: <end-user-id>' \
    --data '{
      "query": "How do I reset my password?",
      "max_num_results": 5,
      "filters": {
        "type": "and",
        "filters": [
          { "type": "eq", "key": "category", "value": "manual" },
          { "type": "ne", "key": "version", "value": "1.0" }
        ]
      }
    }'
  ```
</CodeGroup>

Filter evaluation follows these rules:

* A file that does not have the filter's `key` never matches — including for `ne` and `nin`. A filter only opts a file in on evidence, never by absence.
* `eq` and `ne` are strict equality with no type coercion: the string `"2"` does not equal the number `2`.
* `gt`, `gte`, `lt`, and `lte` compare numbers only; a non-numeric attribute or filter value fails the comparison.
* `in` and `nin` take an array `value` and test whether the file's attribute is (or is not) one of its elements.
* `and` and `or` compounds nest to any depth.
* On [graph stores](/docs/graph-retrieval#create-a-graph-store), filtering is applied after retrieval, so a filtered search can return fewer than `max_num_results` matches.

## Typical workflow

Use this sequence for most retrieval setups:

1. Upload the source file.
2. Create a vector store with `file_ids`, or attach the file later.
3. Wait for file processing to complete (for example, file `status: "processed"`, and vector-store file indexing `status: "completed"`).
4. Search the vector store when you need relevant context.

You can then feed the returned text into your own application logic or a Responses request.

For graph-aware search, see [Graph retrieval](/docs/graph-retrieval).
