@schmock/schema 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +18 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +165 -0
- package/dist/test-utils.d.ts +59 -0
- package/dist/test-utils.d.ts.map +1 -0
- package/dist/test-utils.js +269 -0
- package/package.json +39 -0
- package/src/advanced-features.test.ts +911 -0
- package/src/data-quality.test.ts +415 -0
- package/src/error-handling.test.ts +507 -0
- package/src/index.test.ts +1208 -0
- package/src/index.ts +859 -0
- package/src/integration.test.ts +632 -0
- package/src/performance.test.ts +477 -0
- package/src/plugin-integration.test.ts +574 -0
- package/src/real-world.test.ts +636 -0
- package/src/test-utils.ts +357 -0
|
@@ -0,0 +1,574 @@
|
|
|
1
|
+
import { describe, expect, it } from "vitest";
|
|
2
|
+
import { schemaPlugin } from "./index";
|
|
3
|
+
import { schemas, validators } from "./test-utils";
|
|
4
|
+
|
|
5
|
+
describe("Schema Plugin Integration", () => {
|
|
6
|
+
describe("Plugin Lifecycle", () => {
|
|
7
|
+
it("validates schema during plugin creation", () => {
|
|
8
|
+
// Valid schema should create plugin
|
|
9
|
+
const validPlugin = schemaPlugin({
|
|
10
|
+
schema: schemas.complex.user(),
|
|
11
|
+
});
|
|
12
|
+
expect(validPlugin).toBeDefined();
|
|
13
|
+
expect(validPlugin.name).toBe("schema");
|
|
14
|
+
expect(validPlugin.version).toBe("1.0.0");
|
|
15
|
+
|
|
16
|
+
// Invalid schema should throw immediately
|
|
17
|
+
expect(() => {
|
|
18
|
+
schemaPlugin({
|
|
19
|
+
schema: { type: "invalid" as any },
|
|
20
|
+
});
|
|
21
|
+
}).toThrow("Invalid schema type");
|
|
22
|
+
});
|
|
23
|
+
|
|
24
|
+
it("processes context through plugin pipeline", () => {
|
|
25
|
+
const plugin = schemaPlugin({
|
|
26
|
+
schema: schemas.simple.object({
|
|
27
|
+
requestId: { type: "string" },
|
|
28
|
+
timestamp: { type: "string" },
|
|
29
|
+
data: { type: "object" },
|
|
30
|
+
}),
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
const context = {
|
|
34
|
+
method: "POST",
|
|
35
|
+
path: "/api/data",
|
|
36
|
+
params: {},
|
|
37
|
+
query: {},
|
|
38
|
+
state: { requestId: "req-123" },
|
|
39
|
+
headers: { "content-type": "application/json" },
|
|
40
|
+
body: { value: 42 },
|
|
41
|
+
route: { pattern: "/api/data" },
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
const result = plugin.process(context);
|
|
45
|
+
|
|
46
|
+
expect(result).toHaveProperty("context");
|
|
47
|
+
expect(result).toHaveProperty("response");
|
|
48
|
+
expect(result.context).toBe(context); // Context passed through
|
|
49
|
+
expect(result.response).toHaveProperty("requestId");
|
|
50
|
+
expect(result.response).toHaveProperty("timestamp");
|
|
51
|
+
expect(result.response).toHaveProperty("data");
|
|
52
|
+
});
|
|
53
|
+
|
|
54
|
+
it("preserves existing responses when present", () => {
|
|
55
|
+
const plugin = schemaPlugin({
|
|
56
|
+
schema: schemas.simple.object({ id: schemas.simple.number() }),
|
|
57
|
+
});
|
|
58
|
+
|
|
59
|
+
const context = {
|
|
60
|
+
method: "GET",
|
|
61
|
+
path: "/test",
|
|
62
|
+
params: {},
|
|
63
|
+
query: {},
|
|
64
|
+
state: {},
|
|
65
|
+
headers: {},
|
|
66
|
+
body: null,
|
|
67
|
+
route: {},
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
const existingResponse = {
|
|
71
|
+
cached: true,
|
|
72
|
+
data: [1, 2, 3],
|
|
73
|
+
metadata: { source: "cache" },
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
const result = plugin.process(context, existingResponse);
|
|
77
|
+
|
|
78
|
+
expect(result.response).toBe(existingResponse);
|
|
79
|
+
expect(result.response).toEqual(existingResponse);
|
|
80
|
+
});
|
|
81
|
+
});
|
|
82
|
+
|
|
83
|
+
describe("Context Integration", () => {
|
|
84
|
+
it("uses params in template overrides", () => {
|
|
85
|
+
const plugin = schemaPlugin({
|
|
86
|
+
schema: schemas.simple.object({
|
|
87
|
+
userId: { type: "string" },
|
|
88
|
+
postId: { type: "string" },
|
|
89
|
+
action: { type: "string" },
|
|
90
|
+
}),
|
|
91
|
+
overrides: {
|
|
92
|
+
userId: "{{params.userId}}",
|
|
93
|
+
postId: "{{params.postId}}",
|
|
94
|
+
action: "view",
|
|
95
|
+
},
|
|
96
|
+
});
|
|
97
|
+
|
|
98
|
+
const result = plugin.process({
|
|
99
|
+
method: "GET",
|
|
100
|
+
path: "/users/123/posts/456",
|
|
101
|
+
params: { userId: "123", postId: "456" },
|
|
102
|
+
query: {},
|
|
103
|
+
state: {},
|
|
104
|
+
headers: {},
|
|
105
|
+
body: null,
|
|
106
|
+
route: {},
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
expect(result.response.userId).toBe("123"); // Template values are strings
|
|
110
|
+
expect(result.response.postId).toBe("456");
|
|
111
|
+
expect(result.response.action).toBe("view");
|
|
112
|
+
});
|
|
113
|
+
|
|
114
|
+
it("uses query parameters in templates", () => {
|
|
115
|
+
const plugin = schemaPlugin({
|
|
116
|
+
schema: schemas.simple.object({
|
|
117
|
+
page: { type: "number" },
|
|
118
|
+
limit: { type: "number" },
|
|
119
|
+
sort: { type: "string" },
|
|
120
|
+
filter: { type: "string" },
|
|
121
|
+
}),
|
|
122
|
+
overrides: {
|
|
123
|
+
page: "{{query.page}}",
|
|
124
|
+
limit: "{{query.limit}}",
|
|
125
|
+
sort: "{{query.sort}}",
|
|
126
|
+
filter: "{{query.filter}}",
|
|
127
|
+
},
|
|
128
|
+
});
|
|
129
|
+
|
|
130
|
+
const result = plugin.process({
|
|
131
|
+
method: "GET",
|
|
132
|
+
path: "/api/items",
|
|
133
|
+
params: {},
|
|
134
|
+
query: {
|
|
135
|
+
page: "2",
|
|
136
|
+
limit: "50",
|
|
137
|
+
sort: "name",
|
|
138
|
+
filter: "active",
|
|
139
|
+
},
|
|
140
|
+
state: {},
|
|
141
|
+
headers: {},
|
|
142
|
+
body: null,
|
|
143
|
+
route: {},
|
|
144
|
+
});
|
|
145
|
+
|
|
146
|
+
expect(result.response.page).toBe("2"); // Query values are strings
|
|
147
|
+
expect(result.response.limit).toBe("50");
|
|
148
|
+
expect(result.response.sort).toBe("name");
|
|
149
|
+
expect(result.response.filter).toBe("active");
|
|
150
|
+
});
|
|
151
|
+
|
|
152
|
+
it("uses state in template processing", () => {
|
|
153
|
+
const plugin = schemaPlugin({
|
|
154
|
+
schema: schemas.simple.object({
|
|
155
|
+
currentUser: { type: "string" },
|
|
156
|
+
sessionId: { type: "string" },
|
|
157
|
+
permissions: { type: "array", items: { type: "string" } },
|
|
158
|
+
}),
|
|
159
|
+
overrides: {
|
|
160
|
+
currentUser: "{{state.user.name}}",
|
|
161
|
+
sessionId: "{{state.session.id}}",
|
|
162
|
+
permissions: ["read", "write"],
|
|
163
|
+
},
|
|
164
|
+
});
|
|
165
|
+
|
|
166
|
+
const result = plugin.process({
|
|
167
|
+
method: "GET",
|
|
168
|
+
path: "/api/profile",
|
|
169
|
+
params: {},
|
|
170
|
+
query: {},
|
|
171
|
+
state: new Map(),
|
|
172
|
+
routeState: {
|
|
173
|
+
user: { id: 1, name: "John Doe" },
|
|
174
|
+
session: { id: "sess-123", expires: "2024-12-31" },
|
|
175
|
+
},
|
|
176
|
+
headers: {},
|
|
177
|
+
body: null,
|
|
178
|
+
route: {},
|
|
179
|
+
});
|
|
180
|
+
|
|
181
|
+
expect(result.response.currentUser).toBe("John Doe");
|
|
182
|
+
expect(result.response.sessionId).toBe("sess-123");
|
|
183
|
+
expect(result.response.permissions).toEqual(["read", "write"]);
|
|
184
|
+
});
|
|
185
|
+
|
|
186
|
+
it("handles missing template values gracefully", () => {
|
|
187
|
+
const plugin = schemaPlugin({
|
|
188
|
+
schema: schemas.simple.object({
|
|
189
|
+
value1: { type: "string" },
|
|
190
|
+
value2: { type: "string" },
|
|
191
|
+
value3: { type: "string" },
|
|
192
|
+
}),
|
|
193
|
+
overrides: {
|
|
194
|
+
value1: "{{params.missing}}",
|
|
195
|
+
value2: "{{state.nonexistent.nested}}",
|
|
196
|
+
value3: "default",
|
|
197
|
+
},
|
|
198
|
+
});
|
|
199
|
+
|
|
200
|
+
const result = plugin.process({
|
|
201
|
+
method: "GET",
|
|
202
|
+
path: "/test",
|
|
203
|
+
params: { other: "value" },
|
|
204
|
+
query: {},
|
|
205
|
+
state: new Map(),
|
|
206
|
+
routeState: { different: "data" },
|
|
207
|
+
headers: {},
|
|
208
|
+
body: null,
|
|
209
|
+
route: {},
|
|
210
|
+
});
|
|
211
|
+
|
|
212
|
+
// Missing values return original template
|
|
213
|
+
expect(result.response.value1).toBe("{{params.missing}}");
|
|
214
|
+
expect(result.response.value2).toBe("{{state.nonexistent.nested}}");
|
|
215
|
+
expect(result.response.value3).toBe("default");
|
|
216
|
+
});
|
|
217
|
+
});
|
|
218
|
+
|
|
219
|
+
describe("Array Generation with Plugin", () => {
|
|
220
|
+
it("generates arrays with count parameter", () => {
|
|
221
|
+
const plugin = schemaPlugin({
|
|
222
|
+
schema: schemas.simple.array(
|
|
223
|
+
schemas.simple.object({
|
|
224
|
+
id: { type: "number" },
|
|
225
|
+
name: { type: "string" },
|
|
226
|
+
}),
|
|
227
|
+
),
|
|
228
|
+
count: 5,
|
|
229
|
+
});
|
|
230
|
+
|
|
231
|
+
const result = plugin.process({
|
|
232
|
+
method: "GET",
|
|
233
|
+
path: "/api/items",
|
|
234
|
+
params: {},
|
|
235
|
+
query: {},
|
|
236
|
+
state: {},
|
|
237
|
+
headers: {},
|
|
238
|
+
body: null,
|
|
239
|
+
route: {},
|
|
240
|
+
});
|
|
241
|
+
|
|
242
|
+
expect(Array.isArray(result.response)).toBe(true);
|
|
243
|
+
expect(result.response).toHaveLength(5);
|
|
244
|
+
result.response.forEach((item) => {
|
|
245
|
+
expect(item).toHaveProperty("id");
|
|
246
|
+
expect(item).toHaveProperty("name");
|
|
247
|
+
});
|
|
248
|
+
});
|
|
249
|
+
|
|
250
|
+
it("applies overrides to array items", () => {
|
|
251
|
+
const plugin = schemaPlugin({
|
|
252
|
+
schema: schemas.simple.array(
|
|
253
|
+
schemas.simple.object({
|
|
254
|
+
index: { type: "number" },
|
|
255
|
+
category: { type: "string" },
|
|
256
|
+
}),
|
|
257
|
+
),
|
|
258
|
+
count: 3,
|
|
259
|
+
overrides: {
|
|
260
|
+
category: "{{state.defaultCategory}}",
|
|
261
|
+
},
|
|
262
|
+
});
|
|
263
|
+
|
|
264
|
+
const result = plugin.process({
|
|
265
|
+
method: "GET",
|
|
266
|
+
path: "/api/items",
|
|
267
|
+
params: {},
|
|
268
|
+
query: {},
|
|
269
|
+
state: new Map(),
|
|
270
|
+
routeState: { defaultCategory: "electronics" },
|
|
271
|
+
headers: {},
|
|
272
|
+
body: null,
|
|
273
|
+
route: {},
|
|
274
|
+
});
|
|
275
|
+
|
|
276
|
+
expect(result.response).toHaveLength(3);
|
|
277
|
+
result.response.forEach((item) => {
|
|
278
|
+
expect(item.category).toBe("electronics");
|
|
279
|
+
});
|
|
280
|
+
});
|
|
281
|
+
});
|
|
282
|
+
|
|
283
|
+
describe("Error Handling in Plugin", () => {
|
|
284
|
+
it("wraps generation errors with context", () => {
|
|
285
|
+
const plugin = schemaPlugin({
|
|
286
|
+
schema: {
|
|
287
|
+
type: "string",
|
|
288
|
+
pattern: "[", // Invalid regex
|
|
289
|
+
},
|
|
290
|
+
});
|
|
291
|
+
|
|
292
|
+
const context = {
|
|
293
|
+
method: "GET",
|
|
294
|
+
path: "/api/test/123",
|
|
295
|
+
params: { id: "123" },
|
|
296
|
+
query: {},
|
|
297
|
+
state: {},
|
|
298
|
+
headers: {},
|
|
299
|
+
body: null,
|
|
300
|
+
route: {},
|
|
301
|
+
};
|
|
302
|
+
|
|
303
|
+
try {
|
|
304
|
+
plugin.process(context);
|
|
305
|
+
expect.fail("Should have thrown");
|
|
306
|
+
} catch (error: any) {
|
|
307
|
+
// Should throw some kind of error for invalid pattern
|
|
308
|
+
expect(error).toBeDefined();
|
|
309
|
+
expect(error.name).toContain("Error");
|
|
310
|
+
}
|
|
311
|
+
});
|
|
312
|
+
|
|
313
|
+
it("handles null or undefined context properties", () => {
|
|
314
|
+
const plugin = schemaPlugin({
|
|
315
|
+
schema: schemas.simple.object({
|
|
316
|
+
data: { type: "string" },
|
|
317
|
+
}),
|
|
318
|
+
});
|
|
319
|
+
|
|
320
|
+
// Should not crash with null/undefined properties
|
|
321
|
+
const result = plugin.process({
|
|
322
|
+
method: "GET",
|
|
323
|
+
path: "/test",
|
|
324
|
+
params: null as any,
|
|
325
|
+
query: undefined as any,
|
|
326
|
+
state: null as any,
|
|
327
|
+
headers: {},
|
|
328
|
+
body: null,
|
|
329
|
+
route: {},
|
|
330
|
+
});
|
|
331
|
+
|
|
332
|
+
expect(result.response).toHaveProperty("data");
|
|
333
|
+
expect(typeof result.response.data).toBe("string");
|
|
334
|
+
});
|
|
335
|
+
});
|
|
336
|
+
|
|
337
|
+
describe("Complex Schema Scenarios", () => {
|
|
338
|
+
it("handles conditional schemas in plugin", () => {
|
|
339
|
+
const plugin = schemaPlugin({
|
|
340
|
+
schema: {
|
|
341
|
+
type: "object",
|
|
342
|
+
properties: {
|
|
343
|
+
type: { type: "string", enum: ["user", "admin"] },
|
|
344
|
+
data: { type: "object" },
|
|
345
|
+
},
|
|
346
|
+
required: ["type", "data"],
|
|
347
|
+
},
|
|
348
|
+
});
|
|
349
|
+
|
|
350
|
+
const result = plugin.process({
|
|
351
|
+
method: "GET",
|
|
352
|
+
path: "/api/profile",
|
|
353
|
+
params: {},
|
|
354
|
+
query: {},
|
|
355
|
+
state: {},
|
|
356
|
+
headers: {},
|
|
357
|
+
body: null,
|
|
358
|
+
route: {},
|
|
359
|
+
});
|
|
360
|
+
|
|
361
|
+
expect(["user", "admin"]).toContain(result.response.type);
|
|
362
|
+
expect(result.response).toHaveProperty("data");
|
|
363
|
+
});
|
|
364
|
+
|
|
365
|
+
it("generates nested data with references", () => {
|
|
366
|
+
const plugin = schemaPlugin({
|
|
367
|
+
schema: {
|
|
368
|
+
definitions: {
|
|
369
|
+
timestamp: { type: "string", format: "date-time" },
|
|
370
|
+
user: {
|
|
371
|
+
type: "object",
|
|
372
|
+
properties: {
|
|
373
|
+
id: { type: "string", format: "uuid" },
|
|
374
|
+
name: { type: "string" },
|
|
375
|
+
},
|
|
376
|
+
},
|
|
377
|
+
},
|
|
378
|
+
type: "object",
|
|
379
|
+
properties: {
|
|
380
|
+
created: { $ref: "#/definitions/timestamp" },
|
|
381
|
+
updated: { $ref: "#/definitions/timestamp" },
|
|
382
|
+
author: { $ref: "#/definitions/user" },
|
|
383
|
+
editor: { $ref: "#/definitions/user" },
|
|
384
|
+
},
|
|
385
|
+
},
|
|
386
|
+
});
|
|
387
|
+
|
|
388
|
+
const result = plugin.process({
|
|
389
|
+
method: "GET",
|
|
390
|
+
path: "/api/document",
|
|
391
|
+
params: {},
|
|
392
|
+
query: {},
|
|
393
|
+
state: {},
|
|
394
|
+
headers: {},
|
|
395
|
+
body: null,
|
|
396
|
+
route: {},
|
|
397
|
+
});
|
|
398
|
+
|
|
399
|
+
expect(
|
|
400
|
+
validators.appearsToBeFromCategory([result.response.created], "date"),
|
|
401
|
+
).toBe(true);
|
|
402
|
+
expect(
|
|
403
|
+
validators.appearsToBeFromCategory([result.response.updated], "date"),
|
|
404
|
+
).toBe(true);
|
|
405
|
+
expect(
|
|
406
|
+
validators.appearsToBeFromCategory([result.response.author.id], "uuid"),
|
|
407
|
+
).toBe(true);
|
|
408
|
+
expect(
|
|
409
|
+
validators.appearsToBeFromCategory([result.response.editor.id], "uuid"),
|
|
410
|
+
).toBe(true);
|
|
411
|
+
});
|
|
412
|
+
});
|
|
413
|
+
|
|
414
|
+
describe("Performance Characteristics", () => {
|
|
415
|
+
it("maintains consistent performance across multiple calls", () => {
|
|
416
|
+
const plugin = schemaPlugin({
|
|
417
|
+
schema: schemas.complex.user(),
|
|
418
|
+
});
|
|
419
|
+
|
|
420
|
+
const context = {
|
|
421
|
+
method: "GET",
|
|
422
|
+
path: "/api/user",
|
|
423
|
+
params: {},
|
|
424
|
+
query: {},
|
|
425
|
+
state: {},
|
|
426
|
+
headers: {},
|
|
427
|
+
body: null,
|
|
428
|
+
route: {},
|
|
429
|
+
};
|
|
430
|
+
|
|
431
|
+
// Generate multiple times
|
|
432
|
+
const results = Array.from(
|
|
433
|
+
{ length: 10 },
|
|
434
|
+
() => plugin.process(context).response,
|
|
435
|
+
);
|
|
436
|
+
|
|
437
|
+
// All should be valid but different
|
|
438
|
+
results.forEach((result) => {
|
|
439
|
+
expect(result).toHaveProperty("id");
|
|
440
|
+
expect(result).toHaveProperty("email");
|
|
441
|
+
});
|
|
442
|
+
|
|
443
|
+
// Should generate different data each time
|
|
444
|
+
const emails = results.map((r) => r.email);
|
|
445
|
+
const uniqueEmails = new Set(emails);
|
|
446
|
+
expect(uniqueEmails.size).toBeGreaterThan(5);
|
|
447
|
+
});
|
|
448
|
+
|
|
449
|
+
it("handles large schemas efficiently", () => {
|
|
450
|
+
const plugin = schemaPlugin({
|
|
451
|
+
schema: {
|
|
452
|
+
type: "object",
|
|
453
|
+
properties: Object.fromEntries(
|
|
454
|
+
Array.from({ length: 50 }, (_, i) => [
|
|
455
|
+
`field${i}`,
|
|
456
|
+
{ type: i % 2 === 0 ? "string" : "number" },
|
|
457
|
+
]),
|
|
458
|
+
),
|
|
459
|
+
},
|
|
460
|
+
});
|
|
461
|
+
|
|
462
|
+
const context = {
|
|
463
|
+
method: "GET",
|
|
464
|
+
path: "/api/data",
|
|
465
|
+
params: {},
|
|
466
|
+
query: {},
|
|
467
|
+
state: {},
|
|
468
|
+
headers: {},
|
|
469
|
+
body: null,
|
|
470
|
+
route: {},
|
|
471
|
+
};
|
|
472
|
+
|
|
473
|
+
const result = plugin.process(context);
|
|
474
|
+
|
|
475
|
+
// Should have all fields
|
|
476
|
+
expect(Object.keys(result.response).length).toBeGreaterThanOrEqual(50);
|
|
477
|
+
});
|
|
478
|
+
});
|
|
479
|
+
|
|
480
|
+
describe("Real-world Plugin Usage", () => {
|
|
481
|
+
it("generates mock API responses for testing", () => {
|
|
482
|
+
const plugin = schemaPlugin({
|
|
483
|
+
schema: {
|
|
484
|
+
type: "object",
|
|
485
|
+
properties: {
|
|
486
|
+
success: { type: "boolean", const: true },
|
|
487
|
+
data: {
|
|
488
|
+
type: "object",
|
|
489
|
+
properties: {
|
|
490
|
+
id: { type: "string", format: "uuid" },
|
|
491
|
+
email: { type: "string", format: "email" },
|
|
492
|
+
profile: {
|
|
493
|
+
type: "object",
|
|
494
|
+
properties: {
|
|
495
|
+
name: { type: "string" },
|
|
496
|
+
avatar: { type: "string", format: "uri" },
|
|
497
|
+
},
|
|
498
|
+
},
|
|
499
|
+
},
|
|
500
|
+
},
|
|
501
|
+
timestamp: { type: "string", format: "date-time" },
|
|
502
|
+
},
|
|
503
|
+
},
|
|
504
|
+
overrides: {
|
|
505
|
+
"data.id": "{{params.userId}}",
|
|
506
|
+
timestamp: "{{state.currentTime}}",
|
|
507
|
+
},
|
|
508
|
+
});
|
|
509
|
+
|
|
510
|
+
const result = plugin.process({
|
|
511
|
+
method: "GET",
|
|
512
|
+
path: "/api/users/user-123",
|
|
513
|
+
params: { userId: "user-123" },
|
|
514
|
+
query: {},
|
|
515
|
+
state: new Map(),
|
|
516
|
+
routeState: { currentTime: "2024-01-01T12:00:00Z" },
|
|
517
|
+
headers: {},
|
|
518
|
+
body: null,
|
|
519
|
+
route: {},
|
|
520
|
+
});
|
|
521
|
+
|
|
522
|
+
expect(result.response.success).toBe(true);
|
|
523
|
+
expect(result.response.data.id).toBe("user-123");
|
|
524
|
+
expect(result.response.timestamp).toBe("2024-01-01T12:00:00Z");
|
|
525
|
+
expect(
|
|
526
|
+
validators.appearsToBeFromCategory(
|
|
527
|
+
[result.response.data.email],
|
|
528
|
+
"email",
|
|
529
|
+
),
|
|
530
|
+
).toBe(true);
|
|
531
|
+
});
|
|
532
|
+
|
|
533
|
+
it("works with schmock plugin pipeline", () => {
|
|
534
|
+
const schemaPlug = schemaPlugin({
|
|
535
|
+
schema: schemas.simple.object({
|
|
536
|
+
message: { type: "string" },
|
|
537
|
+
code: { type: "number" },
|
|
538
|
+
}),
|
|
539
|
+
});
|
|
540
|
+
|
|
541
|
+
// Mock another plugin in the pipeline
|
|
542
|
+
const loggingPlugin = {
|
|
543
|
+
name: "logger",
|
|
544
|
+
version: "1.0.0",
|
|
545
|
+
process: (ctx: any, response: any) => {
|
|
546
|
+
console.log(`Processing ${ctx.path}`);
|
|
547
|
+
return { context: ctx, response };
|
|
548
|
+
},
|
|
549
|
+
};
|
|
550
|
+
|
|
551
|
+
// Simulate pipeline execution
|
|
552
|
+
const context = {
|
|
553
|
+
method: "GET",
|
|
554
|
+
path: "/api/status",
|
|
555
|
+
params: {},
|
|
556
|
+
query: {},
|
|
557
|
+
state: {},
|
|
558
|
+
headers: {},
|
|
559
|
+
body: null,
|
|
560
|
+
route: {},
|
|
561
|
+
};
|
|
562
|
+
|
|
563
|
+
// First plugin generates response
|
|
564
|
+
const result1 = schemaPlug.process(context);
|
|
565
|
+
|
|
566
|
+
// Second plugin receives generated response
|
|
567
|
+
const result2 = loggingPlugin.process(result1.context, result1.response);
|
|
568
|
+
|
|
569
|
+
expect(result2.response).toHaveProperty("message");
|
|
570
|
+
expect(result2.response).toHaveProperty("code");
|
|
571
|
+
expect(result2.response).toBe(result1.response); // Same reference
|
|
572
|
+
});
|
|
573
|
+
});
|
|
574
|
+
});
|