@upstash/vector 0.1.0-alpha → 0.1.0-alpha-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/README.md CHANGED
@@ -1,15 +1,221 @@
1
- # vector-sdk
1
+ # Upstash Vector Node.js Client
2
2
 
3
- To install dependencies:
3
+ This is the official Node.js client for [Upstash](https://upstash.com/), written in TypeScript.
4
4
 
5
- ```bash
6
- bun install
5
+ ## Documentation
6
+
7
+ - [**Reference Documentation**](https://upstash.com/docs/vector/overall/getstarted)
8
+
9
+ ## Installation
10
+
11
+ ```
12
+ npm install @upstash/vector
13
+ pnpm add @upstash/vector
7
14
  ```
8
15
 
9
- To run:
16
+ ## Usage
17
+
18
+ ### Initializing the client
19
+
20
+ There are two pieces of configuration required to use the Upstash vector client: an REST token and REST URL. These values can be passed using environment variables or in code through a configuration object. Find your configuration values in the console dashboard at [https://console.upstash.com/](https://console.upstash.com/).
21
+
22
+ #### Using environment variables
23
+
24
+ The environment variables used to configure the client are the following:
10
25
 
11
26
  ```bash
12
- bun run index.ts
27
+ UPSTASH_VECTOR_REST_URL="your_rest_url"
28
+ UPSTASH_VECTOR_REST_TOKEN="your_rest_token"
29
+ ```
30
+
31
+ When these environment variables are set, the client constructor does not require any additional arguments.
32
+
33
+ ```typescript
34
+ import { fromEnv } from "@upstash/vector";
35
+
36
+ const index = fromEnv();
37
+ ```
38
+
39
+ #### Using a configuration object
40
+
41
+ If you prefer to pass configuration in code, the constructor accepts a config object containing the `url` and `token` values. This
42
+ could be useful if your application needs to interact with multiple projects, each with a different configuration.
43
+
44
+ ```typescript
45
+ import { Index } from "@upstash/vector";
46
+
47
+ const index = new Index({
48
+ url: "<UPSTASH_VECTOR_REST_URL>",
49
+ token: "<UPSTASH_VECTOR_REST_TOKEN>",
50
+ });
51
+ ```
52
+
53
+ ## Index operations
54
+
55
+ Upstash vector indexes support operations for working with vector data using operations such as upsert, query, fetch, and delete.
56
+
57
+ ### Targeting an index
58
+
59
+ To perform data operations on an index, you target it using the `index` method.
60
+
61
+ ```typescript
62
+ const index = new Index();
63
+
64
+ // Now perform index operations
65
+ await index.fetch([1, 2, 3], { includeMetadata: true, includeVectors: true });
66
+ ```
67
+
68
+ ### Targeting an index, with metadata typing
69
+
70
+ If you are storing metadata alongside your vector values, you can pass a type parameter to `index()` in order to get proper TypeScript typechecking.
71
+
72
+ ```typescript
73
+ const index = new Index();
74
+
75
+ type Metadata = {
76
+ title: string,
77
+ genre: 'sci-fi' | 'fantasy' | 'horror' | 'action'
78
+ }
79
+
80
+ await index.upsert([{
81
+ id: '1234',
82
+ vector: [
83
+ .... // embedding values
84
+ ],
85
+ metadata: {
86
+ title: 'Lord of The Rings',
87
+ genre: 'drama',
88
+ category: 'classic'
89
+ }
90
+ }])
91
+
92
+ const results = await index.query<Metadata>({
93
+ vector: [
94
+ ... // query embedding
95
+ ],
96
+ includeVectors: true,
97
+ topK: 1,
98
+ })
99
+
100
+ if (results[0].metadata) {
101
+ // Since we passed the Metadata type parameter above,
102
+ // we can interact with metadata fields without having to
103
+ // do any typecasting.
104
+ const { title, genre, category } = movie.metadata;
105
+ console.log(`The best match in fantasy was ${title}`)
106
+ }
13
107
  ```
14
108
 
15
- This project was created using `bun init` in bun v1.0.4. [Bun](https://bun.sh) is a fast all-in-one JavaScript runtime.
109
+ ### Upsert records
110
+
111
+ Upstash vector expects records inserted into indexes to have the following form:
112
+
113
+ ```typescript
114
+ type UpstashRecord = {
115
+ id: number | string;
116
+ vector: number[];
117
+ metadata?: Record<string, unknown>;
118
+ };
119
+ ```
120
+
121
+ To upsert some records, you can use the client like so:
122
+
123
+ ```typescript
124
+ const index = new Index();
125
+
126
+ // Prepare your data. The length of each array
127
+ // of vector values must match the dimension of
128
+ // the index where you plan to store them.
129
+ const records = [
130
+ {
131
+ id: "1",
132
+ vector: [0.236, 0.971, 0.559],
133
+ },
134
+ {
135
+ id: "2",
136
+ vector: [0.685, 0.111, 0.857],
137
+ },
138
+ ];
139
+
140
+ // Upsert the data into your index
141
+ await index.upsert(records);
142
+ ```
143
+
144
+ ### Querying
145
+
146
+ #### Querying with vector values
147
+
148
+ The query method accepts a large number of options. The dimension of the query vector must match the dimension of your index.
149
+
150
+ ```typescript
151
+ type QueryOptions = {
152
+ vector: number[];
153
+ topK: number;
154
+ includeVectors?: boolean;
155
+ includeMetadata?: boolean;
156
+ };
157
+ ```
158
+
159
+ For example, to query by vector values you would pass the `vector` param in the options configuration. For brevity sake this example query vector is tiny (dimension 2), but in a more realistic use case this query vector would be an embedding outputted by a model. Look at the [Example code](#example-code) to see more realistic examples of how to use `query`.
160
+
161
+ ```typescript
162
+ > await index.query({ topK: 3, vector: [ 0.22, 0.66 ]})
163
+ {
164
+ matches: [
165
+ {
166
+ id: '6345',
167
+ score: 1.00000012,
168
+ vector: [],
169
+ metadata: undefined
170
+ },
171
+ {
172
+ id: '1233',
173
+ score: 1.00000012,
174
+ vector: [],
175
+ metadata: undefined
176
+ },
177
+ {
178
+ id: '4142',
179
+ score: 1.00000012,
180
+ vector: [],
181
+ metadata: undefined
182
+ }
183
+ ],
184
+ namespace: ''
185
+ }
186
+ ```
187
+
188
+ You include options to `includeMetadata: true` or `includeVectors: true` if you need this information. By default these are not returned to keep the response payload small.
189
+
190
+ ### Update a record
191
+
192
+ You may want to update vector `vector` or `metadata`. Specify the id and the attribute value you want to update.
193
+
194
+ ```typescript
195
+ await index.upsert({
196
+ id: "18593",
197
+ metadata: { genre: "romance" },
198
+ });
199
+ ```
200
+
201
+ ### Fetch records by their IDs
202
+
203
+ ```typescript
204
+ const fetchResult = await index.fetch(["id-1", "id-2"]);
205
+ ```
206
+
207
+ ### Delete records
208
+
209
+ For convenience there are several delete-related options. You can verify the results of a delete operation by trying to `fetch()` a record.
210
+
211
+ #### Delete one
212
+
213
+ ```typescript
214
+ await index.delete("id-to-delete");
215
+ ```
216
+
217
+ #### Delete many by id
218
+
219
+ ```typescript
220
+ await index.delete(["id-1", "id-2", "id-3"]);
221
+ ```
package/dist/index.d.mts CHANGED
@@ -42,12 +42,6 @@ type RequesterConfig = {
42
42
  cache?: CacheSetting;
43
43
  };
44
44
 
45
- type Vector<TMetadata> = {
46
- id: string;
47
- vector: number[];
48
- metadata?: TMetadata;
49
- };
50
-
51
45
  declare const ENDPOINTS: readonly ["upsert", "query", "delete", "fetch", "reset", "range"];
52
46
  type EndpointVariants = (typeof ENDPOINTS)[number];
53
47
  /**
@@ -63,55 +57,17 @@ declare class Command<TResult> {
63
57
  exec(client: Requester): Promise<TResult>;
64
58
  }
65
59
 
66
- /**
67
- * Payload Type Definition for DeleteCommand
68
- *
69
- * This type defines the structure of the payload specifically used in the DeleteCommand.
70
- *
71
- * Properties:
72
- * - ids: An array of numbers or strings representing the unique identifiers of the records to be deleted. These could be database IDs, unique keys, or any identifier used to uniquely refer to records in a specific context.
73
- *
74
- * Usage:
75
- * This type is typically used in scenarios where a batch deletion of records is required. The `ids` array allows specifying multiple records for deletion in a single command, thereby facilitating efficient bulk operations.
76
- */
77
- type Payload$4 = {
78
- ids: number[] | string[];
79
- };
80
- /**
81
- * DeleteCommand Class
82
- *
83
- * This class extends the generic Command class to implement the deletion functionality.
84
- *
85
- * Example:
86
- * ```
87
- * const deletionIds = [123, 456, 789];
88
- * const deleteCommand = new DeleteCommand({ ids: deletionIds });
89
- * // Use deleteCommand to execute the deletion operation
90
- * ```
91
- */
92
- declare class DeleteCommand extends Command<string> {
93
- constructor(payload: Payload$4);
60
+ declare class DeleteCommand extends Command<{
61
+ deleted: number;
62
+ }> {
63
+ constructor(id: (number[] | string[]) | number | string);
94
64
  }
95
65
 
96
- /**
97
- * Payload Type Definition
98
- *
99
- * This type defines the structure of the payload used in a specific function or API call.
100
- *
101
- * Properties:
102
- * - vector: An array of numbers representing a specific vector. This could be coordinates, data points, or any numerical representation depending on the context of the function or API.
103
- *
104
- * - topK: A number indicating the 'top K' elements to be considered or returned. In many contexts, this refers to the top 'K' results, items, or entities based on certain criteria like highest score, most relevance, etc.
105
- *
106
- * - includeVectors: A boolean value indicating whether to include the vector data in the response or output. Setting this to 'true' includes the vector data.
107
- *
108
- * Usage:
109
- * This type is typically used when sending or receiving data where a combination of a numerical vector, a limit on the number of elements to consider, and an option to include or exclude detailed vector data is required.
110
- */
111
- type Payload$3 = {
66
+ type QueryCommandPayload = {
112
67
  vector: number[];
113
68
  topK: number;
114
- includeVectors: boolean;
69
+ includeVectors?: boolean;
70
+ includeMetadata?: boolean;
115
71
  };
116
72
  type QueryReturnResponse<TMetadata> = {
117
73
  id: number | string;
@@ -119,141 +75,39 @@ type QueryReturnResponse<TMetadata> = {
119
75
  vector: number[];
120
76
  metadata?: TMetadata;
121
77
  };
122
- /**
123
- * QueryCommand Class
124
- * Example:
125
- * ```
126
- * const payload = { vector: [1, 2, 3], topK: 5, includeVectors: true };
127
- * const queryCommand = new QueryCommand(payload);
128
- * // Use queryCommand for further operations
129
- * ```
130
- */
131
- declare class QueryCommand<TResult> extends Command<QueryReturnResponse<TResult>[]> {
132
- constructor(payload: Payload$3);
78
+ declare class QueryCommand<TMetadata> extends Command<QueryReturnResponse<TMetadata>[]> {
79
+ constructor(payload: QueryCommandPayload);
133
80
  }
134
81
 
135
- /**
136
- * Payload Type Definition for UpsertCommand
137
- *
138
- * This type defines the structure of the payload used in the UpsertCommand.
139
- *
140
- * Properties:
141
- * - id: A number or string representing the unique identifier of the record to be upserted (inserted or updated).
142
- * - vector: An array of numbers representing a specific vector. This could be coordinates, data points, or any numerical representation depending on the context.
143
- * - metadata (optional): An object with key-value pairs, where the keys are strings and the values are of unknown type. This allows for flexible and additional data to be associated with the record being upserted.
144
- *
145
- * Usage:
146
- * This type is primarily used in scenarios where a record needs to be inserted into a database if it does not already exist, or updated if it does. The flexibility of the metadata field allows for various additional information to be passed along with the primary data.
147
- */
148
- type Payload$2 = {
82
+ type UpsertCommandPayload = {
149
83
  id: number | string;
150
84
  vector: number[];
151
85
  metadata?: Record<string, unknown>;
152
86
  };
153
- /**
154
- * UpsertCommand Class
155
- *
156
- * Extends the generic Command class to implement an upsert (insert or update) operation.
157
- *
158
- * Example:
159
- * ```
160
- * const upsertPayload = { id: 123, vector: [1.1, 2.2, 3.3], metadata: { key: "value" } };
161
- * const upsertCommand = new UpsertCommand(upsertPayload);
162
- * // Use upsertCommand to execute the upsert operation
163
- * ```
164
- *
165
- * The UpsertCommand takes a payload containing the necessary data for the upsert operation. It supports handling both insertion and update of records based on the provided identifier.
166
- */
167
87
  declare class UpsertCommand extends Command<string> {
168
- constructor(payload: Payload$2);
88
+ constructor(payload: UpsertCommandPayload | UpsertCommandPayload[]);
169
89
  }
170
90
 
171
- /**
172
- * Type definition for FetchCommand payload
173
- *
174
- * Properties:
175
- * - ids: An array of numbers or strings, representing the unique identifiers of the records to be fetched.
176
- * - includeMetadata (optional): A boolean flag indicating whether to include metadata in the response.
177
- * - includeVectors (optional): A boolean flag indicating whether to include vector data in the response.
178
- *
179
- * The Payload type is used in the FetchCommand to specify the data required to fetch specific records.
180
- * The optional flags allow for more detailed responses depending on the requirements.
181
- */
182
- type Payload$1 = {
183
- ids: number[] | string[];
184
- includeMetadata?: boolean;
185
- includeVectors?: boolean;
91
+ type Vector<TMetadata> = {
92
+ id: string;
93
+ vector: number[];
94
+ metadata?: TMetadata;
186
95
  };
187
- /**
188
- * Generic response type for FetchCommand
189
- *
190
- * This type represents the possible return type of a FetchCommand. It can be either a Vector
191
- * containing metadata or null, depending on whether the fetch operation was successful or not.
192
- */
96
+
193
97
  type FetchReturnResponse<TMetadata> = Vector<TMetadata> | null;
194
- /**
195
- * FetchCommand Class
196
- *
197
- * Extends the generic Command class to implement a fetch operation.
198
- *
199
- * Example:
200
- * ```
201
- * const fetchPayload = { ids: [1, 2, 3], includeMetadata: true };
202
- * const fetchCommand = new FetchCommand(fetchPayload);
203
- * // Use fetchCommand to execute the fetch operation
204
- * ```
205
- */
206
- declare class FetchCommand<TMetadata> extends Command<FetchReturnResponse<TMetadata>[]> {
207
- constructor(payload: Payload$1);
208
- }
209
98
 
210
- /**
211
- * Type definition for RangeCommand payload
212
- *
213
- * This type specifies the structure of the payload used in the RangeCommand.
214
- *
215
- * Properties:
216
- * - cursor: A number indicating the starting point for the range query.
217
- * - limit: A number specifying the maximum number of records to be returned.
218
- * - includeVectors (optional): A boolean flag indicating whether to include vector data in the response.
219
- * - includeMetadata (optional): A boolean flag indicating whether to include metadata in the response.
220
- *
221
- * This payload type is used for range queries, where a set of records is retrieved based on the specified cursor
222
- * and limit. The optional inclusion of vectors and metadata allows for flexible and detailed data retrieval.
223
- */
224
- type Payload = {
225
- cursor: number;
99
+ type RangeCommandPayload = {
100
+ cursor: number | string;
226
101
  limit: number;
227
102
  includeVectors?: boolean;
228
103
  includeMetadata?: boolean;
229
104
  };
230
- /**
231
- * Type definition for the response returned by RangeCommand
232
- *
233
- * This type outlines the structure of the response from a RangeCommand.
234
- *
235
- * Properties:
236
- * - nextCursor: A string that indicates the cursor to be used for the next range query, facilitating pagination.
237
- * - vectors: An array of Vector objects, each containing TMetadata, representing the data retrieved in the range query.
238
- *
239
- * The RangeReturnResponse type is crucial for operations that involve retrieving a range of records,
240
- * providing both the data (in the form of vectors) and the means to continue fetching subsequent ranges (via nextCursor).
241
- */
242
105
  type RangeReturnResponse<TMetadata> = {
243
106
  nextCursor: string;
244
107
  vectors: Vector<TMetadata>[];
245
108
  };
246
- /**
247
- * RangeCommand Class
248
- * Example:
249
- * ```
250
- * const rangePayload = { cursor: 0, limit: 10, includeVectors: true };
251
- * const rangeCommand = new RangeCommand(rangePayload);
252
- * // Use rangeCommand to execute the range query and retrieve data
253
- * ```
254
- */
255
- declare class RangeCommand<TResult> extends Command<RangeReturnResponse<TResult>> {
256
- constructor(payload: Payload);
109
+ declare class RangeCommand<TMetadata> extends Command<RangeReturnResponse<TMetadata>> {
110
+ constructor(payload: RangeCommandPayload);
257
111
  }
258
112
 
259
113
  type CommandArgs<TCommand extends new (_args: any) => any> = ConstructorParameters<TCommand>[0];
@@ -274,27 +128,129 @@ declare class Index$1 {
274
128
  * ```
275
129
  */
276
130
  constructor(client: Requester);
277
- delete: (args: CommandArgs<typeof DeleteCommand>) => Promise<string>;
278
- query: (args: CommandArgs<typeof QueryCommand>) => Promise<{
279
- id: string | number;
280
- score: number;
281
- vector: number[];
282
- metadata?: unknown;
283
- }[]>;
131
+ /**
132
+ * Deletes a specific item or items from the index by their ID(s). *
133
+ *
134
+ * @example
135
+ * ```js
136
+ * await index.delete('test-id')
137
+ * ```
138
+ *
139
+ * @param id - List of ids or single id
140
+ * @returns A promise that resolves when the request to delete the index is completed.
141
+ */
142
+ delete: (args: CommandArgs<typeof DeleteCommand>) => Promise<{
143
+ deleted: number;
144
+ }>;
145
+ /**
146
+ * Queries an index with specified parameters.
147
+ * This method creates and executes a query command on an index based on the provided arguments.
148
+ *
149
+ * @example
150
+ * ```js
151
+ * await index.query({ topK: 3, vector: [ 0.22, 0.66 ]})
152
+ * ```
153
+ *
154
+ * @param {Object} args - The arguments for the query command.
155
+ * @param {number[]} args.vector - An array of numbers representing the feature vector for the query.
156
+ * This vector is utilized to find the most relevant items in the index.
157
+ * @param {number} args.topK - The desired number of top results to be returned, based on relevance or similarity to the query vector.
158
+ * @param {boolean} [args.includeVectors=false] - When set to true, includes the feature vectors of the returned items in the response.
159
+ * @param {boolean} [args.includeMetadata=false] - When set to true, includes additional metadata of the returned items in the response.
160
+ *
161
+ * @returns A promise that resolves with an array of query result objects when the request to query the index is completed.
162
+ */
163
+ query: (args: CommandArgs<typeof QueryCommand>) => Promise<QueryReturnResponse<unknown>[]>;
164
+ /**
165
+ * Upserts (Updates and Inserts) specific items into the index.
166
+ * It's used for adding new items to the index or updating existing ones.
167
+ *
168
+ * @example
169
+ * ```js
170
+ * const upsertArgs = {
171
+ * id: '123',
172
+ * vector: [0.42, 0.87, ...],
173
+ * metadata: { property1: 'value1', property2: 'value2' }
174
+ * };
175
+ * const upsertResult = await index.upsert(upsertArgs);
176
+ * console.log(upsertResult); // Outputs the result of the upsert operation
177
+ * ```
178
+ *
179
+ * @param {CommandArgs<typeof UpsertCommand>} args - The arguments for the upsert command.
180
+ * @param {number|string} args.id - The unique identifier for the item being upserted.
181
+ * @param {number[]} args.vector - The feature vector associated with the item.
182
+ * @param {Record<string, unknown>} [args.metadata] - Optional metadata to be associated with the item.
183
+ *
184
+ * @returns {string} A promise that resolves with the result of the upsert operation after the command is executed.
185
+ */
284
186
  upsert: (args: CommandArgs<typeof UpsertCommand>) => Promise<string>;
285
- fetch: (args: CommandArgs<typeof FetchCommand>) => Promise<(Vector<unknown> | null)[]>;
187
+ /**
188
+ * It's used for retrieving specific items from the index, optionally including
189
+ * their metadata and feature vectors.
190
+ *
191
+ * @example
192
+ * ```js
193
+ * const fetchIds = ['123', '456'];
194
+ * const fetchOptions = { includeMetadata: true, includeVectors: false };
195
+ * const fetchResults = await index.fetch(fetchIds, fetchOptions);
196
+ * console.log(fetchResults); // Outputs the fetched items
197
+ * ```
198
+ *
199
+ * @param {...CommandArgs<typeof FetchCommand>} args - The arguments for the fetch command.
200
+ * @param {(number[]|string[])} args[0] - An array of IDs of the items to be fetched.
201
+ * @param {FetchCommandOptions} args[1] - Options for the fetch operation.
202
+ * @param {boolean} [args[1].includeMetadata=false] - Optionally include metadata of the fetched items.
203
+ * @param {boolean} [args[1].includeVectors=false] - Optionally include feature vectors of the fetched items.
204
+ *
205
+ * @returns {Promise<FetchReturnResponse<TMetadata>[]>} A promise that resolves with an array of fetched items or null if not found, after the command is executed.
206
+ */
207
+ fetch: (ids: string[] | number[], opts: {
208
+ includeMetadata?: boolean | undefined;
209
+ includeVectors?: boolean | undefined;
210
+ }) => Promise<FetchReturnResponse<unknown>[]>;
211
+ /**
212
+ * It's used for wiping an entire index.
213
+ *
214
+ * @example
215
+ * ```js
216
+ * await index.reset();
217
+ * console.log('Index has been reset');
218
+ * ```
219
+ *
220
+ * @returns {Promise<string>} A promise that resolves with the result of the reset operation after the command is executed.
221
+ */
286
222
  reset: () => Promise<string>;
287
- range: (args: CommandArgs<typeof RangeCommand>) => Promise<{
288
- nextCursor: string;
289
- vectors: Vector<unknown>[];
290
- }>;
223
+ /**
224
+ * Retrieves a range of items from the index.
225
+ *
226
+ * @example
227
+ * ```js
228
+ * const rangeArgs = {
229
+ * cursor: 0,
230
+ * limit: 10,
231
+ * includeVectors: true,
232
+ * includeMetadata: false
233
+ * };
234
+ * const rangeResults = await index.range(rangeArgs);
235
+ * console.log(rangeResults); // Outputs the result of the range operation
236
+ * ```
237
+ *
238
+ * @param {CommandArgs<typeof RangeCommand>} args - The arguments for the range command.
239
+ * @param {number|string} args.cursor - The starting point (cursor) for the range query.
240
+ * @param {number} args.limit - The maximum number of items to return in this range.
241
+ * @param {boolean} [args.includeVectors=false] - Optionally include the feature vectors of the items in the response.
242
+ * @param {boolean} [args.includeMetadata=false] - Optionally include additional metadata of the items in the response.
243
+ *
244
+ * @returns {Promise<RangeReturnResponse<TMetadata>>} A promise that resolves with the response containing the next cursor and an array of vectors, after the command is executed.
245
+ */
246
+ range: (args: CommandArgs<typeof RangeCommand>) => Promise<RangeReturnResponse<unknown>>;
291
247
  }
