@karmaniverous/entity-manager 8.0.0 → 8.0.1
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/dist/cjs/BaseQueryBuilder/BaseQueryBuilder.js +11 -0
- package/dist/cjs/EntityManager/ParsedConfig.js +103 -21
- package/dist/cjs/EntityManager/findIndexToken.js +1 -2
- package/dist/cjs/EntityManager/getIndexComponents.js +1 -6
- package/dist/cjs/EntityManager/query.js +1 -1
- package/dist/index.d.ts +293 -11
- package/dist/mjs/BaseQueryBuilder/BaseQueryBuilder.js +11 -0
- package/dist/mjs/EntityManager/ParsedConfig.js +103 -21
- package/dist/mjs/EntityManager/findIndexToken.js +1 -2
- package/dist/mjs/EntityManager/getIndexComponents.js +1 -6
- package/dist/mjs/EntityManager/query.js +1 -1
- package/package.json +35 -35
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
var radash = require('radash');
|
|
4
4
|
|
|
5
|
+
/* eslint-disable @typescript-eslint/no-unused-vars */
|
|
5
6
|
/**
|
|
6
7
|
* Abstract base class supporting a fluent API for building a {@link ShardQueryMap | `ShardQueryMap`} using a database client.
|
|
7
8
|
*
|
|
@@ -36,6 +37,16 @@ class BaseQueryBuilder {
|
|
|
36
37
|
build() {
|
|
37
38
|
return radash.mapValues(this.indexParamsMap, (_indexConfig, indexToken) => this.getShardQueryFunction(indexToken));
|
|
38
39
|
}
|
|
40
|
+
/**
|
|
41
|
+
* Execute the built query across shards and indexes via {@link EntityManager.query | `EntityManager.query`}.
|
|
42
|
+
*
|
|
43
|
+
* @param options - Query options excluding `entityToken`, `pageKeyMap`, and `shardQueryMap`, which are supplied by the builder.
|
|
44
|
+
*
|
|
45
|
+
* @returns The merged, de-duplicated, sorted query result, including a compact `pageKeyMap` token for the next page.
|
|
46
|
+
*
|
|
47
|
+
* @remarks
|
|
48
|
+
* This delegates orchestration to Entity Manager; provider-specific behavior lives in {@link getShardQueryFunction | `getShardQueryFunction`}.
|
|
49
|
+
*/
|
|
39
50
|
async query(options) {
|
|
40
51
|
const { entityClient: { entityManager }, entityToken, pageKeyMap, } = this;
|
|
41
52
|
const shardQueryMap = this.build();
|
|
@@ -29,19 +29,54 @@ const componentArray = zod.z
|
|
|
29
29
|
.array(zod.z.string().min(1))
|
|
30
30
|
.nonempty()
|
|
31
31
|
.superRefine(validateArrayUnique);
|
|
32
|
+
/**
|
|
33
|
+
* Runtime configuration schema for {@link EntityManager | `EntityManager`}.
|
|
34
|
+
*
|
|
35
|
+
* @remarks
|
|
36
|
+
* This is authoritative at runtime and used internally by the {@link EntityManager | `EntityManager`} constructor.
|
|
37
|
+
* It is also used by tests. It is not intended as a user-facing TypeDoc artifact.
|
|
38
|
+
*
|
|
39
|
+
* @hidden
|
|
40
|
+
*/
|
|
32
41
|
const configSchema = zod.z
|
|
33
42
|
.object({
|
|
34
43
|
entities: zod.z
|
|
35
44
|
.record(zod.z.string(), zod.z
|
|
36
45
|
.object({
|
|
37
|
-
defaultLimit: zod.z
|
|
38
|
-
|
|
46
|
+
defaultLimit: zod.z
|
|
47
|
+
.number()
|
|
48
|
+
.int()
|
|
49
|
+
.positive()
|
|
50
|
+
.optional()
|
|
51
|
+
.default(10)
|
|
52
|
+
.describe('Default max items returned by EntityManager.query for this entity (across all shards).'),
|
|
53
|
+
defaultPageSize: zod.z
|
|
54
|
+
.number()
|
|
55
|
+
.int()
|
|
56
|
+
.positive()
|
|
57
|
+
.optional()
|
|
58
|
+
.default(10)
|
|
59
|
+
.describe('Default per-shard page size used by EntityManager.query for this entity.'),
|
|
39
60
|
shardBumps: zod.z
|
|
40
61
|
.array(zod.z
|
|
41
62
|
.object({
|
|
42
|
-
timestamp: zod.z
|
|
43
|
-
|
|
44
|
-
|
|
63
|
+
timestamp: zod.z
|
|
64
|
+
.number()
|
|
65
|
+
.int()
|
|
66
|
+
.nonnegative()
|
|
67
|
+
.describe('Start timestamp (ms) for this shard bump (inclusive).'),
|
|
68
|
+
charBits: zod.z
|
|
69
|
+
.number()
|
|
70
|
+
.int()
|
|
71
|
+
.min(1)
|
|
72
|
+
.max(5)
|
|
73
|
+
.describe('Bits per shard character (radix = 2**charBits).'),
|
|
74
|
+
chars: zod.z
|
|
75
|
+
.number()
|
|
76
|
+
.int()
|
|
77
|
+
.min(0)
|
|
78
|
+
.max(40)
|
|
79
|
+
.describe('Shard suffix width (chars); controls shard space.'),
|
|
45
80
|
})
|
|
46
81
|
.strict())
|
|
47
82
|
.optional()
|
|
@@ -73,45 +108,92 @@ const configSchema = zod.z
|
|
|
73
108
|
});
|
|
74
109
|
}
|
|
75
110
|
}),
|
|
76
|
-
timestampProperty: zod.z
|
|
77
|
-
|
|
111
|
+
timestampProperty: zod.z
|
|
112
|
+
.string()
|
|
113
|
+
.min(1)
|
|
114
|
+
.describe('Property token whose value selects the shard bump (typically a timestamp).'),
|
|
115
|
+
uniqueProperty: zod.z
|
|
116
|
+
.string()
|
|
117
|
+
.min(1)
|
|
118
|
+
.describe('Property token used to dedupe and build the global range key.'),
|
|
78
119
|
})
|
|
79
120
|
.strict())
|
|
80
121
|
.optional()
|
|
81
|
-
.default({})
|
|
122
|
+
.default({})
|
|
123
|
+
.describe('Entity definitions keyed by entity token.'),
|
|
82
124
|
generatedProperties: zod.z
|
|
83
125
|
.object({
|
|
84
|
-
sharded: zod.z
|
|
85
|
-
|
|
126
|
+
sharded: zod.z
|
|
127
|
+
.record(zod.z.string(), componentArray)
|
|
128
|
+
.optional()
|
|
129
|
+
.default({})
|
|
130
|
+
.describe('Sharded generated property tokens (hash-side); atomic encoding semantics.'),
|
|
131
|
+
unsharded: zod.z
|
|
132
|
+
.record(zod.z.string(), componentArray)
|
|
133
|
+
.optional()
|
|
134
|
+
.default({})
|
|
135
|
+
.describe('Unsharded generated property tokens (range-side); non-atomic encoding semantics.'),
|
|
86
136
|
})
|
|
87
137
|
.optional()
|
|
88
138
|
.default({ sharded: {}, unsharded: {} }),
|
|
89
|
-
hashKey: zod.z.string(),
|
|
139
|
+
hashKey: zod.z.string().describe('Global hash key property name.'),
|
|
90
140
|
indexes: zod.z
|
|
91
141
|
.record(zod.z.string(), zod.z.object({
|
|
92
|
-
hashKey: zod.z
|
|
93
|
-
|
|
142
|
+
hashKey: zod.z
|
|
143
|
+
.string()
|
|
144
|
+
.min(1)
|
|
145
|
+
.describe('Index hash key token (global hash key or a sharded generated key).'),
|
|
146
|
+
rangeKey: zod.z
|
|
147
|
+
.string()
|
|
148
|
+
.min(1)
|
|
149
|
+
.describe('Index range key token (global range key, an unsharded generated key, or a transcoded property).'),
|
|
94
150
|
projections: zod.z
|
|
95
151
|
.array(zod.z.string().min(1))
|
|
96
152
|
.superRefine(validateArrayUnique)
|
|
97
153
|
.optional(),
|
|
98
154
|
}))
|
|
99
155
|
.optional()
|
|
100
|
-
.default({})
|
|
101
|
-
|
|
102
|
-
|
|
156
|
+
.default({})
|
|
157
|
+
.describe('Index definitions keyed by index token.'),
|
|
158
|
+
generatedKeyDelimiter: zod.z
|
|
159
|
+
.string()
|
|
160
|
+
.regex(/\W+/)
|
|
161
|
+
.optional()
|
|
162
|
+
.default('|')
|
|
163
|
+
.describe('Delimiter between generated key elements (default `|`).'),
|
|
164
|
+
generatedValueDelimiter: zod.z
|
|
165
|
+
.string()
|
|
166
|
+
.regex(/\W+/)
|
|
167
|
+
.optional()
|
|
168
|
+
.default('#')
|
|
169
|
+
.describe('Delimiter between generated element name and value (default `#`).'),
|
|
103
170
|
propertyTranscodes: zod.z.record(zod.z.string(), zod.z.string()).optional().default({}),
|
|
104
|
-
rangeKey: zod.z.string(),
|
|
105
|
-
shardKeyDelimiter: zod.z
|
|
106
|
-
|
|
171
|
+
rangeKey: zod.z.string().describe('Global range key property name.'),
|
|
172
|
+
shardKeyDelimiter: zod.z
|
|
173
|
+
.string()
|
|
174
|
+
.regex(/\W+/)
|
|
175
|
+
.optional()
|
|
176
|
+
.default('!')
|
|
177
|
+
.describe('Delimiter between entity token and shard suffix in hash key values.'),
|
|
178
|
+
throttle: zod.z
|
|
179
|
+
.number()
|
|
180
|
+
.int()
|
|
181
|
+
.positive()
|
|
182
|
+
.optional()
|
|
183
|
+
.default(10)
|
|
184
|
+
.describe('Default max concurrency for shard queries during EntityManager.query.'),
|
|
107
185
|
transcodes: zod.z
|
|
108
186
|
.record(zod.z.string(), zod.z
|
|
109
187
|
.object({
|
|
110
188
|
// Accept function shapes without relying on z.function()
|
|
111
189
|
// to avoid TS inference conflicts across Zod versions and
|
|
112
190
|
// to remain compatible with narrower parameter types.
|
|
113
|
-
encode: zod.z
|
|
114
|
-
|
|
191
|
+
encode: zod.z
|
|
192
|
+
.custom((fn) => typeof fn === 'function')
|
|
193
|
+
.describe('Encode a value to a lexicographically sortable string.'),
|
|
194
|
+
decode: zod.z
|
|
195
|
+
.custom((fn) => typeof fn === 'function')
|
|
196
|
+
.describe('Decode a previously encoded string back to the value type.'),
|
|
115
197
|
})
|
|
116
198
|
.strict())
|
|
117
199
|
.optional()
|
|
@@ -1,8 +1,7 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
3
|
function findIndexToken(entityManager, hashKeyToken, rangeKeyToken, suppressError) {
|
|
4
|
-
const indexToken = (Object.entries(entityManager.config.indexes).find(([, index]) => index.hashKey === hashKeyToken &&
|
|
5
|
-
index.rangeKey === rangeKeyToken)?.[0] ?? undefined);
|
|
4
|
+
const indexToken = (Object.entries(entityManager.config.indexes).find(([, index]) => index.hashKey === hashKeyToken && index.rangeKey === rangeKeyToken)?.[0] ?? undefined);
|
|
6
5
|
if (!indexToken && !suppressError)
|
|
7
6
|
throw new Error(`No index token found for hashKey '${hashKeyToken}' & rangeKey '${rangeKeyToken}'.`);
|
|
8
7
|
return indexToken;
|
|
@@ -17,12 +17,7 @@ function getIndexComponents(entityManager, indexToken) {
|
|
|
17
17
|
validateIndexToken.validateIndexToken(entityManager, indexToken);
|
|
18
18
|
const { hashKey, rangeKey, indexes } = entityManager.config;
|
|
19
19
|
const { hashKey: indexHashKey, rangeKey: indexRangeKey } = indexes[indexToken];
|
|
20
|
-
return radash.unique([
|
|
21
|
-
hashKey,
|
|
22
|
-
rangeKey,
|
|
23
|
-
indexHashKey,
|
|
24
|
-
indexRangeKey,
|
|
25
|
-
]);
|
|
20
|
+
return radash.unique([hashKey, rangeKey, indexHashKey, indexRangeKey]);
|
|
26
21
|
}
|
|
27
22
|
|
|
28
23
|
exports.getIndexComponents = getIndexComponents;
|
|
@@ -40,7 +40,7 @@ async function query(entityManager, options) {
|
|
|
40
40
|
if (!(radash.isInt(pageSize) && pageSize >= 1))
|
|
41
41
|
throw new Error('pageSize must be a positive integer');
|
|
42
42
|
// Rehydrate pageKeyMap.
|
|
43
|
-
const [hashKeyToken, rehydratedPageKeyMap] = rehydratePageKeyMap.rehydratePageKeyMap(entityManager, entityToken, Object.keys(shardQueryMap), item, pageKeyMap
|
|
43
|
+
const [hashKeyToken, rehydratedPageKeyMap] = rehydratePageKeyMap.rehydratePageKeyMap(entityManager, entityToken, Object.keys(shardQueryMap).sort(), item, pageKeyMap
|
|
44
44
|
? JSON.parse(decompressFromEncodedURIComponent(pageKeyMap))
|
|
45
45
|
: undefined, timestampFrom, timestampTo);
|
|
46
46
|
// Shortcut if pageKeyMap is empty.
|
package/dist/index.d.ts
CHANGED
|
@@ -9,12 +9,19 @@ import { BatchProcessOptions } from '@karmaniverous/batch-process';
|
|
|
9
9
|
* @category EntityManager
|
|
10
10
|
*/
|
|
11
11
|
interface BaseConfigMap {
|
|
12
|
+
/** Entity map type (entity token -\> entity shape). */
|
|
12
13
|
EntityMap: EntityMap;
|
|
14
|
+
/** Global hash-key property name used by the storage layer. */
|
|
13
15
|
HashKey: string;
|
|
16
|
+
/** Global range-key property name used by the storage layer. */
|
|
14
17
|
RangeKey: string;
|
|
18
|
+
/** Union of sharded generated key tokens (string-valued generated properties). */
|
|
15
19
|
ShardedKeys: string;
|
|
20
|
+
/** Union of unsharded generated key tokens (string-valued generated properties). */
|
|
16
21
|
UnshardedKeys: string;
|
|
22
|
+
/** Union of transcoded property tokens (domain properties mapped in `propertyTranscodes`). */
|
|
17
23
|
TranscodedProperties: string;
|
|
24
|
+
/** Transcode registry mapping transcode names to value types. */
|
|
18
25
|
TranscodeRegistry: TranscodeRegistry;
|
|
19
26
|
}
|
|
20
27
|
|
|
@@ -55,25 +62,45 @@ interface ShardBump {
|
|
|
55
62
|
*/
|
|
56
63
|
type Config<C extends BaseConfigMap = BaseConfigMap> = ConditionalProperty<'entities', keyof Exactify<C['EntityMap']>, {
|
|
57
64
|
[E in keyof Exactify<C['EntityMap']>]: {
|
|
65
|
+
/** Default max number of items returned by {@link EntityManager.query | `query`} for this entity (across all shards). */
|
|
58
66
|
defaultLimit?: number;
|
|
67
|
+
/** Default per-shard page size used by {@link EntityManager.query | `query`} for this entity. */
|
|
59
68
|
defaultPageSize?: number;
|
|
69
|
+
/** Shard bump schedule for this entity (time-based sharding scale-up). */
|
|
60
70
|
shardBumps?: ShardBump[];
|
|
71
|
+
/** Property token whose value selects the active shard bump (must be a transcoded numeric property). */
|
|
61
72
|
timestampProperty: Extract<Extract<C['TranscodedProperties'], PropertiesOfType<C['EntityMap'][E], number>>, TranscodableProperties<C['EntityMap'], C['TranscodeRegistry']>>;
|
|
73
|
+
/** Property token used as the logical unique identifier for this entity (must be a transcoded scalar). */
|
|
62
74
|
uniqueProperty: Extract<Extract<C['TranscodedProperties'], keyof C['EntityMap'][E]>, TranscodableProperties<C['EntityMap'], C['TranscodeRegistry']>>;
|
|
63
75
|
};
|
|
64
76
|
}> & ConditionalProperty<'generatedProperties', C['ShardedKeys'] | C['UnshardedKeys'], ConditionalProperty<'sharded', C['ShardedKeys'], Record<C['ShardedKeys'], (C['TranscodedProperties'] & TranscodableProperties<C['EntityMap'], C['TranscodeRegistry']>)[]>> & ConditionalProperty<'unsharded', C['UnshardedKeys'], Record<C['UnshardedKeys'], (C['TranscodedProperties'] & TranscodableProperties<C['EntityMap'], C['TranscodeRegistry']>)[]>>> & ConditionalProperty<'propertyTranscodes', C['TranscodedProperties'] & TranscodableProperties<C['EntityMap'], C['TranscodeRegistry']>, {
|
|
65
77
|
[P in C['TranscodedProperties'] & TranscodableProperties<C['EntityMap'], C['TranscodeRegistry']>]: PropertiesOfType<C['TranscodeRegistry'], FlattenEntityMap<C['EntityMap']>[P]>;
|
|
66
78
|
}> & ConditionalProperty<'transcodes', keyof C['TranscodeRegistry'], Transcodes<C['TranscodeRegistry']>> & {
|
|
79
|
+
/** Delimiter between generated key elements (default `|`). Must not collide with other delimiters. */
|
|
67
80
|
generatedKeyDelimiter?: string;
|
|
81
|
+
/** Delimiter between a generated property key and its encoded value (default `#`). Must not collide with other delimiters. */
|
|
68
82
|
generatedValueDelimiter?: string;
|
|
83
|
+
/** Global hash key property name. */
|
|
69
84
|
hashKey: C['HashKey'];
|
|
85
|
+
/**
|
|
86
|
+
* Index token map. Keys are index names; values define the index hash/range key tokens and optional projections.
|
|
87
|
+
*
|
|
88
|
+
* @remarks
|
|
89
|
+
* This is provider-agnostic metadata used for page-key narrowing and (de)hydration; provider adapters map this to platform-specific indexes.
|
|
90
|
+
*/
|
|
70
91
|
indexes?: Record<string, {
|
|
92
|
+
/** Index hash key token (global hash key or a sharded generated key token). */
|
|
71
93
|
hashKey: C['HashKey'] | C['ShardedKeys'];
|
|
94
|
+
/** Index range key token (global range key, an unsharded generated key token, or a transcoded scalar property token). */
|
|
72
95
|
rangeKey: C['RangeKey'] | C['UnshardedKeys'] | (C['TranscodedProperties'] & TranscodableProperties<C['EntityMap'], C['TranscodeRegistry']>);
|
|
96
|
+
/** Optional list of projected attribute names (validated to exclude key tokens). */
|
|
73
97
|
projections?: string[];
|
|
74
98
|
}>;
|
|
99
|
+
/** Global range key property name. */
|
|
75
100
|
rangeKey: C['RangeKey'];
|
|
101
|
+
/** Delimiter between entity token and shard suffix in the global hash key value (default `!`). */
|
|
76
102
|
shardKeyDelimiter?: string;
|
|
103
|
+
/** Maximum number of shard queries to execute concurrently during {@link EntityManager.query | `query`}. */
|
|
77
104
|
throttle?: number;
|
|
78
105
|
};
|
|
79
106
|
|
|
@@ -109,12 +136,19 @@ type ValidateConfigMap<CC extends BaseConfigMap> = MutuallyExclusive<[
|
|
|
109
136
|
* @category EntityManager
|
|
110
137
|
*/
|
|
111
138
|
type ConfigMap<M extends Partial<BaseConfigMap> = Partial<BaseConfigMap>> = ValidateConfigMap<{
|
|
139
|
+
/** Entity map type (entity token -\> entity shape). */
|
|
112
140
|
EntityMap: 'EntityMap' extends keyof M ? NonNullable<M['EntityMap']> : Record<string, never>;
|
|
141
|
+
/** Global hash key property name (defaults to `"hashKey"`). */
|
|
113
142
|
HashKey: 'HashKey' extends keyof M ? NonNullable<M['HashKey']> : 'hashKey';
|
|
143
|
+
/** Global range key property name (defaults to `"rangeKey"`). */
|
|
114
144
|
RangeKey: 'RangeKey' extends keyof M ? NonNullable<M['RangeKey']> : 'rangeKey';
|
|
145
|
+
/** Union of sharded generated key tokens (defaults to `never`). */
|
|
115
146
|
ShardedKeys: 'ShardedKeys' extends keyof M ? NonNullable<M['ShardedKeys']> : never;
|
|
147
|
+
/** Union of unsharded generated key tokens (defaults to `never`). */
|
|
116
148
|
UnshardedKeys: 'UnshardedKeys' extends keyof M ? NonNullable<M['UnshardedKeys']> : never;
|
|
149
|
+
/** Union of transcoded property tokens (defaults to `never`). */
|
|
117
150
|
TranscodedProperties: 'TranscodedProperties' extends keyof M ? NonNullable<M['TranscodedProperties']> : never;
|
|
151
|
+
/** Transcode registry type (defaults to {@link DefaultTranscodeRegistry | `DefaultTranscodeRegistry`}). */
|
|
118
152
|
TranscodeRegistry: 'TranscodeRegistry' extends keyof M ? NonNullable<M['TranscodeRegistry']> : DefaultTranscodeRegistry;
|
|
119
153
|
}>;
|
|
120
154
|
|
|
@@ -167,13 +201,23 @@ type PageKey<CC extends BaseConfigMap> = Pick<StorageItem<CC>, CC['HashKey'] | C
|
|
|
167
201
|
* literal types when available.
|
|
168
202
|
*/
|
|
169
203
|
type IndexHashKeyOf<CF, IT extends string> = CF extends {
|
|
204
|
+
/** Optional values-first index map used for literal narrowing. */
|
|
170
205
|
indexes?: infer I;
|
|
171
206
|
} ? I extends Record<string, unknown> ? IT extends keyof I ? I[IT] extends {
|
|
207
|
+
/** Index hash key token. */
|
|
172
208
|
hashKey: infer HK;
|
|
173
209
|
} ? HK & string : never : never : never : never;
|
|
210
|
+
/**
|
|
211
|
+
* Derive the index range-key token for a specific index token.
|
|
212
|
+
*
|
|
213
|
+
* When CF carries an `indexes` object and IT is a member key, this extracts the
|
|
214
|
+
* concrete `rangeKey` token type.
|
|
215
|
+
*/
|
|
174
216
|
type IndexRangeKeyOf<CF, IT extends string> = CF extends {
|
|
217
|
+
/** Optional values-first index map used for literal narrowing. */
|
|
175
218
|
indexes?: infer I;
|
|
176
219
|
} ? I extends Record<string, unknown> ? IT extends keyof I ? I[IT] extends {
|
|
220
|
+
/** Index range key token. */
|
|
177
221
|
rangeKey: infer RK;
|
|
178
222
|
} ? RK & string : never : never : never : never;
|
|
179
223
|
/**
|
|
@@ -183,9 +227,17 @@ type IndexRangeKeyOf<CF, IT extends string> = CF extends {
|
|
|
183
227
|
* this helper captures the index token union. Falls back to `string` if absent.
|
|
184
228
|
*/
|
|
185
229
|
type IndexTokensOf<CF> = CF extends {
|
|
230
|
+
/** Optional values-first index map used for index-token narrowing. */
|
|
186
231
|
indexes?: infer I;
|
|
187
232
|
} ? I extends Record<string, unknown> ? Extract<keyof I, string> : string : string;
|
|
233
|
+
/**
|
|
234
|
+
* Test whether a values-first config literal CF carries a concrete index IT.
|
|
235
|
+
*
|
|
236
|
+
* @remarks
|
|
237
|
+
* Used to decide whether index-aware narrowing is available.
|
|
238
|
+
*/
|
|
188
239
|
type HasIndexFor<CF, IT extends string> = CF extends {
|
|
240
|
+
/** Optional values-first index map used for literal narrowing. */
|
|
189
241
|
indexes?: infer I;
|
|
190
242
|
} ? I extends Record<string, unknown> ? IT extends keyof I ? true : false : false : false;
|
|
191
243
|
/**
|
|
@@ -216,6 +268,13 @@ type PresentIndexTokenSet<CC extends BaseConfigMap, CF, IT extends string> = Rec
|
|
|
216
268
|
* @category QueryBuilder
|
|
217
269
|
*/
|
|
218
270
|
type FallbackIndexTokenSet<CC extends BaseConfigMap> = Record<CC['HashKey'] | CC['RangeKey'] | CC['ShardedKeys'] | CC['UnshardedKeys'] | CC['TranscodedProperties'], true>;
|
|
271
|
+
/**
|
|
272
|
+
* Derive the union of token names that may appear in a page key for a specific index.
|
|
273
|
+
*
|
|
274
|
+
* @remarks
|
|
275
|
+
* If CF carries a concrete `indexes` map and IT is a member key, this narrows to the
|
|
276
|
+
* exact component-token set for that index. Otherwise, it falls back to the broad key set.
|
|
277
|
+
*/
|
|
219
278
|
type IndexComponentTokens<CC extends BaseConfigMap, CF, IT extends string> = HasIndexFor<CF, IT> extends true ? keyof PresentIndexTokenSet<CC, CF, IT> : keyof FallbackIndexTokenSet<CC>;
|
|
220
279
|
/**
|
|
221
280
|
* Page key typed for a specific index token.
|
|
@@ -226,6 +285,15 @@ type IndexComponentTokens<CC extends BaseConfigMap, CF, IT extends string> = Has
|
|
|
226
285
|
*/
|
|
227
286
|
type PageKeyByIndex<CC extends BaseConfigMap, ET extends EntityToken<CC>, IT extends string = string, CF = unknown> = Pick<StorageItem<CC>, IndexComponentTokens<CC, CF, IT>>;
|
|
228
287
|
|
|
288
|
+
/**
|
|
289
|
+
* Runtime configuration schema for {@link EntityManager | `EntityManager`}.
|
|
290
|
+
*
|
|
291
|
+
* @remarks
|
|
292
|
+
* This is authoritative at runtime and used internally by the {@link EntityManager | `EntityManager`} constructor.
|
|
293
|
+
* It is also used by tests. It is not intended as a user-facing TypeDoc artifact.
|
|
294
|
+
*
|
|
295
|
+
* @hidden
|
|
296
|
+
*/
|
|
229
297
|
declare const configSchema: z$1.ZodObject<{
|
|
230
298
|
entities: z$1.ZodDefault<z$1.ZodOptional<z$1.ZodRecord<z$1.ZodString, z$1.ZodObject<{
|
|
231
299
|
defaultLimit: z$1.ZodDefault<z$1.ZodOptional<z$1.ZodNumber>>;
|
|
@@ -268,11 +336,88 @@ declare const configSchema: z$1.ZodObject<{
|
|
|
268
336
|
}, z$1.core.$strict>>>>;
|
|
269
337
|
}, z$1.core.$strict>;
|
|
270
338
|
/**
|
|
271
|
-
*
|
|
339
|
+
* Parsed transcoder entry.
|
|
340
|
+
*
|
|
341
|
+
* @remarks
|
|
342
|
+
* This reflects the runtime contract enforced by Zod for entries in `transcodes`.
|
|
343
|
+
*/
|
|
344
|
+
interface ParsedTranscoder {
|
|
345
|
+
/** Encode a value to a lexicographically sortable string. */
|
|
346
|
+
encode: unknown;
|
|
347
|
+
/** Decode a previously encoded string back to the value type. */
|
|
348
|
+
decode: unknown;
|
|
349
|
+
}
|
|
350
|
+
/**
|
|
351
|
+
* Parsed index definition (provider-agnostic).
|
|
352
|
+
*
|
|
353
|
+
* @remarks
|
|
354
|
+
* Provider adapters map these tokens to provider-specific index queries.
|
|
355
|
+
*/
|
|
356
|
+
interface ParsedIndexConfig {
|
|
357
|
+
/** Index hash key token (global hash key or a sharded generated key). */
|
|
358
|
+
hashKey: string;
|
|
359
|
+
/** Index range key token (global range key, an unsharded generated key, or a transcoded scalar). */
|
|
360
|
+
rangeKey: string;
|
|
361
|
+
/** Optional list of projected attribute names (validated to exclude key tokens). */
|
|
362
|
+
projections?: string[] | undefined;
|
|
363
|
+
}
|
|
364
|
+
/**
|
|
365
|
+
* Parsed generated properties configuration.
|
|
366
|
+
*/
|
|
367
|
+
interface ParsedGeneratedPropertiesConfig {
|
|
368
|
+
/** Sharded generated property tokens (hash-side); atomic encoding semantics. */
|
|
369
|
+
sharded: Record<string, string[]>;
|
|
370
|
+
/** Unsharded generated property tokens (range-side); non-atomic encoding semantics. */
|
|
371
|
+
unsharded: Record<string, string[]>;
|
|
372
|
+
}
|
|
373
|
+
/**
|
|
374
|
+
* Parsed per-entity configuration.
|
|
375
|
+
*/
|
|
376
|
+
interface ParsedEntityConfig {
|
|
377
|
+
/** Default max items returned by EntityManager.query for this entity (across all shards). */
|
|
378
|
+
defaultLimit: number;
|
|
379
|
+
/** Default per-shard page size used by EntityManager.query for this entity. */
|
|
380
|
+
defaultPageSize: number;
|
|
381
|
+
/** Shard bump schedule for this entity (time-based sharding scale-up). */
|
|
382
|
+
shardBumps: ShardBump[];
|
|
383
|
+
/** Property token whose value selects the shard bump (typically a timestamp). */
|
|
384
|
+
timestampProperty: string;
|
|
385
|
+
/** Property token used to dedupe and build the global range key. */
|
|
386
|
+
uniqueProperty: string;
|
|
387
|
+
}
|
|
388
|
+
/**
|
|
389
|
+
* Simplified runtime configuration shape after parsing/validation.
|
|
390
|
+
*
|
|
391
|
+
* @remarks
|
|
392
|
+
* This is the type exposed by {@link EntityManager.config | `EntityManager.config`}.
|
|
393
|
+
* It mirrors the validated Zod schema output.
|
|
272
394
|
*
|
|
273
395
|
* @category EntityManager
|
|
274
396
|
*/
|
|
275
|
-
|
|
397
|
+
interface ParsedConfig {
|
|
398
|
+
/** Entity definitions keyed by entity token. */
|
|
399
|
+
entities: Record<string, ParsedEntityConfig>;
|
|
400
|
+
/** Generated property token maps. */
|
|
401
|
+
generatedProperties: ParsedGeneratedPropertiesConfig;
|
|
402
|
+
/** Global hash key property name. */
|
|
403
|
+
hashKey: string;
|
|
404
|
+
/** Provider-agnostic index definitions keyed by index token. */
|
|
405
|
+
indexes: Record<string, ParsedIndexConfig>;
|
|
406
|
+
/** Delimiter between generated key elements (default `|`). */
|
|
407
|
+
generatedKeyDelimiter: string;
|
|
408
|
+
/** Delimiter between generated element name and value (default `#`). */
|
|
409
|
+
generatedValueDelimiter: string;
|
|
410
|
+
/** Map of transcoded property token -\> transcode name. */
|
|
411
|
+
propertyTranscodes: Record<string, string>;
|
|
412
|
+
/** Global range key property name. */
|
|
413
|
+
rangeKey: string;
|
|
414
|
+
/** Delimiter between entity token and shard suffix in hash key values (default `!`). */
|
|
415
|
+
shardKeyDelimiter: string;
|
|
416
|
+
/** Default max concurrency for shard queries during EntityManager.query. */
|
|
417
|
+
throttle: number;
|
|
418
|
+
/** Transcoder registry used for encoding/decoding values. */
|
|
419
|
+
transcodes: Record<string, ParsedTranscoder>;
|
|
420
|
+
}
|
|
276
421
|
|
|
277
422
|
/** EntityOfToken — resolves the concrete entity shape for a specific entity token. */
|
|
278
423
|
type EntityOfToken<CC extends BaseConfigMap, ET extends EntityToken<CC>> = Exactify<CC['EntityMap']>[ET];
|
|
@@ -340,6 +485,7 @@ interface ShardQueryResult<CC extends BaseConfigMap, ET extends EntityToken<CC>,
|
|
|
340
485
|
* @protected
|
|
341
486
|
*/
|
|
342
487
|
type ShardQueryFunction<CC extends BaseConfigMap, ET extends EntityToken<CC>, IT extends string, CF = unknown, K = unknown> = CF extends {
|
|
488
|
+
/** Optional values-first index map used for index-token narrowing. */
|
|
343
489
|
indexes?: infer I;
|
|
344
490
|
} ? I extends Record<string, unknown> ? IT extends Extract<keyof I, string> ? (hashKey: string, pageKey?: PageKeyByIndex<CC, ET, IT, CF>, pageSize?: number) => Promise<ShardQueryResult<CC, ET, IT, CF, K>> : never : (hashKey: string, pageKey?: PageKeyByIndex<CC, ET, IT, CF>, pageSize?: number) => Promise<ShardQueryResult<CC, ET, IT, CF, K>> : (hashKey: string, pageKey?: PageKeyByIndex<CC, ET, IT, CF>, pageSize?: number) => Promise<ShardQueryResult<CC, ET, IT, CF, K>>;
|
|
345
491
|
|
|
@@ -360,6 +506,7 @@ type ShardQueryFunction<CC extends BaseConfigMap, ET extends EntityToken<CC>, IT
|
|
|
360
506
|
* @protected
|
|
361
507
|
*/
|
|
362
508
|
type ShardQueryMap<CC extends BaseConfigMap, ET extends EntityToken<CC>, ITS extends string, CF = unknown, K = unknown> = CF extends {
|
|
509
|
+
/** Optional values-first index map used for index-token narrowing. */
|
|
363
510
|
indexes?: infer I;
|
|
364
511
|
} ? I extends Record<string, unknown> ? Record<Extract<ITS, Extract<keyof I, string>>, ShardQueryFunction<CC, ET, Extract<ITS, Extract<keyof I, string>>, CF, K>> : Record<ITS, ShardQueryFunction<CC, ET, ITS, CF, K>> : Record<ITS, ShardQueryFunction<CC, ET, ITS, CF, K>>;
|
|
365
512
|
/**
|
|
@@ -567,9 +714,9 @@ declare class EntityManager<CC extends BaseConfigMap, CF = unknown> {
|
|
|
567
714
|
/**
|
|
568
715
|
* Update generated properties, hash key, and range key on an {@link EntityItem | `EntityItem`} object.
|
|
569
716
|
*
|
|
570
|
-
* @param entityToken -
|
|
571
|
-
* @param item -
|
|
572
|
-
* @param overwrite - Overwrite existing properties (default `false`).
|
|
717
|
+
* @param entityToken - Entity token (narrows types by token).
|
|
718
|
+
* @param item - Single item to update with generated keys/properties.
|
|
719
|
+
* @param overwrite - Overwrite existing keys/properties (default `false`).
|
|
573
720
|
*
|
|
574
721
|
* @returns {@link EntityRecord | `EntityRecord`} object with updated properties.
|
|
575
722
|
*
|
|
@@ -579,22 +726,44 @@ declare class EntityManager<CC extends BaseConfigMap, CF = unknown> {
|
|
|
579
726
|
*/
|
|
580
727
|
addKeys<ET extends EntityToken<CC>>(entityToken: ET, item: EntityItemPartial<CC, ET>, overwrite?: boolean): EntityRecordPartial<CC, ET>;
|
|
581
728
|
/**
|
|
729
|
+
* Update generated properties, hash key, and range key on an array of {@link EntityItem | `EntityItem`} objects.
|
|
730
|
+
*
|
|
731
|
+
* @param entityToken - Entity token (narrows types by token).
|
|
732
|
+
* @param item - Items to update with generated keys/properties.
|
|
733
|
+
* @param overwrite - Overwrite existing keys/properties (default `false`).
|
|
734
|
+
*
|
|
735
|
+
* @returns Array of {@link EntityRecord | `EntityRecord`} objects with updated properties.
|
|
736
|
+
*
|
|
737
|
+
* @throws `Error` if `entityToken` is invalid.
|
|
738
|
+
*
|
|
582
739
|
* @overload
|
|
583
740
|
*/
|
|
584
741
|
addKeys<ET extends EntityToken<CC>>(entityToken: ET, item: EntityItemPartial<CC, ET>[], overwrite?: boolean): EntityRecordPartial<CC, ET>[];
|
|
585
742
|
/**
|
|
586
743
|
* Convert one or more {@link EntityItem | `EntityItem`} objects into an array of {@link EntityKey | `EntityKey`} values.
|
|
587
744
|
*
|
|
588
|
-
* @param entityToken -
|
|
589
|
-
* @param item -
|
|
590
|
-
* @param overwrite - Overwrite existing
|
|
745
|
+
* @param entityToken - Entity token (narrows types by token).
|
|
746
|
+
* @param item - Single item to derive primary keys for.
|
|
747
|
+
* @param overwrite - Overwrite existing keys on the item before deriving (default `false`).
|
|
591
748
|
*
|
|
592
749
|
* @returns Array of {@link EntityKey | `EntityKey`} values derived from `item`.
|
|
593
750
|
*
|
|
594
751
|
* @throws `Error` if `entityToken` is invalid.
|
|
752
|
+
*
|
|
753
|
+
* @overload
|
|
595
754
|
*/
|
|
596
755
|
getPrimaryKey<ET extends EntityToken<CC>>(entityToken: ET, item: EntityItemPartial<CC, ET>, overwrite?: boolean): EntityKey<CC>[];
|
|
597
756
|
/**
|
|
757
|
+
* Convert an array of {@link EntityItem | `EntityItem`} objects into {@link EntityKey | `EntityKey`} values.
|
|
758
|
+
*
|
|
759
|
+
* @param entityToken - Entity token (narrows types by token).
|
|
760
|
+
* @param items - Array of items to derive primary keys for.
|
|
761
|
+
* @param overwrite - Overwrite existing keys on each item before deriving (default `false`).
|
|
762
|
+
*
|
|
763
|
+
* @returns Array of {@link EntityKey | `EntityKey`} values derived from all `items`.
|
|
764
|
+
*
|
|
765
|
+
* @throws `Error` if `entityToken` is invalid.
|
|
766
|
+
*
|
|
598
767
|
* @overload
|
|
599
768
|
*/
|
|
600
769
|
getPrimaryKey<ET extends EntityToken<CC>>(entityToken: ET, items: EntityItemPartial<CC, ET>[], overwrite?: boolean): EntityKey<CC>[];
|
|
@@ -660,56 +829,110 @@ declare class EntityManager<CC extends BaseConfigMap, CF = unknown> {
|
|
|
660
829
|
* Keep this intentionally permissive to maximize inference from `as const`.
|
|
661
830
|
*/
|
|
662
831
|
interface ConfigInput {
|
|
832
|
+
/** Global hash key property name (e.g., `"pk"`). */
|
|
663
833
|
hashKey: string;
|
|
834
|
+
/** Global range key property name (e.g., `"sk"`). */
|
|
664
835
|
rangeKey: string;
|
|
836
|
+
/**
|
|
837
|
+
* Optional generated property token maps.
|
|
838
|
+
*
|
|
839
|
+
* @remarks
|
|
840
|
+
* - `sharded` keys are hash-side generated property tokens and are encoded atomically.
|
|
841
|
+
* - `unsharded` keys are range-side generated property tokens.
|
|
842
|
+
*/
|
|
665
843
|
generatedProperties?: {
|
|
844
|
+
/** Sharded generated property tokens (hash-side). */
|
|
666
845
|
sharded?: Record<string, readonly string[]>;
|
|
846
|
+
/** Unsharded generated property tokens (range-side). */
|
|
667
847
|
unsharded?: Record<string, readonly string[]>;
|
|
668
848
|
};
|
|
849
|
+
/**
|
|
850
|
+
* Optional map of transcodable property token -\> transcode name.
|
|
851
|
+
*
|
|
852
|
+
* @remarks
|
|
853
|
+
* Only properties present here are treated as “transcoded properties”.
|
|
854
|
+
*/
|
|
669
855
|
propertyTranscodes?: Record<string, string>;
|
|
856
|
+
/**
|
|
857
|
+
* Optional index token map used for typing and paging-key narrowing.
|
|
858
|
+
*
|
|
859
|
+
* @remarks
|
|
860
|
+
* This is provider-agnostic metadata (not a provider-specific index definition).
|
|
861
|
+
*/
|
|
670
862
|
indexes?: Record<string, {
|
|
863
|
+
/** Index hash key token (global hash key or sharded generated key). */
|
|
671
864
|
hashKey: string;
|
|
865
|
+
/** Index range key token (global range key, unsharded generated key, or transcoded scalar). */
|
|
672
866
|
rangeKey: string;
|
|
867
|
+
/** Optional list of projected attribute names (validated at runtime to exclude key tokens). */
|
|
673
868
|
projections?: string[];
|
|
674
869
|
}>;
|
|
870
|
+
/**
|
|
871
|
+
* Optional per-entity configuration (runtime semantics).
|
|
872
|
+
*
|
|
873
|
+
* @remarks
|
|
874
|
+
* This is intentionally permissive in `ConfigInput`; runtime validation occurs
|
|
875
|
+
* in the {@link EntityManager | `EntityManager`} constructor via Zod.
|
|
876
|
+
*/
|
|
675
877
|
entities?: Record<string, unknown>;
|
|
676
878
|
/**
|
|
677
879
|
* Optional Zod schemas for per-entity domain shapes (non-generated fields only).
|
|
678
880
|
*
|
|
679
|
-
*
|
|
680
|
-
*
|
|
881
|
+
* @remarks
|
|
882
|
+
* Schemas MUST declare only base (non-generated) properties. Do not include:
|
|
883
|
+
* - global keys (hashKey/rangeKey), or
|
|
884
|
+
* - generated property tokens (sharded/unsharded keys).
|
|
681
885
|
*/
|
|
682
886
|
entitiesSchema?: Record<string, ZodType>;
|
|
887
|
+
/** Optional delimiter between generated key elements (default `|`). */
|
|
683
888
|
generatedKeyDelimiter?: string;
|
|
889
|
+
/** Optional delimiter between a generated element name and its value (default `#`). */
|
|
684
890
|
generatedValueDelimiter?: string;
|
|
891
|
+
/** Optional delimiter between entity token and shard suffix in hash key values (default `!`). */
|
|
685
892
|
shardKeyDelimiter?: string;
|
|
893
|
+
/** Optional transcode registry/value (validated at runtime). */
|
|
686
894
|
transcodes?: unknown;
|
|
895
|
+
/** Optional maximum concurrency for shard queries. */
|
|
687
896
|
throttle?: number;
|
|
688
897
|
}
|
|
898
|
+
/** Extract the hash key token string literal from a values-first config input type. */
|
|
689
899
|
type HashKeyFrom<CC> = CC extends {
|
|
900
|
+
/** Hash key token property name. */
|
|
690
901
|
hashKey: infer H;
|
|
691
902
|
} ? H & string : 'hashKey';
|
|
903
|
+
/** Extract the range key token string literal from a values-first config input type. */
|
|
692
904
|
type RangeKeyFrom<CC> = CC extends {
|
|
905
|
+
/** Range key token property name. */
|
|
693
906
|
rangeKey: infer R;
|
|
694
907
|
} ? R & string : 'rangeKey';
|
|
908
|
+
/** Extract the union of sharded generated key tokens from a values-first config input type. */
|
|
695
909
|
type ShardedKeysFrom<CC> = CC extends {
|
|
910
|
+
/** Optional generated properties object containing sharded/unsharded maps. */
|
|
696
911
|
generatedProperties?: infer GP;
|
|
697
912
|
} ? GP extends {
|
|
913
|
+
/** Sharded generated property token map. */
|
|
698
914
|
sharded?: infer S;
|
|
699
915
|
} ? keyof S & string : never : never;
|
|
916
|
+
/** Extract the union of unsharded generated key tokens from a values-first config input type. */
|
|
700
917
|
type UnshardedKeysFrom<CC> = CC extends {
|
|
918
|
+
/** Optional generated properties object containing sharded/unsharded maps. */
|
|
701
919
|
generatedProperties?: infer GP;
|
|
702
920
|
} ? GP extends {
|
|
921
|
+
/** Unsharded generated property token map. */
|
|
703
922
|
unsharded?: infer U;
|
|
704
923
|
} ? keyof U & string : never : never;
|
|
924
|
+
/** Extract the union of transcoded property tokens from a values-first config input type. */
|
|
705
925
|
type TranscodedPropertiesFrom<CC> = CC extends {
|
|
926
|
+
/** Optional map of property token -\> transcode name. */
|
|
706
927
|
propertyTranscodes?: infer PT;
|
|
707
928
|
} ? keyof PT & string : never;
|
|
708
929
|
/**
|
|
709
930
|
* Derive an EntityMap from CC.entitiesSchema when provided (values-first, no generics).
|
|
931
|
+
*
|
|
710
932
|
* Fallback to broad EntityMap if schemas are absent.
|
|
711
933
|
*/
|
|
712
934
|
type EntitiesFromSchema<CC> = CC extends {
|
|
935
|
+
/** Optional per-entity Zod schema map used only for type inference. */
|
|
713
936
|
entitiesSchema?: infer S;
|
|
714
937
|
} ? S extends Record<string, ZodType> ? {
|
|
715
938
|
[K in Extract<keyof S, string>]: z.infer<S[K]>;
|
|
@@ -722,6 +945,7 @@ type EntitiesFromSchema<CC> = CC extends {
|
|
|
722
945
|
* index token union. Falls back to `string` if absent.
|
|
723
946
|
*/
|
|
724
947
|
type IndexTokensFrom<CC> = CC extends {
|
|
948
|
+
/** Optional index token map used for index-token inference. */
|
|
725
949
|
indexes?: infer I;
|
|
726
950
|
} ? keyof I & string : string;
|
|
727
951
|
/**
|
|
@@ -729,12 +953,19 @@ type IndexTokensFrom<CC> = CC extends {
|
|
|
729
953
|
* and an EntityMap (defaults to MinimalEntityMapFrom<CC>).
|
|
730
954
|
*/
|
|
731
955
|
interface CapturedConfigMapFrom<CC, EM extends EntityMap> extends BaseConfigMap {
|
|
956
|
+
/** Entity map type (from schemas when provided; otherwise broad). */
|
|
732
957
|
EntityMap: EM;
|
|
958
|
+
/** Hash key token captured from the config literal. */
|
|
733
959
|
HashKey: HashKeyFrom<CC>;
|
|
960
|
+
/** Range key token captured from the config literal. */
|
|
734
961
|
RangeKey: RangeKeyFrom<CC>;
|
|
962
|
+
/** Sharded generated key token union captured from the config literal. */
|
|
735
963
|
ShardedKeys: ShardedKeysFrom<CC>;
|
|
964
|
+
/** Unsharded generated key token union captured from the config literal. */
|
|
736
965
|
UnshardedKeys: UnshardedKeysFrom<CC>;
|
|
966
|
+
/** Transcoded property token union captured from the config literal. */
|
|
737
967
|
TranscodedProperties: TranscodedPropertiesFrom<CC>;
|
|
968
|
+
/** Transcode registry type (default registry; runtime validation still applies). */
|
|
738
969
|
TranscodeRegistry: DefaultTranscodeRegistry;
|
|
739
970
|
}
|
|
740
971
|
/**
|
|
@@ -804,8 +1035,32 @@ declare abstract class BaseEntityClient<CC extends BaseConfigMap, CF = unknown>
|
|
|
804
1035
|
constructor(options: BaseEntityClientOptions<CC, CF>);
|
|
805
1036
|
}
|
|
806
1037
|
|
|
1038
|
+
/**
|
|
1039
|
+
* Extract the captured config map type from a {@link BaseEntityClient | `BaseEntityClient`} instance type.
|
|
1040
|
+
*
|
|
1041
|
+
* @typeParam EC - A {@link BaseEntityClient | `BaseEntityClient`} instance type.
|
|
1042
|
+
*
|
|
1043
|
+
* @remarks
|
|
1044
|
+
* This is a pure type-level helper used to derive token-aware types from a client
|
|
1045
|
+
* instance type without requiring callers to restate the config map type.
|
|
1046
|
+
*/
|
|
807
1047
|
type ConfigOfClient<EC> = EC extends BaseEntityClient<infer CC> ? CC : never;
|
|
1048
|
+
/**
|
|
1049
|
+
* Map a client instance type + entity token to the storage-facing record type.
|
|
1050
|
+
*
|
|
1051
|
+
* @typeParam EC - A {@link BaseEntityClient | `BaseEntityClient`} instance type.
|
|
1052
|
+
* @typeParam ET - An {@link EntityToken | `EntityToken`} for that client’s config.
|
|
1053
|
+
*/
|
|
808
1054
|
type EntityClientRecordByToken<EC, ET extends EntityToken<ConfigOfClient<EC>>> = EntityRecord<ConfigOfClient<EC>, ET>;
|
|
1055
|
+
/**
|
|
1056
|
+
* Map a client instance type + entity token to the domain-facing item type.
|
|
1057
|
+
*
|
|
1058
|
+
* This is the “item-facing” shape (global keys and generated property tokens are
|
|
1059
|
+
* not required and are typically stripped via {@link EntityManager.removeKeys | `removeKeys`}).
|
|
1060
|
+
*
|
|
1061
|
+
* @typeParam EC - A {@link BaseEntityClient | `BaseEntityClient`} instance type.
|
|
1062
|
+
* @typeParam ET - An {@link EntityToken | `EntityToken`} for that client’s config.
|
|
1063
|
+
*/
|
|
809
1064
|
type EntityClientItemByToken<EC, ET extends EntityToken<ConfigOfClient<EC>>> = EntityItem<ConfigOfClient<EC>, ET>;
|
|
810
1065
|
|
|
811
1066
|
/**
|
|
@@ -867,6 +1122,23 @@ declare abstract class BaseQueryBuilder<CC extends BaseConfigMap, EntityClient e
|
|
|
867
1122
|
readonly indexParamsMap: Record<ITS, IndexParams>;
|
|
868
1123
|
/** BaseQueryBuilder constructor. */
|
|
869
1124
|
constructor(options: BaseQueryBuilderOptions<CC, EntityClient>);
|
|
1125
|
+
/**
|
|
1126
|
+
* Build a shard query function for a specific index token.
|
|
1127
|
+
*
|
|
1128
|
+
* @param indexToken - Index token identifying which index to query.
|
|
1129
|
+
*
|
|
1130
|
+
* @returns A {@link ShardQueryFunction | `ShardQueryFunction`} that queries a single shard for this index.
|
|
1131
|
+
*
|
|
1132
|
+
* @remarks
|
|
1133
|
+
* Implementations are provider-specific (e.g., DynamoDB). The returned function must:
|
|
1134
|
+
* - Query exactly one shard (partition) per invocation using the provided hash key value.
|
|
1135
|
+
* - Respect `pageKey` and `pageSize` for pagination.
|
|
1136
|
+
* - Return `pageKey: undefined` when that shard is exhausted.
|
|
1137
|
+
*
|
|
1138
|
+
* Entity Manager will orchestrate calling these functions across shards and indexes.
|
|
1139
|
+
*
|
|
1140
|
+
* @protected
|
|
1141
|
+
*/
|
|
870
1142
|
protected abstract getShardQueryFunction(indexToken: ITS): ShardQueryFunction<CC, ET, ITS, CF, K>;
|
|
871
1143
|
/**
|
|
872
1144
|
* Builds a {@link ShardQueryMap | `ShardQueryMap`} object.
|
|
@@ -874,8 +1146,18 @@ declare abstract class BaseQueryBuilder<CC extends BaseConfigMap, EntityClient e
|
|
|
874
1146
|
* @returns - The {@link ShardQueryMap | `ShardQueryMap`} object.
|
|
875
1147
|
*/
|
|
876
1148
|
build(): ShardQueryMap<CC, ET, ITS, CF, K>;
|
|
1149
|
+
/**
|
|
1150
|
+
* Execute the built query across shards and indexes via {@link EntityManager.query | `EntityManager.query`}.
|
|
1151
|
+
*
|
|
1152
|
+
* @param options - Query options excluding `entityToken`, `pageKeyMap`, and `shardQueryMap`, which are supplied by the builder.
|
|
1153
|
+
*
|
|
1154
|
+
* @returns The merged, de-duplicated, sorted query result, including a compact `pageKeyMap` token for the next page.
|
|
1155
|
+
*
|
|
1156
|
+
* @remarks
|
|
1157
|
+
* This delegates orchestration to Entity Manager; provider-specific behavior lives in {@link getShardQueryFunction | `getShardQueryFunction`}.
|
|
1158
|
+
*/
|
|
877
1159
|
query(options: QueryBuilderQueryOptions<CC, ET, CF>): Promise<QueryResult<CC, ET, ITS, K>>;
|
|
878
1160
|
}
|
|
879
1161
|
|
|
880
1162
|
export { BaseEntityClient, BaseQueryBuilder, EntityManager, configSchema, createEntityManager };
|
|
881
|
-
export type { BaseConfigMap, BaseEntityClientOptions, BaseKeyTokens, BaseQueryBuilderOptions, CapturedConfigMapFrom, Config, ConfigInput, ConfigMap, ConfigOfClient, EntitiesFromSchema, EntityClientItemByToken, EntityClientRecordByToken, EntityItem, EntityItemPartial, EntityKey, EntityOfToken, EntityRecord, EntityRecordPartial, EntityToken, FallbackIndexTokenSet, HasIndexFor, HashKeyFrom, IndexComponentTokens, IndexHashKeyOf, IndexRangeKeyOf, IndexTokensFrom, IndexTokensOf, KeysFrom, PageKey, PageKeyByIndex, ParsedConfig, PresentIndexTokenSet, Projected, QueryBuilderQueryOptions, QueryOptions, QueryOptionsByCC, QueryOptionsByCF, QueryResult, RangeKeyFrom, ShardBump, ShardQueryFunction, ShardQueryMap, ShardQueryMapByCC, ShardQueryMapByCF, ShardQueryResult, ShardedKeysFrom, StorageItem, StorageRecord, TranscodedPropertiesFrom, UnshardedKeysFrom, ValidateConfigMap };
|
|
1163
|
+
export type { BaseConfigMap, BaseEntityClientOptions, BaseKeyTokens, BaseQueryBuilderOptions, CapturedConfigMapFrom, Config, ConfigInput, ConfigMap, ConfigOfClient, EntitiesFromSchema, EntityClientItemByToken, EntityClientRecordByToken, EntityItem, EntityItemPartial, EntityKey, EntityOfToken, EntityRecord, EntityRecordPartial, EntityToken, FallbackIndexTokenSet, HasIndexFor, HashKeyFrom, IndexComponentTokens, IndexHashKeyOf, IndexRangeKeyOf, IndexTokensFrom, IndexTokensOf, KeysFrom, PageKey, PageKeyByIndex, ParsedConfig, ParsedEntityConfig, ParsedGeneratedPropertiesConfig, ParsedIndexConfig, ParsedTranscoder, PresentIndexTokenSet, Projected, QueryBuilderQueryOptions, QueryOptions, QueryOptionsByCC, QueryOptionsByCF, QueryResult, RangeKeyFrom, ShardBump, ShardQueryFunction, ShardQueryMap, ShardQueryMapByCC, ShardQueryMapByCF, ShardQueryResult, ShardedKeysFrom, StorageItem, StorageRecord, TranscodedPropertiesFrom, UnshardedKeysFrom, ValidateConfigMap };
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { mapValues } from 'radash';
|
|
2
2
|
|
|
3
|
+
/* eslint-disable @typescript-eslint/no-unused-vars */
|
|
3
4
|
/**
|
|
4
5
|
* Abstract base class supporting a fluent API for building a {@link ShardQueryMap | `ShardQueryMap`} using a database client.
|
|
5
6
|
*
|
|
@@ -34,6 +35,16 @@ class BaseQueryBuilder {
|
|
|
34
35
|
build() {
|
|
35
36
|
return mapValues(this.indexParamsMap, (_indexConfig, indexToken) => this.getShardQueryFunction(indexToken));
|
|
36
37
|
}
|
|
38
|
+
/**
|
|
39
|
+
* Execute the built query across shards and indexes via {@link EntityManager.query | `EntityManager.query`}.
|
|
40
|
+
*
|
|
41
|
+
* @param options - Query options excluding `entityToken`, `pageKeyMap`, and `shardQueryMap`, which are supplied by the builder.
|
|
42
|
+
*
|
|
43
|
+
* @returns The merged, de-duplicated, sorted query result, including a compact `pageKeyMap` token for the next page.
|
|
44
|
+
*
|
|
45
|
+
* @remarks
|
|
46
|
+
* This delegates orchestration to Entity Manager; provider-specific behavior lives in {@link getShardQueryFunction | `getShardQueryFunction`}.
|
|
47
|
+
*/
|
|
37
48
|
async query(options) {
|
|
38
49
|
const { entityClient: { entityManager }, entityToken, pageKeyMap, } = this;
|
|
39
50
|
const shardQueryMap = this.build();
|
|
@@ -27,19 +27,54 @@ const componentArray = z
|
|
|
27
27
|
.array(z.string().min(1))
|
|
28
28
|
.nonempty()
|
|
29
29
|
.superRefine(validateArrayUnique);
|
|
30
|
+
/**
|
|
31
|
+
* Runtime configuration schema for {@link EntityManager | `EntityManager`}.
|
|
32
|
+
*
|
|
33
|
+
* @remarks
|
|
34
|
+
* This is authoritative at runtime and used internally by the {@link EntityManager | `EntityManager`} constructor.
|
|
35
|
+
* It is also used by tests. It is not intended as a user-facing TypeDoc artifact.
|
|
36
|
+
*
|
|
37
|
+
* @hidden
|
|
38
|
+
*/
|
|
30
39
|
const configSchema = z
|
|
31
40
|
.object({
|
|
32
41
|
entities: z
|
|
33
42
|
.record(z.string(), z
|
|
34
43
|
.object({
|
|
35
|
-
defaultLimit: z
|
|
36
|
-
|
|
44
|
+
defaultLimit: z
|
|
45
|
+
.number()
|
|
46
|
+
.int()
|
|
47
|
+
.positive()
|
|
48
|
+
.optional()
|
|
49
|
+
.default(10)
|
|
50
|
+
.describe('Default max items returned by EntityManager.query for this entity (across all shards).'),
|
|
51
|
+
defaultPageSize: z
|
|
52
|
+
.number()
|
|
53
|
+
.int()
|
|
54
|
+
.positive()
|
|
55
|
+
.optional()
|
|
56
|
+
.default(10)
|
|
57
|
+
.describe('Default per-shard page size used by EntityManager.query for this entity.'),
|
|
37
58
|
shardBumps: z
|
|
38
59
|
.array(z
|
|
39
60
|
.object({
|
|
40
|
-
timestamp: z
|
|
41
|
-
|
|
42
|
-
|
|
61
|
+
timestamp: z
|
|
62
|
+
.number()
|
|
63
|
+
.int()
|
|
64
|
+
.nonnegative()
|
|
65
|
+
.describe('Start timestamp (ms) for this shard bump (inclusive).'),
|
|
66
|
+
charBits: z
|
|
67
|
+
.number()
|
|
68
|
+
.int()
|
|
69
|
+
.min(1)
|
|
70
|
+
.max(5)
|
|
71
|
+
.describe('Bits per shard character (radix = 2**charBits).'),
|
|
72
|
+
chars: z
|
|
73
|
+
.number()
|
|
74
|
+
.int()
|
|
75
|
+
.min(0)
|
|
76
|
+
.max(40)
|
|
77
|
+
.describe('Shard suffix width (chars); controls shard space.'),
|
|
43
78
|
})
|
|
44
79
|
.strict())
|
|
45
80
|
.optional()
|
|
@@ -71,45 +106,92 @@ const configSchema = z
|
|
|
71
106
|
});
|
|
72
107
|
}
|
|
73
108
|
}),
|
|
74
|
-
timestampProperty: z
|
|
75
|
-
|
|
109
|
+
timestampProperty: z
|
|
110
|
+
.string()
|
|
111
|
+
.min(1)
|
|
112
|
+
.describe('Property token whose value selects the shard bump (typically a timestamp).'),
|
|
113
|
+
uniqueProperty: z
|
|
114
|
+
.string()
|
|
115
|
+
.min(1)
|
|
116
|
+
.describe('Property token used to dedupe and build the global range key.'),
|
|
76
117
|
})
|
|
77
118
|
.strict())
|
|
78
119
|
.optional()
|
|
79
|
-
.default({})
|
|
120
|
+
.default({})
|
|
121
|
+
.describe('Entity definitions keyed by entity token.'),
|
|
80
122
|
generatedProperties: z
|
|
81
123
|
.object({
|
|
82
|
-
sharded: z
|
|
83
|
-
|
|
124
|
+
sharded: z
|
|
125
|
+
.record(z.string(), componentArray)
|
|
126
|
+
.optional()
|
|
127
|
+
.default({})
|
|
128
|
+
.describe('Sharded generated property tokens (hash-side); atomic encoding semantics.'),
|
|
129
|
+
unsharded: z
|
|
130
|
+
.record(z.string(), componentArray)
|
|
131
|
+
.optional()
|
|
132
|
+
.default({})
|
|
133
|
+
.describe('Unsharded generated property tokens (range-side); non-atomic encoding semantics.'),
|
|
84
134
|
})
|
|
85
135
|
.optional()
|
|
86
136
|
.default({ sharded: {}, unsharded: {} }),
|
|
87
|
-
hashKey: z.string(),
|
|
137
|
+
hashKey: z.string().describe('Global hash key property name.'),
|
|
88
138
|
indexes: z
|
|
89
139
|
.record(z.string(), z.object({
|
|
90
|
-
hashKey: z
|
|
91
|
-
|
|
140
|
+
hashKey: z
|
|
141
|
+
.string()
|
|
142
|
+
.min(1)
|
|
143
|
+
.describe('Index hash key token (global hash key or a sharded generated key).'),
|
|
144
|
+
rangeKey: z
|
|
145
|
+
.string()
|
|
146
|
+
.min(1)
|
|
147
|
+
.describe('Index range key token (global range key, an unsharded generated key, or a transcoded property).'),
|
|
92
148
|
projections: z
|
|
93
149
|
.array(z.string().min(1))
|
|
94
150
|
.superRefine(validateArrayUnique)
|
|
95
151
|
.optional(),
|
|
96
152
|
}))
|
|
97
153
|
.optional()
|
|
98
|
-
.default({})
|
|
99
|
-
|
|
100
|
-
|
|
154
|
+
.default({})
|
|
155
|
+
.describe('Index definitions keyed by index token.'),
|
|
156
|
+
generatedKeyDelimiter: z
|
|
157
|
+
.string()
|
|
158
|
+
.regex(/\W+/)
|
|
159
|
+
.optional()
|
|
160
|
+
.default('|')
|
|
161
|
+
.describe('Delimiter between generated key elements (default `|`).'),
|
|
162
|
+
generatedValueDelimiter: z
|
|
163
|
+
.string()
|
|
164
|
+
.regex(/\W+/)
|
|
165
|
+
.optional()
|
|
166
|
+
.default('#')
|
|
167
|
+
.describe('Delimiter between generated element name and value (default `#`).'),
|
|
101
168
|
propertyTranscodes: z.record(z.string(), z.string()).optional().default({}),
|
|
102
|
-
rangeKey: z.string(),
|
|
103
|
-
shardKeyDelimiter: z
|
|
104
|
-
|
|
169
|
+
rangeKey: z.string().describe('Global range key property name.'),
|
|
170
|
+
shardKeyDelimiter: z
|
|
171
|
+
.string()
|
|
172
|
+
.regex(/\W+/)
|
|
173
|
+
.optional()
|
|
174
|
+
.default('!')
|
|
175
|
+
.describe('Delimiter between entity token and shard suffix in hash key values.'),
|
|
176
|
+
throttle: z
|
|
177
|
+
.number()
|
|
178
|
+
.int()
|
|
179
|
+
.positive()
|
|
180
|
+
.optional()
|
|
181
|
+
.default(10)
|
|
182
|
+
.describe('Default max concurrency for shard queries during EntityManager.query.'),
|
|
105
183
|
transcodes: z
|
|
106
184
|
.record(z.string(), z
|
|
107
185
|
.object({
|
|
108
186
|
// Accept function shapes without relying on z.function()
|
|
109
187
|
// to avoid TS inference conflicts across Zod versions and
|
|
110
188
|
// to remain compatible with narrower parameter types.
|
|
111
|
-
encode: z
|
|
112
|
-
|
|
189
|
+
encode: z
|
|
190
|
+
.custom((fn) => typeof fn === 'function')
|
|
191
|
+
.describe('Encode a value to a lexicographically sortable string.'),
|
|
192
|
+
decode: z
|
|
193
|
+
.custom((fn) => typeof fn === 'function')
|
|
194
|
+
.describe('Decode a previously encoded string back to the value type.'),
|
|
113
195
|
})
|
|
114
196
|
.strict())
|
|
115
197
|
.optional()
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
function findIndexToken(entityManager, hashKeyToken, rangeKeyToken, suppressError) {
|
|
2
|
-
const indexToken = (Object.entries(entityManager.config.indexes).find(([, index]) => index.hashKey === hashKeyToken &&
|
|
3
|
-
index.rangeKey === rangeKeyToken)?.[0] ?? undefined);
|
|
2
|
+
const indexToken = (Object.entries(entityManager.config.indexes).find(([, index]) => index.hashKey === hashKeyToken && index.rangeKey === rangeKeyToken)?.[0] ?? undefined);
|
|
4
3
|
if (!indexToken && !suppressError)
|
|
5
4
|
throw new Error(`No index token found for hashKey '${hashKeyToken}' & rangeKey '${rangeKeyToken}'.`);
|
|
6
5
|
return indexToken;
|
|
@@ -15,12 +15,7 @@ function getIndexComponents(entityManager, indexToken) {
|
|
|
15
15
|
validateIndexToken(entityManager, indexToken);
|
|
16
16
|
const { hashKey, rangeKey, indexes } = entityManager.config;
|
|
17
17
|
const { hashKey: indexHashKey, rangeKey: indexRangeKey } = indexes[indexToken];
|
|
18
|
-
return unique([
|
|
19
|
-
hashKey,
|
|
20
|
-
rangeKey,
|
|
21
|
-
indexHashKey,
|
|
22
|
-
indexRangeKey,
|
|
23
|
-
]);
|
|
18
|
+
return unique([hashKey, rangeKey, indexHashKey, indexRangeKey]);
|
|
24
19
|
}
|
|
25
20
|
|
|
26
21
|
export { getIndexComponents };
|
|
@@ -38,7 +38,7 @@ async function query(entityManager, options) {
|
|
|
38
38
|
if (!(isInt(pageSize) && pageSize >= 1))
|
|
39
39
|
throw new Error('pageSize must be a positive integer');
|
|
40
40
|
// Rehydrate pageKeyMap.
|
|
41
|
-
const [hashKeyToken, rehydratedPageKeyMap] = rehydratePageKeyMap(entityManager, entityToken, Object.keys(shardQueryMap), item, pageKeyMap
|
|
41
|
+
const [hashKeyToken, rehydratedPageKeyMap] = rehydratePageKeyMap(entityManager, entityToken, Object.keys(shardQueryMap).sort(), item, pageKeyMap
|
|
42
42
|
? JSON.parse(decompressFromEncodedURIComponent(pageKeyMap))
|
|
43
43
|
: undefined, timestampFrom, timestampTo);
|
|
44
44
|
// Shortcut if pageKeyMap is empty.
|
package/package.json
CHANGED
|
@@ -10,53 +10,53 @@
|
|
|
10
10
|
"url": "https://github.com/karmaniverous/entity-manager/issues"
|
|
11
11
|
},
|
|
12
12
|
"dependencies": {
|
|
13
|
-
"@karmaniverous/batch-process": "^0.1.
|
|
14
|
-
"@karmaniverous/entity-tools": "^0.8.
|
|
15
|
-
"@karmaniverous/string-utilities": "^0.2.
|
|
13
|
+
"@karmaniverous/batch-process": "^0.1.1",
|
|
14
|
+
"@karmaniverous/entity-tools": "^0.8.1",
|
|
15
|
+
"@karmaniverous/string-utilities": "^0.2.3",
|
|
16
16
|
"lz-string": "^1.5.0",
|
|
17
17
|
"radash": "^12.1.1",
|
|
18
18
|
"string-hash": "^1.1.3",
|
|
19
|
-
"zod": "^4.
|
|
19
|
+
"zod": "^4.4.3"
|
|
20
20
|
},
|
|
21
21
|
"description": "Rational indexing & cross-shard querying at scale in your NoSQL database so you can focus on your application logic.",
|
|
22
22
|
"devDependencies": {
|
|
23
|
-
"@dotenvx/dotenvx": "^
|
|
24
|
-
"@eslint/js": "^
|
|
25
|
-
"@faker-js/faker": "^10.
|
|
26
|
-
"@karmaniverous/mock-db": "^0.4.
|
|
23
|
+
"@dotenvx/dotenvx": "^2.9.0",
|
|
24
|
+
"@eslint/js": "^10.0.1",
|
|
25
|
+
"@faker-js/faker": "^10.5.0",
|
|
26
|
+
"@karmaniverous/mock-db": "^0.4.1",
|
|
27
27
|
"@rollup/plugin-alias": "^6.0.0",
|
|
28
|
-
"@rollup/plugin-commonjs": "^29.0.
|
|
28
|
+
"@rollup/plugin-commonjs": "^29.0.3",
|
|
29
29
|
"@rollup/plugin-json": "^6.1.0",
|
|
30
30
|
"@rollup/plugin-node-resolve": "^16.0.3",
|
|
31
31
|
"@rollup/plugin-strip": "^3.0.4",
|
|
32
32
|
"@rollup/plugin-typescript": "^12.3.0",
|
|
33
|
-
"@types/node": "^
|
|
33
|
+
"@types/node": "^26.1.1",
|
|
34
34
|
"@types/string-hash": "^1.1.3",
|
|
35
|
-
"auto-changelog": "^2.
|
|
35
|
+
"auto-changelog": "^2.6.0",
|
|
36
36
|
"cross-env": "^10.1.0",
|
|
37
|
-
"eslint": "^
|
|
37
|
+
"eslint": "^10.7.0",
|
|
38
38
|
"eslint-config-prettier": "^10.1.8",
|
|
39
|
-
"eslint-plugin-prettier": "^5.5.
|
|
40
|
-
"eslint-plugin-simple-import-sort": "^
|
|
41
|
-
"eslint-plugin-tsdoc": "^0.5.
|
|
42
|
-
"knip": "^
|
|
43
|
-
"lefthook": "^2.
|
|
44
|
-
"prettier": "^3.
|
|
45
|
-
"release-it": "^
|
|
46
|
-
"rimraf": "^6.1.
|
|
47
|
-
"rollup": "^4.
|
|
48
|
-
"rollup-plugin-dts": "^6.
|
|
39
|
+
"eslint-plugin-prettier": "^5.5.6",
|
|
40
|
+
"eslint-plugin-simple-import-sort": "^13.0.0",
|
|
41
|
+
"eslint-plugin-tsdoc": "^0.5.2",
|
|
42
|
+
"knip": "^6.27.0",
|
|
43
|
+
"lefthook": "^2.1.10",
|
|
44
|
+
"prettier": "^3.9.5",
|
|
45
|
+
"release-it": "^20.2.1",
|
|
46
|
+
"rimraf": "^6.1.3",
|
|
47
|
+
"rollup": "^4.62.2",
|
|
48
|
+
"rollup-plugin-dts": "^6.4.1",
|
|
49
49
|
"tsd": "^0.33.0",
|
|
50
50
|
"tslib": "^2.8.1",
|
|
51
|
-
"typedoc": "^0.28.
|
|
52
|
-
"typedoc-plugin-mdn-links": "^5.
|
|
51
|
+
"typedoc": "^0.28.20",
|
|
52
|
+
"typedoc-plugin-mdn-links": "^5.1.1",
|
|
53
53
|
"typedoc-plugin-replace-text": "^4.2.0",
|
|
54
54
|
"typedoc-plugin-zod": "^1.4.3",
|
|
55
|
-
"@vitest/coverage-v8": "^4.
|
|
56
|
-
"@vitest/eslint-plugin": "^1.
|
|
57
|
-
"vitest": "^4.
|
|
58
|
-
"typescript": "^
|
|
59
|
-
"typescript-eslint": "^8.
|
|
55
|
+
"@vitest/coverage-v8": "^4.1.10",
|
|
56
|
+
"@vitest/eslint-plugin": "^1.6.23",
|
|
57
|
+
"vitest": "^4.1.10",
|
|
58
|
+
"typescript": "^6.0.3",
|
|
59
|
+
"typescript-eslint": "^8.64.0"
|
|
60
60
|
},
|
|
61
61
|
"exports": {
|
|
62
62
|
".": {
|
|
@@ -101,15 +101,15 @@
|
|
|
101
101
|
"npm run knip",
|
|
102
102
|
"npm run build"
|
|
103
103
|
],
|
|
104
|
-
"before:npm:release": [
|
|
105
|
-
"npx auto-changelog -p",
|
|
106
|
-
"npm run docs",
|
|
107
|
-
"git add -A"
|
|
108
|
-
],
|
|
109
104
|
"after:release": [
|
|
110
105
|
"git switch -c release/${version}",
|
|
111
106
|
"git push -u origin release/${version}",
|
|
112
107
|
"git switch ${branchName}"
|
|
108
|
+
],
|
|
109
|
+
"after:bump": [
|
|
110
|
+
"npx auto-changelog -p",
|
|
111
|
+
"npm run docs",
|
|
112
|
+
"git add CHANGELOG.md"
|
|
113
113
|
]
|
|
114
114
|
},
|
|
115
115
|
"npm": {
|
|
@@ -134,5 +134,5 @@
|
|
|
134
134
|
},
|
|
135
135
|
"type": "module",
|
|
136
136
|
"types": "dist/index.d.ts",
|
|
137
|
-
"version": "8.0.
|
|
137
|
+
"version": "8.0.1"
|
|
138
138
|
}
|