@mastra/s3vectors 1.0.1 → 1.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +18 -0
- package/LICENSE.md +15 -0
- package/dist/docs/SKILL.md +4 -4
- package/dist/docs/assets/SOURCE_MAP.json +1 -1
- package/dist/docs/references/docs-rag-retrieval.md +4 -4
- package/dist/docs/references/docs-rag-vector-databases.md +13 -13
- package/dist/docs/references/reference-vectors-s3vectors.md +46 -46
- package/dist/index.cjs +4 -4
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +4 -4
- package/dist/index.js.map +1 -1
- package/package.json +9 -9
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,23 @@
|
|
|
1
1
|
# @mastra/s3vectors
|
|
2
2
|
|
|
3
|
+
## 1.0.2
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- dependencies updates: ([#14061](https://github.com/mastra-ai/mastra/pull/14061))
|
|
8
|
+
- Updated dependency [`@aws-sdk/client-s3vectors@^3.1004.0` ↗︎](https://www.npmjs.com/package/@aws-sdk/client-s3vectors/v/3.1004.0) (from `^3.901.0`, in `dependencies`)
|
|
9
|
+
- Updated dependencies [[`4f71b43`](https://github.com/mastra-ai/mastra/commit/4f71b436a4a6b8839842d8da47b57b84509af56c), [`a070277`](https://github.com/mastra-ai/mastra/commit/a07027766ce195ba74d0783116d894cbab25d44c), [`b628b91`](https://github.com/mastra-ai/mastra/commit/b628b9128b372c0f54214d902b07279f03443900), [`332c014`](https://github.com/mastra-ai/mastra/commit/332c014e076b81edf7fe45b58205882726415e90), [`6b63153`](https://github.com/mastra-ai/mastra/commit/6b63153878ea841c0f4ce632ba66bb33e57e9c1b), [`4246e34`](https://github.com/mastra-ai/mastra/commit/4246e34cec9c26636d0965942268e6d07c346671), [`b8837ee`](https://github.com/mastra-ai/mastra/commit/b8837ee77e2e84197609762bfabd8b3da326d30c), [`866cc2c`](https://github.com/mastra-ai/mastra/commit/866cc2cb1f0e3b314afab5194f69477fada745d1), [`5d950f7`](https://github.com/mastra-ai/mastra/commit/5d950f7bf426a215a1808f0abef7de5c8336ba1c), [`28c85b1`](https://github.com/mastra-ai/mastra/commit/28c85b184fc32b40f7f160483c982da6d388ecbd), [`e9a08fb`](https://github.com/mastra-ai/mastra/commit/e9a08fbef1ada7e50e961e2f54f55e8c10b4a45c), [`1d0a8a8`](https://github.com/mastra-ai/mastra/commit/1d0a8a8acf33203d5744fc429b090ad8598aa8ed), [`631ffd8`](https://github.com/mastra-ai/mastra/commit/631ffd82fed108648b448b28e6a90e38c5f53bf5), [`6bcbf8a`](https://github.com/mastra-ai/mastra/commit/6bcbf8a6774d5a53b21d61db8a45ce2593ca1616), [`aae2295`](https://github.com/mastra-ai/mastra/commit/aae2295838a2d329ad6640829e87934790ffe5b8), [`aa61f29`](https://github.com/mastra-ai/mastra/commit/aa61f29ff8095ce46a4ae16e46c4d8c79b2b685b), [`7ff3714`](https://github.com/mastra-ai/mastra/commit/7ff37148515439bb3be009a60e02c3e363299760), [`18c3a90`](https://github.com/mastra-ai/mastra/commit/18c3a90c9e48cf69500e308affeb8eba5860b2af), [`41d79a1`](https://github.com/mastra-ai/mastra/commit/41d79a14bd8cb6de1e2565fd0a04786bae2f211b), [`f35487b`](https://github.com/mastra-ai/mastra/commit/f35487bb2d46c636e22aa71d90025613ae38235a), [`6dc2192`](https://github.com/mastra-ai/mastra/commit/6dc21921aef0f0efab15cd0805fa3d18f277a76f), [`eeb3a3f`](https://github.com/mastra-ai/mastra/commit/eeb3a3f43aca10cf49479eed2a84b7d9ecea02ba), [`e673376`](https://github.com/mastra-ai/mastra/commit/e6733763ad1321aa7e5ae15096b9c2104f93b1f3), [`05f8d90`](https://github.com/mastra-ai/mastra/commit/05f8d9009290ce6aa03428b3add635268615db85), [`b2204c9`](https://github.com/mastra-ai/mastra/commit/b2204c98a42848bbfb6f0440f005dc2b6354f1cd), [`a1bf1e3`](https://github.com/mastra-ai/mastra/commit/a1bf1e385ed4c0ef6f11b56c5887442970d127f2), [`b6f647a`](https://github.com/mastra-ai/mastra/commit/b6f647ae2388e091f366581595feb957e37d5b40), [`0c57b8b`](https://github.com/mastra-ai/mastra/commit/0c57b8b0a69a97b5a4ae3f79be6c610f29f3cf7b), [`b081f27`](https://github.com/mastra-ai/mastra/commit/b081f272cf411716e1d6bd72ceac4bcee2657b19), [`4b8da97`](https://github.com/mastra-ai/mastra/commit/4b8da97a5ce306e97869df6c39535d9069e563db), [`0c09eac`](https://github.com/mastra-ai/mastra/commit/0c09eacb1926f64cfdc9ae5c6d63385cf8c9f72c), [`6b9b93d`](https://github.com/mastra-ai/mastra/commit/6b9b93d6f459d1ba6e36f163abf62a085ddb3d64), [`31b6067`](https://github.com/mastra-ai/mastra/commit/31b6067d0cc3ab10e1b29c36147f3b5266bc714a), [`797ac42`](https://github.com/mastra-ai/mastra/commit/797ac4276de231ad2d694d9aeca75980f6cd0419), [`0bc289e`](https://github.com/mastra-ai/mastra/commit/0bc289e2d476bf46c5b91c21969e8d0c6864691c), [`9b75a06`](https://github.com/mastra-ai/mastra/commit/9b75a06e53ebb0b950ba7c1e83a0142047185f46), [`4c3a1b1`](https://github.com/mastra-ai/mastra/commit/4c3a1b122ea083e003d71092f30f3b31680b01c0), [`256df35`](https://github.com/mastra-ai/mastra/commit/256df3571d62beb3ad4971faa432927cc140e603), [`85cc3b3`](https://github.com/mastra-ai/mastra/commit/85cc3b3b6f32ae4b083c26498f50d5b250ba944b), [`97ea28c`](https://github.com/mastra-ai/mastra/commit/97ea28c746e9e4147d56047bbb1c4a92417a3fec), [`d567299`](https://github.com/mastra-ai/mastra/commit/d567299cf81e02bd9d5221d4bc05967d6c224161), [`716ffe6`](https://github.com/mastra-ai/mastra/commit/716ffe68bed81f7c2690bc8581b9e140f7bf1c3d), [`8296332`](https://github.com/mastra-ai/mastra/commit/8296332de21c16e3dfc3d0b2d615720a6dc88f2f), [`4df2116`](https://github.com/mastra-ai/mastra/commit/4df211619dd922c047d396ca41cd7027c8c4c8e7), [`2219c1a`](https://github.com/mastra-ai/mastra/commit/2219c1acbd21da116da877f0036ffb985a9dd5a3), [`17c4145`](https://github.com/mastra-ai/mastra/commit/17c4145166099354545582335b5252bdfdfd908b)]:
|
|
10
|
+
- @mastra/core@1.11.0
|
|
11
|
+
|
|
12
|
+
## 1.0.2-alpha.0
|
|
13
|
+
|
|
14
|
+
### Patch Changes
|
|
15
|
+
|
|
16
|
+
- dependencies updates: ([#14061](https://github.com/mastra-ai/mastra/pull/14061))
|
|
17
|
+
- Updated dependency [`@aws-sdk/client-s3vectors@^3.1004.0` ↗︎](https://www.npmjs.com/package/@aws-sdk/client-s3vectors/v/3.1004.0) (from `^3.901.0`, in `dependencies`)
|
|
18
|
+
- Updated dependencies [[`4f71b43`](https://github.com/mastra-ai/mastra/commit/4f71b436a4a6b8839842d8da47b57b84509af56c), [`a070277`](https://github.com/mastra-ai/mastra/commit/a07027766ce195ba74d0783116d894cbab25d44c), [`b628b91`](https://github.com/mastra-ai/mastra/commit/b628b9128b372c0f54214d902b07279f03443900), [`332c014`](https://github.com/mastra-ai/mastra/commit/332c014e076b81edf7fe45b58205882726415e90), [`6b63153`](https://github.com/mastra-ai/mastra/commit/6b63153878ea841c0f4ce632ba66bb33e57e9c1b), [`4246e34`](https://github.com/mastra-ai/mastra/commit/4246e34cec9c26636d0965942268e6d07c346671), [`b8837ee`](https://github.com/mastra-ai/mastra/commit/b8837ee77e2e84197609762bfabd8b3da326d30c), [`5d950f7`](https://github.com/mastra-ai/mastra/commit/5d950f7bf426a215a1808f0abef7de5c8336ba1c), [`28c85b1`](https://github.com/mastra-ai/mastra/commit/28c85b184fc32b40f7f160483c982da6d388ecbd), [`e9a08fb`](https://github.com/mastra-ai/mastra/commit/e9a08fbef1ada7e50e961e2f54f55e8c10b4a45c), [`631ffd8`](https://github.com/mastra-ai/mastra/commit/631ffd82fed108648b448b28e6a90e38c5f53bf5), [`aae2295`](https://github.com/mastra-ai/mastra/commit/aae2295838a2d329ad6640829e87934790ffe5b8), [`aa61f29`](https://github.com/mastra-ai/mastra/commit/aa61f29ff8095ce46a4ae16e46c4d8c79b2b685b), [`7ff3714`](https://github.com/mastra-ai/mastra/commit/7ff37148515439bb3be009a60e02c3e363299760), [`41d79a1`](https://github.com/mastra-ai/mastra/commit/41d79a14bd8cb6de1e2565fd0a04786bae2f211b), [`e673376`](https://github.com/mastra-ai/mastra/commit/e6733763ad1321aa7e5ae15096b9c2104f93b1f3), [`b2204c9`](https://github.com/mastra-ai/mastra/commit/b2204c98a42848bbfb6f0440f005dc2b6354f1cd), [`a1bf1e3`](https://github.com/mastra-ai/mastra/commit/a1bf1e385ed4c0ef6f11b56c5887442970d127f2), [`b6f647a`](https://github.com/mastra-ai/mastra/commit/b6f647ae2388e091f366581595feb957e37d5b40), [`0c57b8b`](https://github.com/mastra-ai/mastra/commit/0c57b8b0a69a97b5a4ae3f79be6c610f29f3cf7b), [`b081f27`](https://github.com/mastra-ai/mastra/commit/b081f272cf411716e1d6bd72ceac4bcee2657b19), [`0c09eac`](https://github.com/mastra-ai/mastra/commit/0c09eacb1926f64cfdc9ae5c6d63385cf8c9f72c), [`6b9b93d`](https://github.com/mastra-ai/mastra/commit/6b9b93d6f459d1ba6e36f163abf62a085ddb3d64), [`31b6067`](https://github.com/mastra-ai/mastra/commit/31b6067d0cc3ab10e1b29c36147f3b5266bc714a), [`797ac42`](https://github.com/mastra-ai/mastra/commit/797ac4276de231ad2d694d9aeca75980f6cd0419), [`0bc289e`](https://github.com/mastra-ai/mastra/commit/0bc289e2d476bf46c5b91c21969e8d0c6864691c), [`9b75a06`](https://github.com/mastra-ai/mastra/commit/9b75a06e53ebb0b950ba7c1e83a0142047185f46), [`4c3a1b1`](https://github.com/mastra-ai/mastra/commit/4c3a1b122ea083e003d71092f30f3b31680b01c0), [`85cc3b3`](https://github.com/mastra-ai/mastra/commit/85cc3b3b6f32ae4b083c26498f50d5b250ba944b), [`97ea28c`](https://github.com/mastra-ai/mastra/commit/97ea28c746e9e4147d56047bbb1c4a92417a3fec), [`d567299`](https://github.com/mastra-ai/mastra/commit/d567299cf81e02bd9d5221d4bc05967d6c224161), [`716ffe6`](https://github.com/mastra-ai/mastra/commit/716ffe68bed81f7c2690bc8581b9e140f7bf1c3d), [`8296332`](https://github.com/mastra-ai/mastra/commit/8296332de21c16e3dfc3d0b2d615720a6dc88f2f), [`4df2116`](https://github.com/mastra-ai/mastra/commit/4df211619dd922c047d396ca41cd7027c8c4c8e7), [`2219c1a`](https://github.com/mastra-ai/mastra/commit/2219c1acbd21da116da877f0036ffb985a9dd5a3), [`17c4145`](https://github.com/mastra-ai/mastra/commit/17c4145166099354545582335b5252bdfdfd908b)]:
|
|
19
|
+
- @mastra/core@1.11.0-alpha.0
|
|
20
|
+
|
|
3
21
|
## 1.0.1
|
|
4
22
|
|
|
5
23
|
### Patch Changes
|
package/LICENSE.md
CHANGED
|
@@ -1,3 +1,18 @@
|
|
|
1
|
+
Portions of this software are licensed as follows:
|
|
2
|
+
|
|
3
|
+
- All content that resides under any directory named "ee/" within this
|
|
4
|
+
repository, including but not limited to:
|
|
5
|
+
- `packages/core/src/auth/ee/`
|
|
6
|
+
- `packages/server/src/server/auth/ee/`
|
|
7
|
+
is licensed under the license defined in `ee/LICENSE`.
|
|
8
|
+
|
|
9
|
+
- All third-party components incorporated into the Mastra Software are
|
|
10
|
+
licensed under the original license provided by the owner of the
|
|
11
|
+
applicable component.
|
|
12
|
+
|
|
13
|
+
- Content outside of the above-mentioned directories or restrictions is
|
|
14
|
+
available under the "Apache License 2.0" as defined below.
|
|
15
|
+
|
|
1
16
|
# Apache License 2.0
|
|
2
17
|
|
|
3
18
|
Copyright (c) 2025 Kepler Software, Inc.
|
package/dist/docs/SKILL.md
CHANGED
|
@@ -3,7 +3,7 @@ name: mastra-s3vectors
|
|
|
3
3
|
description: Documentation for @mastra/s3vectors. Use when working with @mastra/s3vectors APIs, configuration, or implementation.
|
|
4
4
|
metadata:
|
|
5
5
|
package: "@mastra/s3vectors"
|
|
6
|
-
version: "1.0.
|
|
6
|
+
version: "1.0.2"
|
|
7
7
|
---
|
|
8
8
|
|
|
9
9
|
## When to use
|
|
@@ -16,12 +16,12 @@ Read the individual reference documents for detailed explanations and code examp
|
|
|
16
16
|
|
|
17
17
|
### Docs
|
|
18
18
|
|
|
19
|
-
- [Retrieval,
|
|
20
|
-
- [Storing
|
|
19
|
+
- [Retrieval, semantic search, reranking](references/docs-rag-retrieval.md) - Guide on retrieval processes in Mastra's RAG systems, including semantic search, filtering, and re-ranking.
|
|
20
|
+
- [Storing embeddings in a vector database](references/docs-rag-vector-databases.md) - Guide on vector storage options in Mastra, including embedded and dedicated vector databases for similarity search.
|
|
21
21
|
|
|
22
22
|
### Reference
|
|
23
23
|
|
|
24
|
-
- [Reference: Amazon S3
|
|
24
|
+
- [Reference: Amazon S3 vectors store](references/reference-vectors-s3vectors.md) - Documentation for the S3Vectors class in Mastra, which provides vector search using Amazon S3 Vectors (Preview).
|
|
25
25
|
|
|
26
26
|
|
|
27
27
|
Read [assets/SOURCE_MAP.json](assets/SOURCE_MAP.json) for source code references.
|
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
# Retrieval in RAG
|
|
1
|
+
# Retrieval in RAG systems
|
|
2
2
|
|
|
3
3
|
After storing embeddings, you need to retrieve relevant chunks to answer user queries.
|
|
4
4
|
|
|
5
5
|
Mastra provides flexible retrieval options with support for semantic search, filtering, and re-ranking.
|
|
6
6
|
|
|
7
|
-
## How
|
|
7
|
+
## How retrieval works
|
|
8
8
|
|
|
9
9
|
1. The user's query is converted to an embedding using the same model used for document embeddings
|
|
10
10
|
2. This embedding is compared to stored embeddings using vector similarity
|
|
@@ -14,7 +14,7 @@ Mastra provides flexible retrieval options with support for semantic search, fil
|
|
|
14
14
|
- Re-ranked for better relevance
|
|
15
15
|
- Processed through a knowledge graph
|
|
16
16
|
|
|
17
|
-
## Basic
|
|
17
|
+
## Basic retrieval
|
|
18
18
|
|
|
19
19
|
The simplest approach is direct semantic search. This method uses vector similarity to find chunks that are semantically similar to the query:
|
|
20
20
|
|
|
@@ -63,7 +63,7 @@ Results include both the text content and a similarity score:
|
|
|
63
63
|
]
|
|
64
64
|
```
|
|
65
65
|
|
|
66
|
-
## Advanced
|
|
66
|
+
## Advanced retrieval options
|
|
67
67
|
|
|
68
68
|
### Metadata Filtering
|
|
69
69
|
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
# Storing
|
|
1
|
+
# Storing embeddings in a vector database
|
|
2
2
|
|
|
3
3
|
After generating embeddings, you need to store them in a database that supports vector similarity search. Mastra provides a consistent interface for storing and querying embeddings across various vector databases.
|
|
4
4
|
|
|
5
|
-
## Supported
|
|
5
|
+
## Supported databases
|
|
6
6
|
|
|
7
7
|
**MongoDB**:
|
|
8
8
|
|
|
@@ -234,7 +234,7 @@ await store.upsert({
|
|
|
234
234
|
})
|
|
235
235
|
```
|
|
236
236
|
|
|
237
|
-
**
|
|
237
|
+
**Elasticsearch**:
|
|
238
238
|
|
|
239
239
|
```ts
|
|
240
240
|
import { ElasticSearchVector } from '@mastra/elasticsearch'
|
|
@@ -337,7 +337,7 @@ await store.upsert({
|
|
|
337
337
|
})
|
|
338
338
|
```
|
|
339
339
|
|
|
340
|
-
## Using
|
|
340
|
+
## Using vector storage
|
|
341
341
|
|
|
342
342
|
Once initialized, all vector stores share the same interface for creating indexes, upserting embeddings, and querying.
|
|
343
343
|
|
|
@@ -355,11 +355,11 @@ await store.createIndex({
|
|
|
355
355
|
|
|
356
356
|
The dimension size must match the output dimension of your chosen embedding model. Common dimension sizes are:
|
|
357
357
|
|
|
358
|
-
- OpenAI text-embedding-3-small
|
|
359
|
-
- Cohere embed-multilingual-v3
|
|
360
|
-
- Google gemini-embedding-001
|
|
358
|
+
- `OpenAI text-embedding-3-small`: 1536 dimensions (or custom, e.g., 256)
|
|
359
|
+
- `Cohere embed-multilingual-v3`: 1024 dimensions
|
|
360
|
+
- `Google gemini-embedding-001`: 768 dimensions (or custom)
|
|
361
361
|
|
|
362
|
-
> **Warning:** Index dimensions
|
|
362
|
+
> **Warning:** Index dimensions can't be changed after creation. To use a different model, delete and recreate the index with the new dimension size.
|
|
363
363
|
|
|
364
364
|
### Naming Rules for Databases
|
|
365
365
|
|
|
@@ -490,7 +490,7 @@ Index names must:
|
|
|
490
490
|
- Example: `My_Index` is not valid (contains uppercase letters)
|
|
491
491
|
- Example: `_myindex` is not valid (begins with underscore)
|
|
492
492
|
|
|
493
|
-
**
|
|
493
|
+
**Elasticsearch**:
|
|
494
494
|
|
|
495
495
|
Index names must:
|
|
496
496
|
|
|
@@ -543,7 +543,7 @@ The upsert operation:
|
|
|
543
543
|
- Creates new vectors if they don't exist
|
|
544
544
|
- Automatically handles batching for large datasets
|
|
545
545
|
|
|
546
|
-
## Adding
|
|
546
|
+
## Adding metadata
|
|
547
547
|
|
|
548
548
|
Vector stores support rich metadata (any JSON-serializable fields) for filtering and organization. Since metadata is stored with no fixed schema, use consistent field naming to avoid unexpected query results.
|
|
549
549
|
|
|
@@ -581,9 +581,9 @@ Key metadata considerations:
|
|
|
581
581
|
- Only include fields you plan to filter or sort by - extra fields add overhead
|
|
582
582
|
- Add timestamps (e.g., 'createdAt', 'lastUpdated') to track content freshness
|
|
583
583
|
|
|
584
|
-
## Deleting
|
|
584
|
+
## Deleting vectors
|
|
585
585
|
|
|
586
|
-
When building RAG applications, you often need to clean up stale vectors when documents are deleted or updated. Mastra provides the `deleteVectors` method that supports deleting vectors by metadata filters, making it
|
|
586
|
+
When building RAG applications, you often need to clean up stale vectors when documents are deleted or updated. Mastra provides the `deleteVectors` method that supports deleting vectors by metadata filters, making it straightforward to remove all embeddings associated with a specific document.
|
|
587
587
|
|
|
588
588
|
### Delete by Metadata Filter
|
|
589
589
|
|
|
@@ -637,7 +637,7 @@ await store.deleteVectors({
|
|
|
637
637
|
})
|
|
638
638
|
```
|
|
639
639
|
|
|
640
|
-
## Best
|
|
640
|
+
## Best practices
|
|
641
641
|
|
|
642
642
|
- Create indexes before bulk insertions
|
|
643
643
|
- Use batch operations for large insertions (the upsert method handles batching automatically)
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
# Amazon S3
|
|
1
|
+
# Amazon S3 vectors store
|
|
2
2
|
|
|
3
3
|
The `S3Vectors` class provides vector search using [Amazon S3 Vectors (Preview)](https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-vectors.html). It stores vectors in **vector buckets** and performs similarity search in **vector indexes**, with JSON-based metadata filters.
|
|
4
4
|
|
|
5
|
-
> **Warning:** Amazon S3 Vectors is a Preview service. Preview features may change or be removed without notice and
|
|
5
|
+
> **Warning:** Amazon S3 Vectors is a Preview service. Preview features may change or be removed without notice and aren't covered by AWS SLAs. Behavior, limits, and regional availability can change at any time. This library may introduce breaking changes to stay aligned with AWS.
|
|
6
6
|
|
|
7
7
|
## Installation
|
|
8
8
|
|
|
@@ -30,7 +30,7 @@ yarn add @mastra/s3vectors@latest
|
|
|
30
30
|
bun add @mastra/s3vectors@latest
|
|
31
31
|
```
|
|
32
32
|
|
|
33
|
-
## Usage
|
|
33
|
+
## Usage example
|
|
34
34
|
|
|
35
35
|
```typescript
|
|
36
36
|
import { S3Vectors } from '@mastra/s3vectors'
|
|
@@ -82,59 +82,59 @@ const results = await store.query({
|
|
|
82
82
|
await store.disconnect()
|
|
83
83
|
```
|
|
84
84
|
|
|
85
|
-
## Constructor
|
|
85
|
+
## Constructor options
|
|
86
86
|
|
|
87
|
-
**vectorBucketName
|
|
87
|
+
**vectorBucketName** (`string`): Target S3 Vectors vector bucket name.
|
|
88
88
|
|
|
89
|
-
**clientConfig
|
|
89
|
+
**clientConfig** (`S3VectorsClientConfig`): AWS SDK v3 client options (e.g., \`region\`, \`credentials\`).
|
|
90
90
|
|
|
91
|
-
**nonFilterableMetadataKeys
|
|
91
|
+
**nonFilterableMetadataKeys** (`string[]`): Metadata keys that should NOT be filterable (applied to the index at creation time). Use this for large text fields like \`content\`.
|
|
92
92
|
|
|
93
93
|
## Methods
|
|
94
94
|
|
|
95
|
-
### createIndex()
|
|
95
|
+
### `createIndex()`
|
|
96
96
|
|
|
97
97
|
Creates a new vector index in the configured vector bucket. If the index already exists, the call validates the schema and becomes a no-op (existing metric and dimension are preserved).
|
|
98
98
|
|
|
99
|
-
**indexName
|
|
99
|
+
**indexName** (`string`): Logical index name. Normalized internally: underscores are replaced with hyphens and the name is lowercased.
|
|
100
100
|
|
|
101
|
-
**dimension
|
|
101
|
+
**dimension** (`number`): Vector dimension (must match your embedding model)
|
|
102
102
|
|
|
103
|
-
**metric
|
|
103
|
+
**metric** (`'cosine' | 'euclidean'`): Distance metric for similarity search. \`dotproduct\` is not supported by S3 Vectors. (Default: `cosine`)
|
|
104
104
|
|
|
105
|
-
### upsert()
|
|
105
|
+
### `upsert()`
|
|
106
106
|
|
|
107
|
-
Adds or replaces vectors (full-record put). If `ids`
|
|
107
|
+
Adds or replaces vectors (full-record put). If `ids` aren't provided, UUIDs are generated.
|
|
108
108
|
|
|
109
|
-
**indexName
|
|
109
|
+
**indexName** (`string`): Name of the index to upsert into
|
|
110
110
|
|
|
111
|
-
**vectors
|
|
111
|
+
**vectors** (`number[][]`): Array of embedding vectors
|
|
112
112
|
|
|
113
|
-
**metadata
|
|
113
|
+
**metadata** (`Record<string, any>[]`): Metadata for each vector
|
|
114
114
|
|
|
115
|
-
**ids
|
|
115
|
+
**ids** (`string[]`): Optional vector IDs (auto-generated if not provided)
|
|
116
116
|
|
|
117
|
-
### query()
|
|
117
|
+
### `query()`
|
|
118
118
|
|
|
119
119
|
Searches for nearest neighbors with optional metadata filtering.
|
|
120
120
|
|
|
121
|
-
**indexName
|
|
121
|
+
**indexName** (`string`): Name of the index to query
|
|
122
122
|
|
|
123
|
-
**queryVector
|
|
123
|
+
**queryVector** (`number[]`): Query vector to find similar vectors
|
|
124
124
|
|
|
125
|
-
**topK
|
|
125
|
+
**topK** (`number`): Number of results to return (Default: `10`)
|
|
126
126
|
|
|
127
|
-
**filter
|
|
127
|
+
**filter** (`S3VectorsFilter`): JSON-based metadata filter supporting \`$and\`, \`$or\`, \`$eq\`, \`$ne\`, \`$gt\`, \`$gte\`, \`$lt\`, \`$lte\`, \`$in\`, \`$nin\`, \`$exists\`.
|
|
128
128
|
|
|
129
|
-
**includeVector
|
|
129
|
+
**includeVector** (`boolean`): Whether to include vectors in the results (Default: `false`)
|
|
130
130
|
|
|
131
131
|
> **Note:** Results include `score = 1/(1 + distance)` so that higher is better while preserving the underlying distance ranking.
|
|
132
132
|
|
|
133
|
-
### describeIndex()
|
|
133
|
+
### `describeIndex()`
|
|
134
134
|
|
|
135
135
|
Returns information about the index.
|
|
136
136
|
|
|
137
|
-
**indexName
|
|
137
|
+
**indexName** (`string`): Index name to describe.
|
|
138
138
|
|
|
139
139
|
Returns:
|
|
140
140
|
|
|
@@ -146,45 +146,45 @@ interface IndexStats {
|
|
|
146
146
|
}
|
|
147
147
|
```
|
|
148
148
|
|
|
149
|
-
### deleteIndex()
|
|
149
|
+
### `deleteIndex()`
|
|
150
150
|
|
|
151
151
|
Deletes an index and its data.
|
|
152
152
|
|
|
153
|
-
**indexName
|
|
153
|
+
**indexName** (`string`): Index to delete.
|
|
154
154
|
|
|
155
|
-
### listIndexes()
|
|
155
|
+
### `listIndexes()`
|
|
156
156
|
|
|
157
157
|
Lists all indexes in the configured vector bucket.
|
|
158
158
|
|
|
159
159
|
Returns: `Promise<string[]>`
|
|
160
160
|
|
|
161
|
-
### updateVector()
|
|
161
|
+
### `updateVector()`
|
|
162
162
|
|
|
163
163
|
Updates a vector or metadata for a specific ID within an index.
|
|
164
164
|
|
|
165
|
-
**indexName
|
|
165
|
+
**indexName** (`string`): Index containing the vector.
|
|
166
166
|
|
|
167
|
-
**id
|
|
167
|
+
**id** (`string`): ID to update.
|
|
168
168
|
|
|
169
|
-
**update
|
|
169
|
+
**update** (`object`): Update data containing vector and/or metadata
|
|
170
170
|
|
|
171
|
-
**update.vector
|
|
171
|
+
**update.vector** (`number[]`): New vector data to update
|
|
172
172
|
|
|
173
|
-
**update.metadata
|
|
173
|
+
**update.metadata** (`Record<string, any>`): New metadata to update
|
|
174
174
|
|
|
175
|
-
### deleteVector()
|
|
175
|
+
### `deleteVector()`
|
|
176
176
|
|
|
177
177
|
Deletes a specific vector by ID.
|
|
178
178
|
|
|
179
|
-
**indexName
|
|
179
|
+
**indexName** (`string`): Index containing the vector.
|
|
180
180
|
|
|
181
|
-
**id
|
|
181
|
+
**id** (`string`): ID to delete.
|
|
182
182
|
|
|
183
|
-
### disconnect()
|
|
183
|
+
### `disconnect()`
|
|
184
184
|
|
|
185
185
|
Closes the underlying AWS SDK HTTP handler to free sockets.
|
|
186
186
|
|
|
187
|
-
## Response
|
|
187
|
+
## Response types
|
|
188
188
|
|
|
189
189
|
Query results are returned in this format:
|
|
190
190
|
|
|
@@ -197,14 +197,14 @@ interface QueryResult {
|
|
|
197
197
|
}
|
|
198
198
|
```
|
|
199
199
|
|
|
200
|
-
## Filter
|
|
200
|
+
## Filter syntax
|
|
201
201
|
|
|
202
202
|
S3 Vectors supports a strict subset of operators and value types. The Mastra filter translator:
|
|
203
203
|
|
|
204
204
|
- **Canonicalizes implicit AND**: `{a:1,b:2}` → `{ $and: [{a:1},{b:2}] }`.
|
|
205
205
|
- **Normalizes Date values** to epoch ms for numeric comparisons and array elements.
|
|
206
206
|
- **Disallows Date** in equality positions (`field: value` or `$eq/$ne`); equality values must be **string | number | boolean**.
|
|
207
|
-
- **Rejects** null/undefined for equality; **array equality**
|
|
207
|
+
- **Rejects** null/undefined for equality; **array equality** isn't supported (use `$in`/`$nin`).
|
|
208
208
|
- Only **`$and` / `$or`** are allowed as top-level logical operators.
|
|
209
209
|
- Logical operators must contain **field conditions** (not direct operators).
|
|
210
210
|
|
|
@@ -236,9 +236,9 @@ S3 Vectors supports a strict subset of operators and value types. The Mastra fil
|
|
|
236
236
|
{ timestamp: { $gt: new Date("2024-01-01T00:00:00Z") } }
|
|
237
237
|
```
|
|
238
238
|
|
|
239
|
-
> **Note:** If you set `nonFilterableMetadataKeys` at index creation, those keys are stored but **
|
|
239
|
+
> **Note:** If you set `nonFilterableMetadataKeys` at index creation, those keys are stored but **can't** be used in filters.
|
|
240
240
|
|
|
241
|
-
## Error
|
|
241
|
+
## Error handling
|
|
242
242
|
|
|
243
243
|
The store throws typed errors that can be caught:
|
|
244
244
|
|
|
@@ -256,7 +256,7 @@ try {
|
|
|
256
256
|
}
|
|
257
257
|
```
|
|
258
258
|
|
|
259
|
-
## Environment
|
|
259
|
+
## Environment variables
|
|
260
260
|
|
|
261
261
|
Typical environment variables when wiring your app:
|
|
262
262
|
|
|
@@ -264,9 +264,9 @@ Typical environment variables when wiring your app:
|
|
|
264
264
|
- `AWS_REGION`: AWS region for the S3 Vectors bucket.
|
|
265
265
|
- **AWS credentials**: via the standard AWS SDK provider chain (`AWS_ACCESS_KEY_ID`, `AWS_SECRET_ACCESS_KEY`, `AWS_PROFILE`, etc.).
|
|
266
266
|
|
|
267
|
-
## Best
|
|
267
|
+
## Best practices
|
|
268
268
|
|
|
269
|
-
- Choose the metric (`cosine` or `euclidean`) to match your embedding model; `dotproduct`
|
|
269
|
+
- Choose the metric (`cosine` or `euclidean`) to match your embedding model; `dotproduct` isn't supported.
|
|
270
270
|
- Keep **filterable** metadata small and structured (string/number/boolean). Store large text (e.g., `content`) as **non-filterable**.
|
|
271
271
|
- Use **dotted paths** for nested metadata and explicit `$and`/`$or` for complex logic.
|
|
272
272
|
- Avoid calling `describeIndex()` on hot paths—`count` is computed with paginated `ListVectors` (**O(n)**).
|
package/dist/index.cjs
CHANGED
|
@@ -363,13 +363,13 @@ var S3Vectors = class _S3Vectors extends vector.MastraVector {
|
|
|
363
363
|
const vectors = (out.vectors ?? []).filter((v) => !!v?.key);
|
|
364
364
|
let dataMap;
|
|
365
365
|
if (includeVector) {
|
|
366
|
-
const
|
|
367
|
-
if (
|
|
366
|
+
const keys = vectors.filter((v) => v.key).map((v) => v.key);
|
|
367
|
+
if (keys.length > 0) {
|
|
368
368
|
const got = await this.client.send(
|
|
369
369
|
new clientS3vectors.GetVectorsCommand({
|
|
370
370
|
...this.bucketParams(),
|
|
371
371
|
indexName,
|
|
372
|
-
keys
|
|
372
|
+
keys,
|
|
373
373
|
returnData: true,
|
|
374
374
|
returnMetadata: false
|
|
375
375
|
})
|
|
@@ -387,7 +387,7 @@ var S3Vectors = class _S3Vectors extends vector.MastraVector {
|
|
|
387
387
|
const md = v.metadata;
|
|
388
388
|
if (md !== void 0) result.metadata = md;
|
|
389
389
|
if (includeVector) {
|
|
390
|
-
const vec =
|
|
390
|
+
const vec = dataMap?.[id];
|
|
391
391
|
if (vec !== void 0) result.vector = vec;
|
|
392
392
|
}
|
|
393
393
|
return result;
|
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/vector/filter.ts","../src/vector/index.ts","../src/vector/prompt.ts"],"names":["BaseFilterTranslator","MastraVector","MastraError","createVectorErrorId","ErrorDomain","ErrorCategory","S3VectorsClient","error","CreateIndexCommand","uuidv4","PutVectorsCommand","QueryVectorsCommand","GetVectorsCommand","ListIndexesCommand","DeleteIndexCommand","DeleteVectorsCommand","GetIndexCommand","ListVectorsCommand"],"mappings":"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","file":"index.cjs","sourcesContent":["import { BaseFilterTranslator } from '@mastra/core/vector/filter';\nimport type {\n VectorFilter,\n LogicalOperatorValueMap,\n OperatorSupport,\n QueryOperator,\n OperatorValueMap,\n BlacklistedRootOperators,\n} from '@mastra/core/vector/filter';\n\n/**\n * S3 Vectors supports a strict subset of operators and value types.\n *\n * - logical: `$and`, `$or` (non-empty arrays)\n * - basic: `$eq`, `$ne` (string | number | boolean)\n * - numeric: `$gt`, `$gte`, `$lt`, `$lte` (number)\n * - array: `$in`, `$nin` (non-empty arrays of string | number | boolean)\n * - element: `$exists` (boolean)\n */\ntype S3VectorsOperatorValueMap = Pick<\n OperatorValueMap,\n '$eq' | '$ne' | '$gt' | '$gte' | '$lt' | '$lte' | '$in' | '$nin' | '$exists'\n>;\n\ntype S3VectorsLogicalOperatorValueMap = Pick<LogicalOperatorValueMap, '$and' | '$or'>;\n\ntype S3VectorsBlacklisted = BlacklistedRootOperators;\n\ntype S3VectorsFieldValue = string | number | boolean;\n\n/**\n * High-level filter type accepted by this translator.\n * @remarks\n * Field values are limited to string/number/boolean at equality positions.\n */\nexport type S3VectorsFilter = VectorFilter<\n keyof S3VectorsOperatorValueMap,\n S3VectorsOperatorValueMap,\n S3VectorsLogicalOperatorValueMap,\n S3VectorsBlacklisted,\n S3VectorsFieldValue\n>;\n\n/**\n * Translates a high-level filter into the S3 Vectors filter shape.\n *\n * @remarks\n * - Canonicalizes **implicit AND** (e.g. `{a:1,b:2}`) into explicit `{$and:[{a:1},{b:2}]}` in any\n * non-field context that lacks `$and/$or`.\n * - Normalizes `Date` values to epoch milliseconds where allowed (numeric comparisons and array elements).\n * - Disallows `Date` at equality positions (including implicit equality).\n * - Validates shapes using the base class after translation.\n */\nexport class S3VectorsFilterTranslator extends BaseFilterTranslator<S3VectorsFilter> {\n /** @inheritdoc */\n protected override getSupportedOperators(): OperatorSupport {\n return {\n logical: ['$and', '$or'],\n basic: ['$eq', '$ne'],\n numeric: ['$gt', '$gte', '$lt', '$lte'],\n array: ['$in', '$nin'],\n element: ['$exists'],\n };\n }\n\n /**\n * Translates and validates a filter.\n * @param filter - Input filter; may be `undefined`, `null`, or `{}` (all treated as empty).\n * @returns The translated filter (or the original value if empty).\n */\n translate(filter?: S3VectorsFilter): any {\n if (this.isEmpty(filter)) return filter;\n // Perform translation (including Date → number normalization) before base shape validation.\n const translated = this.translateNode(filter as any, false);\n this.validateFilter(translated as any);\n return translated;\n }\n\n /**\n * Recursively translates a node.\n * @param node - Current node to translate.\n * @param inFieldValue - When `true`, the node is the value of a field (i.e., equality context).\n * @remarks\n * - In a **field-value** context, only primitives or operator objects are allowed.\n * - In a **non-field** context (root / logical branches), operator keys are processed;\n * plain keys become field equalities and are validated.\n * - Implicit AND is canonicalized in non-field contexts when multiple non-logical keys exist.\n */\n private translateNode(node: any, inFieldValue = false): any {\n // Primitive or Date (normalize when in a field-equality context)\n if (this.isPrimitive(node) || node instanceof Date) {\n return inFieldValue ? this.validateAndNormalizePrimitive(node) : node;\n }\n\n // Arrays are not allowed as direct equality values\n if (Array.isArray(node)) {\n if (inFieldValue) {\n throw new Error('Array equality is not supported in S3 Vectors. Use $in / $nin operators.');\n }\n return node;\n }\n\n // Object\n const entries = Object.entries(node as Record<string, any>);\n\n if (inFieldValue) {\n if (entries.length === 0) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n const allOperatorKeys = entries.every(([k]) => this.isOperator(k));\n if (!allOperatorKeys) {\n // Disallow shapes like: { field: { a:1, b:2 } }\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n const opEntries = entries.map(([key, value]) => [key, this.translateOperatorValue(key as QueryOperator, value)]);\n return Object.fromEntries(opEntries);\n }\n\n // Root / filter context\n const translatedEntries = entries.map(([key, value]) => {\n if (this.isOperator(key)) {\n return [key, this.translateOperatorValue(key as QueryOperator, value)];\n }\n return [key, this.translateNode(value, true)];\n });\n const obj = Object.fromEntries(translatedEntries);\n\n // Canonicalize implicit AND → explicit $and (if no $and/$or present and multiple non-logical keys)\n const keys = Object.keys(obj);\n const hasLogical = keys.some(k => k === '$and' || k === '$or');\n if (!hasLogical) {\n const nonLogical = keys.filter(k => k !== '$and' && k !== '$or');\n if (nonLogical.length > 1) {\n return { $and: nonLogical.map(k => ({ [k]: obj[k] })) };\n }\n }\n\n return obj;\n }\n\n /**\n * Translates a single operator and validates its value.\n * @param operator - One of the supported query operators.\n * @param value - Operator value to normalize/validate.\n */\n private translateOperatorValue(operator: QueryOperator, value: any): any {\n // Logical operators\n if (operator === '$and' || operator === '$or') {\n if (!Array.isArray(value) || value.length === 0) {\n throw new Error(`Value for logical operator ${operator} must be a non-empty array`);\n }\n return value.map(item => this.translateNode(item));\n }\n\n // Equality / inequality (Date is not allowed)\n if (operator === '$eq' || operator === '$ne') {\n if (value instanceof Date) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n return this.toPrimitiveForS3(value, operator);\n }\n\n // Numeric comparisons: require number; allow Date by converting to epoch ms\n if (operator === '$gt' || operator === '$gte' || operator === '$lt' || operator === '$lte') {\n const n = this.toNumberForRange(value, operator);\n return n;\n }\n\n // Array operators: non-empty arrays of primitives (Date converted to number)\n if (operator === '$in' || operator === '$nin') {\n if (!Array.isArray(value) || value.length === 0) {\n throw new Error(`Value for array operator ${operator} must be a non-empty array`);\n }\n return value.map(v => this.toPrimitiveForS3(v, operator));\n }\n\n // Existence check\n if (operator === '$exists') {\n if (typeof value !== 'boolean') {\n throw new Error(`Value for $exists operator must be a boolean`);\n }\n return value;\n }\n\n throw new Error(`Unsupported operator: ${operator}`);\n }\n\n /**\n * Normalizes a value to an S3-accepted primitive.\n * @param value - String | Number | Boolean | Date.\n * @param operatorForMessage - Operator name used in error messages.\n * @returns The normalized primitive; `Date` becomes epoch milliseconds.\n * @throws If the value is not a supported primitive or is null/undefined.\n */\n private toPrimitiveForS3(value: any, operatorForMessage: string): string | number | boolean {\n if (value === null || value === undefined) {\n // Error message for equality matches tests\n if (operatorForMessage === 'equality') {\n throw new Error('S3 Vectors does not support null/undefined for equality');\n }\n throw new Error(`Value for ${operatorForMessage} must be string, number, or boolean`);\n }\n if (value instanceof Date) {\n return value.getTime();\n }\n const t = typeof value;\n if (t === 'string' || t === 'boolean') return value;\n if (t === 'number') return Object.is(value, -0) ? 0 : value;\n throw new Error(`Value for ${operatorForMessage} must be string, number, or boolean`);\n }\n\n /**\n * Ensures a numeric value for range operators; allows `Date` by converting to epoch ms.\n * @param value - Candidate value.\n * @param operatorForMessage - Operator name used in error messages.\n * @throws If the value is not a number (or a Date).\n */\n private toNumberForRange(value: any, operatorForMessage: string): number {\n if (value instanceof Date) return value.getTime();\n if (typeof value === 'number' && !Number.isNaN(value)) return Object.is(value, -0) ? 0 : value;\n throw new Error(`Value for ${operatorForMessage} must be a number`);\n }\n\n /**\n * Validates and normalizes a primitive used in field equality (implicit `$eq`).\n * @param value - Candidate equality value.\n * @throws If the value is a `Date` or not a supported primitive.\n */\n private validateAndNormalizePrimitive(value: any): S3VectorsFieldValue {\n if (value instanceof Date) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n return this.toPrimitiveForS3(value, 'equality') as S3VectorsFieldValue;\n }\n\n /**\n * Determines whether a filter is considered empty.\n * @param filter - Input filter.\n */\n protected override isEmpty(filter: any): boolean {\n return filter === undefined || filter === null || (typeof filter === 'object' && Object.keys(filter).length === 0);\n }\n}\n","import {\n S3VectorsClient,\n CreateIndexCommand,\n DeleteIndexCommand,\n ListIndexesCommand,\n GetIndexCommand,\n PutVectorsCommand,\n QueryVectorsCommand,\n GetVectorsCommand,\n DeleteVectorsCommand,\n ListVectorsCommand,\n} from '@aws-sdk/client-s3vectors';\nimport type { S3VectorsClientConfig } from '@aws-sdk/client-s3vectors';\nimport { MastraError, ErrorDomain, ErrorCategory } from '@mastra/core/error';\nimport { createVectorErrorId } from '@mastra/core/storage';\nimport { MastraVector } from '@mastra/core/vector';\nimport type {\n QueryResult,\n IndexStats,\n CreateIndexParams,\n UpsertVectorParams,\n DeleteVectorsParams,\n QueryVectorParams,\n DescribeIndexParams,\n DeleteIndexParams,\n DeleteVectorParams,\n UpdateVectorParams,\n} from '@mastra/core/vector';\nimport { v4 as uuidv4 } from 'uuid';\nimport { S3VectorsFilterTranslator } from './filter';\nimport type { S3VectorsFilter } from './filter';\n\n/**\n * Options for the S3Vectors store.\n * @property vectorBucketName - Target S3 Vectors bucket name.\n * @property clientConfig - AWS SDK client options (e.g., region/credentials).\n * @property nonFilterableMetadataKeys - Metadata keys that must not be filterable (forwarded to S3 Vectors).\n */\nexport interface S3VectorsOptions {\n vectorBucketName: string;\n clientConfig?: S3VectorsClientConfig;\n nonFilterableMetadataKeys?: string[];\n}\n\ntype S3DistanceMetric = 'cosine' | 'euclidean';\ntype MastraMetric = NonNullable<CreateIndexParams['metric']>;\ntype SupportedMastraMetric = Exclude<MastraMetric, 'dotproduct'>;\n\n/**\n * Vector store backed by Amazon S3 Vectors.\n *\n * @remarks\n * - Supports `cosine` and `euclidean` distance metrics.\n * - Filters must use explicit logical operators (`$and` / `$or`). The attached translator\n * canonicalizes implicit AND (e.g., `{a:1,b:2}` → `{ $and: [{a:1},{b:2}] }`) where permitted by spec.\n * - Methods wrap AWS errors in `MastraError` with domain/category metadata.\n */\nexport class S3Vectors extends MastraVector<S3VectorsFilter> {\n private readonly client: S3VectorsClient;\n private readonly vectorBucketName: string;\n private readonly nonFilterableMetadataKeys?: string[];\n private readonly filterTranslator = new S3VectorsFilterTranslator();\n\n private static readonly METRIC_MAP: Record<SupportedMastraMetric, S3DistanceMetric> = {\n cosine: 'cosine',\n euclidean: 'euclidean',\n } as const;\n\n constructor(opts: S3VectorsOptions & { id: string }) {\n super({ id: opts.id });\n if (!opts?.vectorBucketName) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'INITIALIZATION', 'MISSING_BUCKET_NAME'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n },\n new Error('vectorBucketName is required'),\n );\n }\n this.vectorBucketName = opts.vectorBucketName;\n this.nonFilterableMetadataKeys = opts.nonFilterableMetadataKeys;\n this.client = new S3VectorsClient({ ...(opts.clientConfig ?? {}) });\n }\n\n /**\n * No-op to satisfy the base interface.\n *\n * @remarks The AWS SDK manages HTTP per request; no persistent connection is needed.\n */\n async connect(): Promise<void> {}\n\n /**\n * Closes the underlying AWS SDK HTTP handler to free sockets.\n */\n async disconnect(): Promise<void> {\n try {\n this.client.destroy();\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DISCONNECT', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n },\n error,\n );\n }\n }\n\n /**\n * Creates an index or validates an existing one.\n *\n * @param params.indexName - Logical index name; normalized internally.\n * @param params.dimension - Vector dimension (must be a positive integer).\n * @param params.metric - Distance metric (`cosine` | `euclidean`). Defaults to `cosine`.\n * @throws {MastraError} If arguments are invalid or AWS returns an error.\n * @remarks\n * On `ConflictException`, we verify the existing index schema via the parent implementation\n * and return if it matches.\n */\n async createIndex({ indexName, dimension, metric = 'cosine' }: CreateIndexParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n\n let s3Metric: S3DistanceMetric;\n try {\n assertPositiveInteger(dimension, 'dimension');\n s3Metric = S3Vectors.toS3Metric(metric);\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'CREATE_INDEX', 'INVALID_ARGS'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n details: { indexName, dimension, metric },\n },\n error,\n );\n }\n\n try {\n const input: any = {\n ...this.bucketParams(),\n indexName,\n dataType: 'float32',\n dimension,\n distanceMetric: s3Metric,\n };\n if (this.nonFilterableMetadataKeys?.length) {\n input.metadataConfiguration = { nonFilterableMetadataKeys: this.nonFilterableMetadataKeys };\n }\n\n await this.client.send(new CreateIndexCommand(input));\n } catch (error: any) {\n if (error?.name === 'ConflictException') {\n await this.validateExistingIndex(indexName, dimension, metric);\n return;\n }\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'CREATE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName, dimension, metric },\n },\n error,\n );\n }\n }\n\n /**\n * Upserts vectors in bulk.\n *\n * @param params.indexName - Index to write to.\n * @param params.vectors - Array of vectors; each must match the index dimension.\n * @param params.metadata - Optional metadata per vector; `Date` values are normalized to epoch ms.\n * @param params.ids - Optional explicit IDs; if omitted, UUIDs are generated.\n * @returns Array of IDs used for the upsert (explicit or generated).\n * @throws {MastraError} If validation fails or AWS returns an error.\n */\n async upsert({ indexName, vectors, metadata, ids }: UpsertVectorParams): Promise<string[]> {\n indexName = normalizeIndexName(indexName);\n try {\n const { dimension } = await this.getIndexInfo(indexName);\n validateVectorDimensions(vectors, dimension);\n\n const generatedIds = ids ?? vectors.map(() => uuidv4());\n\n const putInput = {\n ...this.bucketParams(),\n indexName,\n vectors: vectors.map((vec, i) => ({\n key: generatedIds[i],\n data: { float32: vec },\n metadata: normalizeMetadata(metadata?.[i]),\n })),\n };\n\n await this.client.send(new PutVectorsCommand(putInput));\n return generatedIds;\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'UPSERT', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Queries nearest neighbors.\n *\n * @param params.indexName - Target index.\n * @param params.queryVector - Query vector (non-empty float32 array).\n * @param params.topK - Number of neighbors to return (positive integer). Defaults to 10.\n * @param params.filter - Metadata filter using explicit `$and`/`$or` (translator canonicalizes implicit AND).\n * @param params.includeVector - If `true`, fetches missing vector data in a second call.\n * @returns Results sorted by `score` descending.\n * @throws {MastraError} If validation fails or AWS returns an error.\n * @remarks\n * `score = 1/(1+distance)` (monotonic transform), so ranking matches the underlying distance.\n */\n async query({\n indexName,\n queryVector,\n topK = 10,\n filter,\n includeVector = false,\n }: QueryVectorParams<S3VectorsFilter>): Promise<QueryResult[]> {\n indexName = normalizeIndexName(indexName);\n\n if (!queryVector) {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'QUERY', 'MISSING_VECTOR'),\n text: 'queryVector is required for S3 Vectors queries. Metadata-only queries are not supported by this vector store.',\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n details: { indexName },\n });\n }\n\n try {\n if (!Array.isArray(queryVector) || queryVector.length === 0) {\n throw new Error('queryVector must be a non-empty float32 array');\n }\n assertPositiveInteger(topK, 'topK');\n\n const translated = this.transformFilter(filter);\n\n const out = await this.client.send(\n new QueryVectorsCommand({\n ...this.bucketParams(),\n indexName,\n topK,\n queryVector: { float32: queryVector },\n filter: translated && Object.keys(translated).length > 0 ? (translated as any) : undefined,\n returnMetadata: true,\n returnDistance: true,\n }),\n );\n\n const vectors = (out.vectors ?? []).filter(v => !!v?.key);\n\n // If includeVector is requested and some results lack data, fetch only the missing ones.\n let dataMap: Record<string, number[] | undefined> | undefined;\n if (includeVector) {\n const missingKeys = vectors.filter(v => !v.data?.float32 && v.key).map(v => v.key!) as string[];\n\n if (missingKeys.length > 0) {\n const got = await this.client.send(\n new GetVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: missingKeys,\n returnData: true,\n returnMetadata: false,\n }),\n );\n dataMap = {};\n for (const g of got.vectors ?? []) {\n if (g.key) dataMap[g.key] = g.data?.float32 as number[] | undefined;\n }\n }\n }\n\n return vectors.map(v => {\n const id = v.key!;\n const score = S3Vectors.distanceToScore(v.distance ?? 0);\n\n const result: QueryResult = { id, score };\n\n const md = v.metadata as Record<string, unknown> | undefined;\n if (md !== undefined) result.metadata = md;\n\n if (includeVector) {\n const vec = (v.data?.float32 as number[] | undefined) ?? dataMap?.[id];\n if (vec !== undefined) result.vector = vec;\n }\n\n return result;\n });\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'QUERY', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Lists indexes within the configured bucket.\n *\n * @returns Array of index names.\n * @throws {MastraError} On AWS errors.\n */\n async listIndexes(): Promise<string[]> {\n try {\n const names: string[] = [];\n let nextToken: string | undefined;\n\n do {\n const out = await this.client.send(\n new ListIndexesCommand({\n ...this.bucketParams(),\n nextToken,\n } as any),\n );\n for (const idx of out.indexes ?? []) {\n if (idx.indexName) names.push(idx.indexName);\n }\n nextToken = out.nextToken;\n } while (nextToken);\n\n return names;\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'LIST_INDEXES', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n },\n error,\n );\n }\n }\n\n /**\n * Returns index attributes.\n *\n * @param params.indexName - Index name.\n * @returns Object containing `dimension`, `metric`, and `count`.\n * @throws {MastraError} On AWS errors.\n * @remarks\n * `count` is computed via `ListVectors` pagination and may be costly (O(n)).\n */\n async describeIndex({ indexName }: DescribeIndexParams): Promise<IndexStats> {\n indexName = normalizeIndexName(indexName);\n try {\n const { dimension, metric } = await this.getIndexInfo(indexName);\n const count = await this.countVectors(indexName);\n return { dimension, metric, count };\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DESCRIBE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Deletes an index.\n *\n * @param params.indexName - Index name.\n * @throws {MastraError} On AWS errors.\n */\n async deleteIndex({ indexName }: DeleteIndexParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n try {\n await this.client.send(new DeleteIndexCommand({ ...this.bucketParams(), indexName } as any));\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DELETE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Updates (replaces) a vector and/or its metadata by ID.\n *\n * @param params.indexName - Target index.\n * @param params.id - Vector ID.\n * @param params.update.vector - New vector; if omitted, the existing vector is reused.\n * @param params.update.metadata - New metadata, merged with current metadata.\n * @throws {MastraError} If the vector does not exist and `update.vector` is omitted, or on AWS error.\n * @remarks\n * S3 Vectors `PutVectors` is replace-all; we `Get` the current item, merge, then `Put`.\n */\n async updateVector({ indexName, id, update }: UpdateVectorParams): Promise<void> {\n if (!id) {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'UPDATE_VECTOR', 'INVALID_ARGS'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n text: 'id is required for S3Vectors updateVector',\n details: { indexName },\n });\n }\n\n indexName = normalizeIndexName(indexName);\n try {\n if (!update.vector && !update.metadata) {\n throw new Error('No updates provided');\n }\n\n const got = await this.client.send(\n new GetVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: [id],\n returnData: true,\n returnMetadata: true,\n }),\n );\n const current = (got.vectors ?? [])[0];\n\n const newVector: number[] | undefined = update.vector ?? (current?.data?.float32 as number[] | undefined);\n if (!newVector) {\n throw new Error(`Vector \"${id}\" not found. Provide update.vector to create it.`);\n }\n\n const newMetadata =\n update.metadata !== undefined\n ? normalizeMetadata(update.metadata)\n : ((current?.metadata as Record<string, any>) ?? {});\n\n await this.client.send(\n new PutVectorsCommand({\n ...this.bucketParams(),\n indexName,\n vectors: [{ key: id, data: { float32: newVector }, metadata: newMetadata }],\n }),\n );\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'UPDATE_VECTOR', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: {\n indexName,\n ...(id && { id }),\n },\n },\n error,\n );\n }\n }\n\n /**\n * Deletes a vector by ID.\n *\n * @param params.indexName - Target index.\n * @param params.id - Vector ID to delete.\n * @throws {MastraError} On AWS errors.\n */\n async deleteVector({ indexName, id }: DeleteVectorParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n try {\n await this.client.send(\n new DeleteVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: [id],\n }),\n );\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DELETE_VECTOR', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: {\n indexName,\n ...(id && { id }),\n },\n },\n error,\n );\n }\n }\n\n async deleteVectors({ indexName, filter, ids }: DeleteVectorsParams): Promise<void> {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'DELETE_VECTORS', 'NOT_SUPPORTED'),\n text: 'deleteVectors is not yet implemented for S3Vectors vector store',\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.SYSTEM,\n details: {\n indexName,\n ...(filter && { filter: JSON.stringify(filter) }),\n ...(ids && { idsCount: ids.length }),\n },\n });\n }\n\n // -------- internal helpers --------\n\n /**\n * Returns shared bucket parameters for AWS SDK calls.\n * @internal\n */\n private bucketParams(): { vectorBucketName: string } {\n return { vectorBucketName: this.vectorBucketName };\n }\n\n /**\n * Retrieves index dimension/metric via `GetIndex`.\n * @internal\n * @throws {Error} If the index does not exist.\n * @returns `{ dimension, metric }`, where `metric` includes `'dotproduct'` to satisfy Mastra types (S3 never returns it).\n */\n private async getIndexInfo(\n indexName: string,\n ): Promise<{ dimension: number; metric: 'cosine' | 'euclidean' | 'dotproduct' }> {\n const out = await this.client.send(new GetIndexCommand({ ...this.bucketParams(), indexName } as any));\n const idx = out.index;\n if (!idx) throw new Error(`Index \"${indexName}\" not found`);\n const metric = (idx.distanceMetric as S3DistanceMetric) ?? 'cosine';\n return {\n dimension: idx.dimension ?? 0,\n metric,\n };\n }\n\n /**\n * Pages through `ListVectors` and counts total items.\n * @internal\n * @remarks O(n). Avoid calling on hot paths.\n */\n private async countVectors(indexName: string): Promise<number> {\n let total = 0;\n let nextToken: string | undefined;\n\n do {\n const out = await this.client.send(\n new ListVectorsCommand({\n ...this.bucketParams(),\n indexName,\n maxResults: 1000,\n nextToken,\n returnData: false,\n returnMetadata: false,\n }),\n );\n total += (out.vectors ?? []).length;\n nextToken = out.nextToken;\n } while (nextToken);\n\n return total;\n }\n\n /**\n * Translates a high-level filter to the S3 Vectors filter shape.\n * @internal\n * @remarks Implicit AND is canonicalized by the translator where permitted by spec.\n */\n private transformFilter(filter?: S3VectorsFilter): any {\n if (!filter) return undefined;\n return this.filterTranslator.translate(filter);\n }\n\n /**\n * Converts a Mastra metric to an S3 metric.\n * @internal\n * @throws {Error} If the metric is not supported by S3 Vectors.\n */\n private static toS3Metric(metric: MastraMetric): S3DistanceMetric {\n const m = S3Vectors.METRIC_MAP[metric as SupportedMastraMetric];\n if (!m) {\n throw new Error(`Invalid metric: \"${metric}\". S3 Vectors supports only: cosine, euclidean`);\n }\n return m;\n }\n\n /**\n * Monotonic transform from distance (smaller is better) to score (larger is better).\n * @returns Number in (0, 1], preserving ranking.\n */\n private static distanceToScore(distance: number): number {\n return 1 / (1 + distance);\n }\n}\n\n// --- module-private utilities (not exported) ---\n\n/**\n * Ensures a value is a positive integer.\n * @throws {Error} If the value is not a positive integer.\n * @internal\n */\nfunction assertPositiveInteger(value: number, name: string): void {\n if (!Number.isInteger(value) || value <= 0) {\n throw new Error(`${name} must be a positive integer`);\n }\n}\n\n/**\n * Validates that all vectors match the required dimension.\n * @throws {Error} If any vector length differs from `dimension`.\n * @internal\n */\nfunction validateVectorDimensions(vectors: number[][], dimension: number): void {\n if (!Array.isArray(vectors) || vectors.length === 0) {\n throw new Error('No vectors provided for validation');\n }\n for (let i = 0; i < vectors.length; i++) {\n const len = vectors[i]?.length;\n if (len !== dimension) {\n throw new Error(`Vector at index ${i} has invalid dimension ${len}. Expected ${dimension} dimensions.`);\n }\n }\n}\n\n/**\n * Normalizes metadata values for S3 Vectors: `Date` → epoch ms.\n * @internal\n */\nfunction normalizeMetadata(meta: Record<string, any> | undefined): Record<string, any> {\n if (!meta) return {};\n const out: Record<string, any> = {};\n for (const [k, v] of Object.entries(meta)) {\n out[k] = v instanceof Date ? v.getTime() : v;\n }\n return out;\n}\n\n/**\n * Normalizes an index name to this store's canonical form (underscore → hyphen, lowercase).\n * @internal\n * @throws {TypeError} If the provided name is not a string.\n */\nfunction normalizeIndexName(str: string) {\n if (typeof str !== 'string') {\n throw new TypeError('Index name must be a string');\n }\n return str.replace(/_/g, '-').toLowerCase();\n}\n","/**\n * Vector store specific prompt that details supported operators and examples.\n * This prompt helps users construct valid filters for Amazon S3 Vectors.\n */\nexport const S3VECTORS_PROMPT = `When querying Amazon S3 Vectors, you can ONLY use the operators listed below. Any other operators will be rejected.\nImportant: Don't explain how to construct the filter - use the specified operators and fields to search the content and return relevant results.\nIf a user tries to give an explicit operator that is not supported, reject the filter entirely and let them know that the operator is not supported.\n\nBasic Comparison Operators:\n- $eq: Exact match (default when using field: value)\n Example: { \"category\": \"electronics\" }\n- $ne: Not equal\n Example: { \"category\": { \"$ne\": \"electronics\" } }\n- $gt: Greater than\n Example: { \"price\": { \"$gt\": 100 } }\n- $gte: Greater than or equal\n Example: { \"price\": { \"$gte\": 100 } }\n- $lt: Less than\n Example: { \"price\": { \"$lt\": 100 } }\n- $lte: Less than or equal\n Example: { \"price\": { \"$lte\": 100 } }\n\nArray Operators (non-empty arrays of string | number | boolean):\n- $in: Match any value in array\n Example: { \"category\": { \"$in\": [\"electronics\", \"books\"] } }\n- $nin: Does not match any value in array\n Example: { \"category\": { \"$nin\": [\"electronics\", \"books\"] } }\n\nLogical Operators:\n- $and: Logical AND (can be implicit or explicit)\n Implicit Example: { \"price\": { \"$gt\": 100 }, \"category\": \"electronics\" }\n Explicit Example: { \"$and\": [{ \"price\": { \"$gt\": 100 } }, { \"category\": \"electronics\" }] }\n- $or: Logical OR\n Example: { \"$or\": [{ \"price\": { \"$lt\": 50 } }, { \"category\": \"books\" }] }\n\nElement Operators:\n- $exists: Check if field exists\n Example: { \"rating\": { \"$exists\": true } }\n\nUnsupported / Disallowed Operators (REJECT if present):\n- $not, $nor, $regex, $all, $elemMatch, $size, $text (and any operator not listed as supported)\n\nRestrictions:\n- Only logical operators ($and, $or) can be used at the top level\n- Empty arrays for $and / $or / $in / $nin are NOT allowed\n- Nested fields are supported using dot notation\n- Multiple conditions on the same field are supported\n- At least one key-value pair is required in filter object\n- Empty objects and undefined values are treated as no filter\n- Invalid types in comparison operators will throw errors\n- All non-logical operators must be used within a field condition\n Valid: { \"field\": { \"$gt\": 100 } }\n Valid: { \"$and\": [...] }\n Invalid: { \"$gt\": 100 }\n- Logical operators must contain field conditions, not direct operators\n Valid: { \"$and\": [{ \"field\": { \"$gt\": 100 } }] }\n Invalid: { \"$and\": [{ \"$gt\": 100 }] }\n- Logical operators ($and, $or):\n - Can only be used at top level or nested within other logical operators\n - Can not be used on a field level, or be nested inside a field\n - Can not be used inside an operator\n - Valid: { \"$and\": [{ \"field\": { \"$gt\": 100 } }] }\n - Valid: { \"$or\": [{ \"$and\": [{ \"field\": { \"$gt\": 100 } }] }] }\n - Invalid: { \"field\": { \"$and\": [{ \"$gt\": 100 }] } }\n - Invalid: { \"field\": { \"$or\": [{ \"$gt\": 100 }] } }\n - Invalid: { \"field\": { \"$gt\": { \"$and\": [{...}] } } }\n- Equality values must be string, number, or boolean (arrays and objects are not allowed for equality)\n- Filters operate only on filterable metadata keys; using a non-filterable key will fail\n- Filterable metadata values are primitives (string/number/boolean) or arrays of primitives; large/long-text fields should be non-filterable and are not usable in filters\n\nExample Complex Query:\n{\n \"$and\": [\n { \"category\": { \"$in\": [\"electronics\", \"computers\"] } },\n { \"price\": { \"$gte\": 100, \"$lte\": 1000 } },\n { \"$or\": [\n { \"stock\": { \"$gt\": 0 } },\n { \"preorder\": true }\n ] }\n ]\n}`;\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/vector/filter.ts","../src/vector/index.ts","../src/vector/prompt.ts"],"names":["BaseFilterTranslator","MastraVector","MastraError","createVectorErrorId","ErrorDomain","ErrorCategory","S3VectorsClient","error","CreateIndexCommand","uuidv4","PutVectorsCommand","QueryVectorsCommand","GetVectorsCommand","ListIndexesCommand","DeleteIndexCommand","DeleteVectorsCommand","GetIndexCommand","ListVectorsCommand"],"mappings":"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","file":"index.cjs","sourcesContent":["import { BaseFilterTranslator } from '@mastra/core/vector/filter';\nimport type {\n VectorFilter,\n LogicalOperatorValueMap,\n OperatorSupport,\n QueryOperator,\n OperatorValueMap,\n BlacklistedRootOperators,\n} from '@mastra/core/vector/filter';\n\n/**\n * S3 Vectors supports a strict subset of operators and value types.\n *\n * - logical: `$and`, `$or` (non-empty arrays)\n * - basic: `$eq`, `$ne` (string | number | boolean)\n * - numeric: `$gt`, `$gte`, `$lt`, `$lte` (number)\n * - array: `$in`, `$nin` (non-empty arrays of string | number | boolean)\n * - element: `$exists` (boolean)\n */\ntype S3VectorsOperatorValueMap = Pick<\n OperatorValueMap,\n '$eq' | '$ne' | '$gt' | '$gte' | '$lt' | '$lte' | '$in' | '$nin' | '$exists'\n>;\n\ntype S3VectorsLogicalOperatorValueMap = Pick<LogicalOperatorValueMap, '$and' | '$or'>;\n\ntype S3VectorsBlacklisted = BlacklistedRootOperators;\n\ntype S3VectorsFieldValue = string | number | boolean;\n\n/**\n * High-level filter type accepted by this translator.\n * @remarks\n * Field values are limited to string/number/boolean at equality positions.\n */\nexport type S3VectorsFilter = VectorFilter<\n keyof S3VectorsOperatorValueMap,\n S3VectorsOperatorValueMap,\n S3VectorsLogicalOperatorValueMap,\n S3VectorsBlacklisted,\n S3VectorsFieldValue\n>;\n\n/**\n * Translates a high-level filter into the S3 Vectors filter shape.\n *\n * @remarks\n * - Canonicalizes **implicit AND** (e.g. `{a:1,b:2}`) into explicit `{$and:[{a:1},{b:2}]}` in any\n * non-field context that lacks `$and/$or`.\n * - Normalizes `Date` values to epoch milliseconds where allowed (numeric comparisons and array elements).\n * - Disallows `Date` at equality positions (including implicit equality).\n * - Validates shapes using the base class after translation.\n */\nexport class S3VectorsFilterTranslator extends BaseFilterTranslator<S3VectorsFilter> {\n /** @inheritdoc */\n protected override getSupportedOperators(): OperatorSupport {\n return {\n logical: ['$and', '$or'],\n basic: ['$eq', '$ne'],\n numeric: ['$gt', '$gte', '$lt', '$lte'],\n array: ['$in', '$nin'],\n element: ['$exists'],\n };\n }\n\n /**\n * Translates and validates a filter.\n * @param filter - Input filter; may be `undefined`, `null`, or `{}` (all treated as empty).\n * @returns The translated filter (or the original value if empty).\n */\n translate(filter?: S3VectorsFilter): any {\n if (this.isEmpty(filter)) return filter;\n // Perform translation (including Date → number normalization) before base shape validation.\n const translated = this.translateNode(filter as any, false);\n this.validateFilter(translated as any);\n return translated;\n }\n\n /**\n * Recursively translates a node.\n * @param node - Current node to translate.\n * @param inFieldValue - When `true`, the node is the value of a field (i.e., equality context).\n * @remarks\n * - In a **field-value** context, only primitives or operator objects are allowed.\n * - In a **non-field** context (root / logical branches), operator keys are processed;\n * plain keys become field equalities and are validated.\n * - Implicit AND is canonicalized in non-field contexts when multiple non-logical keys exist.\n */\n private translateNode(node: any, inFieldValue = false): any {\n // Primitive or Date (normalize when in a field-equality context)\n if (this.isPrimitive(node) || node instanceof Date) {\n return inFieldValue ? this.validateAndNormalizePrimitive(node) : node;\n }\n\n // Arrays are not allowed as direct equality values\n if (Array.isArray(node)) {\n if (inFieldValue) {\n throw new Error('Array equality is not supported in S3 Vectors. Use $in / $nin operators.');\n }\n return node;\n }\n\n // Object\n const entries = Object.entries(node as Record<string, any>);\n\n if (inFieldValue) {\n if (entries.length === 0) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n const allOperatorKeys = entries.every(([k]) => this.isOperator(k));\n if (!allOperatorKeys) {\n // Disallow shapes like: { field: { a:1, b:2 } }\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n const opEntries = entries.map(([key, value]) => [key, this.translateOperatorValue(key as QueryOperator, value)]);\n return Object.fromEntries(opEntries);\n }\n\n // Root / filter context\n const translatedEntries = entries.map(([key, value]) => {\n if (this.isOperator(key)) {\n return [key, this.translateOperatorValue(key as QueryOperator, value)];\n }\n return [key, this.translateNode(value, true)];\n });\n const obj = Object.fromEntries(translatedEntries);\n\n // Canonicalize implicit AND → explicit $and (if no $and/$or present and multiple non-logical keys)\n const keys = Object.keys(obj);\n const hasLogical = keys.some(k => k === '$and' || k === '$or');\n if (!hasLogical) {\n const nonLogical = keys.filter(k => k !== '$and' && k !== '$or');\n if (nonLogical.length > 1) {\n return { $and: nonLogical.map(k => ({ [k]: obj[k] })) };\n }\n }\n\n return obj;\n }\n\n /**\n * Translates a single operator and validates its value.\n * @param operator - One of the supported query operators.\n * @param value - Operator value to normalize/validate.\n */\n private translateOperatorValue(operator: QueryOperator, value: any): any {\n // Logical operators\n if (operator === '$and' || operator === '$or') {\n if (!Array.isArray(value) || value.length === 0) {\n throw new Error(`Value for logical operator ${operator} must be a non-empty array`);\n }\n return value.map(item => this.translateNode(item));\n }\n\n // Equality / inequality (Date is not allowed)\n if (operator === '$eq' || operator === '$ne') {\n if (value instanceof Date) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n return this.toPrimitiveForS3(value, operator);\n }\n\n // Numeric comparisons: require number; allow Date by converting to epoch ms\n if (operator === '$gt' || operator === '$gte' || operator === '$lt' || operator === '$lte') {\n const n = this.toNumberForRange(value, operator);\n return n;\n }\n\n // Array operators: non-empty arrays of primitives (Date converted to number)\n if (operator === '$in' || operator === '$nin') {\n if (!Array.isArray(value) || value.length === 0) {\n throw new Error(`Value for array operator ${operator} must be a non-empty array`);\n }\n return value.map(v => this.toPrimitiveForS3(v, operator));\n }\n\n // Existence check\n if (operator === '$exists') {\n if (typeof value !== 'boolean') {\n throw new Error(`Value for $exists operator must be a boolean`);\n }\n return value;\n }\n\n throw new Error(`Unsupported operator: ${operator}`);\n }\n\n /**\n * Normalizes a value to an S3-accepted primitive.\n * @param value - String | Number | Boolean | Date.\n * @param operatorForMessage - Operator name used in error messages.\n * @returns The normalized primitive; `Date` becomes epoch milliseconds.\n * @throws If the value is not a supported primitive or is null/undefined.\n */\n private toPrimitiveForS3(value: any, operatorForMessage: string): string | number | boolean {\n if (value === null || value === undefined) {\n // Error message for equality matches tests\n if (operatorForMessage === 'equality') {\n throw new Error('S3 Vectors does not support null/undefined for equality');\n }\n throw new Error(`Value for ${operatorForMessage} must be string, number, or boolean`);\n }\n if (value instanceof Date) {\n return value.getTime();\n }\n const t = typeof value;\n if (t === 'string' || t === 'boolean') return value;\n if (t === 'number') return Object.is(value, -0) ? 0 : value;\n throw new Error(`Value for ${operatorForMessage} must be string, number, or boolean`);\n }\n\n /**\n * Ensures a numeric value for range operators; allows `Date` by converting to epoch ms.\n * @param value - Candidate value.\n * @param operatorForMessage - Operator name used in error messages.\n * @throws If the value is not a number (or a Date).\n */\n private toNumberForRange(value: any, operatorForMessage: string): number {\n if (value instanceof Date) return value.getTime();\n if (typeof value === 'number' && !Number.isNaN(value)) return Object.is(value, -0) ? 0 : value;\n throw new Error(`Value for ${operatorForMessage} must be a number`);\n }\n\n /**\n * Validates and normalizes a primitive used in field equality (implicit `$eq`).\n * @param value - Candidate equality value.\n * @throws If the value is a `Date` or not a supported primitive.\n */\n private validateAndNormalizePrimitive(value: any): S3VectorsFieldValue {\n if (value instanceof Date) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n return this.toPrimitiveForS3(value, 'equality') as S3VectorsFieldValue;\n }\n\n /**\n * Determines whether a filter is considered empty.\n * @param filter - Input filter.\n */\n protected override isEmpty(filter: any): boolean {\n return filter === undefined || filter === null || (typeof filter === 'object' && Object.keys(filter).length === 0);\n }\n}\n","import {\n S3VectorsClient,\n CreateIndexCommand,\n DeleteIndexCommand,\n ListIndexesCommand,\n GetIndexCommand,\n PutVectorsCommand,\n QueryVectorsCommand,\n GetVectorsCommand,\n DeleteVectorsCommand,\n ListVectorsCommand,\n} from '@aws-sdk/client-s3vectors';\nimport type { S3VectorsClientConfig } from '@aws-sdk/client-s3vectors';\nimport { MastraError, ErrorDomain, ErrorCategory } from '@mastra/core/error';\nimport { createVectorErrorId } from '@mastra/core/storage';\nimport { MastraVector } from '@mastra/core/vector';\nimport type {\n QueryResult,\n IndexStats,\n CreateIndexParams,\n UpsertVectorParams,\n DeleteVectorsParams,\n QueryVectorParams,\n DescribeIndexParams,\n DeleteIndexParams,\n DeleteVectorParams,\n UpdateVectorParams,\n} from '@mastra/core/vector';\nimport { v4 as uuidv4 } from 'uuid';\nimport { S3VectorsFilterTranslator } from './filter';\nimport type { S3VectorsFilter } from './filter';\n\n/**\n * Options for the S3Vectors store.\n * @property vectorBucketName - Target S3 Vectors bucket name.\n * @property clientConfig - AWS SDK client options (e.g., region/credentials).\n * @property nonFilterableMetadataKeys - Metadata keys that must not be filterable (forwarded to S3 Vectors).\n */\nexport interface S3VectorsOptions {\n vectorBucketName: string;\n clientConfig?: S3VectorsClientConfig;\n nonFilterableMetadataKeys?: string[];\n}\n\ntype S3DistanceMetric = 'cosine' | 'euclidean';\ntype MastraMetric = NonNullable<CreateIndexParams['metric']>;\ntype SupportedMastraMetric = Exclude<MastraMetric, 'dotproduct'>;\n\n/**\n * Vector store backed by Amazon S3 Vectors.\n *\n * @remarks\n * - Supports `cosine` and `euclidean` distance metrics.\n * - Filters must use explicit logical operators (`$and` / `$or`). The attached translator\n * canonicalizes implicit AND (e.g., `{a:1,b:2}` → `{ $and: [{a:1},{b:2}] }`) where permitted by spec.\n * - Methods wrap AWS errors in `MastraError` with domain/category metadata.\n */\nexport class S3Vectors extends MastraVector<S3VectorsFilter> {\n private readonly client: S3VectorsClient;\n private readonly vectorBucketName: string;\n private readonly nonFilterableMetadataKeys?: string[];\n private readonly filterTranslator = new S3VectorsFilterTranslator();\n\n private static readonly METRIC_MAP: Record<SupportedMastraMetric, S3DistanceMetric> = {\n cosine: 'cosine',\n euclidean: 'euclidean',\n } as const;\n\n constructor(opts: S3VectorsOptions & { id: string }) {\n super({ id: opts.id });\n if (!opts?.vectorBucketName) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'INITIALIZATION', 'MISSING_BUCKET_NAME'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n },\n new Error('vectorBucketName is required'),\n );\n }\n this.vectorBucketName = opts.vectorBucketName;\n this.nonFilterableMetadataKeys = opts.nonFilterableMetadataKeys;\n this.client = new S3VectorsClient({ ...(opts.clientConfig ?? {}) });\n }\n\n /**\n * No-op to satisfy the base interface.\n *\n * @remarks The AWS SDK manages HTTP per request; no persistent connection is needed.\n */\n async connect(): Promise<void> {}\n\n /**\n * Closes the underlying AWS SDK HTTP handler to free sockets.\n */\n async disconnect(): Promise<void> {\n try {\n this.client.destroy();\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DISCONNECT', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n },\n error,\n );\n }\n }\n\n /**\n * Creates an index or validates an existing one.\n *\n * @param params.indexName - Logical index name; normalized internally.\n * @param params.dimension - Vector dimension (must be a positive integer).\n * @param params.metric - Distance metric (`cosine` | `euclidean`). Defaults to `cosine`.\n * @throws {MastraError} If arguments are invalid or AWS returns an error.\n * @remarks\n * On `ConflictException`, we verify the existing index schema via the parent implementation\n * and return if it matches.\n */\n async createIndex({ indexName, dimension, metric = 'cosine' }: CreateIndexParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n\n let s3Metric: S3DistanceMetric;\n try {\n assertPositiveInteger(dimension, 'dimension');\n s3Metric = S3Vectors.toS3Metric(metric);\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'CREATE_INDEX', 'INVALID_ARGS'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n details: { indexName, dimension, metric },\n },\n error,\n );\n }\n\n try {\n const input: any = {\n ...this.bucketParams(),\n indexName,\n dataType: 'float32',\n dimension,\n distanceMetric: s3Metric,\n };\n if (this.nonFilterableMetadataKeys?.length) {\n input.metadataConfiguration = { nonFilterableMetadataKeys: this.nonFilterableMetadataKeys };\n }\n\n await this.client.send(new CreateIndexCommand(input));\n } catch (error: any) {\n if (error?.name === 'ConflictException') {\n await this.validateExistingIndex(indexName, dimension, metric);\n return;\n }\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'CREATE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName, dimension, metric },\n },\n error,\n );\n }\n }\n\n /**\n * Upserts vectors in bulk.\n *\n * @param params.indexName - Index to write to.\n * @param params.vectors - Array of vectors; each must match the index dimension.\n * @param params.metadata - Optional metadata per vector; `Date` values are normalized to epoch ms.\n * @param params.ids - Optional explicit IDs; if omitted, UUIDs are generated.\n * @returns Array of IDs used for the upsert (explicit or generated).\n * @throws {MastraError} If validation fails or AWS returns an error.\n */\n async upsert({ indexName, vectors, metadata, ids }: UpsertVectorParams): Promise<string[]> {\n indexName = normalizeIndexName(indexName);\n try {\n const { dimension } = await this.getIndexInfo(indexName);\n validateVectorDimensions(vectors, dimension);\n\n const generatedIds = ids ?? vectors.map(() => uuidv4());\n\n const putInput = {\n ...this.bucketParams(),\n indexName,\n vectors: vectors.map((vec, i) => ({\n key: generatedIds[i],\n data: { float32: vec },\n metadata: normalizeMetadata(metadata?.[i]),\n })),\n };\n\n await this.client.send(new PutVectorsCommand(putInput));\n return generatedIds;\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'UPSERT', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Queries nearest neighbors.\n *\n * @param params.indexName - Target index.\n * @param params.queryVector - Query vector (non-empty float32 array).\n * @param params.topK - Number of neighbors to return (positive integer). Defaults to 10.\n * @param params.filter - Metadata filter using explicit `$and`/`$or` (translator canonicalizes implicit AND).\n * @param params.includeVector - If `true`, fetches missing vector data in a second call.\n * @returns Results sorted by `score` descending.\n * @throws {MastraError} If validation fails or AWS returns an error.\n * @remarks\n * `score = 1/(1+distance)` (monotonic transform), so ranking matches the underlying distance.\n */\n async query({\n indexName,\n queryVector,\n topK = 10,\n filter,\n includeVector = false,\n }: QueryVectorParams<S3VectorsFilter>): Promise<QueryResult[]> {\n indexName = normalizeIndexName(indexName);\n\n if (!queryVector) {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'QUERY', 'MISSING_VECTOR'),\n text: 'queryVector is required for S3 Vectors queries. Metadata-only queries are not supported by this vector store.',\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n details: { indexName },\n });\n }\n\n try {\n if (!Array.isArray(queryVector) || queryVector.length === 0) {\n throw new Error('queryVector must be a non-empty float32 array');\n }\n assertPositiveInteger(topK, 'topK');\n\n const translated = this.transformFilter(filter);\n\n const out = await this.client.send(\n new QueryVectorsCommand({\n ...this.bucketParams(),\n indexName,\n topK,\n queryVector: { float32: queryVector },\n filter: translated && Object.keys(translated).length > 0 ? (translated as any) : undefined,\n returnMetadata: true,\n returnDistance: true,\n }),\n );\n\n const vectors = (out.vectors ?? []).filter(v => !!v?.key);\n\n // Query results don't include vector data; fetch via GetVectors when requested.\n let dataMap: Record<string, number[] | undefined> | undefined;\n if (includeVector) {\n const keys = vectors.filter(v => v.key).map(v => v.key!) as string[];\n\n if (keys.length > 0) {\n const got = await this.client.send(\n new GetVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys,\n returnData: true,\n returnMetadata: false,\n }),\n );\n dataMap = {};\n for (const g of got.vectors ?? []) {\n if (g.key) dataMap[g.key] = g.data?.float32 as number[] | undefined;\n }\n }\n }\n\n return vectors.map(v => {\n const id = v.key!;\n const score = S3Vectors.distanceToScore(v.distance ?? 0);\n\n const result: QueryResult = { id, score };\n\n const md = v.metadata as Record<string, unknown> | undefined;\n if (md !== undefined) result.metadata = md;\n\n if (includeVector) {\n const vec = dataMap?.[id];\n if (vec !== undefined) result.vector = vec;\n }\n\n return result;\n });\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'QUERY', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Lists indexes within the configured bucket.\n *\n * @returns Array of index names.\n * @throws {MastraError} On AWS errors.\n */\n async listIndexes(): Promise<string[]> {\n try {\n const names: string[] = [];\n let nextToken: string | undefined;\n\n do {\n const out = await this.client.send(\n new ListIndexesCommand({\n ...this.bucketParams(),\n nextToken,\n } as any),\n );\n for (const idx of out.indexes ?? []) {\n if (idx.indexName) names.push(idx.indexName);\n }\n nextToken = out.nextToken;\n } while (nextToken);\n\n return names;\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'LIST_INDEXES', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n },\n error,\n );\n }\n }\n\n /**\n * Returns index attributes.\n *\n * @param params.indexName - Index name.\n * @returns Object containing `dimension`, `metric`, and `count`.\n * @throws {MastraError} On AWS errors.\n * @remarks\n * `count` is computed via `ListVectors` pagination and may be costly (O(n)).\n */\n async describeIndex({ indexName }: DescribeIndexParams): Promise<IndexStats> {\n indexName = normalizeIndexName(indexName);\n try {\n const { dimension, metric } = await this.getIndexInfo(indexName);\n const count = await this.countVectors(indexName);\n return { dimension, metric, count };\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DESCRIBE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Deletes an index.\n *\n * @param params.indexName - Index name.\n * @throws {MastraError} On AWS errors.\n */\n async deleteIndex({ indexName }: DeleteIndexParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n try {\n await this.client.send(new DeleteIndexCommand({ ...this.bucketParams(), indexName } as any));\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DELETE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Updates (replaces) a vector and/or its metadata by ID.\n *\n * @param params.indexName - Target index.\n * @param params.id - Vector ID.\n * @param params.update.vector - New vector; if omitted, the existing vector is reused.\n * @param params.update.metadata - New metadata, merged with current metadata.\n * @throws {MastraError} If the vector does not exist and `update.vector` is omitted, or on AWS error.\n * @remarks\n * S3 Vectors `PutVectors` is replace-all; we `Get` the current item, merge, then `Put`.\n */\n async updateVector({ indexName, id, update }: UpdateVectorParams): Promise<void> {\n if (!id) {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'UPDATE_VECTOR', 'INVALID_ARGS'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n text: 'id is required for S3Vectors updateVector',\n details: { indexName },\n });\n }\n\n indexName = normalizeIndexName(indexName);\n try {\n if (!update.vector && !update.metadata) {\n throw new Error('No updates provided');\n }\n\n const got = await this.client.send(\n new GetVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: [id],\n returnData: true,\n returnMetadata: true,\n }),\n );\n const current = (got.vectors ?? [])[0];\n\n const newVector: number[] | undefined = update.vector ?? (current?.data?.float32 as number[] | undefined);\n if (!newVector) {\n throw new Error(`Vector \"${id}\" not found. Provide update.vector to create it.`);\n }\n\n const newMetadata =\n update.metadata !== undefined\n ? normalizeMetadata(update.metadata)\n : ((current?.metadata as Record<string, any>) ?? {});\n\n await this.client.send(\n new PutVectorsCommand({\n ...this.bucketParams(),\n indexName,\n vectors: [{ key: id, data: { float32: newVector }, metadata: newMetadata }],\n }),\n );\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'UPDATE_VECTOR', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: {\n indexName,\n ...(id && { id }),\n },\n },\n error,\n );\n }\n }\n\n /**\n * Deletes a vector by ID.\n *\n * @param params.indexName - Target index.\n * @param params.id - Vector ID to delete.\n * @throws {MastraError} On AWS errors.\n */\n async deleteVector({ indexName, id }: DeleteVectorParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n try {\n await this.client.send(\n new DeleteVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: [id],\n }),\n );\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DELETE_VECTOR', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: {\n indexName,\n ...(id && { id }),\n },\n },\n error,\n );\n }\n }\n\n async deleteVectors({ indexName, filter, ids }: DeleteVectorsParams): Promise<void> {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'DELETE_VECTORS', 'NOT_SUPPORTED'),\n text: 'deleteVectors is not yet implemented for S3Vectors vector store',\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.SYSTEM,\n details: {\n indexName,\n ...(filter && { filter: JSON.stringify(filter) }),\n ...(ids && { idsCount: ids.length }),\n },\n });\n }\n\n // -------- internal helpers --------\n\n /**\n * Returns shared bucket parameters for AWS SDK calls.\n * @internal\n */\n private bucketParams(): { vectorBucketName: string } {\n return { vectorBucketName: this.vectorBucketName };\n }\n\n /**\n * Retrieves index dimension/metric via `GetIndex`.\n * @internal\n * @throws {Error} If the index does not exist.\n * @returns `{ dimension, metric }`, where `metric` includes `'dotproduct'` to satisfy Mastra types (S3 never returns it).\n */\n private async getIndexInfo(\n indexName: string,\n ): Promise<{ dimension: number; metric: 'cosine' | 'euclidean' | 'dotproduct' }> {\n const out = await this.client.send(new GetIndexCommand({ ...this.bucketParams(), indexName } as any));\n const idx = out.index;\n if (!idx) throw new Error(`Index \"${indexName}\" not found`);\n const metric = (idx.distanceMetric as S3DistanceMetric) ?? 'cosine';\n return {\n dimension: idx.dimension ?? 0,\n metric,\n };\n }\n\n /**\n * Pages through `ListVectors` and counts total items.\n * @internal\n * @remarks O(n). Avoid calling on hot paths.\n */\n private async countVectors(indexName: string): Promise<number> {\n let total = 0;\n let nextToken: string | undefined;\n\n do {\n const out = await this.client.send(\n new ListVectorsCommand({\n ...this.bucketParams(),\n indexName,\n maxResults: 1000,\n nextToken,\n returnData: false,\n returnMetadata: false,\n }),\n );\n total += (out.vectors ?? []).length;\n nextToken = out.nextToken;\n } while (nextToken);\n\n return total;\n }\n\n /**\n * Translates a high-level filter to the S3 Vectors filter shape.\n * @internal\n * @remarks Implicit AND is canonicalized by the translator where permitted by spec.\n */\n private transformFilter(filter?: S3VectorsFilter): any {\n if (!filter) return undefined;\n return this.filterTranslator.translate(filter);\n }\n\n /**\n * Converts a Mastra metric to an S3 metric.\n * @internal\n * @throws {Error} If the metric is not supported by S3 Vectors.\n */\n private static toS3Metric(metric: MastraMetric): S3DistanceMetric {\n const m = S3Vectors.METRIC_MAP[metric as SupportedMastraMetric];\n if (!m) {\n throw new Error(`Invalid metric: \"${metric}\". S3 Vectors supports only: cosine, euclidean`);\n }\n return m;\n }\n\n /**\n * Monotonic transform from distance (smaller is better) to score (larger is better).\n * @returns Number in (0, 1], preserving ranking.\n */\n private static distanceToScore(distance: number): number {\n return 1 / (1 + distance);\n }\n}\n\n// --- module-private utilities (not exported) ---\n\n/**\n * Ensures a value is a positive integer.\n * @throws {Error} If the value is not a positive integer.\n * @internal\n */\nfunction assertPositiveInteger(value: number, name: string): void {\n if (!Number.isInteger(value) || value <= 0) {\n throw new Error(`${name} must be a positive integer`);\n }\n}\n\n/**\n * Validates that all vectors match the required dimension.\n * @throws {Error} If any vector length differs from `dimension`.\n * @internal\n */\nfunction validateVectorDimensions(vectors: number[][], dimension: number): void {\n if (!Array.isArray(vectors) || vectors.length === 0) {\n throw new Error('No vectors provided for validation');\n }\n for (let i = 0; i < vectors.length; i++) {\n const len = vectors[i]?.length;\n if (len !== dimension) {\n throw new Error(`Vector at index ${i} has invalid dimension ${len}. Expected ${dimension} dimensions.`);\n }\n }\n}\n\n/**\n * Normalizes metadata values for S3 Vectors: `Date` → epoch ms.\n * @internal\n */\nfunction normalizeMetadata(meta: Record<string, any> | undefined): Record<string, any> {\n if (!meta) return {};\n const out: Record<string, any> = {};\n for (const [k, v] of Object.entries(meta)) {\n out[k] = v instanceof Date ? v.getTime() : v;\n }\n return out;\n}\n\n/**\n * Normalizes an index name to this store's canonical form (underscore → hyphen, lowercase).\n * @internal\n * @throws {TypeError} If the provided name is not a string.\n */\nfunction normalizeIndexName(str: string) {\n if (typeof str !== 'string') {\n throw new TypeError('Index name must be a string');\n }\n return str.replace(/_/g, '-').toLowerCase();\n}\n","/**\n * Vector store specific prompt that details supported operators and examples.\n * This prompt helps users construct valid filters for Amazon S3 Vectors.\n */\nexport const S3VECTORS_PROMPT = `When querying Amazon S3 Vectors, you can ONLY use the operators listed below. Any other operators will be rejected.\nImportant: Don't explain how to construct the filter - use the specified operators and fields to search the content and return relevant results.\nIf a user tries to give an explicit operator that is not supported, reject the filter entirely and let them know that the operator is not supported.\n\nBasic Comparison Operators:\n- $eq: Exact match (default when using field: value)\n Example: { \"category\": \"electronics\" }\n- $ne: Not equal\n Example: { \"category\": { \"$ne\": \"electronics\" } }\n- $gt: Greater than\n Example: { \"price\": { \"$gt\": 100 } }\n- $gte: Greater than or equal\n Example: { \"price\": { \"$gte\": 100 } }\n- $lt: Less than\n Example: { \"price\": { \"$lt\": 100 } }\n- $lte: Less than or equal\n Example: { \"price\": { \"$lte\": 100 } }\n\nArray Operators (non-empty arrays of string | number | boolean):\n- $in: Match any value in array\n Example: { \"category\": { \"$in\": [\"electronics\", \"books\"] } }\n- $nin: Does not match any value in array\n Example: { \"category\": { \"$nin\": [\"electronics\", \"books\"] } }\n\nLogical Operators:\n- $and: Logical AND (can be implicit or explicit)\n Implicit Example: { \"price\": { \"$gt\": 100 }, \"category\": \"electronics\" }\n Explicit Example: { \"$and\": [{ \"price\": { \"$gt\": 100 } }, { \"category\": \"electronics\" }] }\n- $or: Logical OR\n Example: { \"$or\": [{ \"price\": { \"$lt\": 50 } }, { \"category\": \"books\" }] }\n\nElement Operators:\n- $exists: Check if field exists\n Example: { \"rating\": { \"$exists\": true } }\n\nUnsupported / Disallowed Operators (REJECT if present):\n- $not, $nor, $regex, $all, $elemMatch, $size, $text (and any operator not listed as supported)\n\nRestrictions:\n- Only logical operators ($and, $or) can be used at the top level\n- Empty arrays for $and / $or / $in / $nin are NOT allowed\n- Nested fields are supported using dot notation\n- Multiple conditions on the same field are supported\n- At least one key-value pair is required in filter object\n- Empty objects and undefined values are treated as no filter\n- Invalid types in comparison operators will throw errors\n- All non-logical operators must be used within a field condition\n Valid: { \"field\": { \"$gt\": 100 } }\n Valid: { \"$and\": [...] }\n Invalid: { \"$gt\": 100 }\n- Logical operators must contain field conditions, not direct operators\n Valid: { \"$and\": [{ \"field\": { \"$gt\": 100 } }] }\n Invalid: { \"$and\": [{ \"$gt\": 100 }] }\n- Logical operators ($and, $or):\n - Can only be used at top level or nested within other logical operators\n - Can not be used on a field level, or be nested inside a field\n - Can not be used inside an operator\n - Valid: { \"$and\": [{ \"field\": { \"$gt\": 100 } }] }\n - Valid: { \"$or\": [{ \"$and\": [{ \"field\": { \"$gt\": 100 } }] }] }\n - Invalid: { \"field\": { \"$and\": [{ \"$gt\": 100 }] } }\n - Invalid: { \"field\": { \"$or\": [{ \"$gt\": 100 }] } }\n - Invalid: { \"field\": { \"$gt\": { \"$and\": [{...}] } } }\n- Equality values must be string, number, or boolean (arrays and objects are not allowed for equality)\n- Filters operate only on filterable metadata keys; using a non-filterable key will fail\n- Filterable metadata values are primitives (string/number/boolean) or arrays of primitives; large/long-text fields should be non-filterable and are not usable in filters\n\nExample Complex Query:\n{\n \"$and\": [\n { \"category\": { \"$in\": [\"electronics\", \"computers\"] } },\n { \"price\": { \"$gte\": 100, \"$lte\": 1000 } },\n { \"$or\": [\n { \"stock\": { \"$gt\": 0 } },\n { \"preorder\": true }\n ] }\n ]\n}`;\n"]}
|
package/dist/index.js
CHANGED
|
@@ -361,13 +361,13 @@ var S3Vectors = class _S3Vectors extends MastraVector {
|
|
|
361
361
|
const vectors = (out.vectors ?? []).filter((v) => !!v?.key);
|
|
362
362
|
let dataMap;
|
|
363
363
|
if (includeVector) {
|
|
364
|
-
const
|
|
365
|
-
if (
|
|
364
|
+
const keys = vectors.filter((v) => v.key).map((v) => v.key);
|
|
365
|
+
if (keys.length > 0) {
|
|
366
366
|
const got = await this.client.send(
|
|
367
367
|
new GetVectorsCommand({
|
|
368
368
|
...this.bucketParams(),
|
|
369
369
|
indexName,
|
|
370
|
-
keys
|
|
370
|
+
keys,
|
|
371
371
|
returnData: true,
|
|
372
372
|
returnMetadata: false
|
|
373
373
|
})
|
|
@@ -385,7 +385,7 @@ var S3Vectors = class _S3Vectors extends MastraVector {
|
|
|
385
385
|
const md = v.metadata;
|
|
386
386
|
if (md !== void 0) result.metadata = md;
|
|
387
387
|
if (includeVector) {
|
|
388
|
-
const vec =
|
|
388
|
+
const vec = dataMap?.[id];
|
|
389
389
|
if (vec !== void 0) result.vector = vec;
|
|
390
390
|
}
|
|
391
391
|
return result;
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/vector/filter.ts","../src/vector/index.ts","../src/vector/prompt.ts"],"names":["uuidv4"],"mappings":"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","file":"index.js","sourcesContent":["import { BaseFilterTranslator } from '@mastra/core/vector/filter';\nimport type {\n VectorFilter,\n LogicalOperatorValueMap,\n OperatorSupport,\n QueryOperator,\n OperatorValueMap,\n BlacklistedRootOperators,\n} from '@mastra/core/vector/filter';\n\n/**\n * S3 Vectors supports a strict subset of operators and value types.\n *\n * - logical: `$and`, `$or` (non-empty arrays)\n * - basic: `$eq`, `$ne` (string | number | boolean)\n * - numeric: `$gt`, `$gte`, `$lt`, `$lte` (number)\n * - array: `$in`, `$nin` (non-empty arrays of string | number | boolean)\n * - element: `$exists` (boolean)\n */\ntype S3VectorsOperatorValueMap = Pick<\n OperatorValueMap,\n '$eq' | '$ne' | '$gt' | '$gte' | '$lt' | '$lte' | '$in' | '$nin' | '$exists'\n>;\n\ntype S3VectorsLogicalOperatorValueMap = Pick<LogicalOperatorValueMap, '$and' | '$or'>;\n\ntype S3VectorsBlacklisted = BlacklistedRootOperators;\n\ntype S3VectorsFieldValue = string | number | boolean;\n\n/**\n * High-level filter type accepted by this translator.\n * @remarks\n * Field values are limited to string/number/boolean at equality positions.\n */\nexport type S3VectorsFilter = VectorFilter<\n keyof S3VectorsOperatorValueMap,\n S3VectorsOperatorValueMap,\n S3VectorsLogicalOperatorValueMap,\n S3VectorsBlacklisted,\n S3VectorsFieldValue\n>;\n\n/**\n * Translates a high-level filter into the S3 Vectors filter shape.\n *\n * @remarks\n * - Canonicalizes **implicit AND** (e.g. `{a:1,b:2}`) into explicit `{$and:[{a:1},{b:2}]}` in any\n * non-field context that lacks `$and/$or`.\n * - Normalizes `Date` values to epoch milliseconds where allowed (numeric comparisons and array elements).\n * - Disallows `Date` at equality positions (including implicit equality).\n * - Validates shapes using the base class after translation.\n */\nexport class S3VectorsFilterTranslator extends BaseFilterTranslator<S3VectorsFilter> {\n /** @inheritdoc */\n protected override getSupportedOperators(): OperatorSupport {\n return {\n logical: ['$and', '$or'],\n basic: ['$eq', '$ne'],\n numeric: ['$gt', '$gte', '$lt', '$lte'],\n array: ['$in', '$nin'],\n element: ['$exists'],\n };\n }\n\n /**\n * Translates and validates a filter.\n * @param filter - Input filter; may be `undefined`, `null`, or `{}` (all treated as empty).\n * @returns The translated filter (or the original value if empty).\n */\n translate(filter?: S3VectorsFilter): any {\n if (this.isEmpty(filter)) return filter;\n // Perform translation (including Date → number normalization) before base shape validation.\n const translated = this.translateNode(filter as any, false);\n this.validateFilter(translated as any);\n return translated;\n }\n\n /**\n * Recursively translates a node.\n * @param node - Current node to translate.\n * @param inFieldValue - When `true`, the node is the value of a field (i.e., equality context).\n * @remarks\n * - In a **field-value** context, only primitives or operator objects are allowed.\n * - In a **non-field** context (root / logical branches), operator keys are processed;\n * plain keys become field equalities and are validated.\n * - Implicit AND is canonicalized in non-field contexts when multiple non-logical keys exist.\n */\n private translateNode(node: any, inFieldValue = false): any {\n // Primitive or Date (normalize when in a field-equality context)\n if (this.isPrimitive(node) || node instanceof Date) {\n return inFieldValue ? this.validateAndNormalizePrimitive(node) : node;\n }\n\n // Arrays are not allowed as direct equality values\n if (Array.isArray(node)) {\n if (inFieldValue) {\n throw new Error('Array equality is not supported in S3 Vectors. Use $in / $nin operators.');\n }\n return node;\n }\n\n // Object\n const entries = Object.entries(node as Record<string, any>);\n\n if (inFieldValue) {\n if (entries.length === 0) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n const allOperatorKeys = entries.every(([k]) => this.isOperator(k));\n if (!allOperatorKeys) {\n // Disallow shapes like: { field: { a:1, b:2 } }\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n const opEntries = entries.map(([key, value]) => [key, this.translateOperatorValue(key as QueryOperator, value)]);\n return Object.fromEntries(opEntries);\n }\n\n // Root / filter context\n const translatedEntries = entries.map(([key, value]) => {\n if (this.isOperator(key)) {\n return [key, this.translateOperatorValue(key as QueryOperator, value)];\n }\n return [key, this.translateNode(value, true)];\n });\n const obj = Object.fromEntries(translatedEntries);\n\n // Canonicalize implicit AND → explicit $and (if no $and/$or present and multiple non-logical keys)\n const keys = Object.keys(obj);\n const hasLogical = keys.some(k => k === '$and' || k === '$or');\n if (!hasLogical) {\n const nonLogical = keys.filter(k => k !== '$and' && k !== '$or');\n if (nonLogical.length > 1) {\n return { $and: nonLogical.map(k => ({ [k]: obj[k] })) };\n }\n }\n\n return obj;\n }\n\n /**\n * Translates a single operator and validates its value.\n * @param operator - One of the supported query operators.\n * @param value - Operator value to normalize/validate.\n */\n private translateOperatorValue(operator: QueryOperator, value: any): any {\n // Logical operators\n if (operator === '$and' || operator === '$or') {\n if (!Array.isArray(value) || value.length === 0) {\n throw new Error(`Value for logical operator ${operator} must be a non-empty array`);\n }\n return value.map(item => this.translateNode(item));\n }\n\n // Equality / inequality (Date is not allowed)\n if (operator === '$eq' || operator === '$ne') {\n if (value instanceof Date) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n return this.toPrimitiveForS3(value, operator);\n }\n\n // Numeric comparisons: require number; allow Date by converting to epoch ms\n if (operator === '$gt' || operator === '$gte' || operator === '$lt' || operator === '$lte') {\n const n = this.toNumberForRange(value, operator);\n return n;\n }\n\n // Array operators: non-empty arrays of primitives (Date converted to number)\n if (operator === '$in' || operator === '$nin') {\n if (!Array.isArray(value) || value.length === 0) {\n throw new Error(`Value for array operator ${operator} must be a non-empty array`);\n }\n return value.map(v => this.toPrimitiveForS3(v, operator));\n }\n\n // Existence check\n if (operator === '$exists') {\n if (typeof value !== 'boolean') {\n throw new Error(`Value for $exists operator must be a boolean`);\n }\n return value;\n }\n\n throw new Error(`Unsupported operator: ${operator}`);\n }\n\n /**\n * Normalizes a value to an S3-accepted primitive.\n * @param value - String | Number | Boolean | Date.\n * @param operatorForMessage - Operator name used in error messages.\n * @returns The normalized primitive; `Date` becomes epoch milliseconds.\n * @throws If the value is not a supported primitive or is null/undefined.\n */\n private toPrimitiveForS3(value: any, operatorForMessage: string): string | number | boolean {\n if (value === null || value === undefined) {\n // Error message for equality matches tests\n if (operatorForMessage === 'equality') {\n throw new Error('S3 Vectors does not support null/undefined for equality');\n }\n throw new Error(`Value for ${operatorForMessage} must be string, number, or boolean`);\n }\n if (value instanceof Date) {\n return value.getTime();\n }\n const t = typeof value;\n if (t === 'string' || t === 'boolean') return value;\n if (t === 'number') return Object.is(value, -0) ? 0 : value;\n throw new Error(`Value for ${operatorForMessage} must be string, number, or boolean`);\n }\n\n /**\n * Ensures a numeric value for range operators; allows `Date` by converting to epoch ms.\n * @param value - Candidate value.\n * @param operatorForMessage - Operator name used in error messages.\n * @throws If the value is not a number (or a Date).\n */\n private toNumberForRange(value: any, operatorForMessage: string): number {\n if (value instanceof Date) return value.getTime();\n if (typeof value === 'number' && !Number.isNaN(value)) return Object.is(value, -0) ? 0 : value;\n throw new Error(`Value for ${operatorForMessage} must be a number`);\n }\n\n /**\n * Validates and normalizes a primitive used in field equality (implicit `$eq`).\n * @param value - Candidate equality value.\n * @throws If the value is a `Date` or not a supported primitive.\n */\n private validateAndNormalizePrimitive(value: any): S3VectorsFieldValue {\n if (value instanceof Date) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n return this.toPrimitiveForS3(value, 'equality') as S3VectorsFieldValue;\n }\n\n /**\n * Determines whether a filter is considered empty.\n * @param filter - Input filter.\n */\n protected override isEmpty(filter: any): boolean {\n return filter === undefined || filter === null || (typeof filter === 'object' && Object.keys(filter).length === 0);\n }\n}\n","import {\n S3VectorsClient,\n CreateIndexCommand,\n DeleteIndexCommand,\n ListIndexesCommand,\n GetIndexCommand,\n PutVectorsCommand,\n QueryVectorsCommand,\n GetVectorsCommand,\n DeleteVectorsCommand,\n ListVectorsCommand,\n} from '@aws-sdk/client-s3vectors';\nimport type { S3VectorsClientConfig } from '@aws-sdk/client-s3vectors';\nimport { MastraError, ErrorDomain, ErrorCategory } from '@mastra/core/error';\nimport { createVectorErrorId } from '@mastra/core/storage';\nimport { MastraVector } from '@mastra/core/vector';\nimport type {\n QueryResult,\n IndexStats,\n CreateIndexParams,\n UpsertVectorParams,\n DeleteVectorsParams,\n QueryVectorParams,\n DescribeIndexParams,\n DeleteIndexParams,\n DeleteVectorParams,\n UpdateVectorParams,\n} from '@mastra/core/vector';\nimport { v4 as uuidv4 } from 'uuid';\nimport { S3VectorsFilterTranslator } from './filter';\nimport type { S3VectorsFilter } from './filter';\n\n/**\n * Options for the S3Vectors store.\n * @property vectorBucketName - Target S3 Vectors bucket name.\n * @property clientConfig - AWS SDK client options (e.g., region/credentials).\n * @property nonFilterableMetadataKeys - Metadata keys that must not be filterable (forwarded to S3 Vectors).\n */\nexport interface S3VectorsOptions {\n vectorBucketName: string;\n clientConfig?: S3VectorsClientConfig;\n nonFilterableMetadataKeys?: string[];\n}\n\ntype S3DistanceMetric = 'cosine' | 'euclidean';\ntype MastraMetric = NonNullable<CreateIndexParams['metric']>;\ntype SupportedMastraMetric = Exclude<MastraMetric, 'dotproduct'>;\n\n/**\n * Vector store backed by Amazon S3 Vectors.\n *\n * @remarks\n * - Supports `cosine` and `euclidean` distance metrics.\n * - Filters must use explicit logical operators (`$and` / `$or`). The attached translator\n * canonicalizes implicit AND (e.g., `{a:1,b:2}` → `{ $and: [{a:1},{b:2}] }`) where permitted by spec.\n * - Methods wrap AWS errors in `MastraError` with domain/category metadata.\n */\nexport class S3Vectors extends MastraVector<S3VectorsFilter> {\n private readonly client: S3VectorsClient;\n private readonly vectorBucketName: string;\n private readonly nonFilterableMetadataKeys?: string[];\n private readonly filterTranslator = new S3VectorsFilterTranslator();\n\n private static readonly METRIC_MAP: Record<SupportedMastraMetric, S3DistanceMetric> = {\n cosine: 'cosine',\n euclidean: 'euclidean',\n } as const;\n\n constructor(opts: S3VectorsOptions & { id: string }) {\n super({ id: opts.id });\n if (!opts?.vectorBucketName) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'INITIALIZATION', 'MISSING_BUCKET_NAME'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n },\n new Error('vectorBucketName is required'),\n );\n }\n this.vectorBucketName = opts.vectorBucketName;\n this.nonFilterableMetadataKeys = opts.nonFilterableMetadataKeys;\n this.client = new S3VectorsClient({ ...(opts.clientConfig ?? {}) });\n }\n\n /**\n * No-op to satisfy the base interface.\n *\n * @remarks The AWS SDK manages HTTP per request; no persistent connection is needed.\n */\n async connect(): Promise<void> {}\n\n /**\n * Closes the underlying AWS SDK HTTP handler to free sockets.\n */\n async disconnect(): Promise<void> {\n try {\n this.client.destroy();\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DISCONNECT', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n },\n error,\n );\n }\n }\n\n /**\n * Creates an index or validates an existing one.\n *\n * @param params.indexName - Logical index name; normalized internally.\n * @param params.dimension - Vector dimension (must be a positive integer).\n * @param params.metric - Distance metric (`cosine` | `euclidean`). Defaults to `cosine`.\n * @throws {MastraError} If arguments are invalid or AWS returns an error.\n * @remarks\n * On `ConflictException`, we verify the existing index schema via the parent implementation\n * and return if it matches.\n */\n async createIndex({ indexName, dimension, metric = 'cosine' }: CreateIndexParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n\n let s3Metric: S3DistanceMetric;\n try {\n assertPositiveInteger(dimension, 'dimension');\n s3Metric = S3Vectors.toS3Metric(metric);\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'CREATE_INDEX', 'INVALID_ARGS'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n details: { indexName, dimension, metric },\n },\n error,\n );\n }\n\n try {\n const input: any = {\n ...this.bucketParams(),\n indexName,\n dataType: 'float32',\n dimension,\n distanceMetric: s3Metric,\n };\n if (this.nonFilterableMetadataKeys?.length) {\n input.metadataConfiguration = { nonFilterableMetadataKeys: this.nonFilterableMetadataKeys };\n }\n\n await this.client.send(new CreateIndexCommand(input));\n } catch (error: any) {\n if (error?.name === 'ConflictException') {\n await this.validateExistingIndex(indexName, dimension, metric);\n return;\n }\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'CREATE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName, dimension, metric },\n },\n error,\n );\n }\n }\n\n /**\n * Upserts vectors in bulk.\n *\n * @param params.indexName - Index to write to.\n * @param params.vectors - Array of vectors; each must match the index dimension.\n * @param params.metadata - Optional metadata per vector; `Date` values are normalized to epoch ms.\n * @param params.ids - Optional explicit IDs; if omitted, UUIDs are generated.\n * @returns Array of IDs used for the upsert (explicit or generated).\n * @throws {MastraError} If validation fails or AWS returns an error.\n */\n async upsert({ indexName, vectors, metadata, ids }: UpsertVectorParams): Promise<string[]> {\n indexName = normalizeIndexName(indexName);\n try {\n const { dimension } = await this.getIndexInfo(indexName);\n validateVectorDimensions(vectors, dimension);\n\n const generatedIds = ids ?? vectors.map(() => uuidv4());\n\n const putInput = {\n ...this.bucketParams(),\n indexName,\n vectors: vectors.map((vec, i) => ({\n key: generatedIds[i],\n data: { float32: vec },\n metadata: normalizeMetadata(metadata?.[i]),\n })),\n };\n\n await this.client.send(new PutVectorsCommand(putInput));\n return generatedIds;\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'UPSERT', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Queries nearest neighbors.\n *\n * @param params.indexName - Target index.\n * @param params.queryVector - Query vector (non-empty float32 array).\n * @param params.topK - Number of neighbors to return (positive integer). Defaults to 10.\n * @param params.filter - Metadata filter using explicit `$and`/`$or` (translator canonicalizes implicit AND).\n * @param params.includeVector - If `true`, fetches missing vector data in a second call.\n * @returns Results sorted by `score` descending.\n * @throws {MastraError} If validation fails or AWS returns an error.\n * @remarks\n * `score = 1/(1+distance)` (monotonic transform), so ranking matches the underlying distance.\n */\n async query({\n indexName,\n queryVector,\n topK = 10,\n filter,\n includeVector = false,\n }: QueryVectorParams<S3VectorsFilter>): Promise<QueryResult[]> {\n indexName = normalizeIndexName(indexName);\n\n if (!queryVector) {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'QUERY', 'MISSING_VECTOR'),\n text: 'queryVector is required for S3 Vectors queries. Metadata-only queries are not supported by this vector store.',\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n details: { indexName },\n });\n }\n\n try {\n if (!Array.isArray(queryVector) || queryVector.length === 0) {\n throw new Error('queryVector must be a non-empty float32 array');\n }\n assertPositiveInteger(topK, 'topK');\n\n const translated = this.transformFilter(filter);\n\n const out = await this.client.send(\n new QueryVectorsCommand({\n ...this.bucketParams(),\n indexName,\n topK,\n queryVector: { float32: queryVector },\n filter: translated && Object.keys(translated).length > 0 ? (translated as any) : undefined,\n returnMetadata: true,\n returnDistance: true,\n }),\n );\n\n const vectors = (out.vectors ?? []).filter(v => !!v?.key);\n\n // If includeVector is requested and some results lack data, fetch only the missing ones.\n let dataMap: Record<string, number[] | undefined> | undefined;\n if (includeVector) {\n const missingKeys = vectors.filter(v => !v.data?.float32 && v.key).map(v => v.key!) as string[];\n\n if (missingKeys.length > 0) {\n const got = await this.client.send(\n new GetVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: missingKeys,\n returnData: true,\n returnMetadata: false,\n }),\n );\n dataMap = {};\n for (const g of got.vectors ?? []) {\n if (g.key) dataMap[g.key] = g.data?.float32 as number[] | undefined;\n }\n }\n }\n\n return vectors.map(v => {\n const id = v.key!;\n const score = S3Vectors.distanceToScore(v.distance ?? 0);\n\n const result: QueryResult = { id, score };\n\n const md = v.metadata as Record<string, unknown> | undefined;\n if (md !== undefined) result.metadata = md;\n\n if (includeVector) {\n const vec = (v.data?.float32 as number[] | undefined) ?? dataMap?.[id];\n if (vec !== undefined) result.vector = vec;\n }\n\n return result;\n });\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'QUERY', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Lists indexes within the configured bucket.\n *\n * @returns Array of index names.\n * @throws {MastraError} On AWS errors.\n */\n async listIndexes(): Promise<string[]> {\n try {\n const names: string[] = [];\n let nextToken: string | undefined;\n\n do {\n const out = await this.client.send(\n new ListIndexesCommand({\n ...this.bucketParams(),\n nextToken,\n } as any),\n );\n for (const idx of out.indexes ?? []) {\n if (idx.indexName) names.push(idx.indexName);\n }\n nextToken = out.nextToken;\n } while (nextToken);\n\n return names;\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'LIST_INDEXES', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n },\n error,\n );\n }\n }\n\n /**\n * Returns index attributes.\n *\n * @param params.indexName - Index name.\n * @returns Object containing `dimension`, `metric`, and `count`.\n * @throws {MastraError} On AWS errors.\n * @remarks\n * `count` is computed via `ListVectors` pagination and may be costly (O(n)).\n */\n async describeIndex({ indexName }: DescribeIndexParams): Promise<IndexStats> {\n indexName = normalizeIndexName(indexName);\n try {\n const { dimension, metric } = await this.getIndexInfo(indexName);\n const count = await this.countVectors(indexName);\n return { dimension, metric, count };\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DESCRIBE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Deletes an index.\n *\n * @param params.indexName - Index name.\n * @throws {MastraError} On AWS errors.\n */\n async deleteIndex({ indexName }: DeleteIndexParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n try {\n await this.client.send(new DeleteIndexCommand({ ...this.bucketParams(), indexName } as any));\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DELETE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Updates (replaces) a vector and/or its metadata by ID.\n *\n * @param params.indexName - Target index.\n * @param params.id - Vector ID.\n * @param params.update.vector - New vector; if omitted, the existing vector is reused.\n * @param params.update.metadata - New metadata, merged with current metadata.\n * @throws {MastraError} If the vector does not exist and `update.vector` is omitted, or on AWS error.\n * @remarks\n * S3 Vectors `PutVectors` is replace-all; we `Get` the current item, merge, then `Put`.\n */\n async updateVector({ indexName, id, update }: UpdateVectorParams): Promise<void> {\n if (!id) {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'UPDATE_VECTOR', 'INVALID_ARGS'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n text: 'id is required for S3Vectors updateVector',\n details: { indexName },\n });\n }\n\n indexName = normalizeIndexName(indexName);\n try {\n if (!update.vector && !update.metadata) {\n throw new Error('No updates provided');\n }\n\n const got = await this.client.send(\n new GetVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: [id],\n returnData: true,\n returnMetadata: true,\n }),\n );\n const current = (got.vectors ?? [])[0];\n\n const newVector: number[] | undefined = update.vector ?? (current?.data?.float32 as number[] | undefined);\n if (!newVector) {\n throw new Error(`Vector \"${id}\" not found. Provide update.vector to create it.`);\n }\n\n const newMetadata =\n update.metadata !== undefined\n ? normalizeMetadata(update.metadata)\n : ((current?.metadata as Record<string, any>) ?? {});\n\n await this.client.send(\n new PutVectorsCommand({\n ...this.bucketParams(),\n indexName,\n vectors: [{ key: id, data: { float32: newVector }, metadata: newMetadata }],\n }),\n );\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'UPDATE_VECTOR', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: {\n indexName,\n ...(id && { id }),\n },\n },\n error,\n );\n }\n }\n\n /**\n * Deletes a vector by ID.\n *\n * @param params.indexName - Target index.\n * @param params.id - Vector ID to delete.\n * @throws {MastraError} On AWS errors.\n */\n async deleteVector({ indexName, id }: DeleteVectorParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n try {\n await this.client.send(\n new DeleteVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: [id],\n }),\n );\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DELETE_VECTOR', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: {\n indexName,\n ...(id && { id }),\n },\n },\n error,\n );\n }\n }\n\n async deleteVectors({ indexName, filter, ids }: DeleteVectorsParams): Promise<void> {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'DELETE_VECTORS', 'NOT_SUPPORTED'),\n text: 'deleteVectors is not yet implemented for S3Vectors vector store',\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.SYSTEM,\n details: {\n indexName,\n ...(filter && { filter: JSON.stringify(filter) }),\n ...(ids && { idsCount: ids.length }),\n },\n });\n }\n\n // -------- internal helpers --------\n\n /**\n * Returns shared bucket parameters for AWS SDK calls.\n * @internal\n */\n private bucketParams(): { vectorBucketName: string } {\n return { vectorBucketName: this.vectorBucketName };\n }\n\n /**\n * Retrieves index dimension/metric via `GetIndex`.\n * @internal\n * @throws {Error} If the index does not exist.\n * @returns `{ dimension, metric }`, where `metric` includes `'dotproduct'` to satisfy Mastra types (S3 never returns it).\n */\n private async getIndexInfo(\n indexName: string,\n ): Promise<{ dimension: number; metric: 'cosine' | 'euclidean' | 'dotproduct' }> {\n const out = await this.client.send(new GetIndexCommand({ ...this.bucketParams(), indexName } as any));\n const idx = out.index;\n if (!idx) throw new Error(`Index \"${indexName}\" not found`);\n const metric = (idx.distanceMetric as S3DistanceMetric) ?? 'cosine';\n return {\n dimension: idx.dimension ?? 0,\n metric,\n };\n }\n\n /**\n * Pages through `ListVectors` and counts total items.\n * @internal\n * @remarks O(n). Avoid calling on hot paths.\n */\n private async countVectors(indexName: string): Promise<number> {\n let total = 0;\n let nextToken: string | undefined;\n\n do {\n const out = await this.client.send(\n new ListVectorsCommand({\n ...this.bucketParams(),\n indexName,\n maxResults: 1000,\n nextToken,\n returnData: false,\n returnMetadata: false,\n }),\n );\n total += (out.vectors ?? []).length;\n nextToken = out.nextToken;\n } while (nextToken);\n\n return total;\n }\n\n /**\n * Translates a high-level filter to the S3 Vectors filter shape.\n * @internal\n * @remarks Implicit AND is canonicalized by the translator where permitted by spec.\n */\n private transformFilter(filter?: S3VectorsFilter): any {\n if (!filter) return undefined;\n return this.filterTranslator.translate(filter);\n }\n\n /**\n * Converts a Mastra metric to an S3 metric.\n * @internal\n * @throws {Error} If the metric is not supported by S3 Vectors.\n */\n private static toS3Metric(metric: MastraMetric): S3DistanceMetric {\n const m = S3Vectors.METRIC_MAP[metric as SupportedMastraMetric];\n if (!m) {\n throw new Error(`Invalid metric: \"${metric}\". S3 Vectors supports only: cosine, euclidean`);\n }\n return m;\n }\n\n /**\n * Monotonic transform from distance (smaller is better) to score (larger is better).\n * @returns Number in (0, 1], preserving ranking.\n */\n private static distanceToScore(distance: number): number {\n return 1 / (1 + distance);\n }\n}\n\n// --- module-private utilities (not exported) ---\n\n/**\n * Ensures a value is a positive integer.\n * @throws {Error} If the value is not a positive integer.\n * @internal\n */\nfunction assertPositiveInteger(value: number, name: string): void {\n if (!Number.isInteger(value) || value <= 0) {\n throw new Error(`${name} must be a positive integer`);\n }\n}\n\n/**\n * Validates that all vectors match the required dimension.\n * @throws {Error} If any vector length differs from `dimension`.\n * @internal\n */\nfunction validateVectorDimensions(vectors: number[][], dimension: number): void {\n if (!Array.isArray(vectors) || vectors.length === 0) {\n throw new Error('No vectors provided for validation');\n }\n for (let i = 0; i < vectors.length; i++) {\n const len = vectors[i]?.length;\n if (len !== dimension) {\n throw new Error(`Vector at index ${i} has invalid dimension ${len}. Expected ${dimension} dimensions.`);\n }\n }\n}\n\n/**\n * Normalizes metadata values for S3 Vectors: `Date` → epoch ms.\n * @internal\n */\nfunction normalizeMetadata(meta: Record<string, any> | undefined): Record<string, any> {\n if (!meta) return {};\n const out: Record<string, any> = {};\n for (const [k, v] of Object.entries(meta)) {\n out[k] = v instanceof Date ? v.getTime() : v;\n }\n return out;\n}\n\n/**\n * Normalizes an index name to this store's canonical form (underscore → hyphen, lowercase).\n * @internal\n * @throws {TypeError} If the provided name is not a string.\n */\nfunction normalizeIndexName(str: string) {\n if (typeof str !== 'string') {\n throw new TypeError('Index name must be a string');\n }\n return str.replace(/_/g, '-').toLowerCase();\n}\n","/**\n * Vector store specific prompt that details supported operators and examples.\n * This prompt helps users construct valid filters for Amazon S3 Vectors.\n */\nexport const S3VECTORS_PROMPT = `When querying Amazon S3 Vectors, you can ONLY use the operators listed below. Any other operators will be rejected.\nImportant: Don't explain how to construct the filter - use the specified operators and fields to search the content and return relevant results.\nIf a user tries to give an explicit operator that is not supported, reject the filter entirely and let them know that the operator is not supported.\n\nBasic Comparison Operators:\n- $eq: Exact match (default when using field: value)\n Example: { \"category\": \"electronics\" }\n- $ne: Not equal\n Example: { \"category\": { \"$ne\": \"electronics\" } }\n- $gt: Greater than\n Example: { \"price\": { \"$gt\": 100 } }\n- $gte: Greater than or equal\n Example: { \"price\": { \"$gte\": 100 } }\n- $lt: Less than\n Example: { \"price\": { \"$lt\": 100 } }\n- $lte: Less than or equal\n Example: { \"price\": { \"$lte\": 100 } }\n\nArray Operators (non-empty arrays of string | number | boolean):\n- $in: Match any value in array\n Example: { \"category\": { \"$in\": [\"electronics\", \"books\"] } }\n- $nin: Does not match any value in array\n Example: { \"category\": { \"$nin\": [\"electronics\", \"books\"] } }\n\nLogical Operators:\n- $and: Logical AND (can be implicit or explicit)\n Implicit Example: { \"price\": { \"$gt\": 100 }, \"category\": \"electronics\" }\n Explicit Example: { \"$and\": [{ \"price\": { \"$gt\": 100 } }, { \"category\": \"electronics\" }] }\n- $or: Logical OR\n Example: { \"$or\": [{ \"price\": { \"$lt\": 50 } }, { \"category\": \"books\" }] }\n\nElement Operators:\n- $exists: Check if field exists\n Example: { \"rating\": { \"$exists\": true } }\n\nUnsupported / Disallowed Operators (REJECT if present):\n- $not, $nor, $regex, $all, $elemMatch, $size, $text (and any operator not listed as supported)\n\nRestrictions:\n- Only logical operators ($and, $or) can be used at the top level\n- Empty arrays for $and / $or / $in / $nin are NOT allowed\n- Nested fields are supported using dot notation\n- Multiple conditions on the same field are supported\n- At least one key-value pair is required in filter object\n- Empty objects and undefined values are treated as no filter\n- Invalid types in comparison operators will throw errors\n- All non-logical operators must be used within a field condition\n Valid: { \"field\": { \"$gt\": 100 } }\n Valid: { \"$and\": [...] }\n Invalid: { \"$gt\": 100 }\n- Logical operators must contain field conditions, not direct operators\n Valid: { \"$and\": [{ \"field\": { \"$gt\": 100 } }] }\n Invalid: { \"$and\": [{ \"$gt\": 100 }] }\n- Logical operators ($and, $or):\n - Can only be used at top level or nested within other logical operators\n - Can not be used on a field level, or be nested inside a field\n - Can not be used inside an operator\n - Valid: { \"$and\": [{ \"field\": { \"$gt\": 100 } }] }\n - Valid: { \"$or\": [{ \"$and\": [{ \"field\": { \"$gt\": 100 } }] }] }\n - Invalid: { \"field\": { \"$and\": [{ \"$gt\": 100 }] } }\n - Invalid: { \"field\": { \"$or\": [{ \"$gt\": 100 }] } }\n - Invalid: { \"field\": { \"$gt\": { \"$and\": [{...}] } } }\n- Equality values must be string, number, or boolean (arrays and objects are not allowed for equality)\n- Filters operate only on filterable metadata keys; using a non-filterable key will fail\n- Filterable metadata values are primitives (string/number/boolean) or arrays of primitives; large/long-text fields should be non-filterable and are not usable in filters\n\nExample Complex Query:\n{\n \"$and\": [\n { \"category\": { \"$in\": [\"electronics\", \"computers\"] } },\n { \"price\": { \"$gte\": 100, \"$lte\": 1000 } },\n { \"$or\": [\n { \"stock\": { \"$gt\": 0 } },\n { \"preorder\": true }\n ] }\n ]\n}`;\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/vector/filter.ts","../src/vector/index.ts","../src/vector/prompt.ts"],"names":["uuidv4"],"mappings":"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","file":"index.js","sourcesContent":["import { BaseFilterTranslator } from '@mastra/core/vector/filter';\nimport type {\n VectorFilter,\n LogicalOperatorValueMap,\n OperatorSupport,\n QueryOperator,\n OperatorValueMap,\n BlacklistedRootOperators,\n} from '@mastra/core/vector/filter';\n\n/**\n * S3 Vectors supports a strict subset of operators and value types.\n *\n * - logical: `$and`, `$or` (non-empty arrays)\n * - basic: `$eq`, `$ne` (string | number | boolean)\n * - numeric: `$gt`, `$gte`, `$lt`, `$lte` (number)\n * - array: `$in`, `$nin` (non-empty arrays of string | number | boolean)\n * - element: `$exists` (boolean)\n */\ntype S3VectorsOperatorValueMap = Pick<\n OperatorValueMap,\n '$eq' | '$ne' | '$gt' | '$gte' | '$lt' | '$lte' | '$in' | '$nin' | '$exists'\n>;\n\ntype S3VectorsLogicalOperatorValueMap = Pick<LogicalOperatorValueMap, '$and' | '$or'>;\n\ntype S3VectorsBlacklisted = BlacklistedRootOperators;\n\ntype S3VectorsFieldValue = string | number | boolean;\n\n/**\n * High-level filter type accepted by this translator.\n * @remarks\n * Field values are limited to string/number/boolean at equality positions.\n */\nexport type S3VectorsFilter = VectorFilter<\n keyof S3VectorsOperatorValueMap,\n S3VectorsOperatorValueMap,\n S3VectorsLogicalOperatorValueMap,\n S3VectorsBlacklisted,\n S3VectorsFieldValue\n>;\n\n/**\n * Translates a high-level filter into the S3 Vectors filter shape.\n *\n * @remarks\n * - Canonicalizes **implicit AND** (e.g. `{a:1,b:2}`) into explicit `{$and:[{a:1},{b:2}]}` in any\n * non-field context that lacks `$and/$or`.\n * - Normalizes `Date` values to epoch milliseconds where allowed (numeric comparisons and array elements).\n * - Disallows `Date` at equality positions (including implicit equality).\n * - Validates shapes using the base class after translation.\n */\nexport class S3VectorsFilterTranslator extends BaseFilterTranslator<S3VectorsFilter> {\n /** @inheritdoc */\n protected override getSupportedOperators(): OperatorSupport {\n return {\n logical: ['$and', '$or'],\n basic: ['$eq', '$ne'],\n numeric: ['$gt', '$gte', '$lt', '$lte'],\n array: ['$in', '$nin'],\n element: ['$exists'],\n };\n }\n\n /**\n * Translates and validates a filter.\n * @param filter - Input filter; may be `undefined`, `null`, or `{}` (all treated as empty).\n * @returns The translated filter (or the original value if empty).\n */\n translate(filter?: S3VectorsFilter): any {\n if (this.isEmpty(filter)) return filter;\n // Perform translation (including Date → number normalization) before base shape validation.\n const translated = this.translateNode(filter as any, false);\n this.validateFilter(translated as any);\n return translated;\n }\n\n /**\n * Recursively translates a node.\n * @param node - Current node to translate.\n * @param inFieldValue - When `true`, the node is the value of a field (i.e., equality context).\n * @remarks\n * - In a **field-value** context, only primitives or operator objects are allowed.\n * - In a **non-field** context (root / logical branches), operator keys are processed;\n * plain keys become field equalities and are validated.\n * - Implicit AND is canonicalized in non-field contexts when multiple non-logical keys exist.\n */\n private translateNode(node: any, inFieldValue = false): any {\n // Primitive or Date (normalize when in a field-equality context)\n if (this.isPrimitive(node) || node instanceof Date) {\n return inFieldValue ? this.validateAndNormalizePrimitive(node) : node;\n }\n\n // Arrays are not allowed as direct equality values\n if (Array.isArray(node)) {\n if (inFieldValue) {\n throw new Error('Array equality is not supported in S3 Vectors. Use $in / $nin operators.');\n }\n return node;\n }\n\n // Object\n const entries = Object.entries(node as Record<string, any>);\n\n if (inFieldValue) {\n if (entries.length === 0) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n const allOperatorKeys = entries.every(([k]) => this.isOperator(k));\n if (!allOperatorKeys) {\n // Disallow shapes like: { field: { a:1, b:2 } }\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n const opEntries = entries.map(([key, value]) => [key, this.translateOperatorValue(key as QueryOperator, value)]);\n return Object.fromEntries(opEntries);\n }\n\n // Root / filter context\n const translatedEntries = entries.map(([key, value]) => {\n if (this.isOperator(key)) {\n return [key, this.translateOperatorValue(key as QueryOperator, value)];\n }\n return [key, this.translateNode(value, true)];\n });\n const obj = Object.fromEntries(translatedEntries);\n\n // Canonicalize implicit AND → explicit $and (if no $and/$or present and multiple non-logical keys)\n const keys = Object.keys(obj);\n const hasLogical = keys.some(k => k === '$and' || k === '$or');\n if (!hasLogical) {\n const nonLogical = keys.filter(k => k !== '$and' && k !== '$or');\n if (nonLogical.length > 1) {\n return { $and: nonLogical.map(k => ({ [k]: obj[k] })) };\n }\n }\n\n return obj;\n }\n\n /**\n * Translates a single operator and validates its value.\n * @param operator - One of the supported query operators.\n * @param value - Operator value to normalize/validate.\n */\n private translateOperatorValue(operator: QueryOperator, value: any): any {\n // Logical operators\n if (operator === '$and' || operator === '$or') {\n if (!Array.isArray(value) || value.length === 0) {\n throw new Error(`Value for logical operator ${operator} must be a non-empty array`);\n }\n return value.map(item => this.translateNode(item));\n }\n\n // Equality / inequality (Date is not allowed)\n if (operator === '$eq' || operator === '$ne') {\n if (value instanceof Date) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n return this.toPrimitiveForS3(value, operator);\n }\n\n // Numeric comparisons: require number; allow Date by converting to epoch ms\n if (operator === '$gt' || operator === '$gte' || operator === '$lt' || operator === '$lte') {\n const n = this.toNumberForRange(value, operator);\n return n;\n }\n\n // Array operators: non-empty arrays of primitives (Date converted to number)\n if (operator === '$in' || operator === '$nin') {\n if (!Array.isArray(value) || value.length === 0) {\n throw new Error(`Value for array operator ${operator} must be a non-empty array`);\n }\n return value.map(v => this.toPrimitiveForS3(v, operator));\n }\n\n // Existence check\n if (operator === '$exists') {\n if (typeof value !== 'boolean') {\n throw new Error(`Value for $exists operator must be a boolean`);\n }\n return value;\n }\n\n throw new Error(`Unsupported operator: ${operator}`);\n }\n\n /**\n * Normalizes a value to an S3-accepted primitive.\n * @param value - String | Number | Boolean | Date.\n * @param operatorForMessage - Operator name used in error messages.\n * @returns The normalized primitive; `Date` becomes epoch milliseconds.\n * @throws If the value is not a supported primitive or is null/undefined.\n */\n private toPrimitiveForS3(value: any, operatorForMessage: string): string | number | boolean {\n if (value === null || value === undefined) {\n // Error message for equality matches tests\n if (operatorForMessage === 'equality') {\n throw new Error('S3 Vectors does not support null/undefined for equality');\n }\n throw new Error(`Value for ${operatorForMessage} must be string, number, or boolean`);\n }\n if (value instanceof Date) {\n return value.getTime();\n }\n const t = typeof value;\n if (t === 'string' || t === 'boolean') return value;\n if (t === 'number') return Object.is(value, -0) ? 0 : value;\n throw new Error(`Value for ${operatorForMessage} must be string, number, or boolean`);\n }\n\n /**\n * Ensures a numeric value for range operators; allows `Date` by converting to epoch ms.\n * @param value - Candidate value.\n * @param operatorForMessage - Operator name used in error messages.\n * @throws If the value is not a number (or a Date).\n */\n private toNumberForRange(value: any, operatorForMessage: string): number {\n if (value instanceof Date) return value.getTime();\n if (typeof value === 'number' && !Number.isNaN(value)) return Object.is(value, -0) ? 0 : value;\n throw new Error(`Value for ${operatorForMessage} must be a number`);\n }\n\n /**\n * Validates and normalizes a primitive used in field equality (implicit `$eq`).\n * @param value - Candidate equality value.\n * @throws If the value is a `Date` or not a supported primitive.\n */\n private validateAndNormalizePrimitive(value: any): S3VectorsFieldValue {\n if (value instanceof Date) {\n throw new Error('Invalid equality value. Only string, number, or boolean are supported by S3 Vectors');\n }\n return this.toPrimitiveForS3(value, 'equality') as S3VectorsFieldValue;\n }\n\n /**\n * Determines whether a filter is considered empty.\n * @param filter - Input filter.\n */\n protected override isEmpty(filter: any): boolean {\n return filter === undefined || filter === null || (typeof filter === 'object' && Object.keys(filter).length === 0);\n }\n}\n","import {\n S3VectorsClient,\n CreateIndexCommand,\n DeleteIndexCommand,\n ListIndexesCommand,\n GetIndexCommand,\n PutVectorsCommand,\n QueryVectorsCommand,\n GetVectorsCommand,\n DeleteVectorsCommand,\n ListVectorsCommand,\n} from '@aws-sdk/client-s3vectors';\nimport type { S3VectorsClientConfig } from '@aws-sdk/client-s3vectors';\nimport { MastraError, ErrorDomain, ErrorCategory } from '@mastra/core/error';\nimport { createVectorErrorId } from '@mastra/core/storage';\nimport { MastraVector } from '@mastra/core/vector';\nimport type {\n QueryResult,\n IndexStats,\n CreateIndexParams,\n UpsertVectorParams,\n DeleteVectorsParams,\n QueryVectorParams,\n DescribeIndexParams,\n DeleteIndexParams,\n DeleteVectorParams,\n UpdateVectorParams,\n} from '@mastra/core/vector';\nimport { v4 as uuidv4 } from 'uuid';\nimport { S3VectorsFilterTranslator } from './filter';\nimport type { S3VectorsFilter } from './filter';\n\n/**\n * Options for the S3Vectors store.\n * @property vectorBucketName - Target S3 Vectors bucket name.\n * @property clientConfig - AWS SDK client options (e.g., region/credentials).\n * @property nonFilterableMetadataKeys - Metadata keys that must not be filterable (forwarded to S3 Vectors).\n */\nexport interface S3VectorsOptions {\n vectorBucketName: string;\n clientConfig?: S3VectorsClientConfig;\n nonFilterableMetadataKeys?: string[];\n}\n\ntype S3DistanceMetric = 'cosine' | 'euclidean';\ntype MastraMetric = NonNullable<CreateIndexParams['metric']>;\ntype SupportedMastraMetric = Exclude<MastraMetric, 'dotproduct'>;\n\n/**\n * Vector store backed by Amazon S3 Vectors.\n *\n * @remarks\n * - Supports `cosine` and `euclidean` distance metrics.\n * - Filters must use explicit logical operators (`$and` / `$or`). The attached translator\n * canonicalizes implicit AND (e.g., `{a:1,b:2}` → `{ $and: [{a:1},{b:2}] }`) where permitted by spec.\n * - Methods wrap AWS errors in `MastraError` with domain/category metadata.\n */\nexport class S3Vectors extends MastraVector<S3VectorsFilter> {\n private readonly client: S3VectorsClient;\n private readonly vectorBucketName: string;\n private readonly nonFilterableMetadataKeys?: string[];\n private readonly filterTranslator = new S3VectorsFilterTranslator();\n\n private static readonly METRIC_MAP: Record<SupportedMastraMetric, S3DistanceMetric> = {\n cosine: 'cosine',\n euclidean: 'euclidean',\n } as const;\n\n constructor(opts: S3VectorsOptions & { id: string }) {\n super({ id: opts.id });\n if (!opts?.vectorBucketName) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'INITIALIZATION', 'MISSING_BUCKET_NAME'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n },\n new Error('vectorBucketName is required'),\n );\n }\n this.vectorBucketName = opts.vectorBucketName;\n this.nonFilterableMetadataKeys = opts.nonFilterableMetadataKeys;\n this.client = new S3VectorsClient({ ...(opts.clientConfig ?? {}) });\n }\n\n /**\n * No-op to satisfy the base interface.\n *\n * @remarks The AWS SDK manages HTTP per request; no persistent connection is needed.\n */\n async connect(): Promise<void> {}\n\n /**\n * Closes the underlying AWS SDK HTTP handler to free sockets.\n */\n async disconnect(): Promise<void> {\n try {\n this.client.destroy();\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DISCONNECT', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n },\n error,\n );\n }\n }\n\n /**\n * Creates an index or validates an existing one.\n *\n * @param params.indexName - Logical index name; normalized internally.\n * @param params.dimension - Vector dimension (must be a positive integer).\n * @param params.metric - Distance metric (`cosine` | `euclidean`). Defaults to `cosine`.\n * @throws {MastraError} If arguments are invalid or AWS returns an error.\n * @remarks\n * On `ConflictException`, we verify the existing index schema via the parent implementation\n * and return if it matches.\n */\n async createIndex({ indexName, dimension, metric = 'cosine' }: CreateIndexParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n\n let s3Metric: S3DistanceMetric;\n try {\n assertPositiveInteger(dimension, 'dimension');\n s3Metric = S3Vectors.toS3Metric(metric);\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'CREATE_INDEX', 'INVALID_ARGS'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n details: { indexName, dimension, metric },\n },\n error,\n );\n }\n\n try {\n const input: any = {\n ...this.bucketParams(),\n indexName,\n dataType: 'float32',\n dimension,\n distanceMetric: s3Metric,\n };\n if (this.nonFilterableMetadataKeys?.length) {\n input.metadataConfiguration = { nonFilterableMetadataKeys: this.nonFilterableMetadataKeys };\n }\n\n await this.client.send(new CreateIndexCommand(input));\n } catch (error: any) {\n if (error?.name === 'ConflictException') {\n await this.validateExistingIndex(indexName, dimension, metric);\n return;\n }\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'CREATE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName, dimension, metric },\n },\n error,\n );\n }\n }\n\n /**\n * Upserts vectors in bulk.\n *\n * @param params.indexName - Index to write to.\n * @param params.vectors - Array of vectors; each must match the index dimension.\n * @param params.metadata - Optional metadata per vector; `Date` values are normalized to epoch ms.\n * @param params.ids - Optional explicit IDs; if omitted, UUIDs are generated.\n * @returns Array of IDs used for the upsert (explicit or generated).\n * @throws {MastraError} If validation fails or AWS returns an error.\n */\n async upsert({ indexName, vectors, metadata, ids }: UpsertVectorParams): Promise<string[]> {\n indexName = normalizeIndexName(indexName);\n try {\n const { dimension } = await this.getIndexInfo(indexName);\n validateVectorDimensions(vectors, dimension);\n\n const generatedIds = ids ?? vectors.map(() => uuidv4());\n\n const putInput = {\n ...this.bucketParams(),\n indexName,\n vectors: vectors.map((vec, i) => ({\n key: generatedIds[i],\n data: { float32: vec },\n metadata: normalizeMetadata(metadata?.[i]),\n })),\n };\n\n await this.client.send(new PutVectorsCommand(putInput));\n return generatedIds;\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'UPSERT', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Queries nearest neighbors.\n *\n * @param params.indexName - Target index.\n * @param params.queryVector - Query vector (non-empty float32 array).\n * @param params.topK - Number of neighbors to return (positive integer). Defaults to 10.\n * @param params.filter - Metadata filter using explicit `$and`/`$or` (translator canonicalizes implicit AND).\n * @param params.includeVector - If `true`, fetches missing vector data in a second call.\n * @returns Results sorted by `score` descending.\n * @throws {MastraError} If validation fails or AWS returns an error.\n * @remarks\n * `score = 1/(1+distance)` (monotonic transform), so ranking matches the underlying distance.\n */\n async query({\n indexName,\n queryVector,\n topK = 10,\n filter,\n includeVector = false,\n }: QueryVectorParams<S3VectorsFilter>): Promise<QueryResult[]> {\n indexName = normalizeIndexName(indexName);\n\n if (!queryVector) {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'QUERY', 'MISSING_VECTOR'),\n text: 'queryVector is required for S3 Vectors queries. Metadata-only queries are not supported by this vector store.',\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n details: { indexName },\n });\n }\n\n try {\n if (!Array.isArray(queryVector) || queryVector.length === 0) {\n throw new Error('queryVector must be a non-empty float32 array');\n }\n assertPositiveInteger(topK, 'topK');\n\n const translated = this.transformFilter(filter);\n\n const out = await this.client.send(\n new QueryVectorsCommand({\n ...this.bucketParams(),\n indexName,\n topK,\n queryVector: { float32: queryVector },\n filter: translated && Object.keys(translated).length > 0 ? (translated as any) : undefined,\n returnMetadata: true,\n returnDistance: true,\n }),\n );\n\n const vectors = (out.vectors ?? []).filter(v => !!v?.key);\n\n // Query results don't include vector data; fetch via GetVectors when requested.\n let dataMap: Record<string, number[] | undefined> | undefined;\n if (includeVector) {\n const keys = vectors.filter(v => v.key).map(v => v.key!) as string[];\n\n if (keys.length > 0) {\n const got = await this.client.send(\n new GetVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys,\n returnData: true,\n returnMetadata: false,\n }),\n );\n dataMap = {};\n for (const g of got.vectors ?? []) {\n if (g.key) dataMap[g.key] = g.data?.float32 as number[] | undefined;\n }\n }\n }\n\n return vectors.map(v => {\n const id = v.key!;\n const score = S3Vectors.distanceToScore(v.distance ?? 0);\n\n const result: QueryResult = { id, score };\n\n const md = v.metadata as Record<string, unknown> | undefined;\n if (md !== undefined) result.metadata = md;\n\n if (includeVector) {\n const vec = dataMap?.[id];\n if (vec !== undefined) result.vector = vec;\n }\n\n return result;\n });\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'QUERY', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Lists indexes within the configured bucket.\n *\n * @returns Array of index names.\n * @throws {MastraError} On AWS errors.\n */\n async listIndexes(): Promise<string[]> {\n try {\n const names: string[] = [];\n let nextToken: string | undefined;\n\n do {\n const out = await this.client.send(\n new ListIndexesCommand({\n ...this.bucketParams(),\n nextToken,\n } as any),\n );\n for (const idx of out.indexes ?? []) {\n if (idx.indexName) names.push(idx.indexName);\n }\n nextToken = out.nextToken;\n } while (nextToken);\n\n return names;\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'LIST_INDEXES', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n },\n error,\n );\n }\n }\n\n /**\n * Returns index attributes.\n *\n * @param params.indexName - Index name.\n * @returns Object containing `dimension`, `metric`, and `count`.\n * @throws {MastraError} On AWS errors.\n * @remarks\n * `count` is computed via `ListVectors` pagination and may be costly (O(n)).\n */\n async describeIndex({ indexName }: DescribeIndexParams): Promise<IndexStats> {\n indexName = normalizeIndexName(indexName);\n try {\n const { dimension, metric } = await this.getIndexInfo(indexName);\n const count = await this.countVectors(indexName);\n return { dimension, metric, count };\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DESCRIBE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Deletes an index.\n *\n * @param params.indexName - Index name.\n * @throws {MastraError} On AWS errors.\n */\n async deleteIndex({ indexName }: DeleteIndexParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n try {\n await this.client.send(new DeleteIndexCommand({ ...this.bucketParams(), indexName } as any));\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DELETE_INDEX', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: { indexName },\n },\n error,\n );\n }\n }\n\n /**\n * Updates (replaces) a vector and/or its metadata by ID.\n *\n * @param params.indexName - Target index.\n * @param params.id - Vector ID.\n * @param params.update.vector - New vector; if omitted, the existing vector is reused.\n * @param params.update.metadata - New metadata, merged with current metadata.\n * @throws {MastraError} If the vector does not exist and `update.vector` is omitted, or on AWS error.\n * @remarks\n * S3 Vectors `PutVectors` is replace-all; we `Get` the current item, merge, then `Put`.\n */\n async updateVector({ indexName, id, update }: UpdateVectorParams): Promise<void> {\n if (!id) {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'UPDATE_VECTOR', 'INVALID_ARGS'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.USER,\n text: 'id is required for S3Vectors updateVector',\n details: { indexName },\n });\n }\n\n indexName = normalizeIndexName(indexName);\n try {\n if (!update.vector && !update.metadata) {\n throw new Error('No updates provided');\n }\n\n const got = await this.client.send(\n new GetVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: [id],\n returnData: true,\n returnMetadata: true,\n }),\n );\n const current = (got.vectors ?? [])[0];\n\n const newVector: number[] | undefined = update.vector ?? (current?.data?.float32 as number[] | undefined);\n if (!newVector) {\n throw new Error(`Vector \"${id}\" not found. Provide update.vector to create it.`);\n }\n\n const newMetadata =\n update.metadata !== undefined\n ? normalizeMetadata(update.metadata)\n : ((current?.metadata as Record<string, any>) ?? {});\n\n await this.client.send(\n new PutVectorsCommand({\n ...this.bucketParams(),\n indexName,\n vectors: [{ key: id, data: { float32: newVector }, metadata: newMetadata }],\n }),\n );\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'UPDATE_VECTOR', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: {\n indexName,\n ...(id && { id }),\n },\n },\n error,\n );\n }\n }\n\n /**\n * Deletes a vector by ID.\n *\n * @param params.indexName - Target index.\n * @param params.id - Vector ID to delete.\n * @throws {MastraError} On AWS errors.\n */\n async deleteVector({ indexName, id }: DeleteVectorParams): Promise<void> {\n indexName = normalizeIndexName(indexName);\n try {\n await this.client.send(\n new DeleteVectorsCommand({\n ...this.bucketParams(),\n indexName,\n keys: [id],\n }),\n );\n } catch (error) {\n throw new MastraError(\n {\n id: createVectorErrorId('S3VECTORS', 'DELETE_VECTOR', 'FAILED'),\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.THIRD_PARTY,\n details: {\n indexName,\n ...(id && { id }),\n },\n },\n error,\n );\n }\n }\n\n async deleteVectors({ indexName, filter, ids }: DeleteVectorsParams): Promise<void> {\n throw new MastraError({\n id: createVectorErrorId('S3VECTORS', 'DELETE_VECTORS', 'NOT_SUPPORTED'),\n text: 'deleteVectors is not yet implemented for S3Vectors vector store',\n domain: ErrorDomain.STORAGE,\n category: ErrorCategory.SYSTEM,\n details: {\n indexName,\n ...(filter && { filter: JSON.stringify(filter) }),\n ...(ids && { idsCount: ids.length }),\n },\n });\n }\n\n // -------- internal helpers --------\n\n /**\n * Returns shared bucket parameters for AWS SDK calls.\n * @internal\n */\n private bucketParams(): { vectorBucketName: string } {\n return { vectorBucketName: this.vectorBucketName };\n }\n\n /**\n * Retrieves index dimension/metric via `GetIndex`.\n * @internal\n * @throws {Error} If the index does not exist.\n * @returns `{ dimension, metric }`, where `metric` includes `'dotproduct'` to satisfy Mastra types (S3 never returns it).\n */\n private async getIndexInfo(\n indexName: string,\n ): Promise<{ dimension: number; metric: 'cosine' | 'euclidean' | 'dotproduct' }> {\n const out = await this.client.send(new GetIndexCommand({ ...this.bucketParams(), indexName } as any));\n const idx = out.index;\n if (!idx) throw new Error(`Index \"${indexName}\" not found`);\n const metric = (idx.distanceMetric as S3DistanceMetric) ?? 'cosine';\n return {\n dimension: idx.dimension ?? 0,\n metric,\n };\n }\n\n /**\n * Pages through `ListVectors` and counts total items.\n * @internal\n * @remarks O(n). Avoid calling on hot paths.\n */\n private async countVectors(indexName: string): Promise<number> {\n let total = 0;\n let nextToken: string | undefined;\n\n do {\n const out = await this.client.send(\n new ListVectorsCommand({\n ...this.bucketParams(),\n indexName,\n maxResults: 1000,\n nextToken,\n returnData: false,\n returnMetadata: false,\n }),\n );\n total += (out.vectors ?? []).length;\n nextToken = out.nextToken;\n } while (nextToken);\n\n return total;\n }\n\n /**\n * Translates a high-level filter to the S3 Vectors filter shape.\n * @internal\n * @remarks Implicit AND is canonicalized by the translator where permitted by spec.\n */\n private transformFilter(filter?: S3VectorsFilter): any {\n if (!filter) return undefined;\n return this.filterTranslator.translate(filter);\n }\n\n /**\n * Converts a Mastra metric to an S3 metric.\n * @internal\n * @throws {Error} If the metric is not supported by S3 Vectors.\n */\n private static toS3Metric(metric: MastraMetric): S3DistanceMetric {\n const m = S3Vectors.METRIC_MAP[metric as SupportedMastraMetric];\n if (!m) {\n throw new Error(`Invalid metric: \"${metric}\". S3 Vectors supports only: cosine, euclidean`);\n }\n return m;\n }\n\n /**\n * Monotonic transform from distance (smaller is better) to score (larger is better).\n * @returns Number in (0, 1], preserving ranking.\n */\n private static distanceToScore(distance: number): number {\n return 1 / (1 + distance);\n }\n}\n\n// --- module-private utilities (not exported) ---\n\n/**\n * Ensures a value is a positive integer.\n * @throws {Error} If the value is not a positive integer.\n * @internal\n */\nfunction assertPositiveInteger(value: number, name: string): void {\n if (!Number.isInteger(value) || value <= 0) {\n throw new Error(`${name} must be a positive integer`);\n }\n}\n\n/**\n * Validates that all vectors match the required dimension.\n * @throws {Error} If any vector length differs from `dimension`.\n * @internal\n */\nfunction validateVectorDimensions(vectors: number[][], dimension: number): void {\n if (!Array.isArray(vectors) || vectors.length === 0) {\n throw new Error('No vectors provided for validation');\n }\n for (let i = 0; i < vectors.length; i++) {\n const len = vectors[i]?.length;\n if (len !== dimension) {\n throw new Error(`Vector at index ${i} has invalid dimension ${len}. Expected ${dimension} dimensions.`);\n }\n }\n}\n\n/**\n * Normalizes metadata values for S3 Vectors: `Date` → epoch ms.\n * @internal\n */\nfunction normalizeMetadata(meta: Record<string, any> | undefined): Record<string, any> {\n if (!meta) return {};\n const out: Record<string, any> = {};\n for (const [k, v] of Object.entries(meta)) {\n out[k] = v instanceof Date ? v.getTime() : v;\n }\n return out;\n}\n\n/**\n * Normalizes an index name to this store's canonical form (underscore → hyphen, lowercase).\n * @internal\n * @throws {TypeError} If the provided name is not a string.\n */\nfunction normalizeIndexName(str: string) {\n if (typeof str !== 'string') {\n throw new TypeError('Index name must be a string');\n }\n return str.replace(/_/g, '-').toLowerCase();\n}\n","/**\n * Vector store specific prompt that details supported operators and examples.\n * This prompt helps users construct valid filters for Amazon S3 Vectors.\n */\nexport const S3VECTORS_PROMPT = `When querying Amazon S3 Vectors, you can ONLY use the operators listed below. Any other operators will be rejected.\nImportant: Don't explain how to construct the filter - use the specified operators and fields to search the content and return relevant results.\nIf a user tries to give an explicit operator that is not supported, reject the filter entirely and let them know that the operator is not supported.\n\nBasic Comparison Operators:\n- $eq: Exact match (default when using field: value)\n Example: { \"category\": \"electronics\" }\n- $ne: Not equal\n Example: { \"category\": { \"$ne\": \"electronics\" } }\n- $gt: Greater than\n Example: { \"price\": { \"$gt\": 100 } }\n- $gte: Greater than or equal\n Example: { \"price\": { \"$gte\": 100 } }\n- $lt: Less than\n Example: { \"price\": { \"$lt\": 100 } }\n- $lte: Less than or equal\n Example: { \"price\": { \"$lte\": 100 } }\n\nArray Operators (non-empty arrays of string | number | boolean):\n- $in: Match any value in array\n Example: { \"category\": { \"$in\": [\"electronics\", \"books\"] } }\n- $nin: Does not match any value in array\n Example: { \"category\": { \"$nin\": [\"electronics\", \"books\"] } }\n\nLogical Operators:\n- $and: Logical AND (can be implicit or explicit)\n Implicit Example: { \"price\": { \"$gt\": 100 }, \"category\": \"electronics\" }\n Explicit Example: { \"$and\": [{ \"price\": { \"$gt\": 100 } }, { \"category\": \"electronics\" }] }\n- $or: Logical OR\n Example: { \"$or\": [{ \"price\": { \"$lt\": 50 } }, { \"category\": \"books\" }] }\n\nElement Operators:\n- $exists: Check if field exists\n Example: { \"rating\": { \"$exists\": true } }\n\nUnsupported / Disallowed Operators (REJECT if present):\n- $not, $nor, $regex, $all, $elemMatch, $size, $text (and any operator not listed as supported)\n\nRestrictions:\n- Only logical operators ($and, $or) can be used at the top level\n- Empty arrays for $and / $or / $in / $nin are NOT allowed\n- Nested fields are supported using dot notation\n- Multiple conditions on the same field are supported\n- At least one key-value pair is required in filter object\n- Empty objects and undefined values are treated as no filter\n- Invalid types in comparison operators will throw errors\n- All non-logical operators must be used within a field condition\n Valid: { \"field\": { \"$gt\": 100 } }\n Valid: { \"$and\": [...] }\n Invalid: { \"$gt\": 100 }\n- Logical operators must contain field conditions, not direct operators\n Valid: { \"$and\": [{ \"field\": { \"$gt\": 100 } }] }\n Invalid: { \"$and\": [{ \"$gt\": 100 }] }\n- Logical operators ($and, $or):\n - Can only be used at top level or nested within other logical operators\n - Can not be used on a field level, or be nested inside a field\n - Can not be used inside an operator\n - Valid: { \"$and\": [{ \"field\": { \"$gt\": 100 } }] }\n - Valid: { \"$or\": [{ \"$and\": [{ \"field\": { \"$gt\": 100 } }] }] }\n - Invalid: { \"field\": { \"$and\": [{ \"$gt\": 100 }] } }\n - Invalid: { \"field\": { \"$or\": [{ \"$gt\": 100 }] } }\n - Invalid: { \"field\": { \"$gt\": { \"$and\": [{...}] } } }\n- Equality values must be string, number, or boolean (arrays and objects are not allowed for equality)\n- Filters operate only on filterable metadata keys; using a non-filterable key will fail\n- Filterable metadata values are primitives (string/number/boolean) or arrays of primitives; large/long-text fields should be non-filterable and are not usable in filters\n\nExample Complex Query:\n{\n \"$and\": [\n { \"category\": { \"$in\": [\"electronics\", \"computers\"] } },\n { \"price\": { \"$gte\": 100, \"$lte\": 1000 } },\n { \"$or\": [\n { \"stock\": { \"$gt\": 0 } },\n { \"preorder\": true }\n ] }\n ]\n}`;\n"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@mastra/s3vectors",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.2",
|
|
4
4
|
"description": "Amazon S3 Vectors store provider for Mastra",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"files": [
|
|
@@ -24,22 +24,22 @@
|
|
|
24
24
|
},
|
|
25
25
|
"license": "Apache-2.0",
|
|
26
26
|
"dependencies": {
|
|
27
|
-
"@aws-sdk/client-s3vectors": "^3.
|
|
27
|
+
"@aws-sdk/client-s3vectors": "^3.1004.0",
|
|
28
28
|
"uuid": "^13.0.0"
|
|
29
29
|
},
|
|
30
30
|
"devDependencies": {
|
|
31
|
-
"@types/node": "22.19.
|
|
31
|
+
"@types/node": "22.19.13",
|
|
32
32
|
"@vitest/coverage-v8": "4.0.18",
|
|
33
33
|
"@vitest/ui": "4.0.18",
|
|
34
|
-
"dotenv": "^17.
|
|
35
|
-
"eslint": "^9.
|
|
34
|
+
"dotenv": "^17.3.1",
|
|
35
|
+
"eslint": "^9.39.4",
|
|
36
36
|
"tsup": "^8.5.1",
|
|
37
37
|
"typescript": "^5.9.3",
|
|
38
38
|
"vitest": "4.0.18",
|
|
39
|
-
"@internal/lint": "0.0.
|
|
40
|
-
"@internal/storage-test-utils": "0.0.
|
|
41
|
-
"@internal/types-builder": "0.0.
|
|
42
|
-
"@mastra/core": "1.
|
|
39
|
+
"@internal/lint": "0.0.67",
|
|
40
|
+
"@internal/storage-test-utils": "0.0.63",
|
|
41
|
+
"@internal/types-builder": "0.0.42",
|
|
42
|
+
"@mastra/core": "1.11.0"
|
|
43
43
|
},
|
|
44
44
|
"peerDependencies": {
|
|
45
45
|
"@mastra/core": ">=1.0.0-0 <2.0.0-0"
|