292
248
 
293
249
  /**
294
250
  * Connection credentials for upstash vector.
295
251
  * Get them from https://console.upstash.com/vector/<uuid>
296
252
  */
297
- type VectorConfig = {
253
+ type IndexConfig = {
298
254
  /**
299
255
  * UPSTASH_VECTOR_REST_URL
300
256
  */
@@ -318,13 +274,13 @@ declare class Index extends Index$1 {
318
274
  *
319
275
  * @example
320
276
  * ```typescript
321
- * const vector = new Vector({
277
+ * const index = new Index({
322
278
  * url: "<UPSTASH_VECTOR_REST_URL>",
323
279
  * token: "<UPSTASH_VECTOR_REST_TOKEN>",
324
280
  * });
325
281
  * ```
326
282
  */
327
- constructor(config: VectorConfig);
283
+ constructor(config: IndexConfig);
328
284
  /**
329
285
  * Create a new vector client by providing a custom `Requester` implementation
330
286
  *
@@ -352,7 +308,7 @@ declare class Index extends Index$1 {
352
308
  * This tries to load `UPSTASH_VECTOR_REST_URL` and `UPSTASH_VECTOR_REST_TOKEN` from
353
309
  * your environment using `process.env`.
354
310
  */
355
- static fromEnv(config?: Omit<VectorConfig, "url" | "token">): Index;
311
+ static fromEnv(config?: Omit<IndexConfig, "url" | "token">): Index;
356
312
  }
357
313
 
358
- export { Index, type Requester, type UpstashRequest, type UpstashResponse, type VectorConfig };
314
+ export { Index, type IndexConfig, type Requester, type UpstashRequest, type UpstashResponse };
package/dist/index.d.ts CHANGED
@@ -42,12 +42,6 @@ type RequesterConfig = {
42
42
  cache?: CacheSetting;
43
43
  };
44
44
 
45
- type Vector<TMetadata> = {
46
- id: string;
47
- vector: number[];
48
- metadata?: TMetadata;
49
- };
50
-
51
45
  declare const ENDPOINTS: readonly ["upsert", "query", "delete", "fetch", "reset", "range"];
52
46
  type EndpointVariants = (typeof ENDPOINTS)[number];
53
47
  /**
@@ -63,55 +57,17 @@ declare class Command<TResult> {
63
57
  exec(client: Requester): Promise<TResult>;
64
58
  }
65
59
 
66
- /**
67
- * Payload Type Definition for DeleteCommand
68
- *
69
- * This type defines the structure of the payload specifically used in the DeleteCommand.
70
- *
71
- * Properties:
72
- * - ids: An array of numbers or strings representing the unique identifiers of the records to be deleted. These could be database IDs, unique keys, or any identifier used to uniquely refer to records in a specific context.
73
- *
74
- * Usage:
75
- * This type is typically used in scenarios where a batch deletion of records is required. The `ids` array allows specifying multiple records for deletion in a single command, thereby facilitating efficient bulk operations.
76
- */
77
- type Payload$4 = {
78
- ids: number[] | string[];
79
- };
80
- /**
81
- * DeleteCommand Class
82
- *
83
- * This class extends the generic Command class to implement the deletion functionality.
84
- *
85
- * Example:
86
- * ```
87
- * const deletionIds = [123, 456, 789];
88
- * const deleteCommand = new DeleteCommand({ ids: deletionIds });
89
- * // Use deleteCommand to execute the deletion operation
90
- * ```
91
- */
92
- declare class DeleteCommand extends Command<string> {
93
- constructor(payload: Payload$4);
60
+ declare class DeleteCommand extends Command<{
61
+ deleted: number;
62
+ }> {
63
+ constructor(id: (number[] | string[]) | number | string);
94
64
  }
95
65
 
96
- /**
97
- * Payload Type Definition
98
- *
99
- * This type defines the structure of the payload used in a specific function or API call.
100
- *
101
- * Properties:
102
- * - vector: An array of numbers representing a specific vector. This could be coordinates, data points, or any numerical representation depending on the context of the function or API.
103
- *
104
- * - topK: A number indicating the 'top K' elements to be considered or returned. In many contexts, this refers to the top 'K' results, items, or entities based on certain criteria like highest score, most relevance, etc.
105
- *
106
- * - includeVectors: A boolean value indicating whether to include the vector data in the response or output. Setting this to 'true' includes the vector data.
107
- *
108
- * Usage:
109
- * This type is typically used when sending or receiving data where a combination of a numerical vector, a limit on the number of elements to consider, and an option to include or exclude detailed vector data is required.
110
- */
111
- type Payload$3 = {
66
+ type QueryCommandPayload = {
112
67
  vector: number[];
113
68
  topK: number;
114
- includeVectors: boolean;
69
+ includeVectors?: boolean;
70
+ includeMetadata?: boolean;
115
71
  };
116
72
  type QueryReturnResponse<TMetadata> = {
117
73
  id: number | string;
@@ -119,141 +75,39 @@ type QueryReturnResponse<TMetadata> = {
119
75
  vector: number[];
120
76
  metadata?: TMetadata;
121
77
  };
122
- /**
123
- * QueryCommand Class
124
- * Example:
125
- * ```
126
- * const payload = { vector: [1, 2, 3], topK: 5, includeVectors: true };
127
- * const queryCommand = new QueryCommand(payload);
128
- * // Use queryCommand for further operations
129
- * ```
130
- */
131
- declare class QueryCommand<TResult> extends Command<QueryReturnResponse<TResult>[]> {
132
- constructor(payload: Payload$3);
78
+ declare class QueryCommand<TMetadata> extends Command<QueryReturnResponse<TMetadata>[]> {
79
+ constructor(payload: QueryCommandPayload);
133
80
  }
134
81
 
135
- /**
136
- * Payload Type Definition for UpsertCommand
137
- *
138
- * This type defines the structure of the payload used in the UpsertCommand.
139
- *
140
- * Properties:
141
- * - id: A number or string representing the unique identifier of the record to be upserted (inserted or updated).
142
- * - vector: An array of numbers representing a specific vector. This could be coordinates, data points, or any numerical representation depending on the context.
143
- * - metadata (optional): An object with key-value pairs, where the keys are strings and the values are of unknown type. This allows for flexible and additional data to be associated with the record being upserted.
144
- *
145
- * Usage:
146
- * This type is primarily used in scenarios where a record needs to be inserted into a database if it does not already exist, or updated if it does. The flexibility of the metadata field allows for various additional information to be passed along with the primary data.
147
- */
148
- type Payload$2 = {
82
+ type UpsertCommandPayload = {
149
83
  id: number | string;
150
84
  vector: number[];
151
85
  metadata?: Record<string, unknown>;
152
86
  };
153
- /**
154
- * UpsertCommand Class
155
- *
156
- * Extends the generic Command class to implement an upsert (insert or update) operation.
157
- *
158
- * Example:
159
- * ```
160
- * const upsertPayload = { id: 123, vector: [1.1, 2.2, 3.3], metadata: { key: "value" } };
161
- * const upsertCommand = new UpsertCommand(upsertPayload);
162
- * // Use upsertCommand to execute the upsert operation
163
- * ```
164
- *
165
- * The UpsertCommand takes a payload containing the necessary data for the upsert operation. It supports handling both insertion and update of records based on the provided identifier.
166
- */
167
87
  declare class UpsertCommand extends Command<string> {
168
- constructor(payload: Payload$2);
88
+ constructor(payload: UpsertCommandPayload | UpsertCommandPayload[]);
169
89
  }
170
90
 
171
- /**
172
- * Type definition for FetchCommand payload
173
- *
174
- * Properties:
175
- * - ids: An array of numbers or strings, representing the unique identifiers of the records to be fetched.
176
- * - includeMetadata (optional): A boolean flag indicating whether to include metadata in the response.
177
- * - includeVectors (optional): A boolean flag indicating whether to include vector data in the response.
178
- *
179
- * The Payload type is used in the FetchCommand to specify the data required to fetch specific records.
180
- * The optional flags allow for more detailed responses depending on the requirements.
181
- */
182
- type Payload$1 = {
183
- ids: number[] | string[];
184
- includeMetadata?: boolean;
185
- includeVectors?: boolean;
91
+ type Vector<TMetadata> = {
92
+ id: string;
93
+ vector: number[];
94
+ metadata?: TMetadata;
186
95
  };
187
- /**
188
- * Generic response type for FetchCommand
189
- *
190
- * This type represents the possible return type of a FetchCommand. It can be either a Vector
191
- * containing metadata or null, depending on whether the fetch operation was successful or not.
192
- */
96
+
193
97
  type FetchReturnResponse<TMetadata> = Vector<TMetadata> | null;
194
- /**
195
- * FetchCommand Class
196
- *
197
- * Extends the generic Command class to implement a fetch operation.
198
- *
199
- * Example:
200
- * ```
201
- * const fetchPayload = { ids: [1, 2, 3], includeMetadata: true };
202
- * const fetchCommand = new FetchCommand(fetchPayload);
203
- * // Use fetchCommand to execute the fetch operation
204
- * ```
205
- */
206
- declare class FetchCommand<TMetadata> extends Command<FetchReturnResponse<TMetadata>[]> {
207
- constructor(payload: Payload$1);
208
- }
209
98
 
210
- /**
211
- * Type definition for RangeCommand payload
212
- *
213
- * This type specifies the structure of the payload used in the RangeCommand.
214
- *
215
- * Properties:
216
- * - cursor: A number indicating the starting point for the range query.
217
- * - limit: A number specifying the maximum number of records to be returned.
218
- * - includeVectors (optional): A boolean flag indicating whether to include vector data in the response.
219
- * - includeMetadata (optional): A boolean flag indicating whether to include metadata in the response.
220
- *
221
- * This payload type is used for range queries, where a set of records is retrieved based on the specified cursor
222
- * and limit. The optional inclusion of vectors and metadata allows for flexible and detailed data retrieval.
223
- */
224
- type Payload = {
225
- cursor: number;
99
+ type RangeCommandPayload = {
100
+ cursor: number | string;
226
101
  limit: number;
227
102
  includeVectors?: boolean;
228
103
  includeMetadata?: boolean;
229
104
  };
230
- /**
231
- * Type definition for the response returned by RangeCommand
232
- *
233
- * This type outlines the structure of the response from a RangeCommand.
234
- *
235
- * Properties:
236
- * - nextCursor: A string that indicates the cursor to be used for the next range query, facilitating pagination.
237
- * - vectors: An array of Vector objects, each containing TMetadata, representing the data retrieved in the range query.
238
- *
239
- * The RangeReturnResponse type is crucial for operations that involve retrieving a range of records,
240
- * providing both the data (in the form of vectors) and the means to continue fetching subsequent ranges (via nextCursor).
241
- */
242
105
  type RangeReturnResponse<TMetadata> = {
243
106
  nextCursor: string;
244
107
  vectors: Vector<TMetadata>[];
245
108
  };
246
- /**
247
- * RangeCommand Class
248
- * Example:
249
- * ```
250
- * const rangePayload = { cursor: 0, limit: 10, includeVectors: true };
251
- * const rangeCommand = new RangeCommand(rangePayload);
252
- * // Use rangeCommand to execute the range query and retrieve data
253
- * ```
254
- */
255
- declare class RangeCommand<TResult> extends Command<RangeReturnResponse<TResult>> {
256
- constructor(payload: Payload);
109
+ declare class RangeCommand<TMetadata> extends Command<RangeReturnResponse<TMetadata>> {
110
+ constructor(payload: RangeCommandPayload);
257
111
  }
258
112
 
259
113
  type CommandArgs<TCommand extends new (_args: any) => any> = ConstructorParameters<TCommand>[0];
@@ -274,27 +128,129 @@ declare class Index$1 {
274
128
  * ```
275
129
  */
276
130
  constructor(client: Requester);
277
- delete: (args: CommandArgs<typeof DeleteCommand>) => Promise<string>;
278
- query: (args: CommandArgs<typeof QueryCommand>) => Promise<{
279
- id: string | number;
280
- score: number;
281
- vector: number[];
282
- metadata?: unknown;
283
- }[]>;
131
+ /**
132
+ * Deletes a specific item or items from the index by their ID(s). *
133
+ *
134
+ * @example
135
+ * ```js
136
+ * await index.delete('test-id')
137
+ * ```
138
+ *
139
+ * @param id - List of ids or single id
140
+ * @returns A promise that resolves when the request to delete the index is completed.
141
+ */
142
+ delete: (args: CommandArgs<typeof DeleteCommand>) => Promise<{
143
+ deleted: number;
144
+ }>;
145
+ /**
146
+ * Queries an index with specified parameters.
147
+ * This method creates and executes a query command on an index based on the provided arguments.
148
+ *
149
+ * @example
150
+ * ```js
151
+ * await index.query({ topK: 3, vector: [ 0.22, 0.66 ]})
152
+ * ```
153
+ *
154
+ * @param {Object} args - The arguments for the query command.
155
+ * @param {number[]} args.vector - An array of numbers representing the feature vector for the query.
156
+ * This vector is utilized to find the most relevant items in the index.
157
+ * @param {number} args.topK - The desired number of top results to be returned, based on relevance or similarity to the query vector.
158
+ * @param {boolean} [args.includeVectors=false] - When set to true, includes the feature vectors of the returned items in the response.
159
+ * @param {boolean} [args.includeMetadata=false] - When set to true, includes additional metadata of the returned items in the response.
160
+ *
161
+ * @returns A promise that resolves with an array of query result objects when the request to query the index is completed.
162
+ */
163
+ query: (args: CommandArgs<typeof QueryCommand>) => Promise<QueryReturnResponse<unknown>[]>;
164
+ /**
165
+ * Upserts (Updates and Inserts) specific items into the index.
166
+ * It's used for adding new items to the index or updating existing ones.
167
+ *
168
+ * @example
169
+ * ```js
170
+ * const upsertArgs = {
171
+ * id: '123',
172
+ * vector: [0.42, 0.87, ...],
173
+ * metadata: { property1: 'value1', property2: 'value2' }
174
+ * };
175
+ * const upsertResult = await index.upsert(upsertArgs);
176
+ * console.log(upsertResult); // Outputs the result of the upsert operation
177
+ * ```
178
+ *
179
+ * @param {CommandArgs<typeof UpsertCommand>} args - The arguments for the upsert command.
180
+ * @param {number|string} args.id - The unique identifier for the item being upserted.
181
+ * @param {number[]} args.vector - The feature vector associated with the item.
182
+ * @param {Record<string, unknown>} [args.metadata] - Optional metadata to be associated with the item.
183
+ *
184
+ * @returns {string} A promise that resolves with the result of the upsert operation after the command is executed.
185
+ */
284
186
  upsert: (args: CommandArgs<typeof UpsertCommand>) => Promise<string>;
285
- fetch: (args: CommandArgs<typeof FetchCommand>) => Promise<(Vector<unknown> | null)[]>;
187
+ /**
188
+ * It's used for retrieving specific items from the index, optionally including
189
+ * their metadata and feature vectors.
190
+ *
191
+ * @example
192
+ * ```js
193
+ * const fetchIds = ['123', '456'];
194
+ * const fetchOptions = { includeMetadata: true, includeVectors: false };
195
+ * const fetchResults = await index.fetch(fetchIds, fetchOptions);
196
+ * console.log(fetchResults); // Outputs the fetched items
197
+ * ```
198
+ *
199
+ * @param {...CommandArgs<typeof FetchCommand>} args - The arguments for the fetch command.
200
+ * @param {(number[]|string[])} args[0] - An array of IDs of the items to be fetched.
201
+ * @param {FetchCommandOptions} args[1] - Options for the fetch operation.
202
+ * @param {boolean} [args[1].includeMetadata=false] - Optionally include metadata of the fetched items.
203
+ * @param {boolean} [args[1].includeVectors=false] - Optionally include feature vectors of the fetched items.
204
+ *
205
+ * @returns {Promise<FetchReturnResponse<TMetadata>[]>} A promise that resolves with an array of fetched items or null if not found, after the command is executed.
206
+ */
207
+ fetch: (ids: string[] | number[], opts: {
208
+ includeMetadata?: boolean | undefined;
209
+ includeVectors?: boolean | undefined;
210
+ }) => Promise<FetchReturnResponse<unknown>[]>;
211
+ /**
212
+ * It's used for wiping an entire index.
213
+ *
214
+ * @example
215
+ * ```js
216
+ * await index.reset();
217
+ * console.log('Index has been reset');
218
+ * ```
219
+ *
220
+ * @returns {Promise<string>} A promise that resolves with the result of the reset operation after the command is executed.
221
+ */
286
222
  reset: () => Promise<string>;
287
- range: (args: CommandArgs<typeof RangeCommand>) => Promise<{
288
- nextCursor: string;
289
- vectors: Vector<unknown>[];
290
- }>;
223
+ /**
224
+ * Retrieves a range of items from the index.
225
+ *
226
+ * @example
227
+ * ```js
228
+ * const rangeArgs = {
229
+ * cursor: 0,
230
+ * limit: 10,
231
+ * includeVectors: true,
232
+ * includeMetadata: false
233
+ * };
234
+ * const rangeResults = await index.range(rangeArgs);
235
+ * console.log(rangeResults); // Outputs the result of the range operation
236
+ * ```
237
+ *
238
+ * @param {CommandArgs<typeof RangeCommand>} args - The arguments for the range command.
239
+ * @param {number|string} args.cursor - The starting point (cursor) for the range query.
240
+ * @param {number} args.limit - The maximum number of items to return in this range.
241
+ * @param {boolean} [args.includeVectors=false] - Optionally include the feature vectors of the items in the response.
242
+ * @param {boolean} [args.includeMetadata=false] - Optionally include additional metadata of the items in the response.
243
+ *
244
+ * @returns {Promise<RangeReturnResponse<TMetadata>>} A promise that resolves with the response containing the next cursor and an array of vectors, after the command is executed.
245
+ */
246
+ range: (args: CommandArgs<typeof RangeCommand>) => Promise<RangeReturnResponse<unknown>>;
291
247
  }
292
248
 
293
249
  /**
294
250
  * Connection credentials for upstash vector.
295
251
  * Get them from https://console.upstash.com/vector/<uuid>
296
252
  */
297
- type VectorConfig = {
253
+ type IndexConfig = {
298
254
  /**
299
255
  * UPSTASH_VECTOR_REST_URL
300
256
  */
@@ -318,13 +274,13 @@ declare class Index extends Index$1 {
318
274
  *
319
275
  * @example
320
276
  * ```typescript
321
- * const vector = new Vector({
277
+ * const index = new Index({
322
278
  * url: "<UPSTASH_VECTOR_REST_URL>",
323
279
  * token: "<UPSTASH_VECTOR_REST_TOKEN>",
324
280
  * });
325
281
  * ```
326
282
  */
327
- constructor(config: VectorConfig);
283
+ constructor(config: IndexConfig);
328
284
  /**
329
285
  * Create a new vector client by providing a custom `Requester` implementation
330
286
  *
@@ -352,7 +308,7 @@ declare class Index extends Index$1 {
352
308
  * This tries to load `UPSTASH_VECTOR_REST_URL` and `UPSTASH_VECTOR_REST_TOKEN` from
353
309
  * your environment using `process.env`.
354
310
  */
355
- static fromEnv(config?: Omit<VectorConfig, "url" | "token">): Index;
311
+ static fromEnv(config?: Omit<IndexConfig, "url" | "token">): Index;
356
312
  }
357
313
 
358
- export { Index, type Requester, type UpstashRequest, type UpstashResponse, type VectorConfig };
314
+ export { Index, type IndexConfig, type Requester, type UpstashRequest, type UpstashResponse };
package/dist/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  'use strict';
2
2
 
3
- var n=class extends Error{constructor(e){super(e),this.name="UpstashError";}};var i=class{baseUrl;headers;options;retry;constructor(e){this.options={cache:e.cache,signal:e.signal},this.baseUrl=e.baseUrl.replace(/\/$/,""),this.headers={"Content-Type":"application/json",...e.headers},typeof e?.retry=="boolean"&&e?.retry===!1?this.retry={attempts:1,backoff:()=>0}:this.retry={attempts:e?.retry?.retries??5,backoff:e?.retry?.backoff??(s=>Math.exp(s)*50)};}async request(e){let s={cache:this.options.cache,method:"POST",headers:this.headers,body:JSON.stringify(e.body),keepalive:!0,signal:this.options.signal},o=null,f=null;for(let y=0;y<=this.retry.attempts;y++)try{o=await fetch([this.baseUrl,...e.path??[]].join("/"),s);break}catch(g){if(this.options.signal?.aborted){let R=new Blob([JSON.stringify({result:this.options.signal.reason??"Aborted"})]),T={status:200,statusText:this.options.signal.reason??"Aborted"};o=new Response(R,T);break}f=g,await new Promise(R=>setTimeout(R,this.retry.backoff(y)));}if(!o)throw f??new Error("Exhausted all retries");let a=await o.json();if(x(a)){if(!o.ok)throw new n(`${a.error}, command was: ${JSON.stringify(e.body)}`);return a}return {result:a}}};function x(t){return t&&typeof t=="object"&&("result"in t||"error"in t)}var r=class{payload;endpoint;constructor(e,s){this.payload=e,this.endpoint=s;}async exec(e){let{result:s,error:o}=await e.request({body:this.payload,path:[this.endpoint]});if(o)throw new n(o);if(typeof s>"u")throw new Error("Request did not return a result");return s}};var p=class extends r{constructor(e){super(e.ids,"delete");}};var l=class extends r{constructor(e){super({...e},"query");}};var u=class extends r{constructor(e){super({...e},"upsert");}};var c=class extends r{constructor(e){super({...e},"fetch");}};var m=class extends r{constructor(e){super(e,"range");}};var d=class extends r{constructor(){super([],"reset");}};var h=class{client;constructor(e){this.client=e;}delete=e=>new p(e).exec(this.client);query=e=>new l(e).exec(this.client);upsert=e=>new u(e).exec(this.client);fetch=e=>new c(e).exec(this.client);reset=()=>new d().exec(this.client);range=e=>new m(e).exec(this.client)};var b=class t extends h{constructor(e){if("request"in e){super(e);return}(e.url.startsWith(" ")||e.url.endsWith(" ")||/\r|\n/.test(e.url))&&console.warn("The vector url contains whitespace or newline, which can cause errors!"),(e.token.startsWith(" ")||e.token.endsWith(" ")||/\r|\n/.test(e.token))&&console.warn("The vector token contains whitespace or newline, which can cause errors!");let s=new i({baseUrl:e.url,retry:e.retry,headers:{authorization:`Bearer ${e.token}`},cache:e.cache||"no-store",signal:e.signal});super(s);}static fromEnv(e){let s=process?.env.UPSTASH_VECTOR_REST_URL;if(!s)throw new Error("Unable to find environment variable: `UPSTASH_VECTOR_REST_URL`");let o=process?.env.UPSTASH_VECTOR_REST_TOKEN;if(!o)throw new Error("Unable to find environment variable: `UPSTASH_VECTOR_REST_TOKEN`");return new t({...e,url:s,token:o})}};
3
+ var n=class extends Error{constructor(e){super(e),this.name="UpstashError";}};var a=class{baseUrl;headers;options;retry;constructor(e){this.options={cache:e.cache,signal:e.signal},this.baseUrl=e.baseUrl.replace(/\/$/,""),this.headers={"Content-Type":"application/json",...e.headers},typeof e?.retry=="boolean"&&e?.retry===!1?this.retry={attempts:1,backoff:()=>0}:this.retry={attempts:e?.retry?.retries??5,backoff:e?.retry?.backoff??(t=>Math.exp(t)*50)};}async request(e){let t={cache:this.options.cache,method:"POST",headers:this.headers,body:JSON.stringify(e.body),keepalive:!0,signal:this.options.signal},o=null,f=null;for(let y=0;y<=this.retry.attempts;y++)try{o=await fetch([this.baseUrl,...e.path??[]].join("/"),t);break}catch(g){if(this.options.signal?.aborted){let b=new Blob([JSON.stringify({result:this.options.signal.reason??"Aborted"})]),x={status:200,statusText:this.options.signal.reason??"Aborted"};o=new Response(b,x);break}f=g,await new Promise(b=>setTimeout(b,this.retry.backoff(y)));}if(!o)throw f??new Error("Exhausted all retries");let h=await o.json();if(!o.ok)throw new n(`${h.error}, command was: ${JSON.stringify(e.body)}`);return {result:h.result,error:h.error}}};var r=class{payload;endpoint;constructor(e,t){this.payload=e,this.endpoint=t;}async exec(e){let{result:t,error:o}=await e.request({body:this.payload,path:[this.endpoint]});if(o)throw new n(o);if(typeof t>"u")throw new Error("Request did not return a result");return t}};var i=class extends r{constructor(e){let t=[];Array.isArray(e)?t.push(...e):t.push(e),super(t,"delete");}};var p=class extends r{constructor(e){super(e,"query");}};var c=class extends r{constructor(e){super(e,"upsert");}};var u=class extends r{constructor([e,t]){super({ids:e,...t},"fetch");}};var l=class extends r{constructor(e){super(e,"range");}};var m=class extends r{constructor(){super([],"reset");}};var d=class{client;constructor(e){this.client=e;}delete=e=>new i(e).exec(this.client);query=e=>new p(e).exec(this.client);upsert=e=>new c(e).exec(this.client);fetch=(...e)=>new u(e).exec(this.client);reset=()=>new m().exec(this.client);range=e=>new l(e).exec(this.client)};var R=class s extends d{constructor(e){if("request"in e){super(e);return}(e.url.startsWith(" ")||e.url.endsWith(" ")||/\r|\n/.test(e.url))&&console.warn("The vector url contains whitespace or newline, which can cause errors!"),(e.token.startsWith(" ")||e.token.endsWith(" ")||/\r|\n/.test(e.token))&&console.warn("The vector token contains whitespace or newline, which can cause errors!");let t=new a({baseUrl:e.url,retry:e.retry,headers:{authorization:`Bearer ${e.token}`},cache:e.cache||"no-store",signal:e.signal});super(t);}static fromEnv(e){let t=process?.env.UPSTASH_VECTOR_REST_URL;if(!t)throw new Error("Unable to find environment variable: `UPSTASH_VECTOR_REST_URL`");let o=process?.env.UPSTASH_VECTOR_REST_TOKEN;if(!o)throw new Error("Unable to find environment variable: `UPSTASH_VECTOR_REST_TOKEN`");return new s({...e,url:t,token:o})}};
4
4
 
5
- exports.Index = b;
5
+ exports.Index = R;
package/dist/index.mjs CHANGED
@@ -1,3 +1,3 @@
1
- var n=class extends Error{constructor(e){super(e),this.name="UpstashError";}};var i=class{baseUrl;headers;options;retry;constructor(e){this.options={cache:e.cache,signal:e.signal},this.baseUrl=e.baseUrl.replace(/\/$/,""),this.headers={"Content-Type":"application/json",...e.headers},typeof e?.retry=="boolean"&&e?.retry===!1?this.retry={attempts:1,backoff:()=>0}:this.retry={attempts:e?.retry?.retries??5,backoff:e?.retry?.backoff??(s=>Math.exp(s)*50)};}async request(e){let s={cache:this.options.cache,method:"POST",headers:this.headers,body:JSON.stringify(e.body),keepalive:!0,signal:this.options.signal},o=null,f=null;for(let y=0;y<=this.retry.attempts;y++)try{o=await fetch([this.baseUrl,...e.path??[]].join("/"),s);break}catch(g){if(this.options.signal?.aborted){let R=new Blob([JSON.stringify({result:this.options.signal.reason??"Aborted"})]),T={status:200,statusText:this.options.signal.reason??"Aborted"};o=new Response(R,T);break}f=g,await new Promise(R=>setTimeout(R,this.retry.backoff(y)));}if(!o)throw f??new Error("Exhausted all retries");let a=await o.json();if(x(a)){if(!o.ok)throw new n(`${a.error}, command was: ${JSON.stringify(e.body)}`);return a}return {result:a}}};function x(t){return t&&typeof t=="object"&&("result"in t||"error"in t)}var r=class{payload;endpoint;constructor(e,s){this.payload=e,this.endpoint=s;}async exec(e){let{result:s,error:o}=await e.request({body:this.payload,path:[this.endpoint]});if(o)throw new n(o);if(typeof s>"u")throw new Error("Request did not return a result");return s}};var p=class extends r{constructor(e){super(e.ids,"delete");}};var l=class extends r{constructor(e){super({...e},"query");}};var u=class extends r{constructor(e){super({...e},"upsert");}};var c=class extends r{constructor(e){super({...e},"fetch");}};var m=class extends r{constructor(e){super(e,"range");}};var d=class extends r{constructor(){super([],"reset");}};var h=class{client;constructor(e){this.client=e;}delete=e=>new p(e).exec(this.client);query=e=>new l(e).exec(this.client);upsert=e=>new u(e).exec(this.client);fetch=e=>new c(e).exec(this.client);reset=()=>new d().exec(this.client);range=e=>new m(e).exec(this.client)};var b=class t extends h{constructor(e){if("request"in e){super(e);return}(e.url.startsWith(" ")||e.url.endsWith(" ")||/\r|\n/.test(e.url))&&console.warn("The vector url contains whitespace or newline, which can cause errors!"),(e.token.startsWith(" ")||e.token.endsWith(" ")||/\r|\n/.test(e.token))&&console.warn("The vector token contains whitespace or newline, which can cause errors!");let s=new i({baseUrl:e.url,retry:e.retry,headers:{authorization:`Bearer ${e.token}`},cache:e.cache||"no-store",signal:e.signal});super(s);}static fromEnv(e){let s=process?.env.UPSTASH_VECTOR_REST_URL;if(!s)throw new Error("Unable to find environment variable: `UPSTASH_VECTOR_REST_URL`");let o=process?.env.UPSTASH_VECTOR_REST_TOKEN;if(!o)throw new Error("Unable to find environment variable: `UPSTASH_VECTOR_REST_TOKEN`");return new t({...e,url:s,token:o})}};
1
+ var n=class extends Error{constructor(e){super(e),this.name="UpstashError";}};var a=class{baseUrl;headers;options;retry;constructor(e){this.options={cache:e.cache,signal:e.signal},this.baseUrl=e.baseUrl.replace(/\/$/,""),this.headers={"Content-Type":"application/json",...e.headers},typeof e?.retry=="boolean"&&e?.retry===!1?this.retry={attempts:1,backoff:()=>0}:this.retry={attempts:e?.retry?.retries??5,backoff:e?.retry?.backoff??(t=>Math.exp(t)*50)};}async request(e){let t={cache:this.options.cache,method:"POST",headers:this.headers,body:JSON.stringify(e.body),keepalive:!0,signal:this.options.signal},o=null,f=null;for(let y=0;y<=this.retry.attempts;y++)try{o=await fetch([this.baseUrl,...e.path??[]].join("/"),t);break}catch(g){if(this.options.signal?.aborted){let b=new Blob([JSON.stringify({result:this.options.signal.reason??"Aborted"})]),x={status:200,statusText:this.options.signal.reason??"Aborted"};o=new Response(b,x);break}f=g,await new Promise(b=>setTimeout(b,this.retry.backoff(y)));}if(!o)throw f??new Error("Exhausted all retries");let h=await o.json();if(!o.ok)throw new n(`${h.error}, command was: ${JSON.stringify(e.body)}`);return {result:h.result,error:h.error}}};var r=class{payload;endpoint;constructor(e,t){this.payload=e,this.endpoint=t;}async exec(e){let{result:t,error:o}=await e.request({body:this.payload,path:[this.endpoint]});if(o)throw new n(o);if(typeof t>"u")throw new Error("Request did not return a result");return t}};var i=class extends r{constructor(e){let t=[];Array.isArray(e)?t.push(...e):t.push(e),super(t,"delete");}};var p=class extends r{constructor(e){super(e,"query");}};var c=class extends r{constructor(e){super(e,"upsert");}};var u=class extends r{constructor([e,t]){super({ids:e,...t},"fetch");}};var l=class extends r{constructor(e){super(e,"range");}};var m=class extends r{constructor(){super([],"reset");}};var d=class{client;constructor(e){this.client=e;}delete=e=>new i(e).exec(this.client);query=e=>new p(e).exec(this.client);upsert=e=>new c(e).exec(this.client);fetch=(...e)=>new u(e).exec(this.client);reset=()=>new m().exec(this.client);range=e=>new l(e).exec(this.client)};var R=class s extends d{constructor(e){if("request"in e){super(e);return}(e.url.startsWith(" ")||e.url.endsWith(" ")||/\r|\n/.test(e.url))&&console.warn("The vector url contains whitespace or newline, which can cause errors!"),(e.token.startsWith(" ")||e.token.endsWith(" ")||/\r|\n/.test(e.token))&&console.warn("The vector token contains whitespace or newline, which can cause errors!");let t=new a({baseUrl:e.url,retry:e.retry,headers:{authorization:`Bearer ${e.token}`},cache:e.cache||"no-store",signal:e.signal});super(t);}static fromEnv(e){let t=process?.env.UPSTASH_VECTOR_REST_URL;if(!t)throw new Error("Unable to find environment variable: `UPSTASH_VECTOR_REST_URL`");let o=process?.env.UPSTASH_VECTOR_REST_TOKEN;if(!o)throw new Error("Unable to find environment variable: `UPSTASH_VECTOR_REST_TOKEN`");return new s({...e,url:t,token:o})}};
2
2
 
3
- export { b as Index };
3
+ export { R as Index };
package/package.json CHANGED
@@ -4,7 +4,7 @@
4
4
  "module": "./dist/index.mjs",
5
5
  "main": "./dist/index.js",
6
6
  "types": "./dist/index.d.ts",
7
- "version": "v0.1.0-alpha",
7
+ "version": "v0.1.0-alpha-2",
8
8
  "keywords": [
9
9
  "vector",
10
10
  "upstash",