zodvex 0.3.2 → 0.4.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/README.md +75 -0
- package/dist/__type-tests__/infer-returns.d.ts +2 -0
- package/dist/__type-tests__/infer-returns.d.ts.map +1 -0
- package/dist/__type-tests__/zodTable-inference.d.ts +2 -0
- package/dist/__type-tests__/zodTable-inference.d.ts.map +1 -0
- package/dist/builders.d.ts +173 -0
- package/dist/builders.d.ts.map +1 -0
- package/dist/codec.d.ts +11 -0
- package/dist/codec.d.ts.map +1 -0
- package/dist/custom.d.ts +147 -0
- package/dist/custom.d.ts.map +1 -0
- package/dist/ids.d.ts +23 -0
- package/dist/ids.d.ts.map +1 -0
- package/dist/index.d.ts +11 -599
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +203 -58
- package/dist/index.js.map +1 -1
- package/dist/mapping/core.d.ts +5 -0
- package/dist/mapping/core.d.ts.map +1 -0
- package/dist/mapping/handlers/enum.d.ts +4 -0
- package/dist/mapping/handlers/enum.d.ts.map +1 -0
- package/dist/mapping/handlers/index.d.ts +5 -0
- package/dist/mapping/handlers/index.d.ts.map +1 -0
- package/dist/mapping/handlers/nullable.d.ts +7 -0
- package/dist/mapping/handlers/nullable.d.ts.map +1 -0
- package/dist/mapping/handlers/record.d.ts +4 -0
- package/dist/mapping/handlers/record.d.ts.map +1 -0
- package/dist/mapping/handlers/union.d.ts +5 -0
- package/dist/mapping/handlers/union.d.ts.map +1 -0
- package/dist/mapping/index.d.ts +4 -0
- package/dist/mapping/index.d.ts.map +1 -0
- package/dist/mapping/types.d.ts +43 -0
- package/dist/mapping/types.d.ts.map +1 -0
- package/dist/mapping/utils.d.ts +6 -0
- package/dist/mapping/utils.d.ts.map +1 -0
- package/dist/registry.d.ts +110 -0
- package/dist/registry.d.ts.map +1 -0
- package/dist/results.d.ts +126 -0
- package/dist/results.d.ts.map +1 -0
- package/dist/tables.d.ts +214 -0
- package/dist/tables.d.ts.map +1 -0
- package/dist/transform/index.d.ts +26 -0
- package/dist/transform/index.d.ts.map +1 -0
- package/dist/transform/index.js +442 -0
- package/dist/transform/index.js.map +1 -0
- package/dist/transform/transform.d.ts +47 -0
- package/dist/transform/transform.d.ts.map +1 -0
- package/dist/transform/traverse.d.ts +62 -0
- package/dist/transform/traverse.d.ts.map +1 -0
- package/dist/transform/types.d.ts +115 -0
- package/dist/transform/types.d.ts.map +1 -0
- package/dist/types.d.ts +29 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/utils.d.ts +55 -0
- package/dist/utils.d.ts.map +1 -0
- package/dist/wrappers.d.ts +22 -0
- package/dist/wrappers.d.ts.map +1 -0
- package/package.json +13 -6
- package/src/__type-tests__/infer-returns.ts +24 -0
- package/src/__type-tests__/zodTable-inference.ts +5 -5
- package/src/custom.ts +205 -28
- package/src/index.ts +1 -0
- package/src/mapping/core.ts +23 -11
- package/src/mapping/types.ts +6 -2
- package/src/results.ts +110 -0
- package/src/tables.ts +306 -28
- package/src/transform/index.ts +38 -0
- package/src/transform/transform.ts +409 -0
- package/src/transform/traverse.ts +320 -0
- package/src/transform/types.ts +128 -0
- package/src/types.ts +3 -2
- package/src/utils.ts +35 -0
- package/src/wrappers.ts +10 -19
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Transform layer - General-purpose schema traversal and value transformation utilities.
|
|
3
|
+
*
|
|
4
|
+
* This module provides primitives for:
|
|
5
|
+
* - Walking Zod schemas (walkSchema, findFieldsWithMeta)
|
|
6
|
+
* - Extracting metadata from schemas (getMetadata, hasMetadata)
|
|
7
|
+
* - Recursively transforming values based on schema structure (transformBySchema, transformBySchemaAsync)
|
|
8
|
+
*
|
|
9
|
+
* @example
|
|
10
|
+
* ```ts
|
|
11
|
+
* import { findFieldsWithMeta, transformBySchema } from 'zodvex/transform'
|
|
12
|
+
*
|
|
13
|
+
* // Find all fields with custom metadata
|
|
14
|
+
* const sensitiveFields = findFieldsWithMeta(schema, meta => meta?.sensitive === true)
|
|
15
|
+
*
|
|
16
|
+
* // Transform values based on metadata
|
|
17
|
+
* const masked = transformBySchema(value, schema, ctx, (val, info) => {
|
|
18
|
+
* if (info.meta?.pii) return '[REDACTED]'
|
|
19
|
+
* return val
|
|
20
|
+
* })
|
|
21
|
+
* ```
|
|
22
|
+
*/
|
|
23
|
+
export { transformBySchema, transformBySchemaAsync } from './transform';
|
|
24
|
+
export { findFieldsWithMeta, getMetadata, hasMetadata, walkSchema } from './traverse';
|
|
25
|
+
export type { AsyncTransformFn, FieldInfo, SchemaVisitor, TransformContext, TransformFn, TransformOptions, WalkSchemaOptions } from './types';
|
|
26
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/transform/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAGH,OAAO,EAAE,iBAAiB,EAAE,sBAAsB,EAAE,MAAM,aAAa,CAAA;AAGvE,OAAO,EAAE,kBAAkB,EAAE,WAAW,EAAE,WAAW,EAAE,UAAU,EAAE,MAAM,YAAY,CAAA;AAErF,YAAY,EACV,gBAAgB,EAChB,SAAS,EACT,aAAa,EACb,gBAAgB,EAChB,WAAW,EACX,gBAAgB,EAChB,iBAAiB,EAClB,MAAM,SAAS,CAAA"}
|
|
@@ -0,0 +1,442 @@
|
|
|
1
|
+
// src/transform/traverse.ts
|
|
2
|
+
var METADATA_CACHE = /* @__PURE__ */ new WeakMap();
|
|
3
|
+
var SENSITIVE_META_KEY = "zodvex:sensitive";
|
|
4
|
+
function isZodSensitiveDef(schema) {
|
|
5
|
+
return schema?._def?.type === "sensitive" && typeof schema?.unwrap === "function";
|
|
6
|
+
}
|
|
7
|
+
function getMetadata(schema) {
|
|
8
|
+
if (METADATA_CACHE.has(schema)) {
|
|
9
|
+
return METADATA_CACHE.get(schema);
|
|
10
|
+
}
|
|
11
|
+
const visited = /* @__PURE__ */ new Set();
|
|
12
|
+
let current = schema;
|
|
13
|
+
while (current) {
|
|
14
|
+
if (visited.has(current)) return void 0;
|
|
15
|
+
visited.add(current);
|
|
16
|
+
if (isZodSensitiveDef(current)) {
|
|
17
|
+
const sensitiveMeta = current._def.sensitiveMetadata;
|
|
18
|
+
const meta2 = { [SENSITIVE_META_KEY]: sensitiveMeta };
|
|
19
|
+
METADATA_CACHE.set(schema, meta2);
|
|
20
|
+
return meta2;
|
|
21
|
+
}
|
|
22
|
+
const meta = current.meta?.();
|
|
23
|
+
if (meta !== void 0) {
|
|
24
|
+
METADATA_CACHE.set(schema, meta);
|
|
25
|
+
return meta;
|
|
26
|
+
}
|
|
27
|
+
current = unwrapOnce(current);
|
|
28
|
+
}
|
|
29
|
+
METADATA_CACHE.set(schema, void 0);
|
|
30
|
+
return void 0;
|
|
31
|
+
}
|
|
32
|
+
function unwrapOnce(schema) {
|
|
33
|
+
const defType = schema._def?.type;
|
|
34
|
+
switch (defType) {
|
|
35
|
+
case "sensitive": {
|
|
36
|
+
if (typeof schema.unwrap === "function") {
|
|
37
|
+
return schema.unwrap();
|
|
38
|
+
}
|
|
39
|
+
return schema._def?.innerType;
|
|
40
|
+
}
|
|
41
|
+
case "optional":
|
|
42
|
+
case "nullable": {
|
|
43
|
+
if (typeof schema.unwrap === "function") {
|
|
44
|
+
return schema.unwrap();
|
|
45
|
+
}
|
|
46
|
+
return schema._def?.innerType;
|
|
47
|
+
}
|
|
48
|
+
case "lazy": {
|
|
49
|
+
const getter = schema._def?.getter;
|
|
50
|
+
if (typeof getter === "function") {
|
|
51
|
+
return getter();
|
|
52
|
+
}
|
|
53
|
+
return void 0;
|
|
54
|
+
}
|
|
55
|
+
case "default":
|
|
56
|
+
case "catch":
|
|
57
|
+
case "readonly":
|
|
58
|
+
case "prefault":
|
|
59
|
+
case "nonoptional": {
|
|
60
|
+
return schema._def?.innerType;
|
|
61
|
+
}
|
|
62
|
+
case "pipe": {
|
|
63
|
+
return schema._def?.in;
|
|
64
|
+
}
|
|
65
|
+
default:
|
|
66
|
+
return void 0;
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
function hasMetadata(schema, predicate) {
|
|
70
|
+
const meta = getMetadata(schema);
|
|
71
|
+
return meta !== void 0 && predicate(meta);
|
|
72
|
+
}
|
|
73
|
+
function walkSchema(schema, visitor, options) {
|
|
74
|
+
const recursionStack = /* @__PURE__ */ new Set();
|
|
75
|
+
const basePath = options?.path ?? "";
|
|
76
|
+
function traverse(sch, currentPath, isOptional) {
|
|
77
|
+
if (recursionStack.has(sch)) return;
|
|
78
|
+
recursionStack.add(sch);
|
|
79
|
+
try {
|
|
80
|
+
const defType = sch._def?.type;
|
|
81
|
+
const meta = getMetadata(sch);
|
|
82
|
+
const info = { path: currentPath, schema: sch, meta, isOptional };
|
|
83
|
+
if (visitor.onField) {
|
|
84
|
+
const result = visitor.onField(info);
|
|
85
|
+
if (result === "skip") return;
|
|
86
|
+
}
|
|
87
|
+
switch (defType) {
|
|
88
|
+
case "sensitive": {
|
|
89
|
+
const inner = sch.unwrap?.() ?? sch._def?.innerType;
|
|
90
|
+
if (inner) {
|
|
91
|
+
traverse(inner, currentPath, isOptional);
|
|
92
|
+
}
|
|
93
|
+
return;
|
|
94
|
+
}
|
|
95
|
+
case "optional": {
|
|
96
|
+
const inner = sch.unwrap();
|
|
97
|
+
traverse(inner, currentPath, true);
|
|
98
|
+
return;
|
|
99
|
+
}
|
|
100
|
+
case "nullable": {
|
|
101
|
+
const inner = sch.unwrap();
|
|
102
|
+
traverse(inner, currentPath, isOptional);
|
|
103
|
+
return;
|
|
104
|
+
}
|
|
105
|
+
case "lazy": {
|
|
106
|
+
const getter = sch._def?.getter;
|
|
107
|
+
if (typeof getter === "function") {
|
|
108
|
+
const inner = getter();
|
|
109
|
+
traverse(inner, currentPath, isOptional);
|
|
110
|
+
}
|
|
111
|
+
return;
|
|
112
|
+
}
|
|
113
|
+
case "default":
|
|
114
|
+
case "catch":
|
|
115
|
+
case "readonly":
|
|
116
|
+
case "prefault":
|
|
117
|
+
case "nonoptional": {
|
|
118
|
+
const inner = sch._def?.innerType;
|
|
119
|
+
if (inner) {
|
|
120
|
+
traverse(inner, currentPath, isOptional);
|
|
121
|
+
}
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
case "pipe": {
|
|
125
|
+
const inner = sch._def?.in;
|
|
126
|
+
if (inner) {
|
|
127
|
+
traverse(inner, currentPath, isOptional);
|
|
128
|
+
}
|
|
129
|
+
return;
|
|
130
|
+
}
|
|
131
|
+
case "object": {
|
|
132
|
+
visitor.onObject?.(info);
|
|
133
|
+
const shape = sch.shape;
|
|
134
|
+
if (shape) {
|
|
135
|
+
for (const [key, fieldSchema] of Object.entries(shape)) {
|
|
136
|
+
const fieldPath = currentPath ? `${currentPath}.${key}` : key;
|
|
137
|
+
traverse(fieldSchema, fieldPath, false);
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
return;
|
|
141
|
+
}
|
|
142
|
+
case "array": {
|
|
143
|
+
visitor.onArray?.(info);
|
|
144
|
+
const element = sch.element;
|
|
145
|
+
if (element) {
|
|
146
|
+
const arrayPath = currentPath ? `${currentPath}[]` : "[]";
|
|
147
|
+
traverse(element, arrayPath, false);
|
|
148
|
+
}
|
|
149
|
+
return;
|
|
150
|
+
}
|
|
151
|
+
case "union": {
|
|
152
|
+
const unionOptions = sch._def.options;
|
|
153
|
+
const variantOptions = unionOptions || (sch._def.optionsMap ? Array.from(sch._def.optionsMap.values()) : []);
|
|
154
|
+
visitor.onUnion?.(info, variantOptions);
|
|
155
|
+
for (const variant of variantOptions) {
|
|
156
|
+
traverse(variant, currentPath, isOptional);
|
|
157
|
+
}
|
|
158
|
+
return;
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
} finally {
|
|
162
|
+
recursionStack.delete(sch);
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
traverse(schema, basePath, false);
|
|
166
|
+
}
|
|
167
|
+
function findFieldsWithMeta(schema, predicate) {
|
|
168
|
+
const results = [];
|
|
169
|
+
walkSchema(schema, {
|
|
170
|
+
onField: (info) => {
|
|
171
|
+
if (predicate(info.meta)) {
|
|
172
|
+
results.push(info);
|
|
173
|
+
return "skip";
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
});
|
|
177
|
+
return results;
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
// src/transform/transform.ts
|
|
181
|
+
function transformBySchema(value, schema, ctx, transform, options) {
|
|
182
|
+
const basePath = options?.path ?? "";
|
|
183
|
+
function recurse(val, sch, currentPath) {
|
|
184
|
+
if (val === void 0 || val === null) {
|
|
185
|
+
return val;
|
|
186
|
+
}
|
|
187
|
+
const defType = sch._def?.type;
|
|
188
|
+
const shouldCall = !options?.shouldTransform || options.shouldTransform(sch);
|
|
189
|
+
if (shouldCall) {
|
|
190
|
+
const meta = getMetadata(sch);
|
|
191
|
+
const context = { path: currentPath, schema: sch, meta, ctx };
|
|
192
|
+
const transformed = transform(val, context);
|
|
193
|
+
if (transformed !== val) {
|
|
194
|
+
return transformed;
|
|
195
|
+
}
|
|
196
|
+
}
|
|
197
|
+
switch (defType) {
|
|
198
|
+
case "sensitive": {
|
|
199
|
+
const inner = sch.unwrap?.() ?? sch._def?.innerType;
|
|
200
|
+
if (inner) {
|
|
201
|
+
return recurse(val, inner, currentPath);
|
|
202
|
+
}
|
|
203
|
+
break;
|
|
204
|
+
}
|
|
205
|
+
case "optional":
|
|
206
|
+
case "nullable": {
|
|
207
|
+
if (val === null) return null;
|
|
208
|
+
const inner = sch.unwrap();
|
|
209
|
+
return recurse(val, inner, currentPath);
|
|
210
|
+
}
|
|
211
|
+
case "lazy": {
|
|
212
|
+
const getter = sch._def?.getter;
|
|
213
|
+
if (typeof getter === "function") {
|
|
214
|
+
const inner = getter();
|
|
215
|
+
return recurse(val, inner, currentPath);
|
|
216
|
+
}
|
|
217
|
+
break;
|
|
218
|
+
}
|
|
219
|
+
case "default":
|
|
220
|
+
case "catch":
|
|
221
|
+
case "readonly":
|
|
222
|
+
case "prefault":
|
|
223
|
+
case "nonoptional": {
|
|
224
|
+
const inner = sch._def?.innerType;
|
|
225
|
+
if (inner) {
|
|
226
|
+
return recurse(val, inner, currentPath);
|
|
227
|
+
}
|
|
228
|
+
break;
|
|
229
|
+
}
|
|
230
|
+
case "pipe": {
|
|
231
|
+
const inner = sch._def?.in;
|
|
232
|
+
if (inner) {
|
|
233
|
+
return recurse(val, inner, currentPath);
|
|
234
|
+
}
|
|
235
|
+
break;
|
|
236
|
+
}
|
|
237
|
+
case "object": {
|
|
238
|
+
if (typeof val === "object" && val !== null) {
|
|
239
|
+
const shape = sch.shape;
|
|
240
|
+
if (shape) {
|
|
241
|
+
const result = {};
|
|
242
|
+
for (const [key, fieldSchema] of Object.entries(shape)) {
|
|
243
|
+
const fieldPath = currentPath ? `${currentPath}.${key}` : key;
|
|
244
|
+
const fieldValue = val[key];
|
|
245
|
+
result[key] = recurse(fieldValue, fieldSchema, fieldPath);
|
|
246
|
+
}
|
|
247
|
+
return result;
|
|
248
|
+
}
|
|
249
|
+
}
|
|
250
|
+
break;
|
|
251
|
+
}
|
|
252
|
+
case "array": {
|
|
253
|
+
if (Array.isArray(val)) {
|
|
254
|
+
const element = sch.element;
|
|
255
|
+
return val.map((item, i) => {
|
|
256
|
+
const itemPath = `${currentPath}[${i}]`;
|
|
257
|
+
return recurse(item, element, itemPath);
|
|
258
|
+
});
|
|
259
|
+
}
|
|
260
|
+
break;
|
|
261
|
+
}
|
|
262
|
+
case "union":
|
|
263
|
+
return handleUnion(val, sch, currentPath, recurse, options);
|
|
264
|
+
}
|
|
265
|
+
return val;
|
|
266
|
+
}
|
|
267
|
+
return recurse(value, schema, basePath);
|
|
268
|
+
}
|
|
269
|
+
async function transformBySchemaAsync(value, schema, ctx, transform, options) {
|
|
270
|
+
const basePath = options?.path ?? "";
|
|
271
|
+
async function recurse(val, sch, currentPath) {
|
|
272
|
+
if (val === void 0 || val === null) {
|
|
273
|
+
return val;
|
|
274
|
+
}
|
|
275
|
+
const defType = sch._def?.type;
|
|
276
|
+
const shouldCall = !options?.shouldTransform || options.shouldTransform(sch);
|
|
277
|
+
if (shouldCall) {
|
|
278
|
+
const meta = getMetadata(sch);
|
|
279
|
+
const context = { path: currentPath, schema: sch, meta, ctx };
|
|
280
|
+
const transformed = await transform(val, context);
|
|
281
|
+
if (transformed !== val) {
|
|
282
|
+
return transformed;
|
|
283
|
+
}
|
|
284
|
+
}
|
|
285
|
+
switch (defType) {
|
|
286
|
+
case "sensitive": {
|
|
287
|
+
const inner = sch.unwrap?.() ?? sch._def?.innerType;
|
|
288
|
+
if (inner) {
|
|
289
|
+
return recurse(val, inner, currentPath);
|
|
290
|
+
}
|
|
291
|
+
break;
|
|
292
|
+
}
|
|
293
|
+
case "optional":
|
|
294
|
+
case "nullable": {
|
|
295
|
+
if (val === null) return null;
|
|
296
|
+
const inner = sch.unwrap();
|
|
297
|
+
return recurse(val, inner, currentPath);
|
|
298
|
+
}
|
|
299
|
+
case "lazy": {
|
|
300
|
+
const getter = sch._def?.getter;
|
|
301
|
+
if (typeof getter === "function") {
|
|
302
|
+
const inner = getter();
|
|
303
|
+
return recurse(val, inner, currentPath);
|
|
304
|
+
}
|
|
305
|
+
break;
|
|
306
|
+
}
|
|
307
|
+
case "default":
|
|
308
|
+
case "catch":
|
|
309
|
+
case "readonly":
|
|
310
|
+
case "prefault":
|
|
311
|
+
case "nonoptional": {
|
|
312
|
+
const inner = sch._def?.innerType;
|
|
313
|
+
if (inner) {
|
|
314
|
+
return recurse(val, inner, currentPath);
|
|
315
|
+
}
|
|
316
|
+
break;
|
|
317
|
+
}
|
|
318
|
+
case "pipe": {
|
|
319
|
+
const inner = sch._def?.in;
|
|
320
|
+
if (inner) {
|
|
321
|
+
return recurse(val, inner, currentPath);
|
|
322
|
+
}
|
|
323
|
+
break;
|
|
324
|
+
}
|
|
325
|
+
case "object": {
|
|
326
|
+
if (typeof val === "object" && val !== null) {
|
|
327
|
+
const shape = sch.shape;
|
|
328
|
+
if (shape) {
|
|
329
|
+
const result = {};
|
|
330
|
+
for (const [key, fieldSchema] of Object.entries(shape)) {
|
|
331
|
+
const fieldPath = currentPath ? `${currentPath}.${key}` : key;
|
|
332
|
+
const fieldValue = val[key];
|
|
333
|
+
result[key] = await recurse(fieldValue, fieldSchema, fieldPath);
|
|
334
|
+
}
|
|
335
|
+
return result;
|
|
336
|
+
}
|
|
337
|
+
}
|
|
338
|
+
break;
|
|
339
|
+
}
|
|
340
|
+
case "array": {
|
|
341
|
+
if (Array.isArray(val)) {
|
|
342
|
+
const element = sch.element;
|
|
343
|
+
if (options?.parallel) {
|
|
344
|
+
return Promise.all(
|
|
345
|
+
val.map((item, i) => {
|
|
346
|
+
const itemPath = `${currentPath}[${i}]`;
|
|
347
|
+
return recurse(item, element, itemPath);
|
|
348
|
+
})
|
|
349
|
+
);
|
|
350
|
+
}
|
|
351
|
+
const results = [];
|
|
352
|
+
for (let i = 0; i < val.length; i++) {
|
|
353
|
+
const itemPath = `${currentPath}[${i}]`;
|
|
354
|
+
results.push(await recurse(val[i], element, itemPath));
|
|
355
|
+
}
|
|
356
|
+
return results;
|
|
357
|
+
}
|
|
358
|
+
break;
|
|
359
|
+
}
|
|
360
|
+
case "union":
|
|
361
|
+
return handleUnionAsync(val, sch, currentPath, recurse, options);
|
|
362
|
+
}
|
|
363
|
+
return val;
|
|
364
|
+
}
|
|
365
|
+
return recurse(value, schema, basePath);
|
|
366
|
+
}
|
|
367
|
+
function handleUnion(val, sch, currentPath, recurse, options) {
|
|
368
|
+
const unionOptions = sch._def.options;
|
|
369
|
+
const discriminator = sch._def?.discriminator;
|
|
370
|
+
if (discriminator && typeof val === "object" && val !== null && unionOptions) {
|
|
371
|
+
const discValue = val[discriminator];
|
|
372
|
+
for (const variant of unionOptions) {
|
|
373
|
+
const variantShape = variant.shape;
|
|
374
|
+
if (variantShape) {
|
|
375
|
+
const discField = variantShape[discriminator];
|
|
376
|
+
if (discField?._def?.type === "literal") {
|
|
377
|
+
const literalValues = discField._def.values;
|
|
378
|
+
if (literalValues?.includes(discValue)) {
|
|
379
|
+
return recurse(val, variant, currentPath);
|
|
380
|
+
}
|
|
381
|
+
}
|
|
382
|
+
}
|
|
383
|
+
}
|
|
384
|
+
return handleUnmatchedUnion(val, currentPath, options);
|
|
385
|
+
}
|
|
386
|
+
if (unionOptions) {
|
|
387
|
+
for (const variant of unionOptions) {
|
|
388
|
+
try {
|
|
389
|
+
const result = recurse(val, variant, currentPath);
|
|
390
|
+
if (result !== null) return result;
|
|
391
|
+
} catch {
|
|
392
|
+
}
|
|
393
|
+
}
|
|
394
|
+
}
|
|
395
|
+
return handleUnmatchedUnion(val, currentPath, options);
|
|
396
|
+
}
|
|
397
|
+
async function handleUnionAsync(val, sch, currentPath, recurse, options) {
|
|
398
|
+
const unionOptions = sch._def.options;
|
|
399
|
+
const discriminator = sch._def?.discriminator;
|
|
400
|
+
if (discriminator && typeof val === "object" && val !== null && unionOptions) {
|
|
401
|
+
const discValue = val[discriminator];
|
|
402
|
+
for (const variant of unionOptions) {
|
|
403
|
+
const variantShape = variant.shape;
|
|
404
|
+
if (variantShape) {
|
|
405
|
+
const discField = variantShape[discriminator];
|
|
406
|
+
if (discField?._def?.type === "literal") {
|
|
407
|
+
const literalValues = discField._def.values;
|
|
408
|
+
if (literalValues?.includes(discValue)) {
|
|
409
|
+
return recurse(val, variant, currentPath);
|
|
410
|
+
}
|
|
411
|
+
}
|
|
412
|
+
}
|
|
413
|
+
}
|
|
414
|
+
return handleUnmatchedUnion(val, currentPath, options);
|
|
415
|
+
}
|
|
416
|
+
if (unionOptions) {
|
|
417
|
+
for (const variant of unionOptions) {
|
|
418
|
+
try {
|
|
419
|
+
const result = await recurse(val, variant, currentPath);
|
|
420
|
+
if (result !== null) return result;
|
|
421
|
+
} catch {
|
|
422
|
+
}
|
|
423
|
+
}
|
|
424
|
+
}
|
|
425
|
+
return handleUnmatchedUnion(val, currentPath, options);
|
|
426
|
+
}
|
|
427
|
+
function handleUnmatchedUnion(val, path, options) {
|
|
428
|
+
options?.onUnmatchedUnion?.(path);
|
|
429
|
+
switch (options?.unmatchedUnion) {
|
|
430
|
+
case "error":
|
|
431
|
+
throw new Error(`No union variant matched at path: ${path}`);
|
|
432
|
+
case "null":
|
|
433
|
+
return null;
|
|
434
|
+
case "passthrough":
|
|
435
|
+
default:
|
|
436
|
+
return val;
|
|
437
|
+
}
|
|
438
|
+
}
|
|
439
|
+
|
|
440
|
+
export { findFieldsWithMeta, getMetadata, hasMetadata, transformBySchema, transformBySchemaAsync, walkSchema };
|
|
441
|
+
//# sourceMappingURL=index.js.map
|
|
442
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/transform/traverse.ts","../../src/transform/transform.ts"],"names":["meta"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * Schema traversal utilities.\n *\n * General-purpose utilities for walking and inspecting Zod schemas.\n */\n\nimport type { z } from 'zod'\nimport type { FieldInfo, SchemaVisitor, WalkSchemaOptions } from './types'\n\nconst METADATA_CACHE = new WeakMap<z.ZodTypeAny, Record<string, unknown> | undefined>()\n\n/**\n * Metadata key for ZodSensitive wrappers.\n */\nconst SENSITIVE_META_KEY = 'zodvex:sensitive'\n\n/**\n * Duck-type check for ZodSensitive wrapper.\n */\nfunction isZodSensitiveDef(schema: any): boolean {\n return schema?._def?.type === 'sensitive' && typeof schema?.unwrap === 'function'\n}\n\n/**\n * Get metadata from a Zod schema.\n *\n * Handles both Zod's native .meta() and ZodSensitive wrappers.\n *\n * @example\n * ```ts\n * const schema = z.string().meta({ encrypted: true })\n * const meta = getMetadata(schema)\n * // => { encrypted: true }\n * ```\n */\nexport function getMetadata(schema: z.ZodTypeAny): Record<string, unknown> | undefined {\n if (METADATA_CACHE.has(schema)) {\n return METADATA_CACHE.get(schema)\n }\n\n const visited = new Set<z.ZodTypeAny>()\n let current: z.ZodTypeAny | undefined = schema\n\n while (current) {\n if (visited.has(current)) return undefined\n visited.add(current)\n\n // Fast path: ZodSensitive wrapper stores metadata directly\n if (isZodSensitiveDef(current)) {\n const sensitiveMeta = (current as any)._def.sensitiveMetadata\n const meta = { [SENSITIVE_META_KEY]: sensitiveMeta }\n METADATA_CACHE.set(schema, meta)\n return meta\n }\n\n const meta = current.meta?.() as Record<string, unknown> | undefined\n if (meta !== undefined) {\n METADATA_CACHE.set(schema, meta)\n return meta\n }\n\n current = unwrapOnce(current)\n }\n\n METADATA_CACHE.set(schema, undefined)\n return undefined\n}\n\nfunction unwrapOnce(schema: z.ZodTypeAny): z.ZodTypeAny | undefined {\n const defType = (schema as any)._def?.type as string | undefined\n\n switch (defType) {\n case 'sensitive': {\n // ZodSensitive wrapper - unwrap to inner schema\n if (typeof (schema as any).unwrap === 'function') {\n return (schema as any).unwrap()\n }\n return (schema as any)._def?.innerType\n }\n\n case 'optional':\n case 'nullable': {\n if (typeof (schema as any).unwrap === 'function') {\n return (schema as any).unwrap()\n }\n return (schema as any)._def?.innerType\n }\n\n case 'lazy': {\n const getter = (schema as any)._def?.getter\n if (typeof getter === 'function') {\n return getter()\n }\n return undefined\n }\n\n case 'default':\n case 'catch':\n case 'readonly':\n case 'prefault':\n case 'nonoptional': {\n return (schema as any)._def?.innerType\n }\n\n case 'pipe': {\n return (schema as any)._def?.in\n }\n\n default:\n return undefined\n }\n}\n\n/**\n * Check if a schema has metadata matching a predicate.\n *\n * @example\n * ```ts\n * const schema = z.string().meta({ sensitive: true })\n * hasMetadata(schema, meta => meta.sensitive === true)\n * // => true\n * ```\n */\nexport function hasMetadata(\n schema: z.ZodTypeAny,\n predicate: (meta: Record<string, unknown>) => boolean\n): boolean {\n const meta = getMetadata(schema)\n return meta !== undefined && predicate(meta)\n}\n\n/**\n * Walk a Zod schema, calling visitor functions for each node.\n *\n * Handles: objects, arrays, optionals, nullables, unions, discriminated unions.\n * Prevents infinite recursion on circular schema references.\n *\n * @example\n * ```ts\n * walkSchema(userSchema, {\n * onField: (info) => {\n * if (info.meta?.encrypted) {\n * console.log(`Encrypted field: ${info.path}`)\n * }\n * }\n * })\n * ```\n */\nexport function walkSchema(\n schema: z.ZodTypeAny,\n visitor: SchemaVisitor,\n options?: WalkSchemaOptions\n): void {\n const recursionStack = new Set<z.ZodTypeAny>()\n const basePath = options?.path ?? ''\n\n function traverse(sch: z.ZodTypeAny, currentPath: string, isOptional: boolean): void {\n // Prevent infinite recursion on circular schema references\n if (recursionStack.has(sch)) return\n recursionStack.add(sch)\n\n try {\n const defType = (sch as any)._def?.type as string | undefined\n const meta = getMetadata(sch)\n const info: FieldInfo = { path: currentPath, schema: sch, meta, isOptional }\n\n // Call onField for every schema node\n if (visitor.onField) {\n const result = visitor.onField(info)\n if (result === 'skip') return\n }\n\n // Dispatch based on schema type\n switch (defType) {\n case 'sensitive': {\n // ZodSensitive wrapper - already reported via onField, now traverse inner\n const inner = (sch as any).unwrap?.() ?? (sch as any)._def?.innerType\n if (inner) {\n traverse(inner, currentPath, isOptional)\n }\n return\n }\n\n case 'optional': {\n const inner = (sch as any).unwrap()\n traverse(inner, currentPath, true)\n return\n }\n\n case 'nullable': {\n const inner = (sch as any).unwrap()\n traverse(inner, currentPath, isOptional)\n return\n }\n\n case 'lazy': {\n const getter = (sch as any)._def?.getter\n if (typeof getter === 'function') {\n const inner = getter()\n traverse(inner, currentPath, isOptional)\n }\n return\n }\n\n case 'default':\n case 'catch':\n case 'readonly':\n case 'prefault':\n case 'nonoptional': {\n const inner = (sch as any)._def?.innerType as z.ZodTypeAny | undefined\n if (inner) {\n traverse(inner, currentPath, isOptional)\n }\n return\n }\n\n case 'pipe': {\n const inner = (sch as any)._def?.in as z.ZodTypeAny | undefined\n if (inner) {\n traverse(inner, currentPath, isOptional)\n }\n return\n }\n\n case 'object': {\n visitor.onObject?.(info)\n const shape = (sch as any).shape\n if (shape) {\n for (const [key, fieldSchema] of Object.entries(shape)) {\n const fieldPath = currentPath ? `${currentPath}.${key}` : key\n traverse(fieldSchema as z.ZodTypeAny, fieldPath, false)\n }\n }\n return\n }\n\n case 'array': {\n visitor.onArray?.(info)\n const element = (sch as any).element\n if (element) {\n const arrayPath = currentPath ? `${currentPath}[]` : '[]'\n traverse(element, arrayPath, false)\n }\n return\n }\n\n case 'union': {\n const unionOptions = (sch as any)._def.options as z.ZodTypeAny[] | undefined\n\n // Get options from either _def.options or _def.optionsMap\n const variantOptions =\n unionOptions ||\n ((sch as any)._def.optionsMap ? Array.from((sch as any)._def.optionsMap.values()) : [])\n\n visitor.onUnion?.(info, variantOptions as z.ZodTypeAny[])\n\n for (const variant of variantOptions as z.ZodTypeAny[]) {\n traverse(variant, currentPath, isOptional)\n }\n return\n }\n }\n\n // Primitives and other types are leaf nodes - nothing more to traverse\n } finally {\n recursionStack.delete(sch)\n }\n }\n\n traverse(schema, basePath, false)\n}\n\n/**\n * Find all fields in a schema where metadata matches a predicate.\n *\n * @overload Type guard version - returns narrowed meta type\n */\nexport function findFieldsWithMeta<TMeta extends Record<string, unknown>>(\n schema: z.ZodTypeAny,\n predicate: (meta: Record<string, unknown> | undefined) => meta is TMeta\n): Array<FieldInfo & { meta: TMeta }>\n\n/**\n * @overload Boolean predicate version\n */\nexport function findFieldsWithMeta(\n schema: z.ZodTypeAny,\n predicate: (meta: Record<string, unknown> | undefined) => boolean\n): FieldInfo[]\n\n/**\n * Find all fields in a schema where metadata matches a predicate.\n *\n * @example\n * ```ts\n * // Find all fields with 'sensitive' metadata\n * const sensitiveFields = findFieldsWithMeta(\n * userSchema,\n * (meta) => meta?.sensitive === true\n * )\n * // => [{ path: 'email', schema: z.string(), meta: { sensitive: true } }, ...]\n * ```\n */\nexport function findFieldsWithMeta(\n schema: z.ZodTypeAny,\n predicate: (meta: Record<string, unknown> | undefined) => boolean\n): FieldInfo[] {\n const results: FieldInfo[] = []\n\n walkSchema(schema, {\n onField: info => {\n if (predicate(info.meta)) {\n results.push(info)\n return 'skip' // Don't recurse into matching fields\n }\n }\n })\n\n return results\n}\n","/**\n * Value transformation utilities.\n *\n * General-purpose utilities for recursively transforming values based on their schema structure.\n */\n\nimport type { z } from 'zod'\nimport { getMetadata } from './traverse'\nimport type { AsyncTransformFn, TransformContext, TransformFn, TransformOptions } from './types'\n\n/**\n * Recursively transform a value based on its schema structure.\n *\n * The transform function is called for each value/schema pair during traversal.\n * If the transform returns a different value (val !== transformed), that value\n * is used and recursion into that subtree stops. If the same value is returned,\n * recursion continues.\n *\n * @example\n * ```ts\n * // Mask all fields with 'pii' metadata for logging\n * const safeForLogs = transformBySchema(userData, userSchema, null, (value, ctx) => {\n * if (ctx.meta?.pii) {\n * return '[REDACTED]'\n * }\n * return value\n * })\n * ```\n */\nexport function transformBySchema<T, TCtx>(\n value: T,\n schema: z.ZodTypeAny,\n ctx: TCtx,\n transform: TransformFn<TCtx>,\n options?: TransformOptions\n): T {\n const basePath = options?.path ?? ''\n\n function recurse(val: unknown, sch: z.ZodTypeAny, currentPath: string): unknown {\n // Pass through null/undefined unchanged\n if (val === undefined || val === null) {\n return val\n }\n\n const defType = (sch as any)._def?.type as string | undefined\n\n // Check shouldTransform predicate - if false, skip callback but continue recursion\n const shouldCall = !options?.shouldTransform || options.shouldTransform(sch)\n\n if (shouldCall) {\n const meta = getMetadata(sch)\n\n // Call transform for this value/schema pair\n const context: TransformContext<TCtx> = { path: currentPath, schema: sch, meta, ctx }\n const transformed = transform(val, context)\n\n // If transform returned something different, use it (don't recurse)\n if (transformed !== val) {\n return transformed\n }\n }\n\n // Dispatch based on schema type\n switch (defType) {\n case 'sensitive': {\n // ZodSensitive wrapper - transform was already called above, now recurse into inner\n const inner = (sch as any).unwrap?.() ?? (sch as any)._def?.innerType\n if (inner) {\n return recurse(val, inner, currentPath)\n }\n break\n }\n\n case 'optional':\n case 'nullable': {\n if (val === null) return null\n const inner = (sch as any).unwrap()\n return recurse(val, inner, currentPath)\n }\n\n case 'lazy': {\n const getter = (sch as any)._def?.getter\n if (typeof getter === 'function') {\n const inner = getter()\n return recurse(val, inner, currentPath)\n }\n break\n }\n\n case 'default':\n case 'catch':\n case 'readonly':\n case 'prefault':\n case 'nonoptional': {\n const inner = (sch as any)._def?.innerType as z.ZodTypeAny | undefined\n if (inner) {\n return recurse(val, inner, currentPath)\n }\n break\n }\n\n case 'pipe': {\n const inner = (sch as any)._def?.in as z.ZodTypeAny | undefined\n if (inner) {\n return recurse(val, inner, currentPath)\n }\n break\n }\n\n case 'object': {\n if (typeof val === 'object' && val !== null) {\n const shape = (sch as any).shape\n if (shape) {\n const result: Record<string, unknown> = {}\n for (const [key, fieldSchema] of Object.entries(shape)) {\n const fieldPath = currentPath ? `${currentPath}.${key}` : key\n const fieldValue = (val as Record<string, unknown>)[key]\n result[key] = recurse(fieldValue, fieldSchema as z.ZodTypeAny, fieldPath)\n }\n return result\n }\n }\n break\n }\n\n case 'array': {\n if (Array.isArray(val)) {\n const element = (sch as any).element\n return val.map((item, i) => {\n const itemPath = `${currentPath}[${i}]`\n return recurse(item, element, itemPath)\n })\n }\n break\n }\n\n case 'union':\n return handleUnion(val, sch, currentPath, recurse, options)\n }\n\n return val\n }\n\n return recurse(value, schema, basePath) as T\n}\n\n/**\n * Async version of transformBySchema.\n *\n * Supports async transform functions for operations like policy resolution\n * or encryption with async key lookup.\n *\n * @example\n * ```ts\n * // Apply security policies (async entitlement checks)\n * const limited = await transformBySchemaAsync(doc, schema, ctx, async (value, info) => {\n * if (isSensitive(info.meta)) {\n * const decision = await resolvePolicy(info, ctx)\n * return applyDecision(value, decision)\n * }\n * return value\n * })\n * ```\n */\nexport async function transformBySchemaAsync<T, TCtx>(\n value: T,\n schema: z.ZodTypeAny,\n ctx: TCtx,\n transform: AsyncTransformFn<TCtx>,\n options?: TransformOptions\n): Promise<T> {\n const basePath = options?.path ?? ''\n\n async function recurse(val: unknown, sch: z.ZodTypeAny, currentPath: string): Promise<unknown> {\n // Pass through null/undefined unchanged\n if (val === undefined || val === null) {\n return val\n }\n\n const defType = (sch as any)._def?.type as string | undefined\n\n // Check shouldTransform predicate - if false, skip callback but continue recursion\n const shouldCall = !options?.shouldTransform || options.shouldTransform(sch)\n\n if (shouldCall) {\n const meta = getMetadata(sch)\n\n // Call transform for this value/schema pair\n const context: TransformContext<TCtx> = { path: currentPath, schema: sch, meta, ctx }\n const transformed = await transform(val, context)\n\n // If transform returned something different, use it\n if (transformed !== val) {\n return transformed\n }\n }\n\n // Dispatch based on schema type\n switch (defType) {\n case 'sensitive': {\n // ZodSensitive wrapper - transform was already called above, now recurse into inner\n const inner = (sch as any).unwrap?.() ?? (sch as any)._def?.innerType\n if (inner) {\n return recurse(val, inner, currentPath)\n }\n break\n }\n\n case 'optional':\n case 'nullable': {\n if (val === null) return null\n const inner = (sch as any).unwrap()\n return recurse(val, inner, currentPath)\n }\n\n case 'lazy': {\n const getter = (sch as any)._def?.getter\n if (typeof getter === 'function') {\n const inner = getter()\n return recurse(val, inner, currentPath)\n }\n break\n }\n\n case 'default':\n case 'catch':\n case 'readonly':\n case 'prefault':\n case 'nonoptional': {\n const inner = (sch as any)._def?.innerType as z.ZodTypeAny | undefined\n if (inner) {\n return recurse(val, inner, currentPath)\n }\n break\n }\n\n case 'pipe': {\n const inner = (sch as any)._def?.in as z.ZodTypeAny | undefined\n if (inner) {\n return recurse(val, inner, currentPath)\n }\n break\n }\n\n case 'object': {\n if (typeof val === 'object' && val !== null) {\n const shape = (sch as any).shape\n if (shape) {\n const result: Record<string, unknown> = {}\n for (const [key, fieldSchema] of Object.entries(shape)) {\n const fieldPath = currentPath ? `${currentPath}.${key}` : key\n const fieldValue = (val as Record<string, unknown>)[key]\n result[key] = await recurse(fieldValue, fieldSchema as z.ZodTypeAny, fieldPath)\n }\n return result\n }\n }\n break\n }\n\n case 'array': {\n if (Array.isArray(val)) {\n const element = (sch as any).element\n if (options?.parallel) {\n // Parallel processing with Promise.all\n return Promise.all(\n val.map((item, i) => {\n const itemPath = `${currentPath}[${i}]`\n return recurse(item, element, itemPath)\n })\n )\n }\n // Sequential processing (default)\n const results: unknown[] = []\n for (let i = 0; i < val.length; i++) {\n const itemPath = `${currentPath}[${i}]`\n results.push(await recurse(val[i], element, itemPath))\n }\n return results\n }\n break\n }\n\n case 'union':\n return handleUnionAsync(val, sch, currentPath, recurse, options)\n }\n\n return val\n }\n\n return recurse(value, schema, basePath) as Promise<T>\n}\n\n/**\n * Handle union matching for sync transforms.\n */\nfunction handleUnion(\n val: unknown,\n sch: z.ZodTypeAny,\n currentPath: string,\n recurse: (v: unknown, s: z.ZodTypeAny, p: string) => unknown,\n options?: TransformOptions\n): unknown {\n const unionOptions = (sch as any)._def.options as z.ZodTypeAny[] | undefined\n const discriminator = (sch as any)._def?.discriminator\n\n // Discriminated union - find matching variant by discriminator value\n if (discriminator && typeof val === 'object' && val !== null && unionOptions) {\n const discValue = (val as Record<string, unknown>)[discriminator]\n\n for (const variant of unionOptions) {\n const variantShape = (variant as any).shape\n if (variantShape) {\n const discField = variantShape[discriminator]\n if ((discField as any)?._def?.type === 'literal') {\n // Zod v4 stores literal values in _def.values array\n const literalValues = (discField as any)._def.values as unknown[]\n if (literalValues?.includes(discValue)) {\n return recurse(val, variant, currentPath)\n }\n }\n }\n }\n\n // No variant matched - handle according to options\n return handleUnmatchedUnion(val, currentPath, options)\n }\n\n // Regular union - try each variant\n if (unionOptions) {\n for (const variant of unionOptions) {\n try {\n const result = recurse(val, variant, currentPath)\n // If we got a non-null result, use it\n if (result !== null) return result\n } catch {\n // This variant didn't work, try next\n }\n }\n }\n\n // No variant matched for regular union\n return handleUnmatchedUnion(val, currentPath, options)\n}\n\n/**\n * Handle union matching for async transforms.\n */\nasync function handleUnionAsync(\n val: unknown,\n sch: z.ZodTypeAny,\n currentPath: string,\n recurse: (v: unknown, s: z.ZodTypeAny, p: string) => Promise<unknown>,\n options?: TransformOptions\n): Promise<unknown> {\n const unionOptions = (sch as any)._def.options as z.ZodTypeAny[] | undefined\n const discriminator = (sch as any)._def?.discriminator\n\n // Discriminated union - find matching variant by discriminator value\n if (discriminator && typeof val === 'object' && val !== null && unionOptions) {\n const discValue = (val as Record<string, unknown>)[discriminator]\n\n for (const variant of unionOptions) {\n const variantShape = (variant as any).shape\n if (variantShape) {\n const discField = variantShape[discriminator]\n if ((discField as any)?._def?.type === 'literal') {\n const literalValues = (discField as any)._def.values as unknown[]\n if (literalValues?.includes(discValue)) {\n return recurse(val, variant, currentPath)\n }\n }\n }\n }\n\n return handleUnmatchedUnion(val, currentPath, options)\n }\n\n // Regular union - try each variant\n if (unionOptions) {\n for (const variant of unionOptions) {\n try {\n const result = await recurse(val, variant, currentPath)\n if (result !== null) return result\n } catch {\n // Try next variant\n }\n }\n }\n\n return handleUnmatchedUnion(val, currentPath, options)\n}\n\n/**\n * Handle unmatched union according to options.\n */\nfunction handleUnmatchedUnion(val: unknown, path: string, options?: TransformOptions): unknown {\n options?.onUnmatchedUnion?.(path)\n\n switch (options?.unmatchedUnion) {\n case 'error':\n throw new Error(`No union variant matched at path: ${path}`)\n case 'null':\n return null\n case 'passthrough':\n default:\n return val\n }\n}\n"]}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Value transformation utilities.
|
|
3
|
+
*
|
|
4
|
+
* General-purpose utilities for recursively transforming values based on their schema structure.
|
|
5
|
+
*/
|
|
6
|
+
import type { z } from 'zod';
|
|
7
|
+
import type { AsyncTransformFn, TransformFn, TransformOptions } from './types';
|
|
8
|
+
/**
|
|
9
|
+
* Recursively transform a value based on its schema structure.
|
|
10
|
+
*
|
|
11
|
+
* The transform function is called for each value/schema pair during traversal.
|
|
12
|
+
* If the transform returns a different value (val !== transformed), that value
|
|
13
|
+
* is used and recursion into that subtree stops. If the same value is returned,
|
|
14
|
+
* recursion continues.
|
|
15
|
+
*
|
|
16
|
+
* @example
|
|
17
|
+
* ```ts
|
|
18
|
+
* // Mask all fields with 'pii' metadata for logging
|
|
19
|
+
* const safeForLogs = transformBySchema(userData, userSchema, null, (value, ctx) => {
|
|
20
|
+
* if (ctx.meta?.pii) {
|
|
21
|
+
* return '[REDACTED]'
|
|
22
|
+
* }
|
|
23
|
+
* return value
|
|
24
|
+
* })
|
|
25
|
+
* ```
|
|
26
|
+
*/
|
|
27
|
+
export declare function transformBySchema<T, TCtx>(value: T, schema: z.ZodTypeAny, ctx: TCtx, transform: TransformFn<TCtx>, options?: TransformOptions): T;
|
|
28
|
+
/**
|
|
29
|
+
* Async version of transformBySchema.
|
|
30
|
+
*
|
|
31
|
+
* Supports async transform functions for operations like policy resolution
|
|
32
|
+
* or encryption with async key lookup.
|
|
33
|
+
*
|
|
34
|
+
* @example
|
|
35
|
+
* ```ts
|
|
36
|
+
* // Apply security policies (async entitlement checks)
|
|
37
|
+
* const limited = await transformBySchemaAsync(doc, schema, ctx, async (value, info) => {
|
|
38
|
+
* if (isSensitive(info.meta)) {
|
|
39
|
+
* const decision = await resolvePolicy(info, ctx)
|
|
40
|
+
* return applyDecision(value, decision)
|
|
41
|
+
* }
|
|
42
|
+
* return value
|
|
43
|
+
* })
|
|
44
|
+
* ```
|
|
45
|
+
*/
|
|
46
|
+
export declare function transformBySchemaAsync<T, TCtx>(value: T, schema: z.ZodTypeAny, ctx: TCtx, transform: AsyncTransformFn<TCtx>, options?: TransformOptions): Promise<T>;
|
|
47
|
+
//# sourceMappingURL=transform.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"transform.d.ts","sourceRoot":"","sources":["../../src/transform/transform.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,CAAC,EAAE,MAAM,KAAK,CAAA;AAE5B,OAAO,KAAK,EAAE,gBAAgB,EAAoB,WAAW,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAA;AAEhG;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,iBAAiB,CAAC,CAAC,EAAE,IAAI,EACvC,KAAK,EAAE,CAAC,EACR,MAAM,EAAE,CAAC,CAAC,UAAU,EACpB,GAAG,EAAE,IAAI,EACT,SAAS,EAAE,WAAW,CAAC,IAAI,CAAC,EAC5B,OAAO,CAAC,EAAE,gBAAgB,GACzB,CAAC,CA6GH;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAsB,sBAAsB,CAAC,CAAC,EAAE,IAAI,EAClD,KAAK,EAAE,CAAC,EACR,MAAM,EAAE,CAAC,CAAC,UAAU,EACpB,GAAG,EAAE,IAAI,EACT,SAAS,EAAE,gBAAgB,CAAC,IAAI,CAAC,EACjC,OAAO,CAAC,EAAE,gBAAgB,GACzB,OAAO,CAAC,CAAC,CAAC,CAyHZ"}
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Schema traversal utilities.
|
|
3
|
+
*
|
|
4
|
+
* General-purpose utilities for walking and inspecting Zod schemas.
|
|
5
|
+
*/
|
|
6
|
+
import type { z } from 'zod';
|
|
7
|
+
import type { FieldInfo, SchemaVisitor, WalkSchemaOptions } from './types';
|
|
8
|
+
/**
|
|
9
|
+
* Get metadata from a Zod schema.
|
|
10
|
+
*
|
|
11
|
+
* Handles both Zod's native .meta() and ZodSensitive wrappers.
|
|
12
|
+
*
|
|
13
|
+
* @example
|
|
14
|
+
* ```ts
|
|
15
|
+
* const schema = z.string().meta({ encrypted: true })
|
|
16
|
+
* const meta = getMetadata(schema)
|
|
17
|
+
* // => { encrypted: true }
|
|
18
|
+
* ```
|
|
19
|
+
*/
|
|
20
|
+
export declare function getMetadata(schema: z.ZodTypeAny): Record<string, unknown> | undefined;
|
|
21
|
+
/**
|
|
22
|
+
* Check if a schema has metadata matching a predicate.
|
|
23
|
+
*
|
|
24
|
+
* @example
|
|
25
|
+
* ```ts
|
|
26
|
+
* const schema = z.string().meta({ sensitive: true })
|
|
27
|
+
* hasMetadata(schema, meta => meta.sensitive === true)
|
|
28
|
+
* // => true
|
|
29
|
+
* ```
|
|
30
|
+
*/
|
|
31
|
+
export declare function hasMetadata(schema: z.ZodTypeAny, predicate: (meta: Record<string, unknown>) => boolean): boolean;
|
|
32
|
+
/**
|
|
33
|
+
* Walk a Zod schema, calling visitor functions for each node.
|
|
34
|
+
*
|
|
35
|
+
* Handles: objects, arrays, optionals, nullables, unions, discriminated unions.
|
|
36
|
+
* Prevents infinite recursion on circular schema references.
|
|
37
|
+
*
|
|
38
|
+
* @example
|
|
39
|
+
* ```ts
|
|
40
|
+
* walkSchema(userSchema, {
|
|
41
|
+
* onField: (info) => {
|
|
42
|
+
* if (info.meta?.encrypted) {
|
|
43
|
+
* console.log(`Encrypted field: ${info.path}`)
|
|
44
|
+
* }
|
|
45
|
+
* }
|
|
46
|
+
* })
|
|
47
|
+
* ```
|
|
48
|
+
*/
|
|
49
|
+
export declare function walkSchema(schema: z.ZodTypeAny, visitor: SchemaVisitor, options?: WalkSchemaOptions): void;
|
|
50
|
+
/**
|
|
51
|
+
* Find all fields in a schema where metadata matches a predicate.
|
|
52
|
+
*
|
|
53
|
+
* @overload Type guard version - returns narrowed meta type
|
|
54
|
+
*/
|
|
55
|
+
export declare function findFieldsWithMeta<TMeta extends Record<string, unknown>>(schema: z.ZodTypeAny, predicate: (meta: Record<string, unknown> | undefined) => meta is TMeta): Array<FieldInfo & {
|
|
56
|
+
meta: TMeta;
|
|
57
|
+
}>;
|
|
58
|
+
/**
|
|
59
|
+
* @overload Boolean predicate version
|
|
60
|
+
*/
|
|
61
|
+
export declare function findFieldsWithMeta(schema: z.ZodTypeAny, predicate: (meta: Record<string, unknown> | undefined) => boolean): FieldInfo[];
|
|
62
|
+
//# sourceMappingURL=traverse.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"traverse.d.ts","sourceRoot":"","sources":["../../src/transform/traverse.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,CAAC,EAAE,MAAM,KAAK,CAAA;AAC5B,OAAO,KAAK,EAAE,SAAS,EAAE,aAAa,EAAE,iBAAiB,EAAE,MAAM,SAAS,CAAA;AAgB1E;;;;;;;;;;;GAWG;AACH,wBAAgB,WAAW,CAAC,MAAM,EAAE,CAAC,CAAC,UAAU,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,CA+BrF;AA+CD;;;;;;;;;GASG;AACH,wBAAgB,WAAW,CACzB,MAAM,EAAE,CAAC,CAAC,UAAU,EACpB,SAAS,EAAE,CAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,KAAK,OAAO,GACpD,OAAO,CAGT;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,UAAU,CACxB,MAAM,EAAE,CAAC,CAAC,UAAU,EACpB,OAAO,EAAE,aAAa,EACtB,OAAO,CAAC,EAAE,iBAAiB,GAC1B,IAAI,CAsHN;AAED;;;;GAIG;AACH,wBAAgB,kBAAkB,CAAC,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACtE,MAAM,EAAE,CAAC,CAAC,UAAU,EACpB,SAAS,EAAE,CAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,KAAK,IAAI,IAAI,KAAK,GACtE,KAAK,CAAC,SAAS,GAAG;IAAE,IAAI,EAAE,KAAK,CAAA;CAAE,CAAC,CAAA;AAErC;;GAEG;AACH,wBAAgB,kBAAkB,CAChC,MAAM,EAAE,CAAC,CAAC,UAAU,EACpB,SAAS,EAAE,CAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,SAAS,KAAK,OAAO,GAChE,SAAS,EAAE,CAAA"}
|