@mantajs/test-utils 0.2.0-beta.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/core-types.d.ts +369 -0
- package/dist/core-types.d.ts.map +1 -0
- package/dist/core-types.js +44 -0
- package/dist/core-types.js.map +1 -0
- package/dist/index.d.ts +127 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +378 -0
- package/dist/index.js.map +1 -0
- package/dist/pg.d.ts +15 -0
- package/dist/pg.d.ts.map +1 -0
- package/dist/pg.js +71 -0
- package/dist/pg.js.map +1 -0
- package/package.json +41 -0
|
@@ -0,0 +1,369 @@
|
|
|
1
|
+
export type MantaErrorType = 'NOT_FOUND' | 'INVALID_DATA' | 'UNAUTHORIZED' | 'FORBIDDEN' | 'DUPLICATE_ERROR' | 'CONFLICT' | 'NOT_ALLOWED' | 'UNEXPECTED_STATE' | 'DB_ERROR' | 'UNKNOWN_MODULES' | 'INVALID_STATE' | 'NOT_IMPLEMENTED' | 'RESOURCE_EXHAUSTED';
|
|
2
|
+
export declare class MantaError extends Error {
|
|
3
|
+
readonly type: MantaErrorType;
|
|
4
|
+
readonly code?: string;
|
|
5
|
+
readonly date: Date;
|
|
6
|
+
readonly __isMantaError: true;
|
|
7
|
+
constructor(type: MantaErrorType, message: string, options?: {
|
|
8
|
+
code?: string;
|
|
9
|
+
});
|
|
10
|
+
static is(err: unknown): err is MantaError;
|
|
11
|
+
}
|
|
12
|
+
export declare class PermanentSubscriberError extends Error {
|
|
13
|
+
readonly cause: Error;
|
|
14
|
+
readonly __isPermanentSubscriber: true;
|
|
15
|
+
constructor(cause: Error);
|
|
16
|
+
}
|
|
17
|
+
export declare function permanentSubscriberFailure(error: Error): PermanentSubscriberError;
|
|
18
|
+
export type ServiceLifetime = 'SINGLETON' | 'SCOPED' | 'TRANSIENT';
|
|
19
|
+
export interface AuthContext {
|
|
20
|
+
id: string;
|
|
21
|
+
type: string;
|
|
22
|
+
email?: string;
|
|
23
|
+
auth_identity_id?: string;
|
|
24
|
+
metadata?: Record<string, unknown>;
|
|
25
|
+
}
|
|
26
|
+
export interface Message<T = unknown> {
|
|
27
|
+
eventName: string;
|
|
28
|
+
data: T;
|
|
29
|
+
metadata: {
|
|
30
|
+
auth_context?: AuthContext;
|
|
31
|
+
eventGroupId?: string;
|
|
32
|
+
transactionId?: string;
|
|
33
|
+
timestamp: number;
|
|
34
|
+
idempotencyKey?: string;
|
|
35
|
+
source?: string;
|
|
36
|
+
};
|
|
37
|
+
}
|
|
38
|
+
export interface Context {
|
|
39
|
+
transactionManager?: unknown;
|
|
40
|
+
manager?: unknown;
|
|
41
|
+
isolationLevel?: string;
|
|
42
|
+
enableNestedTransactions?: boolean;
|
|
43
|
+
eventGroupId?: string;
|
|
44
|
+
transactionId?: string;
|
|
45
|
+
runId?: string;
|
|
46
|
+
requestId?: string;
|
|
47
|
+
messageAggregator?: IMessageAggregator;
|
|
48
|
+
idempotencyKey?: string;
|
|
49
|
+
isCancelling?: boolean;
|
|
50
|
+
auth_context?: AuthContext;
|
|
51
|
+
}
|
|
52
|
+
export interface StepExecutionContext {
|
|
53
|
+
container: MantaApp;
|
|
54
|
+
metadata: {
|
|
55
|
+
attempt: number;
|
|
56
|
+
idempotencyKey: string;
|
|
57
|
+
action: 'invoke' | 'compensate';
|
|
58
|
+
};
|
|
59
|
+
context: Context;
|
|
60
|
+
}
|
|
61
|
+
export interface JobResult {
|
|
62
|
+
status: 'success' | 'failure' | 'skipped';
|
|
63
|
+
data?: unknown;
|
|
64
|
+
error?: MantaError;
|
|
65
|
+
duration_ms: number;
|
|
66
|
+
}
|
|
67
|
+
export interface JobExecution {
|
|
68
|
+
job_name: string;
|
|
69
|
+
started_at: Date;
|
|
70
|
+
finished_at: Date;
|
|
71
|
+
status: 'success' | 'failure' | 'skipped';
|
|
72
|
+
error?: string;
|
|
73
|
+
attempt: number;
|
|
74
|
+
}
|
|
75
|
+
export interface MantaErrorResponse {
|
|
76
|
+
type: string;
|
|
77
|
+
message: string;
|
|
78
|
+
code?: string;
|
|
79
|
+
details?: unknown;
|
|
80
|
+
stack?: string;
|
|
81
|
+
}
|
|
82
|
+
export interface RelationPagination {
|
|
83
|
+
[relationName: string]: {
|
|
84
|
+
limit?: number;
|
|
85
|
+
offset?: number;
|
|
86
|
+
};
|
|
87
|
+
}
|
|
88
|
+
export interface CursorPagination {
|
|
89
|
+
cursor?: string;
|
|
90
|
+
limit: number;
|
|
91
|
+
direction: 'forward' | 'backward';
|
|
92
|
+
}
|
|
93
|
+
export interface WorkflowLifecycleEvent {
|
|
94
|
+
type: 'STEP_SUCCESS' | 'STEP_FAILURE' | 'FINISH' | 'COMPENSATE_BEGIN' | 'COMPENSATE_END';
|
|
95
|
+
workflowId: string;
|
|
96
|
+
transactionId: string;
|
|
97
|
+
stepId?: string;
|
|
98
|
+
result?: unknown;
|
|
99
|
+
error?: MantaError;
|
|
100
|
+
status?: string;
|
|
101
|
+
}
|
|
102
|
+
export interface AuthCredentials {
|
|
103
|
+
bearer?: string;
|
|
104
|
+
apiKey?: string;
|
|
105
|
+
sessionId?: string;
|
|
106
|
+
}
|
|
107
|
+
export interface SessionOptions {
|
|
108
|
+
ttl?: number;
|
|
109
|
+
}
|
|
110
|
+
export interface TransactionOptions {
|
|
111
|
+
isolationLevel?: 'READ UNCOMMITTED' | 'READ COMMITTED' | 'REPEATABLE READ' | 'SERIALIZABLE';
|
|
112
|
+
transaction?: unknown;
|
|
113
|
+
enableNestedTransactions?: boolean;
|
|
114
|
+
}
|
|
115
|
+
export interface DatabaseConfig {
|
|
116
|
+
url: string;
|
|
117
|
+
pool?: {
|
|
118
|
+
min?: number;
|
|
119
|
+
max?: number;
|
|
120
|
+
idleTimeout?: number;
|
|
121
|
+
};
|
|
122
|
+
ssl?: boolean;
|
|
123
|
+
}
|
|
124
|
+
export interface GroupStatus {
|
|
125
|
+
exists: boolean;
|
|
126
|
+
eventCount: number;
|
|
127
|
+
createdAt: number;
|
|
128
|
+
ttlRemainingMs?: number;
|
|
129
|
+
}
|
|
130
|
+
/** SPEC-001 — MantaApp (replaces IContainer) */
|
|
131
|
+
export interface MantaApp<TModules extends Record<string, unknown> = Record<string, unknown>, TWorkflows extends Record<string, (...args: unknown[]) => Promise<unknown>> = Record<string, (...args: unknown[]) => Promise<unknown>>> {
|
|
132
|
+
id: string;
|
|
133
|
+
modules: TModules;
|
|
134
|
+
workflows: TWorkflows;
|
|
135
|
+
resolve<T = unknown>(key: string): T;
|
|
136
|
+
dispose(): Promise<void>;
|
|
137
|
+
}
|
|
138
|
+
/** SPEC-064/077 — Cache */
|
|
139
|
+
export interface ICachePort {
|
|
140
|
+
get(key: string): Promise<string | null>;
|
|
141
|
+
set(key: string, data: string, ttl?: number): Promise<void>;
|
|
142
|
+
invalidate(key: string): Promise<void>;
|
|
143
|
+
clear(): Promise<void>;
|
|
144
|
+
}
|
|
145
|
+
/** SPEC-034 — Event Bus */
|
|
146
|
+
export interface IEventBusPort {
|
|
147
|
+
emit(event: Message | Message[], options?: {
|
|
148
|
+
groupId?: string;
|
|
149
|
+
}): Promise<void>;
|
|
150
|
+
subscribe(eventName: string, handler: (event: Message) => Promise<void> | void, options?: {
|
|
151
|
+
subscriberId?: string;
|
|
152
|
+
}): void;
|
|
153
|
+
unsubscribe(subscriberId: string): void;
|
|
154
|
+
releaseGroupedEvents(eventGroupId: string): Promise<void>;
|
|
155
|
+
clearGroupedEvents(eventGroupId: string): Promise<void>;
|
|
156
|
+
addInterceptor(fn: (message: Message, context?: {
|
|
157
|
+
isGrouped?: boolean;
|
|
158
|
+
eventGroupId?: string;
|
|
159
|
+
}) => Promise<void> | void): void;
|
|
160
|
+
removeInterceptor(fn: (message: Message, context?: {
|
|
161
|
+
isGrouped?: boolean;
|
|
162
|
+
eventGroupId?: string;
|
|
163
|
+
}) => Promise<void> | void): void;
|
|
164
|
+
onGroupCreated?(handler: (eventGroupId: string, eventCount: number) => void): void;
|
|
165
|
+
onGroupReleased?(handler: (eventGroupId: string, eventCount: number) => void): void;
|
|
166
|
+
onGroupCleared?(handler: (eventGroupId: string, eventCount: number, reason: 'explicit' | 'ttl') => void): void;
|
|
167
|
+
getGroupStatus?(eventGroupId: string): GroupStatus | null;
|
|
168
|
+
}
|
|
169
|
+
/** SPEC-066/089/090 — Locking */
|
|
170
|
+
export interface ILockingPort {
|
|
171
|
+
execute<T>(keys: string[], job: () => Promise<T>, options?: {
|
|
172
|
+
timeout?: number;
|
|
173
|
+
}): Promise<T>;
|
|
174
|
+
acquire(keys: string | string[], options?: {
|
|
175
|
+
ownerId?: string;
|
|
176
|
+
expire?: number;
|
|
177
|
+
}): Promise<boolean>;
|
|
178
|
+
release(keys: string | string[], options?: {
|
|
179
|
+
ownerId?: string;
|
|
180
|
+
}): Promise<void>;
|
|
181
|
+
releaseAll(options?: {
|
|
182
|
+
ownerId?: string;
|
|
183
|
+
}): Promise<void>;
|
|
184
|
+
}
|
|
185
|
+
/** SPEC-056 — Database */
|
|
186
|
+
export interface IDatabasePort {
|
|
187
|
+
initialize(config: DatabaseConfig): Promise<void>;
|
|
188
|
+
dispose(): Promise<void>;
|
|
189
|
+
healthCheck(): Promise<boolean>;
|
|
190
|
+
getClient(): unknown;
|
|
191
|
+
getPool(): unknown;
|
|
192
|
+
/** Execute raw parameterized SQL. Use $1, $2 placeholders. Escape hatch for complex queries. */
|
|
193
|
+
raw<T = Record<string, unknown>>(sql: string, params?: unknown[]): Promise<T[]>;
|
|
194
|
+
transaction<T>(fn: (tx: unknown) => Promise<T>, options?: TransactionOptions): Promise<T>;
|
|
195
|
+
introspect?(): Promise<unknown>;
|
|
196
|
+
}
|
|
197
|
+
/** SPEC-126 — Repository */
|
|
198
|
+
export interface IRepository<T = unknown> {
|
|
199
|
+
find(options?: {
|
|
200
|
+
where?: Record<string, unknown>;
|
|
201
|
+
withDeleted?: boolean;
|
|
202
|
+
limit?: number;
|
|
203
|
+
offset?: number;
|
|
204
|
+
order?: Record<string, 'ASC' | 'DESC'>;
|
|
205
|
+
cursor?: CursorPagination;
|
|
206
|
+
}): Promise<T[]>;
|
|
207
|
+
findAndCount(options?: Record<string, unknown>): Promise<[T[], number]>;
|
|
208
|
+
create(data: Record<string, unknown> | Record<string, unknown>[]): Promise<T | T[]>;
|
|
209
|
+
update(data: Record<string, unknown> | Record<string, unknown>[]): Promise<T | T[]>;
|
|
210
|
+
delete(ids: string | string[]): Promise<void>;
|
|
211
|
+
softDelete(ids: string | string[]): Promise<Record<string, string[]>>;
|
|
212
|
+
restore(ids: string | string[]): Promise<void>;
|
|
213
|
+
serialize(data: unknown, options?: unknown): Promise<unknown>;
|
|
214
|
+
upsertWithReplace(data: Record<string, unknown>[], replaceFields?: string[], conflictTarget?: string[]): Promise<T[]>;
|
|
215
|
+
transaction<TManager = unknown>(task: (transactionManager: TManager) => Promise<unknown>, options?: TransactionOptions): Promise<unknown>;
|
|
216
|
+
}
|
|
217
|
+
/** SPEC-063 — Job Scheduler */
|
|
218
|
+
export interface IJobSchedulerPort {
|
|
219
|
+
register(name: string, schedule: string, handler: (app: MantaApp) => Promise<JobResult>, options?: {
|
|
220
|
+
concurrency?: 'allow' | 'forbid';
|
|
221
|
+
numberOfExecutions?: number;
|
|
222
|
+
retry?: {
|
|
223
|
+
maxRetries: number;
|
|
224
|
+
backoff?: 'fixed' | 'exponential';
|
|
225
|
+
delay?: number;
|
|
226
|
+
};
|
|
227
|
+
}): void;
|
|
228
|
+
runJob(name: string): Promise<JobResult>;
|
|
229
|
+
getJobHistory(jobName: string, limit?: number): Promise<JobExecution[]>;
|
|
230
|
+
}
|
|
231
|
+
/** SPEC-065/080/081 — File */
|
|
232
|
+
export interface IFilePort {
|
|
233
|
+
upload(key: string, data: Buffer | ReadableStream, contentType?: string): Promise<{
|
|
234
|
+
key: string;
|
|
235
|
+
url: string;
|
|
236
|
+
}>;
|
|
237
|
+
delete(key: string | string[]): Promise<void>;
|
|
238
|
+
getPresignedDownloadUrl(key: string): Promise<string>;
|
|
239
|
+
getPresignedUploadUrl?(key: string): Promise<string>;
|
|
240
|
+
getDownloadStream(key: string): Promise<ReadableStream>;
|
|
241
|
+
getAsBuffer(key: string): Promise<Buffer>;
|
|
242
|
+
list(prefix?: string): Promise<string[]>;
|
|
243
|
+
getUploadStream?(key: string): Promise<{
|
|
244
|
+
stream: WritableStream;
|
|
245
|
+
done: Promise<void>;
|
|
246
|
+
}>;
|
|
247
|
+
}
|
|
248
|
+
/** SPEC-067/082 — Logger */
|
|
249
|
+
export interface ILoggerPort {
|
|
250
|
+
error(msg: string, ...args: unknown[]): void;
|
|
251
|
+
warn(msg: string, ...args: unknown[]): void;
|
|
252
|
+
info(msg: string, ...args: unknown[]): void;
|
|
253
|
+
http(msg: string, ...args: unknown[]): void;
|
|
254
|
+
verbose(msg: string, ...args: unknown[]): void;
|
|
255
|
+
debug(msg: string, ...args: unknown[]): void;
|
|
256
|
+
silly(msg: string, ...args: unknown[]): void;
|
|
257
|
+
panic(data: unknown): void;
|
|
258
|
+
activity(msg: string): string;
|
|
259
|
+
progress(id: string, msg: string): void;
|
|
260
|
+
success(id: string, msg: string): void;
|
|
261
|
+
failure(id: string, msg: string): void;
|
|
262
|
+
shouldLog(level: string): boolean;
|
|
263
|
+
setLogLevel(level: string): void;
|
|
264
|
+
unsetLogLevel(): void;
|
|
265
|
+
}
|
|
266
|
+
/** SPEC-049 — Auth (crypto pure) */
|
|
267
|
+
export interface IAuthPort {
|
|
268
|
+
verifyJwt(token: string): AuthContext | null;
|
|
269
|
+
verifyApiKey(key: string): AuthContext | null;
|
|
270
|
+
createJwt(payload: AuthContext, options?: {
|
|
271
|
+
expiresIn?: string | number;
|
|
272
|
+
}): string;
|
|
273
|
+
}
|
|
274
|
+
/** SPEC-050 — Auth Module Service (business logic + sessions) */
|
|
275
|
+
export interface IAuthModuleService {
|
|
276
|
+
authenticate(data: Record<string, unknown>): Promise<AuthContext | null>;
|
|
277
|
+
register(data: Record<string, unknown>): Promise<{
|
|
278
|
+
authIdentity: unknown;
|
|
279
|
+
}>;
|
|
280
|
+
validateCallback(data: Record<string, unknown>): Promise<AuthContext | null>;
|
|
281
|
+
createSession(authContext: AuthContext, options?: SessionOptions): Promise<{
|
|
282
|
+
sessionId: string;
|
|
283
|
+
expiresAt: Date;
|
|
284
|
+
}>;
|
|
285
|
+
destroySession(sessionId: string): Promise<void>;
|
|
286
|
+
verifySession(sessionId: string): Promise<AuthContext | null>;
|
|
287
|
+
}
|
|
288
|
+
/** SPEC-049b — Auth Gateway */
|
|
289
|
+
export interface IAuthGateway {
|
|
290
|
+
authenticate(credentials: AuthCredentials): Promise<AuthContext | null>;
|
|
291
|
+
}
|
|
292
|
+
/** SPEC-018 — Message Aggregator */
|
|
293
|
+
export interface IMessageAggregator {
|
|
294
|
+
save(messages: Message[]): void;
|
|
295
|
+
getMessages(options?: {
|
|
296
|
+
groupBy?: string;
|
|
297
|
+
sortBy?: string;
|
|
298
|
+
}): Message[];
|
|
299
|
+
clearMessages(): void;
|
|
300
|
+
}
|
|
301
|
+
/** SPEC-097 — Notification */
|
|
302
|
+
export interface INotificationPort {
|
|
303
|
+
send(notification: {
|
|
304
|
+
to: string;
|
|
305
|
+
channel: string;
|
|
306
|
+
from?: string;
|
|
307
|
+
replyTo?: string | string[];
|
|
308
|
+
subject?: string;
|
|
309
|
+
html?: string;
|
|
310
|
+
text?: string;
|
|
311
|
+
headers?: Record<string, string>;
|
|
312
|
+
tags?: Array<{
|
|
313
|
+
name: string;
|
|
314
|
+
value: string;
|
|
315
|
+
}>;
|
|
316
|
+
idempotency_key?: string;
|
|
317
|
+
}): Promise<{
|
|
318
|
+
status: 'SUCCESS' | 'FAILURE' | 'PENDING';
|
|
319
|
+
id?: string;
|
|
320
|
+
error?: Error;
|
|
321
|
+
}>;
|
|
322
|
+
sendBatch?(notifications: Array<Parameters<INotificationPort['send']>[0]>): Promise<Array<Awaited<ReturnType<INotificationPort['send']>>>>;
|
|
323
|
+
list?(): Promise<unknown[]>;
|
|
324
|
+
retrieve?(id: string): Promise<unknown | null>;
|
|
325
|
+
}
|
|
326
|
+
/** SPEC-039 — HTTP Port (simplified for testing) */
|
|
327
|
+
export interface IHttpPort {
|
|
328
|
+
registerRoute(method: string, path: string, handler: (req: Request) => Promise<Response> | Response): void;
|
|
329
|
+
handleRequest(req: Request): Promise<Response>;
|
|
330
|
+
}
|
|
331
|
+
export interface DmlProperty {
|
|
332
|
+
type: string;
|
|
333
|
+
nullable?: boolean;
|
|
334
|
+
default?: unknown;
|
|
335
|
+
index?: boolean | string;
|
|
336
|
+
unique?: boolean | string;
|
|
337
|
+
primaryKey?: boolean;
|
|
338
|
+
computed?: boolean;
|
|
339
|
+
searchable?: boolean;
|
|
340
|
+
translatable?: boolean;
|
|
341
|
+
}
|
|
342
|
+
export interface DmlRelation {
|
|
343
|
+
type: 'hasOne' | 'hasOneWithFK' | 'belongsTo' | 'hasMany' | 'manyToMany';
|
|
344
|
+
target: () => unknown;
|
|
345
|
+
options?: Record<string, unknown>;
|
|
346
|
+
}
|
|
347
|
+
export interface DmlEntity {
|
|
348
|
+
name: string;
|
|
349
|
+
tableName?: string;
|
|
350
|
+
schema: Record<string, DmlProperty | DmlRelation>;
|
|
351
|
+
cascades?: {
|
|
352
|
+
delete?: string[];
|
|
353
|
+
detach?: string[];
|
|
354
|
+
};
|
|
355
|
+
indexes?: Array<{
|
|
356
|
+
on: string[];
|
|
357
|
+
unique?: boolean;
|
|
358
|
+
where?: string | Record<string, unknown>;
|
|
359
|
+
name?: string;
|
|
360
|
+
type?: string;
|
|
361
|
+
}>;
|
|
362
|
+
checks?: Array<{
|
|
363
|
+
name?: string;
|
|
364
|
+
expression: string | ((columns: Record<string, string>) => string);
|
|
365
|
+
}>;
|
|
366
|
+
}
|
|
367
|
+
export declare function deriveWorkflowTransactionId(workflowId: string, event: Message): string;
|
|
368
|
+
export declare function mapExternalError(error: Error, context?: string): MantaError;
|
|
369
|
+
//# sourceMappingURL=core-types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"core-types.d.ts","sourceRoot":"","sources":["../src/core-types.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
// @mantajs/core — Port interfaces and framework types
|
|
2
|
+
// This file defines the contracts. Adapters implement them. Tests assert against them.
|
|
3
|
+
export class MantaError extends Error {
|
|
4
|
+
type;
|
|
5
|
+
code;
|
|
6
|
+
date;
|
|
7
|
+
__isMantaError = true;
|
|
8
|
+
constructor(type, message, options) {
|
|
9
|
+
super(message);
|
|
10
|
+
this.type = type;
|
|
11
|
+
this.code = options?.code;
|
|
12
|
+
this.date = new Date();
|
|
13
|
+
this.name = 'MantaError';
|
|
14
|
+
}
|
|
15
|
+
static is(err) {
|
|
16
|
+
return (typeof err === 'object' && err !== null && '__isMantaError' in err && err.__isMantaError === true);
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
export class PermanentSubscriberError extends Error {
|
|
20
|
+
cause;
|
|
21
|
+
__isPermanentSubscriber = true;
|
|
22
|
+
constructor(cause) {
|
|
23
|
+
super(cause.message);
|
|
24
|
+
this.cause = cause;
|
|
25
|
+
this.name = 'PermanentSubscriberError';
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
export function permanentSubscriberFailure(error) {
|
|
29
|
+
return new PermanentSubscriberError(error);
|
|
30
|
+
}
|
|
31
|
+
// =============================================================================
|
|
32
|
+
// Utility exports
|
|
33
|
+
// =============================================================================
|
|
34
|
+
export function deriveWorkflowTransactionId(workflowId, event) {
|
|
35
|
+
if (event.metadata.idempotencyKey) {
|
|
36
|
+
return `${workflowId}:${event.metadata.idempotencyKey}`;
|
|
37
|
+
}
|
|
38
|
+
return `${workflowId}:${crypto.randomUUID()}`;
|
|
39
|
+
}
|
|
40
|
+
export function mapExternalError(error, context) {
|
|
41
|
+
const message = context ? `${context}: ${error.message}` : error.message;
|
|
42
|
+
return new MantaError('UNEXPECTED_STATE', message);
|
|
43
|
+
}
|
|
44
|
+
//# sourceMappingURL=core-types.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"core-types.js","sourceRoot":"","sources":["../src/core-types.ts"],"names":[],"mappings":"AAAA,sDAAsD;AACtD,uFAAuF;AAqBvF,MAAM,OAAO,UAAW,SAAQ,KAAK;IAC1B,IAAI,CAAgB;IACpB,IAAI,CAAS;IACb,IAAI,CAAM;IACV,cAAc,GAAG,IAAa,CAAA;IAEvC,YAAY,IAAoB,EAAE,OAAe,EAAE,OAA2B;QAC5E,KAAK,CAAC,OAAO,CAAC,CAAA;QACd,IAAI,CAAC,IAAI,GAAG,IAAI,CAAA;QAChB,IAAI,CAAC,IAAI,GAAG,OAAO,EAAE,IAAI,CAAA;QACzB,IAAI,CAAC,IAAI,GAAG,IAAI,IAAI,EAAE,CAAA;QACtB,IAAI,CAAC,IAAI,GAAG,YAAY,CAAA;IAC1B,CAAC;IAED,MAAM,CAAC,EAAE,CAAC,GAAY;QACpB,OAAO,CACL,OAAO,GAAG,KAAK,QAAQ,IAAI,GAAG,KAAK,IAAI,IAAI,gBAAgB,IAAI,GAAG,IAAK,GAAkB,CAAC,cAAc,KAAK,IAAI,CAClH,CAAA;IACH,CAAC;CACF;AAED,MAAM,OAAO,wBAAyB,SAAQ,KAAK;IAErB;IADnB,uBAAuB,GAAG,IAAa,CAAA;IAChD,YAA4B,KAAY;QACtC,KAAK,CAAC,KAAK,CAAC,OAAO,CAAC,CAAA;QADM,UAAK,GAAL,KAAK,CAAO;QAEtC,IAAI,CAAC,IAAI,GAAG,0BAA0B,CAAA;IACxC,CAAC;CACF;AAED,MAAM,UAAU,0BAA0B,CAAC,KAAY;IACrD,OAAO,IAAI,wBAAwB,CAAC,KAAK,CAAC,CAAA;AAC5C,CAAC;AAyWD,gFAAgF;AAChF,kBAAkB;AAClB,gFAAgF;AAEhF,MAAM,UAAU,2BAA2B,CAAC,UAAkB,EAAE,KAAc;IAC5E,IAAI,KAAK,CAAC,QAAQ,CAAC,cAAc,EAAE,CAAC;QAClC,OAAO,GAAG,UAAU,IAAI,KAAK,CAAC,QAAQ,CAAC,cAAc,EAAE,CAAA;IACzD,CAAC;IACD,OAAO,GAAG,UAAU,IAAI,MAAM,CAAC,UAAU,EAAE,EAAE,CAAA;AAC/C,CAAC;AAED,MAAM,UAAU,gBAAgB,CAAC,KAAY,EAAE,OAAgB;IAC7D,MAAM,OAAO,GAAG,OAAO,CAAC,CAAC,CAAC,GAAG,OAAO,KAAK,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAA;IACxE,OAAO,IAAI,UAAU,CAAC,kBAAkB,EAAE,OAAO,CAAC,CAAA;AACpD,CAAC"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,127 @@
|
|
|
1
|
+
export type { AuthContext, AuthCredentials, Context, CursorPagination, DatabaseConfig, EnvProfile, GeneratedSchema, GroupStatus, IAnalyticsProvider, IAuthGateway, IAuthModuleService, IAuthPort, ICachePort, IDatabasePort, IEventBusPort, IFilePort, IHttpPort, IJobSchedulerPort, ILockingPort, ILoggerPort, IMessageAggregator, INotificationPort, IRepository, IRepositoryFactory, ISchemaGenerator, ISearchProvider, JobExecution, JobResult, LogEntry, MantaApp, MantaConfig, MantaErrorResponse, MantaErrorType, Message, ParsedDmlEntity, ParsedDmlIndex, ParsedDmlProperty, ParsedDmlRelation, PresetAdapterEntry, PresetDefinition, ProjectConfig, RequestContext, SessionOptions, TestAuthConfig, TransactionOptions, WorkflowLifecycleEvent, } from '@mantajs/core';
|
|
2
|
+
export { ConfigManager, ContainerRegistrationKeys, createApp, defineConfig, FlagRouter, generateDrizzleSchema, InMemoryCacheAdapter, InMemoryDatabaseAdapter, InMemoryEventBusAdapter, InMemoryFileAdapter, InMemoryHttpAdapter, InMemoryJobScheduler, InMemoryLockingAdapter, InMemoryNotificationAdapter, InMemoryRepository, InMemoryRepositoryFactory, InMemoryTransaction, MantaError, MessageAggregator, MockAuthGateway, MockAuthModuleService, MockAuthPort, makeIdempotent, PermanentSubscriberError, parseDmlEntity, permanentSubscriberFailure, runInRequestContext, TestLogger, } from '@mantajs/core';
|
|
3
|
+
import type { Context, MantaApp, Message, RequestContext, TestAuthConfig } from '@mantajs/core';
|
|
4
|
+
import { MockAuthGateway, MockAuthModuleService, MockAuthPort, TestLogger } from '@mantajs/core';
|
|
5
|
+
interface TestAppOptions {
|
|
6
|
+
overrides?: Partial<Record<string, unknown>>;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Creates a MantaApp with all in-memory adapters for testing.
|
|
10
|
+
*/
|
|
11
|
+
export declare function createTestApp(options?: TestAppOptions): MantaApp<Record<string, unknown>>;
|
|
12
|
+
/**
|
|
13
|
+
* Silent logger that captures all output for assertions.
|
|
14
|
+
*/
|
|
15
|
+
export declare function createTestLogger(): TestLogger;
|
|
16
|
+
interface TestAuthResult {
|
|
17
|
+
authPort: MockAuthPort;
|
|
18
|
+
authModuleService: MockAuthModuleService;
|
|
19
|
+
authGateway: MockAuthGateway;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Mock IAuthPort + IAuthModuleService with configurable responses.
|
|
23
|
+
*/
|
|
24
|
+
export declare function createTestAuth(config?: TestAuthConfig): TestAuthResult;
|
|
25
|
+
/**
|
|
26
|
+
* Resets all in-memory adapters in the app.
|
|
27
|
+
* Call in `afterEach` for isolation between tests.
|
|
28
|
+
*/
|
|
29
|
+
export declare function resetAll(app: MantaApp): Promise<void>;
|
|
30
|
+
export interface TestDb {
|
|
31
|
+
withRollback<T>(fn: (tx: unknown) => Promise<T>): Promise<T>;
|
|
32
|
+
cleanup(): Promise<void>;
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* Creates an in-memory test database with rollback-per-test isolation.
|
|
36
|
+
*/
|
|
37
|
+
export declare function createTestDb(_options?: {
|
|
38
|
+
schema?: unknown[];
|
|
39
|
+
}): Promise<TestDb>;
|
|
40
|
+
export interface EventSpy {
|
|
41
|
+
received(eventName: string): boolean;
|
|
42
|
+
payloads(eventName: string): Message[];
|
|
43
|
+
count(eventName: string): number;
|
|
44
|
+
all(): Array<{
|
|
45
|
+
name: string;
|
|
46
|
+
payload: Message;
|
|
47
|
+
timestamp: number;
|
|
48
|
+
}>;
|
|
49
|
+
reset(): void;
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Intercepts all events emitted via IEventBusPort for assertion.
|
|
53
|
+
* Non-intrusive — real subscribers still receive events.
|
|
54
|
+
*/
|
|
55
|
+
export declare function spyOnEvents(app: MantaApp): EventSpy;
|
|
56
|
+
/**
|
|
57
|
+
* Creates a minimal valid Context (SPEC-060) for testing.
|
|
58
|
+
*/
|
|
59
|
+
export declare function createTestContext(overrides?: Partial<Context>): Context;
|
|
60
|
+
export interface MigrationTestContext {
|
|
61
|
+
defineDml(entities: unknown[]): void;
|
|
62
|
+
generate(): Promise<{
|
|
63
|
+
sql: string;
|
|
64
|
+
}>;
|
|
65
|
+
migrate(): Promise<void>;
|
|
66
|
+
diff(): Promise<{
|
|
67
|
+
differences: Array<{
|
|
68
|
+
table: string;
|
|
69
|
+
column?: string;
|
|
70
|
+
action: string;
|
|
71
|
+
warning?: string;
|
|
72
|
+
}>;
|
|
73
|
+
}>;
|
|
74
|
+
rollback(): Promise<void>;
|
|
75
|
+
cleanup(): Promise<void>;
|
|
76
|
+
}
|
|
77
|
+
/**
|
|
78
|
+
* Stub for migration testing context. Requires PG local.
|
|
79
|
+
*/
|
|
80
|
+
export declare function createMigrationTestContext(_options?: Record<string, unknown>): Promise<MigrationTestContext>;
|
|
81
|
+
export interface ScopeLeakChecker {
|
|
82
|
+
/** Track an object (scope, context) that should be GC'd after the test */
|
|
83
|
+
track(scope: object): void;
|
|
84
|
+
/** Verify all tracked objects were garbage collected */
|
|
85
|
+
verify(): Promise<void>;
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Asserts that no scope references are leaked after a test.
|
|
89
|
+
* Tracks WeakRef to scope/context objects and verifies they are GC'd.
|
|
90
|
+
*
|
|
91
|
+
* Requires Node with --expose-gc flag for reliable results.
|
|
92
|
+
* Without GC access, verify() is a no-op (no false positives).
|
|
93
|
+
*
|
|
94
|
+
* @example
|
|
95
|
+
* const leak = assertNoScopeLeak(app)
|
|
96
|
+
* const ctx = createTestContext()
|
|
97
|
+
* leak.track(ctx)
|
|
98
|
+
* // ... test code that should release ctx ...
|
|
99
|
+
* await leak.verify()
|
|
100
|
+
*/
|
|
101
|
+
export declare function assertNoScopeLeak(_app: MantaApp): ScopeLeakChecker;
|
|
102
|
+
/**
|
|
103
|
+
* Creates a scoped execution context using AsyncLocalStorage.
|
|
104
|
+
* Useful for testing SCOPED services that require an active request context.
|
|
105
|
+
*
|
|
106
|
+
* Wraps the callback in runInRequestContext from @mantajs/core so that
|
|
107
|
+
* getRequestContext() returns a valid RequestContext inside the callback.
|
|
108
|
+
*
|
|
109
|
+
* @example
|
|
110
|
+
* await withScope(app, async (scope) => {
|
|
111
|
+
* // getRequestContext() returns { requestId: scope.requestId }
|
|
112
|
+
* const svc = app.modules.stats
|
|
113
|
+
* await svc.increment('counter')
|
|
114
|
+
* })
|
|
115
|
+
*/
|
|
116
|
+
export declare function withScope<T>(_app: MantaApp, fn: (scope: RequestContext) => Promise<T>): Promise<T>;
|
|
117
|
+
/**
|
|
118
|
+
* Validates that a value can be safely serialized for workflow checkpoints.
|
|
119
|
+
* Throws MantaError if the value contains BigInt, Map, Set, Buffer, or Function.
|
|
120
|
+
*
|
|
121
|
+
* @example
|
|
122
|
+
* validateSerializability({ count: 42, name: 'ok' }) // passes
|
|
123
|
+
* validateSerializability({ m: new Map() }) // throws
|
|
124
|
+
*/
|
|
125
|
+
export declare function validateSerializability(value: unknown, path?: string): void;
|
|
126
|
+
export { deriveWorkflowTransactionId, mapExternalError } from './core-types';
|
|
127
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,378 @@
|
|
|
1
|
+
// =============================================================================
|
|
2
|
+
// @mantajs/test-utils — Test helpers ONLY
|
|
3
|
+
// =============================================================================
|
|
4
|
+
//
|
|
5
|
+
// All adapter implementations live in @mantajs/core/adapters.
|
|
6
|
+
// This package re-exports them for backward compatibility and provides
|
|
7
|
+
// test-only helpers (createTestApp, spyOnEvents, resetAll, etc.).
|
|
8
|
+
//
|
|
9
|
+
// References: TEST_STRATEGY.md Section 4 (§4.1 → §4.12)
|
|
10
|
+
// =============================================================================
|
|
11
|
+
// Re-export everything from @mantajs/core so tests can import from @mantajs/test-utils
|
|
12
|
+
export { ConfigManager, ContainerRegistrationKeys,
|
|
13
|
+
// App
|
|
14
|
+
createApp,
|
|
15
|
+
// Config
|
|
16
|
+
defineConfig, FlagRouter, generateDrizzleSchema,
|
|
17
|
+
// Adapters (re-exported from @mantajs/core)
|
|
18
|
+
InMemoryCacheAdapter, InMemoryDatabaseAdapter, InMemoryEventBusAdapter, InMemoryFileAdapter, InMemoryHttpAdapter, InMemoryJobScheduler, InMemoryLockingAdapter, InMemoryNotificationAdapter, InMemoryRepository, InMemoryRepositoryFactory, InMemoryTransaction,
|
|
19
|
+
// Types & errors
|
|
20
|
+
MantaError,
|
|
21
|
+
// Events
|
|
22
|
+
MessageAggregator, MockAuthGateway, MockAuthModuleService, MockAuthPort,
|
|
23
|
+
// Subscriber utilities
|
|
24
|
+
makeIdempotent, PermanentSubscriberError,
|
|
25
|
+
// DML Generator
|
|
26
|
+
parseDmlEntity, permanentSubscriberFailure,
|
|
27
|
+
// Request context
|
|
28
|
+
runInRequestContext, TestLogger, } from '@mantajs/core';
|
|
29
|
+
import { createApp, InMemoryCacheAdapter, InMemoryEventBusAdapter, InMemoryFileAdapter, InMemoryLockingAdapter, MantaError, MessageAggregator, MockAuthGateway, MockAuthModuleService, MockAuthPort, runInRequestContext, TestLogger, } from '@mantajs/core';
|
|
30
|
+
/**
|
|
31
|
+
* Creates a MantaApp with all in-memory adapters for testing.
|
|
32
|
+
*/
|
|
33
|
+
export function createTestApp(options) {
|
|
34
|
+
const eventBus = new InMemoryEventBusAdapter();
|
|
35
|
+
const logger = new TestLogger();
|
|
36
|
+
const cache = new InMemoryCacheAdapter();
|
|
37
|
+
const locking = new InMemoryLockingAdapter();
|
|
38
|
+
const file = new InMemoryFileAdapter();
|
|
39
|
+
const builder = createApp({
|
|
40
|
+
infra: { eventBus, logger, cache, locking, file, db: {} },
|
|
41
|
+
});
|
|
42
|
+
// Register overrides as modules if provided
|
|
43
|
+
if (options?.overrides) {
|
|
44
|
+
for (const [key, value] of Object.entries(options.overrides)) {
|
|
45
|
+
if (value !== undefined)
|
|
46
|
+
builder.registerModule(key, value);
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
return builder.build();
|
|
50
|
+
}
|
|
51
|
+
// =============================================================================
|
|
52
|
+
// §4.3 — createTestLogger
|
|
53
|
+
// =============================================================================
|
|
54
|
+
/**
|
|
55
|
+
* Silent logger that captures all output for assertions.
|
|
56
|
+
*/
|
|
57
|
+
export function createTestLogger() {
|
|
58
|
+
return new TestLogger();
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* Mock IAuthPort + IAuthModuleService with configurable responses.
|
|
62
|
+
*/
|
|
63
|
+
export function createTestAuth(config) {
|
|
64
|
+
const authPort = new MockAuthPort(config);
|
|
65
|
+
const authModuleService = new MockAuthModuleService(config);
|
|
66
|
+
const authGateway = new MockAuthGateway(authPort, authModuleService);
|
|
67
|
+
return { authPort, authModuleService, authGateway };
|
|
68
|
+
}
|
|
69
|
+
// =============================================================================
|
|
70
|
+
// §4.5 — resetAll (accepts MantaApp)
|
|
71
|
+
// =============================================================================
|
|
72
|
+
/**
|
|
73
|
+
* Resets all in-memory adapters in the app.
|
|
74
|
+
* Call in `afterEach` for isolation between tests.
|
|
75
|
+
*/
|
|
76
|
+
export async function resetAll(app) {
|
|
77
|
+
const resettables = [
|
|
78
|
+
'ICachePort',
|
|
79
|
+
'IEventBusPort',
|
|
80
|
+
'ILoggerPort',
|
|
81
|
+
'IFilePort',
|
|
82
|
+
'INotificationPort',
|
|
83
|
+
'IJobSchedulerPort',
|
|
84
|
+
'IAuthModuleService',
|
|
85
|
+
'IHttpPort',
|
|
86
|
+
'IRepository',
|
|
87
|
+
];
|
|
88
|
+
for (const key of resettables) {
|
|
89
|
+
try {
|
|
90
|
+
const svc = app.resolve(key);
|
|
91
|
+
if (svc && typeof svc._reset === 'function') {
|
|
92
|
+
;
|
|
93
|
+
svc._reset();
|
|
94
|
+
}
|
|
95
|
+
else if (svc && typeof svc.clear === 'function') {
|
|
96
|
+
await svc.clear();
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
catch {
|
|
100
|
+
// Service not registered — skip
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
import { generateDrizzleSchema, InMemoryTransaction, parseDmlEntity } from '@mantajs/core';
|
|
105
|
+
/**
|
|
106
|
+
* Creates an in-memory test database with rollback-per-test isolation.
|
|
107
|
+
*/
|
|
108
|
+
export async function createTestDb(_options) {
|
|
109
|
+
const tables = new Map();
|
|
110
|
+
const schema = new Map();
|
|
111
|
+
let disposed = false;
|
|
112
|
+
return {
|
|
113
|
+
async withRollback(fn) {
|
|
114
|
+
if (disposed) {
|
|
115
|
+
throw new MantaError('INVALID_STATE', 'Database has been disposed');
|
|
116
|
+
}
|
|
117
|
+
const snapshot = new Map();
|
|
118
|
+
for (const [name, rows] of tables) {
|
|
119
|
+
const rowsCopy = new Map();
|
|
120
|
+
for (const [id, row] of rows) {
|
|
121
|
+
rowsCopy.set(id, { ...row });
|
|
122
|
+
}
|
|
123
|
+
snapshot.set(name, rowsCopy);
|
|
124
|
+
}
|
|
125
|
+
const schemaCopy = new Map(schema);
|
|
126
|
+
const tx = new InMemoryTransaction(snapshot, schemaCopy);
|
|
127
|
+
return fn(tx);
|
|
128
|
+
},
|
|
129
|
+
async cleanup() {
|
|
130
|
+
disposed = true;
|
|
131
|
+
tables.clear();
|
|
132
|
+
schema.clear();
|
|
133
|
+
},
|
|
134
|
+
};
|
|
135
|
+
}
|
|
136
|
+
/**
|
|
137
|
+
* Intercepts all events emitted via IEventBusPort for assertion.
|
|
138
|
+
* Non-intrusive — real subscribers still receive events.
|
|
139
|
+
*/
|
|
140
|
+
export function spyOnEvents(app) {
|
|
141
|
+
const captured = [];
|
|
142
|
+
const bus = app.resolve('IEventBusPort');
|
|
143
|
+
const interceptor = (message) => {
|
|
144
|
+
captured.push({ name: message.eventName, payload: message, timestamp: Date.now() });
|
|
145
|
+
};
|
|
146
|
+
bus.addInterceptor(interceptor);
|
|
147
|
+
return {
|
|
148
|
+
received(eventName) {
|
|
149
|
+
return captured.some((e) => e.name === eventName);
|
|
150
|
+
},
|
|
151
|
+
payloads(eventName) {
|
|
152
|
+
return captured.filter((e) => e.name === eventName).map((e) => e.payload);
|
|
153
|
+
},
|
|
154
|
+
count(eventName) {
|
|
155
|
+
return captured.filter((e) => e.name === eventName).length;
|
|
156
|
+
},
|
|
157
|
+
all() {
|
|
158
|
+
return [...captured];
|
|
159
|
+
},
|
|
160
|
+
reset() {
|
|
161
|
+
captured.length = 0;
|
|
162
|
+
},
|
|
163
|
+
};
|
|
164
|
+
}
|
|
165
|
+
// =============================================================================
|
|
166
|
+
// §4.8 — createTestContext
|
|
167
|
+
// =============================================================================
|
|
168
|
+
/**
|
|
169
|
+
* Creates a minimal valid Context (SPEC-060) for testing.
|
|
170
|
+
*/
|
|
171
|
+
export function createTestContext(overrides) {
|
|
172
|
+
return {
|
|
173
|
+
transactionManager: undefined,
|
|
174
|
+
manager: undefined,
|
|
175
|
+
isolationLevel: 'READ COMMITTED',
|
|
176
|
+
enableNestedTransactions: false,
|
|
177
|
+
eventGroupId: undefined,
|
|
178
|
+
transactionId: undefined,
|
|
179
|
+
requestId: crypto.randomUUID(),
|
|
180
|
+
messageAggregator: new MessageAggregator(),
|
|
181
|
+
idempotencyKey: crypto.randomUUID(),
|
|
182
|
+
isCancelling: false,
|
|
183
|
+
auth_context: undefined,
|
|
184
|
+
...overrides,
|
|
185
|
+
};
|
|
186
|
+
}
|
|
187
|
+
/**
|
|
188
|
+
* Stub for migration testing context. Requires PG local.
|
|
189
|
+
*/
|
|
190
|
+
export async function createMigrationTestContext(_options) {
|
|
191
|
+
let entities = [];
|
|
192
|
+
let generatedSchemas = [];
|
|
193
|
+
let migratedSchemas = [];
|
|
194
|
+
let generatedSql = '';
|
|
195
|
+
return {
|
|
196
|
+
defineDml(dmlEntities) {
|
|
197
|
+
entities = dmlEntities;
|
|
198
|
+
generatedSchemas = entities.map((e) => generateDrizzleSchema(parseDmlEntity(e)));
|
|
199
|
+
},
|
|
200
|
+
async generate() {
|
|
201
|
+
const sqlParts = [];
|
|
202
|
+
for (let i = 0; i < entities.length; i++) {
|
|
203
|
+
const entity = entities[i];
|
|
204
|
+
const schema = generatedSchemas[i];
|
|
205
|
+
const tableName = `${entity.name.toLowerCase()}s`;
|
|
206
|
+
const cols = Object.entries(schema.columns)
|
|
207
|
+
.map(([name, col]) => ` "${name}" ${col.type}${col.notNull ? ' NOT NULL' : ''}`)
|
|
208
|
+
.join(',\n');
|
|
209
|
+
sqlParts.push(`CREATE TABLE IF NOT EXISTS "${tableName}" (\n${cols}\n);`);
|
|
210
|
+
for (const idx of schema.indexes) {
|
|
211
|
+
const using = idx.using ? ` USING ${idx.using}` : '';
|
|
212
|
+
const where = idx.where ? ` WHERE ${idx.where}` : '';
|
|
213
|
+
sqlParts.push(`CREATE INDEX "${idx.name}" ON "${tableName}"${using} (${idx.columns.map((c) => `"${c}"`).join(', ')})${where};`);
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
generatedSql = sqlParts.join('\n\n');
|
|
217
|
+
return { sql: generatedSql };
|
|
218
|
+
},
|
|
219
|
+
async migrate() {
|
|
220
|
+
migratedSchemas = generatedSchemas.map((s) => ({
|
|
221
|
+
columns: { ...s.columns },
|
|
222
|
+
relations: { ...s.relations },
|
|
223
|
+
indexes: [...s.indexes],
|
|
224
|
+
checks: [...s.checks],
|
|
225
|
+
}));
|
|
226
|
+
},
|
|
227
|
+
async diff() {
|
|
228
|
+
const differences = [];
|
|
229
|
+
for (let i = 0; i < entities.length; i++) {
|
|
230
|
+
const entity = entities[i];
|
|
231
|
+
const tableName = `${entity.name.toLowerCase()}s`;
|
|
232
|
+
const expected = generatedSchemas[i];
|
|
233
|
+
if (i >= migratedSchemas.length) {
|
|
234
|
+
for (const colName of Object.keys(expected.columns)) {
|
|
235
|
+
differences.push({ table: tableName, column: colName, action: 'CREATE' });
|
|
236
|
+
}
|
|
237
|
+
continue;
|
|
238
|
+
}
|
|
239
|
+
const migrated = migratedSchemas[i];
|
|
240
|
+
for (const [colName, colDef] of Object.entries(expected.columns)) {
|
|
241
|
+
if (!migrated.columns[colName]) {
|
|
242
|
+
differences.push({ table: tableName, column: colName, action: 'CREATE' });
|
|
243
|
+
}
|
|
244
|
+
else if (migrated.columns[colName].type !== colDef.type) {
|
|
245
|
+
differences.push({
|
|
246
|
+
table: tableName,
|
|
247
|
+
column: colName,
|
|
248
|
+
action: 'ALTER',
|
|
249
|
+
warning: `unsafe type change from ${migrated.columns[colName].type} to ${colDef.type}`,
|
|
250
|
+
});
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
}
|
|
254
|
+
return { differences };
|
|
255
|
+
},
|
|
256
|
+
async rollback() {
|
|
257
|
+
if (migratedSchemas.length === 0 && generatedSql === '') {
|
|
258
|
+
throw new MantaError('NOT_FOUND', 'No rollback file found');
|
|
259
|
+
}
|
|
260
|
+
migratedSchemas = [];
|
|
261
|
+
},
|
|
262
|
+
async cleanup() {
|
|
263
|
+
entities = [];
|
|
264
|
+
generatedSchemas = [];
|
|
265
|
+
migratedSchemas = [];
|
|
266
|
+
generatedSql = '';
|
|
267
|
+
},
|
|
268
|
+
};
|
|
269
|
+
}
|
|
270
|
+
/**
|
|
271
|
+
* Asserts that no scope references are leaked after a test.
|
|
272
|
+
* Tracks WeakRef to scope/context objects and verifies they are GC'd.
|
|
273
|
+
*
|
|
274
|
+
* Requires Node with --expose-gc flag for reliable results.
|
|
275
|
+
* Without GC access, verify() is a no-op (no false positives).
|
|
276
|
+
*
|
|
277
|
+
* @example
|
|
278
|
+
* const leak = assertNoScopeLeak(app)
|
|
279
|
+
* const ctx = createTestContext()
|
|
280
|
+
* leak.track(ctx)
|
|
281
|
+
* // ... test code that should release ctx ...
|
|
282
|
+
* await leak.verify()
|
|
283
|
+
*/
|
|
284
|
+
export function assertNoScopeLeak(_app) {
|
|
285
|
+
const scopeRefs = [];
|
|
286
|
+
return {
|
|
287
|
+
track(scope) {
|
|
288
|
+
scopeRefs.push(new WeakRef(scope));
|
|
289
|
+
},
|
|
290
|
+
async verify() {
|
|
291
|
+
// Without --expose-gc, we cannot force GC — skip to avoid false positives
|
|
292
|
+
if (!globalThis.gc)
|
|
293
|
+
return;
|
|
294
|
+
globalThis.gc();
|
|
295
|
+
// Give GC a tick to finalize
|
|
296
|
+
await new Promise((r) => setTimeout(r, 50));
|
|
297
|
+
globalThis.gc();
|
|
298
|
+
const leaked = scopeRefs.filter((ref) => ref.deref() !== undefined);
|
|
299
|
+
if (leaked.length > 0) {
|
|
300
|
+
throw new MantaError('INVALID_STATE', `Scope leak detected: ${leaked.length} scope(s) not garbage collected`);
|
|
301
|
+
}
|
|
302
|
+
},
|
|
303
|
+
};
|
|
304
|
+
}
|
|
305
|
+
// =============================================================================
|
|
306
|
+
// §4.10 — withScope
|
|
307
|
+
// =============================================================================
|
|
308
|
+
/**
|
|
309
|
+
* Creates a scoped execution context using AsyncLocalStorage.
|
|
310
|
+
* Useful for testing SCOPED services that require an active request context.
|
|
311
|
+
*
|
|
312
|
+
* Wraps the callback in runInRequestContext from @mantajs/core so that
|
|
313
|
+
* getRequestContext() returns a valid RequestContext inside the callback.
|
|
314
|
+
*
|
|
315
|
+
* @example
|
|
316
|
+
* await withScope(app, async (scope) => {
|
|
317
|
+
* // getRequestContext() returns { requestId: scope.requestId }
|
|
318
|
+
* const svc = app.modules.stats
|
|
319
|
+
* await svc.increment('counter')
|
|
320
|
+
* })
|
|
321
|
+
*/
|
|
322
|
+
export async function withScope(_app, fn) {
|
|
323
|
+
const ctx = {
|
|
324
|
+
requestId: crypto.randomUUID(),
|
|
325
|
+
};
|
|
326
|
+
return runInRequestContext(ctx, () => fn(ctx));
|
|
327
|
+
}
|
|
328
|
+
// =============================================================================
|
|
329
|
+
// §4.11 — validateSerializability (WS-08/WS-09/WS-10)
|
|
330
|
+
// =============================================================================
|
|
331
|
+
/**
|
|
332
|
+
* Validates that a value can be safely serialized for workflow checkpoints.
|
|
333
|
+
* Throws MantaError if the value contains BigInt, Map, Set, Buffer, or Function.
|
|
334
|
+
*
|
|
335
|
+
* @example
|
|
336
|
+
* validateSerializability({ count: 42, name: 'ok' }) // passes
|
|
337
|
+
* validateSerializability({ m: new Map() }) // throws
|
|
338
|
+
*/
|
|
339
|
+
export function validateSerializability(value, path = '') {
|
|
340
|
+
if (value === null || value === undefined)
|
|
341
|
+
return;
|
|
342
|
+
if (typeof value === 'bigint') {
|
|
343
|
+
throw new MantaError('INVALID_DATA', `Non-serializable value at ${path || 'root'}: BigInt`);
|
|
344
|
+
}
|
|
345
|
+
if (value instanceof Map) {
|
|
346
|
+
throw new MantaError('INVALID_DATA', `Non-serializable value at ${path || 'root'}: Map`);
|
|
347
|
+
}
|
|
348
|
+
if (value instanceof Set) {
|
|
349
|
+
throw new MantaError('INVALID_DATA', `Non-serializable value at ${path || 'root'}: Set`);
|
|
350
|
+
}
|
|
351
|
+
if (typeof Buffer !== 'undefined' && Buffer.isBuffer(value)) {
|
|
352
|
+
throw new MantaError('INVALID_DATA', `Non-serializable value at ${path || 'root'}: Buffer`);
|
|
353
|
+
}
|
|
354
|
+
if (typeof value === 'function') {
|
|
355
|
+
throw new MantaError('INVALID_DATA', `Non-serializable value at ${path || 'root'}: Function`);
|
|
356
|
+
}
|
|
357
|
+
if (value instanceof Date) {
|
|
358
|
+
// Dates are JSON-serializable (toJSON → ISO string)
|
|
359
|
+
return;
|
|
360
|
+
}
|
|
361
|
+
if (Array.isArray(value)) {
|
|
362
|
+
value.forEach((item, i) => {
|
|
363
|
+
validateSerializability(item, `${path}[${i}]`);
|
|
364
|
+
});
|
|
365
|
+
return;
|
|
366
|
+
}
|
|
367
|
+
if (typeof value === 'object') {
|
|
368
|
+
for (const [key, val] of Object.entries(value)) {
|
|
369
|
+
validateSerializability(val, path ? `${path}.${key}` : key);
|
|
370
|
+
}
|
|
371
|
+
}
|
|
372
|
+
}
|
|
373
|
+
// =============================================================================
|
|
374
|
+
// §4.12 — deriveWorkflowTransactionId & mapExternalError
|
|
375
|
+
// =============================================================================
|
|
376
|
+
// Re-export from core-types (standalone contract definitions)
|
|
377
|
+
export { deriveWorkflowTransactionId, mapExternalError } from './core-types';
|
|
378
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
package/dist/pg.d.ts
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
export declare const TEST_DB_URL: string;
|
|
2
|
+
/**
|
|
3
|
+
* Creates an isolated test database.
|
|
4
|
+
* Each test file gets its own database for parallel execution.
|
|
5
|
+
*/
|
|
6
|
+
export declare function createTestDatabase(name?: string): Promise<{
|
|
7
|
+
url: string;
|
|
8
|
+
cleanup: () => Promise<void>;
|
|
9
|
+
}>;
|
|
10
|
+
/**
|
|
11
|
+
* Waits for PostgreSQL to be accessible.
|
|
12
|
+
* Used in globalSetup for integration tests.
|
|
13
|
+
*/
|
|
14
|
+
export declare function waitForPg(maxRetries?: number): Promise<void>;
|
|
15
|
+
//# sourceMappingURL=pg.d.ts.map
|
package/dist/pg.d.ts.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pg.d.ts","sourceRoot":"","sources":["../src/pg.ts"],"names":[],"mappings":"AAYA,eAAO,MAAM,WAAW,QAA0E,CAAA;AAElG;;;GAGG;AACH,wBAAsB,kBAAkB,CAAC,IAAI,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC;IAC/D,GAAG,EAAE,MAAM,CAAA;IACX,OAAO,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAA;CAC7B,CAAC,CA6BD;AAED;;;GAGG;AACH,wBAAsB,SAAS,CAAC,UAAU,SAAK,GAAG,OAAO,CAAC,IAAI,CAAC,CAqB9D"}
|
package/dist/pg.js
ADDED
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
// Test utility for PostgreSQL integration tests
|
|
2
|
+
// Creates isolated databases per test file for parallel execution.
|
|
3
|
+
//
|
|
4
|
+
// TEST_DATABASE_URL is the BOOTSTRAP connection used to CREATE/DROP per-test
|
|
5
|
+
// databases — not the test database itself. It must point to a DB that always
|
|
6
|
+
// exists on the target server. `postgres` is the conventional admin DB on any
|
|
7
|
+
// PostgreSQL install, so we default to that.
|
|
8
|
+
//
|
|
9
|
+
// Consumers of this module (integration tests, runtime smoke, build-start smoke)
|
|
10
|
+
// MUST import from here and MUST NOT redeclare their own TEST_DATABASE_URL
|
|
11
|
+
// default — see BACKLOG BC-F21 for the rationale.
|
|
12
|
+
export const TEST_DB_URL = process.env.TEST_DATABASE_URL || 'postgresql://localhost:5432/postgres';
|
|
13
|
+
/**
|
|
14
|
+
* Creates an isolated test database.
|
|
15
|
+
* Each test file gets its own database for parallel execution.
|
|
16
|
+
*/
|
|
17
|
+
export async function createTestDatabase(name) {
|
|
18
|
+
// Dynamic import to avoid requiring pg for unit tests
|
|
19
|
+
const { default: pg } = await import('pg');
|
|
20
|
+
const { Client } = pg;
|
|
21
|
+
const dbName = name || `test_${Date.now()}_${Math.random().toString(36).slice(2, 8)}`;
|
|
22
|
+
const client = new Client({ connectionString: TEST_DB_URL });
|
|
23
|
+
await client.connect();
|
|
24
|
+
await client.query(`DROP DATABASE IF EXISTS "${dbName}"`);
|
|
25
|
+
await client.query(`CREATE DATABASE "${dbName}"`);
|
|
26
|
+
await client.end();
|
|
27
|
+
const url = TEST_DB_URL.replace(/\/[^/]+$/, `/${dbName}`);
|
|
28
|
+
return {
|
|
29
|
+
url,
|
|
30
|
+
cleanup: async () => {
|
|
31
|
+
const c = new Client({ connectionString: TEST_DB_URL });
|
|
32
|
+
await c.connect();
|
|
33
|
+
// Kill active connections before dropping
|
|
34
|
+
await c.query(`
|
|
35
|
+
SELECT pg_terminate_backend(pid)
|
|
36
|
+
FROM pg_stat_activity
|
|
37
|
+
WHERE datname = '${dbName}' AND pid <> pg_backend_pid()
|
|
38
|
+
`);
|
|
39
|
+
await c.query(`DROP DATABASE IF EXISTS "${dbName}"`);
|
|
40
|
+
await c.end();
|
|
41
|
+
},
|
|
42
|
+
};
|
|
43
|
+
}
|
|
44
|
+
/**
|
|
45
|
+
* Waits for PostgreSQL to be accessible.
|
|
46
|
+
* Used in globalSetup for integration tests.
|
|
47
|
+
*/
|
|
48
|
+
export async function waitForPg(maxRetries = 30) {
|
|
49
|
+
const { default: pg } = await import('pg');
|
|
50
|
+
const { Client } = pg;
|
|
51
|
+
for (let i = 0; i < maxRetries; i++) {
|
|
52
|
+
const client = new Client({ connectionString: TEST_DB_URL });
|
|
53
|
+
try {
|
|
54
|
+
await client.connect();
|
|
55
|
+
await client.query('SELECT 1');
|
|
56
|
+
await client.end();
|
|
57
|
+
return;
|
|
58
|
+
}
|
|
59
|
+
catch {
|
|
60
|
+
try {
|
|
61
|
+
await client.end();
|
|
62
|
+
}
|
|
63
|
+
catch {
|
|
64
|
+
/* ignore */
|
|
65
|
+
}
|
|
66
|
+
await new Promise((r) => setTimeout(r, 1000));
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
throw new Error(`PostgreSQL not reachable at ${TEST_DB_URL} after ${maxRetries}s`);
|
|
70
|
+
}
|
|
71
|
+
//# sourceMappingURL=pg.js.map
|
package/dist/pg.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pg.js","sourceRoot":"","sources":["../src/pg.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@mantajs/test-utils",
|
|
3
|
+
"version": "0.2.0-beta.0",
|
|
4
|
+
"description": "Test helpers and in-memory adapters for the Manta framework",
|
|
5
|
+
"main": "./dist/index.js",
|
|
6
|
+
"types": "./dist/index.d.ts",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": {
|
|
9
|
+
"types": "./dist/index.d.ts",
|
|
10
|
+
"import": "./dist/index.js",
|
|
11
|
+
"default": "./dist/index.js"
|
|
12
|
+
},
|
|
13
|
+
"./core-types": {
|
|
14
|
+
"types": "./dist/core-types.d.ts",
|
|
15
|
+
"import": "./dist/core-types.js",
|
|
16
|
+
"default": "./dist/core-types.js"
|
|
17
|
+
},
|
|
18
|
+
"./pg": {
|
|
19
|
+
"types": "./dist/pg.d.ts",
|
|
20
|
+
"import": "./dist/pg.js",
|
|
21
|
+
"default": "./dist/pg.js"
|
|
22
|
+
}
|
|
23
|
+
},
|
|
24
|
+
"files": [
|
|
25
|
+
"dist"
|
|
26
|
+
],
|
|
27
|
+
"dependencies": {
|
|
28
|
+
"pg": "^8.13.0",
|
|
29
|
+
"@mantajs/core": "0.2.0-beta.0"
|
|
30
|
+
},
|
|
31
|
+
"devDependencies": {
|
|
32
|
+
"@types/pg": "^8.11.10",
|
|
33
|
+
"typescript": "^5.4.0"
|
|
34
|
+
},
|
|
35
|
+
"peerDependencies": {
|
|
36
|
+
"vitest": "^2.0.0"
|
|
37
|
+
},
|
|
38
|
+
"scripts": {
|
|
39
|
+
"typecheck": "tsc --noEmit"
|
|
40
|
+
}
|
|
41
|
+
}
|