redis-vl 0.1.0-beta.0
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/LICENSE +22 -0
- package/README.md +212 -0
- package/dist/errors.d.ts +50 -0
- package/dist/errors.d.ts.map +1 -0
- package/dist/errors.js +87 -0
- package/dist/errors.js.map +1 -0
- package/dist/index.d.ts +21 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +25 -0
- package/dist/index.js.map +1 -0
- package/dist/indexes/search-index.d.ts +368 -0
- package/dist/indexes/search-index.d.ts.map +1 -0
- package/dist/indexes/search-index.js +475 -0
- package/dist/indexes/search-index.js.map +1 -0
- package/dist/query/base.d.ts +51 -0
- package/dist/query/base.d.ts.map +1 -0
- package/dist/query/base.js +6 -0
- package/dist/query/base.js.map +1 -0
- package/dist/query/index.d.ts +7 -0
- package/dist/query/index.d.ts.map +1 -0
- package/dist/query/index.js +7 -0
- package/dist/query/index.js.map +1 -0
- package/dist/query/vector.d.ts +199 -0
- package/dist/query/vector.d.ts.map +1 -0
- package/dist/query/vector.js +198 -0
- package/dist/query/vector.js.map +1 -0
- package/dist/redis/index-info-parser.d.ts +25 -0
- package/dist/redis/index-info-parser.d.ts.map +1 -0
- package/dist/redis/index-info-parser.js +301 -0
- package/dist/redis/index-info-parser.js.map +1 -0
- package/dist/redis/schema-types.d.ts +81 -0
- package/dist/redis/schema-types.d.ts.map +1 -0
- package/dist/redis/schema-types.js +18 -0
- package/dist/redis/schema-types.js.map +1 -0
- package/dist/redis/utils.d.ts +7 -0
- package/dist/redis/utils.d.ts.map +1 -0
- package/dist/redis/utils.js +221 -0
- package/dist/redis/utils.js.map +1 -0
- package/dist/schema/fields.d.ts +163 -0
- package/dist/schema/fields.d.ts.map +1 -0
- package/dist/schema/fields.js +304 -0
- package/dist/schema/fields.js.map +1 -0
- package/dist/schema/index.d.ts +8 -0
- package/dist/schema/index.d.ts.map +1 -0
- package/dist/schema/index.js +8 -0
- package/dist/schema/index.js.map +1 -0
- package/dist/schema/schema.d.ts +247 -0
- package/dist/schema/schema.d.ts.map +1 -0
- package/dist/schema/schema.js +403 -0
- package/dist/schema/schema.js.map +1 -0
- package/dist/schema/types.d.ts +56 -0
- package/dist/schema/types.d.ts.map +1 -0
- package/dist/schema/types.js +62 -0
- package/dist/schema/types.js.map +1 -0
- package/dist/storage/base-storage.d.ts +107 -0
- package/dist/storage/base-storage.d.ts.map +1 -0
- package/dist/storage/base-storage.js +187 -0
- package/dist/storage/base-storage.js.map +1 -0
- package/dist/storage/hash-storage.d.ts +29 -0
- package/dist/storage/hash-storage.d.ts.map +1 -0
- package/dist/storage/hash-storage.js +122 -0
- package/dist/storage/hash-storage.js.map +1 -0
- package/dist/storage/index.d.ts +4 -0
- package/dist/storage/index.d.ts.map +1 -0
- package/dist/storage/index.js +4 -0
- package/dist/storage/index.js.map +1 -0
- package/dist/storage/json-storage.d.ts +19 -0
- package/dist/storage/json-storage.d.ts.map +1 -0
- package/dist/storage/json-storage.js +81 -0
- package/dist/storage/json-storage.js.map +1 -0
- package/dist/utils/distance.d.ts +92 -0
- package/dist/utils/distance.d.ts.map +1 -0
- package/dist/utils/distance.js +98 -0
- package/dist/utils/distance.js.map +1 -0
- package/dist/vectorizers/base-vectorizer.d.ts +88 -0
- package/dist/vectorizers/base-vectorizer.d.ts.map +1 -0
- package/dist/vectorizers/base-vectorizer.js +32 -0
- package/dist/vectorizers/base-vectorizer.js.map +1 -0
- package/dist/vectorizers/huggingface-vectorizer.d.ts +103 -0
- package/dist/vectorizers/huggingface-vectorizer.d.ts.map +1 -0
- package/dist/vectorizers/huggingface-vectorizer.js +142 -0
- package/dist/vectorizers/huggingface-vectorizer.js.map +1 -0
- package/dist/vectorizers/index.d.ts +10 -0
- package/dist/vectorizers/index.d.ts.map +1 -0
- package/dist/vectorizers/index.js +10 -0
- package/dist/vectorizers/index.js.map +1 -0
- package/package.json +96 -0
|
@@ -0,0 +1,247 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import { StorageType } from './types.js';
|
|
3
|
+
import { BaseField, TextFieldAttrs, TagFieldAttrs, NumericFieldAttrs, GeoFieldAttrs, VectorFieldAttrs } from './fields.js';
|
|
4
|
+
/**
|
|
5
|
+
* Zod schema for IndexInfo validation.
|
|
6
|
+
* Validates index configuration including name, prefix, key separator, storage type, and stopwords.
|
|
7
|
+
*/
|
|
8
|
+
export declare const IndexInfoSchema: z.ZodObject<{
|
|
9
|
+
name: z.ZodString;
|
|
10
|
+
prefix: z.ZodDefault<z.ZodUnion<readonly [z.ZodString, z.ZodArray<z.ZodString>]>>;
|
|
11
|
+
keySeparator: z.ZodDefault<z.ZodString>;
|
|
12
|
+
storageType: z.ZodDefault<z.ZodEnum<typeof StorageType>>;
|
|
13
|
+
stopwords: z.ZodOptional<z.ZodArray<z.ZodString>>;
|
|
14
|
+
}, z.core.$strip>;
|
|
15
|
+
/**
|
|
16
|
+
* TypeScript type inferred from IndexInfoSchema.
|
|
17
|
+
*/
|
|
18
|
+
export type IndexInfoOptions = z.input<typeof IndexInfoSchema>;
|
|
19
|
+
/**
|
|
20
|
+
* IndexInfo includes the essential details regarding index settings,
|
|
21
|
+
* such as its name, prefix, key separator, storage type, and stopwords in Redis.
|
|
22
|
+
*/
|
|
23
|
+
export declare class IndexInfo {
|
|
24
|
+
/** The unique name of the index */
|
|
25
|
+
readonly name: string;
|
|
26
|
+
/** The prefix(es) used for Redis keys associated with this index */
|
|
27
|
+
readonly prefix: string | string[];
|
|
28
|
+
/** The separator character used in designing Redis keys */
|
|
29
|
+
readonly keySeparator: string;
|
|
30
|
+
/** The storage type used in Redis (e.g., StorageType.HASH or StorageType.JSON) */
|
|
31
|
+
readonly storageType: StorageType;
|
|
32
|
+
/** Index-level stopwords configuration */
|
|
33
|
+
readonly stopwords?: string[];
|
|
34
|
+
constructor(options: IndexInfoOptions);
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Zod schema for IndexSchema validation.
|
|
38
|
+
*/
|
|
39
|
+
export declare const IndexSchemaOptionsSchema: z.ZodObject<{
|
|
40
|
+
index: z.ZodCustom<IndexInfo, IndexInfo>;
|
|
41
|
+
fields: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodCustom<BaseField, BaseField>>>;
|
|
42
|
+
version: z.ZodOptional<z.ZodLiteral<"0.1.0">>;
|
|
43
|
+
}, z.core.$strip>;
|
|
44
|
+
/**
|
|
45
|
+
* TypeScript type inferred from IndexSchemaOptionsSchema.
|
|
46
|
+
*/
|
|
47
|
+
export type IndexSchemaOptions = z.input<typeof IndexSchemaOptionsSchema>;
|
|
48
|
+
/**
|
|
49
|
+
* Field input type for addField and addFields methods.
|
|
50
|
+
*
|
|
51
|
+
* The attrs property is type-safe based on the field type:
|
|
52
|
+
* - text: TextFieldAttrs
|
|
53
|
+
* - tag: TagFieldAttrs
|
|
54
|
+
* - numeric: NumericFieldAttrs
|
|
55
|
+
* - geo: GeoFieldAttrs
|
|
56
|
+
* - vector: VectorFieldAttrs (FLAT or HNSW)
|
|
57
|
+
*/
|
|
58
|
+
export type FieldInput = {
|
|
59
|
+
name: string;
|
|
60
|
+
type: 'text';
|
|
61
|
+
attrs?: TextFieldAttrs;
|
|
62
|
+
path?: string;
|
|
63
|
+
} | {
|
|
64
|
+
name: string;
|
|
65
|
+
type: 'tag';
|
|
66
|
+
attrs?: TagFieldAttrs;
|
|
67
|
+
path?: string;
|
|
68
|
+
} | {
|
|
69
|
+
name: string;
|
|
70
|
+
type: 'numeric';
|
|
71
|
+
attrs?: NumericFieldAttrs;
|
|
72
|
+
path?: string;
|
|
73
|
+
} | {
|
|
74
|
+
name: string;
|
|
75
|
+
type: 'geo';
|
|
76
|
+
attrs?: GeoFieldAttrs;
|
|
77
|
+
path?: string;
|
|
78
|
+
} | {
|
|
79
|
+
name: string;
|
|
80
|
+
type: 'vector';
|
|
81
|
+
attrs?: VectorFieldAttrs;
|
|
82
|
+
path?: string;
|
|
83
|
+
} | {
|
|
84
|
+
name: string;
|
|
85
|
+
type: string;
|
|
86
|
+
attrs?: Record<string, unknown>;
|
|
87
|
+
path?: string;
|
|
88
|
+
};
|
|
89
|
+
/**
|
|
90
|
+
* A schema definition for a search index in Redis, used in RedisVL for
|
|
91
|
+
* configuring index settings and organizing vector and metadata fields.
|
|
92
|
+
*/
|
|
93
|
+
export declare class IndexSchema {
|
|
94
|
+
/** Details of the basic index configurations */
|
|
95
|
+
readonly index: IndexInfo;
|
|
96
|
+
/** Fields associated with the search index and their properties */
|
|
97
|
+
fields: Record<string, BaseField>;
|
|
98
|
+
/** Version of the underlying index schema */
|
|
99
|
+
readonly version: '0.1.0';
|
|
100
|
+
constructor(options: IndexSchemaOptions);
|
|
101
|
+
/**
|
|
102
|
+
* A list of field names associated with the index schema.
|
|
103
|
+
*
|
|
104
|
+
* @returns A list of field names from the schema
|
|
105
|
+
*/
|
|
106
|
+
get fieldNames(): string[];
|
|
107
|
+
/**
|
|
108
|
+
* Internal helper to create a field and set its path based on storage type.
|
|
109
|
+
* For JSON storage: auto-sets path to $.fieldname if not provided.
|
|
110
|
+
* For HASH storage: sets path to null (paths not used).
|
|
111
|
+
*/
|
|
112
|
+
private makeField;
|
|
113
|
+
/**
|
|
114
|
+
* Adds a single field to the index schema.
|
|
115
|
+
*
|
|
116
|
+
* @param fieldInputs - Field definition object with name, type, and optional attributes
|
|
117
|
+
* @throws {Error} If a field with the same name already exists
|
|
118
|
+
*
|
|
119
|
+
* @example
|
|
120
|
+
* ```typescript
|
|
121
|
+
* schema.addField({ name: 'title', type: 'text' });
|
|
122
|
+
* schema.addField({
|
|
123
|
+
* name: 'embedding',
|
|
124
|
+
* type: 'vector',
|
|
125
|
+
* attrs: { dims: 1536, algorithm: 'hnsw' }
|
|
126
|
+
* });
|
|
127
|
+
* ```
|
|
128
|
+
*/
|
|
129
|
+
addField(fieldInputs: FieldInput): void;
|
|
130
|
+
/**
|
|
131
|
+
* Adds multiple fields to the index schema.
|
|
132
|
+
*
|
|
133
|
+
* @param fields - Array of field definition objects
|
|
134
|
+
* @throws {Error} If any field has a duplicate name
|
|
135
|
+
*
|
|
136
|
+
* @example
|
|
137
|
+
* ```typescript
|
|
138
|
+
* schema.addFields([
|
|
139
|
+
* { name: 'title', type: 'text' },
|
|
140
|
+
* { name: 'category', type: 'tag' },
|
|
141
|
+
* { name: 'price', type: 'numeric' }
|
|
142
|
+
* ]);
|
|
143
|
+
* ```
|
|
144
|
+
*/
|
|
145
|
+
addFields(fields: FieldInput[]): void;
|
|
146
|
+
/**
|
|
147
|
+
* Removes a field from the schema by name.
|
|
148
|
+
*
|
|
149
|
+
* @param fieldName - The name of the field to remove
|
|
150
|
+
*
|
|
151
|
+
* @example
|
|
152
|
+
* ```typescript
|
|
153
|
+
* schema.removeField('old_field');
|
|
154
|
+
* ```
|
|
155
|
+
*/
|
|
156
|
+
removeField(fieldName: string): void;
|
|
157
|
+
/**
|
|
158
|
+
* Create an IndexSchema from a plain object.
|
|
159
|
+
* Accepts both snake_case (from YAML/JSON files) and camelCase (from TypeScript) property names.
|
|
160
|
+
*
|
|
161
|
+
* @param data - The index schema data
|
|
162
|
+
* @returns A new IndexSchema instance
|
|
163
|
+
*
|
|
164
|
+
* @example
|
|
165
|
+
* ```typescript
|
|
166
|
+
* // From YAML/JSON (snake_case)
|
|
167
|
+
* const schema = IndexSchema.fromObject({
|
|
168
|
+
* index: {
|
|
169
|
+
* name: 'docs-index',
|
|
170
|
+
* prefix: 'docs',
|
|
171
|
+
* storage_type: 'hash', // snake_case from YAML/JSON
|
|
172
|
+
* },
|
|
173
|
+
* fields: [
|
|
174
|
+
* { name: 'doc-id', type: 'tag' },
|
|
175
|
+
* { name: 'title', type: 'text' }
|
|
176
|
+
* ]
|
|
177
|
+
* });
|
|
178
|
+
* ```
|
|
179
|
+
*/
|
|
180
|
+
static fromObject(data: {
|
|
181
|
+
index: IndexInfoOptions | IndexInfo | Record<string, unknown>;
|
|
182
|
+
fields?: FieldInput[] | Record<string, FieldInput>;
|
|
183
|
+
version?: '0.1.0';
|
|
184
|
+
}): IndexSchema;
|
|
185
|
+
/**
|
|
186
|
+
* Create an IndexSchema from a YAML file.
|
|
187
|
+
*
|
|
188
|
+
* @param filePath - The path to the YAML file
|
|
189
|
+
* @returns A new IndexSchema instance
|
|
190
|
+
*
|
|
191
|
+
* @throws Error if the file path is invalid
|
|
192
|
+
* @throws Error if the file does not exist
|
|
193
|
+
*
|
|
194
|
+
* @example
|
|
195
|
+
* ```typescript
|
|
196
|
+
* const schema = await IndexSchema.fromYAML('schema.yaml');
|
|
197
|
+
* console.log(schema.index.name);
|
|
198
|
+
* ```
|
|
199
|
+
*/
|
|
200
|
+
static fromYAML(filePath: string): Promise<IndexSchema>;
|
|
201
|
+
/**
|
|
202
|
+
* Serialize the index schema to a plain object.
|
|
203
|
+
* Converts camelCase properties to snake_case for YAML/JSON compatibility.
|
|
204
|
+
*
|
|
205
|
+
* @returns The index schema as a plain object with snake_case keys
|
|
206
|
+
*
|
|
207
|
+
* @example
|
|
208
|
+
* ```typescript
|
|
209
|
+
* const schema = new IndexSchema({ index: indexInfo });
|
|
210
|
+
* const obj = schema.toObject();
|
|
211
|
+
* console.log(obj.index.name);
|
|
212
|
+
* console.log(obj.index.storage_type);
|
|
213
|
+
* ```
|
|
214
|
+
*/
|
|
215
|
+
toObject(): {
|
|
216
|
+
index: {
|
|
217
|
+
name: string;
|
|
218
|
+
prefix: string | string[];
|
|
219
|
+
key_separator: string;
|
|
220
|
+
storage_type: string;
|
|
221
|
+
stopwords?: string[];
|
|
222
|
+
};
|
|
223
|
+
fields: Array<{
|
|
224
|
+
name: string;
|
|
225
|
+
type: string;
|
|
226
|
+
attrs?: Record<string, unknown>;
|
|
227
|
+
path?: string;
|
|
228
|
+
}>;
|
|
229
|
+
version: '0.1.0';
|
|
230
|
+
};
|
|
231
|
+
/**
|
|
232
|
+
* Write the index schema to a YAML file.
|
|
233
|
+
*
|
|
234
|
+
* @param filePath - The path to the YAML file
|
|
235
|
+
* @param overwrite - Whether to overwrite the file if it already exists (default: true)
|
|
236
|
+
*
|
|
237
|
+
* @throws Error if the file already exists and overwrite is false
|
|
238
|
+
*
|
|
239
|
+
* @example
|
|
240
|
+
* ```typescript
|
|
241
|
+
* const schema = new IndexSchema({ index: indexInfo });
|
|
242
|
+
* await schema.toYAML('schema.yaml');
|
|
243
|
+
* ```
|
|
244
|
+
*/
|
|
245
|
+
toYAML(filePath: string, overwrite?: boolean): Promise<void>;
|
|
246
|
+
}
|
|
247
|
+
//# sourceMappingURL=schema.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"schema.d.ts","sourceRoot":"","sources":["../../src/schema/schema.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,403 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
import * as yaml from 'js-yaml';
|
|
3
|
+
import { promises as fs } from 'fs';
|
|
4
|
+
import { resolve } from 'path';
|
|
5
|
+
import { StorageType } from './types.js';
|
|
6
|
+
import { BaseField, FieldFactory, } from './fields.js';
|
|
7
|
+
import { SchemaValidationError, RedisVLError } from '../errors.js';
|
|
8
|
+
/**
|
|
9
|
+
* Zod schema for IndexInfo validation.
|
|
10
|
+
* Validates index configuration including name, prefix, key separator, storage type, and stopwords.
|
|
11
|
+
*/
|
|
12
|
+
export const IndexInfoSchema = z.object({
|
|
13
|
+
name: z
|
|
14
|
+
.string()
|
|
15
|
+
.min(1, 'IndexInfo name cannot be empty')
|
|
16
|
+
.meta({
|
|
17
|
+
title: 'Index Name',
|
|
18
|
+
description: 'The unique name of the index (required, non-empty)',
|
|
19
|
+
examples: ['user-index', 'product-search', 'document-embeddings'],
|
|
20
|
+
}),
|
|
21
|
+
prefix: z
|
|
22
|
+
.union([z.string(), z.array(z.string())])
|
|
23
|
+
.default('rvl')
|
|
24
|
+
.meta({
|
|
25
|
+
title: 'Key Prefix',
|
|
26
|
+
description: 'The prefix(es) used for Redis keys associated with this index. ' +
|
|
27
|
+
'Can be a single string or array of strings. ' +
|
|
28
|
+
'When multiple prefixes are provided, the first one is used for write operations, but the index searches across all prefixes.',
|
|
29
|
+
examples: ['user', ['user', 'person', 'customer'], 'product'],
|
|
30
|
+
}),
|
|
31
|
+
keySeparator: z
|
|
32
|
+
.string()
|
|
33
|
+
.default(':')
|
|
34
|
+
.meta({
|
|
35
|
+
title: 'Key Separator',
|
|
36
|
+
description: 'The separator character used between prefix and key in Redis keys',
|
|
37
|
+
examples: [':', '::', '-', '_'],
|
|
38
|
+
}),
|
|
39
|
+
storageType: z
|
|
40
|
+
.enum(StorageType)
|
|
41
|
+
.default(StorageType.HASH)
|
|
42
|
+
.meta({
|
|
43
|
+
title: 'Storage Type',
|
|
44
|
+
description: 'The storage type used in Redis. ' +
|
|
45
|
+
'Options: "hash" (HASH storage) or "json" (JSON storage)',
|
|
46
|
+
examples: ['hash', 'json'],
|
|
47
|
+
}),
|
|
48
|
+
stopwords: z
|
|
49
|
+
.array(z.string())
|
|
50
|
+
.optional()
|
|
51
|
+
.meta({
|
|
52
|
+
title: 'Stopwords',
|
|
53
|
+
description: 'Index-level stopwords configuration for full-text search. ' +
|
|
54
|
+
'undefined (default) uses Redis default stopwords, ' +
|
|
55
|
+
'empty array [] disables stopwords (STOPWORDS 0), ' +
|
|
56
|
+
'or provide a custom list',
|
|
57
|
+
examples: [[], ['the', 'a', 'an', 'and', 'or']],
|
|
58
|
+
}),
|
|
59
|
+
});
|
|
60
|
+
/**
|
|
61
|
+
* IndexInfo includes the essential details regarding index settings,
|
|
62
|
+
* such as its name, prefix, key separator, storage type, and stopwords in Redis.
|
|
63
|
+
*/
|
|
64
|
+
export class IndexInfo {
|
|
65
|
+
/** The unique name of the index */
|
|
66
|
+
name;
|
|
67
|
+
/** The prefix(es) used for Redis keys associated with this index */
|
|
68
|
+
prefix;
|
|
69
|
+
/** The separator character used in designing Redis keys */
|
|
70
|
+
keySeparator;
|
|
71
|
+
/** The storage type used in Redis (e.g., StorageType.HASH or StorageType.JSON) */
|
|
72
|
+
storageType;
|
|
73
|
+
/** Index-level stopwords configuration */
|
|
74
|
+
stopwords;
|
|
75
|
+
constructor(options) {
|
|
76
|
+
// Validate and parse options using Zod
|
|
77
|
+
const validated = IndexInfoSchema.parse(options);
|
|
78
|
+
this.name = validated.name;
|
|
79
|
+
this.prefix = validated.prefix;
|
|
80
|
+
this.keySeparator = validated.keySeparator;
|
|
81
|
+
this.storageType = validated.storageType;
|
|
82
|
+
this.stopwords = validated.stopwords;
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
/**
|
|
86
|
+
* Zod schema for IndexSchema validation.
|
|
87
|
+
*/
|
|
88
|
+
export const IndexSchemaOptionsSchema = z.object({
|
|
89
|
+
/** Details of the basic index configurations */
|
|
90
|
+
index: z.instanceof(IndexInfo),
|
|
91
|
+
/** Fields associated with the search index and their properties */
|
|
92
|
+
fields: z.record(z.string(), z.instanceof(BaseField)).optional(),
|
|
93
|
+
/** Version of the underlying index schema */
|
|
94
|
+
version: z.literal('0.1.0').optional(),
|
|
95
|
+
});
|
|
96
|
+
/**
|
|
97
|
+
* A schema definition for a search index in Redis, used in RedisVL for
|
|
98
|
+
* configuring index settings and organizing vector and metadata fields.
|
|
99
|
+
*/
|
|
100
|
+
export class IndexSchema {
|
|
101
|
+
/** Details of the basic index configurations */
|
|
102
|
+
index;
|
|
103
|
+
/** Fields associated with the search index and their properties */
|
|
104
|
+
fields;
|
|
105
|
+
/** Version of the underlying index schema */
|
|
106
|
+
version;
|
|
107
|
+
constructor(options) {
|
|
108
|
+
// Validate options using Zod
|
|
109
|
+
const validated = IndexSchemaOptionsSchema.parse(options);
|
|
110
|
+
this.index = validated.index;
|
|
111
|
+
this.fields = validated.fields ?? {};
|
|
112
|
+
this.version = validated.version ?? '0.1.0';
|
|
113
|
+
}
|
|
114
|
+
/**
|
|
115
|
+
* A list of field names associated with the index schema.
|
|
116
|
+
*
|
|
117
|
+
* @returns A list of field names from the schema
|
|
118
|
+
*/
|
|
119
|
+
get fieldNames() {
|
|
120
|
+
return Object.keys(this.fields);
|
|
121
|
+
}
|
|
122
|
+
/**
|
|
123
|
+
* Internal helper to create a field and set its path based on storage type.
|
|
124
|
+
* For JSON storage: auto-sets path to $.fieldname if not provided.
|
|
125
|
+
* For HASH storage: sets path to null (paths not used).
|
|
126
|
+
*/
|
|
127
|
+
makeField(storageType, fieldInputs) {
|
|
128
|
+
// Extract field properties from inputs
|
|
129
|
+
const { name, type, attrs, path } = fieldInputs;
|
|
130
|
+
if (!name) {
|
|
131
|
+
throw new SchemaValidationError('Field name is required');
|
|
132
|
+
}
|
|
133
|
+
if (!type) {
|
|
134
|
+
throw new SchemaValidationError('Field type is required');
|
|
135
|
+
}
|
|
136
|
+
// Create field from inputs using FieldFactory
|
|
137
|
+
const field = FieldFactory.createField(type, name, attrs);
|
|
138
|
+
// Handle field path based on storage type
|
|
139
|
+
if (storageType === StorageType.JSON) {
|
|
140
|
+
// For JSON storage, set path appropriately
|
|
141
|
+
if (path) {
|
|
142
|
+
// Explicit path provided, use it
|
|
143
|
+
field.path = path;
|
|
144
|
+
}
|
|
145
|
+
else if (field.name.startsWith('$.')) {
|
|
146
|
+
// Name already is a JSON path, use it as-is
|
|
147
|
+
field.path = field.name;
|
|
148
|
+
}
|
|
149
|
+
else {
|
|
150
|
+
// Name is a simple field name, add $.prefix
|
|
151
|
+
field.path = `$.${field.name}`;
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
else {
|
|
155
|
+
// For HASH storage, path should always be null
|
|
156
|
+
if (path !== null && path !== undefined) {
|
|
157
|
+
// TODO: log a warning
|
|
158
|
+
}
|
|
159
|
+
field.path = null;
|
|
160
|
+
}
|
|
161
|
+
return field;
|
|
162
|
+
}
|
|
163
|
+
/**
|
|
164
|
+
* Adds a single field to the index schema.
|
|
165
|
+
*
|
|
166
|
+
* @param fieldInputs - Field definition object with name, type, and optional attributes
|
|
167
|
+
* @throws {Error} If a field with the same name already exists
|
|
168
|
+
*
|
|
169
|
+
* @example
|
|
170
|
+
* ```typescript
|
|
171
|
+
* schema.addField({ name: 'title', type: 'text' });
|
|
172
|
+
* schema.addField({
|
|
173
|
+
* name: 'embedding',
|
|
174
|
+
* type: 'vector',
|
|
175
|
+
* attrs: { dims: 1536, algorithm: 'hnsw' }
|
|
176
|
+
* });
|
|
177
|
+
* ```
|
|
178
|
+
*/
|
|
179
|
+
addField(fieldInputs) {
|
|
180
|
+
// Create field with proper path handling
|
|
181
|
+
const field = this.makeField(this.index.storageType, fieldInputs);
|
|
182
|
+
// Check for duplicates
|
|
183
|
+
if (Object.hasOwn(this.fields, field.name)) {
|
|
184
|
+
throw new SchemaValidationError(`Duplicate field name: ${field.name}. Field names must be unique across all fields for this index.`);
|
|
185
|
+
}
|
|
186
|
+
// Add field to schema
|
|
187
|
+
this.fields[field.name] = field;
|
|
188
|
+
}
|
|
189
|
+
/**
|
|
190
|
+
* Adds multiple fields to the index schema.
|
|
191
|
+
*
|
|
192
|
+
* @param fields - Array of field definition objects
|
|
193
|
+
* @throws {Error} If any field has a duplicate name
|
|
194
|
+
*
|
|
195
|
+
* @example
|
|
196
|
+
* ```typescript
|
|
197
|
+
* schema.addFields([
|
|
198
|
+
* { name: 'title', type: 'text' },
|
|
199
|
+
* { name: 'category', type: 'tag' },
|
|
200
|
+
* { name: 'price', type: 'numeric' }
|
|
201
|
+
* ]);
|
|
202
|
+
* ```
|
|
203
|
+
*/
|
|
204
|
+
addFields(fields) {
|
|
205
|
+
for (const fieldInput of fields) {
|
|
206
|
+
this.addField(fieldInput);
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
/**
|
|
210
|
+
* Removes a field from the schema by name.
|
|
211
|
+
*
|
|
212
|
+
* @param fieldName - The name of the field to remove
|
|
213
|
+
*
|
|
214
|
+
* @example
|
|
215
|
+
* ```typescript
|
|
216
|
+
* schema.removeField('old_field');
|
|
217
|
+
* ```
|
|
218
|
+
*/
|
|
219
|
+
removeField(fieldName) {
|
|
220
|
+
if (!Object.hasOwn(this.fields, fieldName)) {
|
|
221
|
+
// TODO: log a warning
|
|
222
|
+
return;
|
|
223
|
+
}
|
|
224
|
+
delete this.fields[fieldName];
|
|
225
|
+
}
|
|
226
|
+
/**
|
|
227
|
+
* Create an IndexSchema from a plain object.
|
|
228
|
+
* Accepts both snake_case (from YAML/JSON files) and camelCase (from TypeScript) property names.
|
|
229
|
+
*
|
|
230
|
+
* @param data - The index schema data
|
|
231
|
+
* @returns A new IndexSchema instance
|
|
232
|
+
*
|
|
233
|
+
* @example
|
|
234
|
+
* ```typescript
|
|
235
|
+
* // From YAML/JSON (snake_case)
|
|
236
|
+
* const schema = IndexSchema.fromObject({
|
|
237
|
+
* index: {
|
|
238
|
+
* name: 'docs-index',
|
|
239
|
+
* prefix: 'docs',
|
|
240
|
+
* storage_type: 'hash', // snake_case from YAML/JSON
|
|
241
|
+
* },
|
|
242
|
+
* fields: [
|
|
243
|
+
* { name: 'doc-id', type: 'tag' },
|
|
244
|
+
* { name: 'title', type: 'text' }
|
|
245
|
+
* ]
|
|
246
|
+
* });
|
|
247
|
+
* ```
|
|
248
|
+
*/
|
|
249
|
+
static fromObject(data) {
|
|
250
|
+
// 1. Create IndexInfo if it's a plain object
|
|
251
|
+
let indexInfo;
|
|
252
|
+
if (data.index instanceof IndexInfo) {
|
|
253
|
+
indexInfo = data.index;
|
|
254
|
+
}
|
|
255
|
+
else {
|
|
256
|
+
// Convert snake_case to camelCase for IndexInfo properties
|
|
257
|
+
const indexData = { ...data.index };
|
|
258
|
+
// Handle storage_type -> storageType conversion
|
|
259
|
+
if ('storage_type' in indexData && !('storageType' in indexData)) {
|
|
260
|
+
indexData.storageType = indexData.storage_type;
|
|
261
|
+
delete indexData.storage_type;
|
|
262
|
+
}
|
|
263
|
+
// Handle key_separator -> keySeparator conversion
|
|
264
|
+
if ('key_separator' in indexData && !('keySeparator' in indexData)) {
|
|
265
|
+
indexData.keySeparator = indexData.key_separator;
|
|
266
|
+
delete indexData.key_separator;
|
|
267
|
+
}
|
|
268
|
+
indexInfo = new IndexInfo(indexData);
|
|
269
|
+
}
|
|
270
|
+
// 2. Create empty schema
|
|
271
|
+
const schema = new IndexSchema({
|
|
272
|
+
index: indexInfo,
|
|
273
|
+
version: data.version,
|
|
274
|
+
});
|
|
275
|
+
// 3. Add fields if provided
|
|
276
|
+
if (data.fields) {
|
|
277
|
+
if (Array.isArray(data.fields)) {
|
|
278
|
+
// Handle array format
|
|
279
|
+
schema.addFields(data.fields);
|
|
280
|
+
}
|
|
281
|
+
else {
|
|
282
|
+
// Handle object format
|
|
283
|
+
for (const [key, fieldData] of Object.entries(data.fields)) {
|
|
284
|
+
// Validate field name matches key
|
|
285
|
+
if (fieldData.name !== key) {
|
|
286
|
+
throw new SchemaValidationError(`Field name mismatch: key is "${key}" but field.name is "${fieldData.name}"`);
|
|
287
|
+
}
|
|
288
|
+
schema.addField(fieldData);
|
|
289
|
+
}
|
|
290
|
+
}
|
|
291
|
+
}
|
|
292
|
+
return schema;
|
|
293
|
+
}
|
|
294
|
+
/**
|
|
295
|
+
* Create an IndexSchema from a YAML file.
|
|
296
|
+
*
|
|
297
|
+
* @param filePath - The path to the YAML file
|
|
298
|
+
* @returns A new IndexSchema instance
|
|
299
|
+
*
|
|
300
|
+
* @throws Error if the file path is invalid
|
|
301
|
+
* @throws Error if the file does not exist
|
|
302
|
+
*
|
|
303
|
+
* @example
|
|
304
|
+
* ```typescript
|
|
305
|
+
* const schema = await IndexSchema.fromYAML('schema.yaml');
|
|
306
|
+
* console.log(schema.index.name);
|
|
307
|
+
* ```
|
|
308
|
+
*/
|
|
309
|
+
static async fromYAML(filePath) {
|
|
310
|
+
const resolvedPath = resolve(filePath);
|
|
311
|
+
// Check if file exists
|
|
312
|
+
try {
|
|
313
|
+
await fs.access(resolvedPath);
|
|
314
|
+
}
|
|
315
|
+
catch {
|
|
316
|
+
throw new RedisVLError(`Schema file ${filePath} does not exist`);
|
|
317
|
+
}
|
|
318
|
+
// Read and parse YAML file
|
|
319
|
+
const yamlContent = await fs.readFile(resolvedPath, 'utf-8');
|
|
320
|
+
const data = yaml.load(yamlContent);
|
|
321
|
+
// Use fromObject to create the schema
|
|
322
|
+
return IndexSchema.fromObject(data);
|
|
323
|
+
}
|
|
324
|
+
/**
|
|
325
|
+
* Serialize the index schema to a plain object.
|
|
326
|
+
* Converts camelCase properties to snake_case for YAML/JSON compatibility.
|
|
327
|
+
*
|
|
328
|
+
* @returns The index schema as a plain object with snake_case keys
|
|
329
|
+
*
|
|
330
|
+
* @example
|
|
331
|
+
* ```typescript
|
|
332
|
+
* const schema = new IndexSchema({ index: indexInfo });
|
|
333
|
+
* const obj = schema.toObject();
|
|
334
|
+
* console.log(obj.index.name);
|
|
335
|
+
* console.log(obj.index.storage_type);
|
|
336
|
+
* ```
|
|
337
|
+
*/
|
|
338
|
+
toObject() {
|
|
339
|
+
// Serialize index info - convert camelCase to snake_case
|
|
340
|
+
const indexDict = {
|
|
341
|
+
name: this.index.name,
|
|
342
|
+
prefix: this.index.prefix,
|
|
343
|
+
key_separator: this.index.keySeparator, // camelCase -> snake_case
|
|
344
|
+
storage_type: this.index.storageType, // camelCase -> snake_case (enum value is already string)
|
|
345
|
+
...(this.index.stopwords !== undefined && { stopwords: this.index.stopwords }),
|
|
346
|
+
};
|
|
347
|
+
// Serialize fields as array
|
|
348
|
+
const fieldsArray = Object.values(this.fields).map((field) => {
|
|
349
|
+
const fieldDict = {
|
|
350
|
+
name: field.name,
|
|
351
|
+
type: field.type,
|
|
352
|
+
};
|
|
353
|
+
if (Object.keys(field.attrs).length > 0) {
|
|
354
|
+
fieldDict.attrs = field.attrs;
|
|
355
|
+
}
|
|
356
|
+
if (field.path !== undefined && field.path !== null) {
|
|
357
|
+
fieldDict.path = field.path;
|
|
358
|
+
}
|
|
359
|
+
return fieldDict;
|
|
360
|
+
});
|
|
361
|
+
return {
|
|
362
|
+
index: indexDict,
|
|
363
|
+
fields: fieldsArray,
|
|
364
|
+
version: this.version,
|
|
365
|
+
};
|
|
366
|
+
}
|
|
367
|
+
/**
|
|
368
|
+
* Write the index schema to a YAML file.
|
|
369
|
+
*
|
|
370
|
+
* @param filePath - The path to the YAML file
|
|
371
|
+
* @param overwrite - Whether to overwrite the file if it already exists (default: true)
|
|
372
|
+
*
|
|
373
|
+
* @throws Error if the file already exists and overwrite is false
|
|
374
|
+
*
|
|
375
|
+
* @example
|
|
376
|
+
* ```typescript
|
|
377
|
+
* const schema = new IndexSchema({ index: indexInfo });
|
|
378
|
+
* await schema.toYAML('schema.yaml');
|
|
379
|
+
* ```
|
|
380
|
+
*/
|
|
381
|
+
async toYAML(filePath, overwrite = true) {
|
|
382
|
+
const resolvedPath = resolve(filePath);
|
|
383
|
+
// Check if file exists
|
|
384
|
+
if (!overwrite) {
|
|
385
|
+
try {
|
|
386
|
+
await fs.access(resolvedPath);
|
|
387
|
+
throw new RedisVLError(`Schema file ${filePath} already exists.`);
|
|
388
|
+
}
|
|
389
|
+
catch (error) {
|
|
390
|
+
// File doesn't exist, which is what we want
|
|
391
|
+
if (error instanceof RedisVLError && error.message.includes('already exists')) {
|
|
392
|
+
throw error;
|
|
393
|
+
}
|
|
394
|
+
// Otherwise, file doesn't exist, continue
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
// Convert to object and write as YAML
|
|
398
|
+
const objData = this.toObject();
|
|
399
|
+
const yamlData = yaml.dump(objData, { sortKeys: false });
|
|
400
|
+
await fs.writeFile(resolvedPath, yamlData, 'utf-8');
|
|
401
|
+
}
|
|
402
|
+
}
|
|
403
|
+
//# sourceMappingURL=schema.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"schema.js","sourceRoot":"","sources":["../../src/schema/schema.ts"],"names":[],"mappings":"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"}
|