@effect-app/infra 0.170.5 → 0.171.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.
Files changed (90) hide show
  1. package/CHANGELOG.md +23 -0
  2. package/_cjs/api/routing/base.cjs.map +1 -1
  3. package/_cjs/api/routing/makeRequestHandler.cjs.map +1 -1
  4. package/_cjs/services/QueueMaker/errors.cjs.map +1 -1
  5. package/_cjs/services/Repository/dsl.cjs +70 -0
  6. package/_cjs/services/Repository/dsl.cjs.map +1 -0
  7. package/_cjs/services/Repository/ext.cjs +202 -0
  8. package/_cjs/services/Repository/ext.cjs.map +1 -0
  9. package/_cjs/services/Repository/service.cjs +6 -0
  10. package/_cjs/services/Repository/service.cjs.map +1 -0
  11. package/_cjs/services/Repository.cjs +32 -252
  12. package/_cjs/services/Repository.cjs.map +1 -1
  13. package/_cjs/services/RepositoryBase.cjs +173 -48
  14. package/_cjs/services/RepositoryBase.cjs.map +1 -1
  15. package/_cjs/services/RequestContextContainer.cjs +6 -7
  16. package/_cjs/services/RequestContextContainer.cjs.map +1 -1
  17. package/_cjs/services/Store/ContextMapContainer.cjs +6 -7
  18. package/_cjs/services/Store/ContextMapContainer.cjs.map +1 -1
  19. package/_cjs/services/Store/Memory.cjs.map +1 -1
  20. package/_cjs/services/Store/utils.cjs.map +1 -1
  21. package/_src/api/routing/base.ts +5 -3
  22. package/_src/api/routing/makeRequestHandler.ts +20 -12
  23. package/_src/rateLimit.ts +2 -2
  24. package/_src/services/Emailer/Sendgrid.ts +2 -2
  25. package/_src/services/QueueMaker/errors.ts +6 -3
  26. package/_src/services/QueueMaker/memQueue.ts +2 -2
  27. package/_src/services/QueueMaker/sbqueue.ts +2 -2
  28. package/_src/services/Repository/dsl.ts +137 -0
  29. package/_src/services/Repository/ext.ts +669 -0
  30. package/_src/services/Repository/service.ts +12 -0
  31. package/_src/services/Repository.ts +3 -791
  32. package/_src/services/RepositoryBase.ts +640 -13
  33. package/_src/services/RequestContextContainer.ts +14 -16
  34. package/_src/services/Store/ContextMapContainer.ts +6 -9
  35. package/_src/services/Store/Cosmos.ts +2 -2
  36. package/_src/services/Store/Disk.ts +2 -2
  37. package/_src/services/Store/Memory.ts +2 -1
  38. package/_src/services/Store/Redis.ts +2 -2
  39. package/_src/services/Store/utils.ts +4 -5
  40. package/_src/services/simpledb/cosmosdb.ts +1 -1
  41. package/_src/services/simpledb/diskdb.ts +1 -1
  42. package/_src/services/simpledb/memdb.ts +1 -1
  43. package/_src/services/simpledb/mongodb.ts +1 -1
  44. package/_src/services/simpledb/redisdb.ts +2 -2
  45. package/dist/api/routing/base.d.ts +1 -2
  46. package/dist/api/routing/base.d.ts.map +1 -1
  47. package/dist/api/routing/base.js +1 -1
  48. package/dist/api/routing/makeRequestHandler.d.ts.map +1 -1
  49. package/dist/api/routing/makeRequestHandler.js +15 -11
  50. package/dist/rateLimit.js +1 -1
  51. package/dist/services/Emailer/Sendgrid.js +1 -1
  52. package/dist/services/QueueMaker/errors.d.ts.map +1 -1
  53. package/dist/services/QueueMaker/errors.js +5 -2
  54. package/dist/services/QueueMaker/memQueue.js +1 -1
  55. package/dist/services/QueueMaker/sbqueue.js +1 -1
  56. package/dist/services/QueueMaker/service.d.ts +2 -2
  57. package/dist/services/Repository/dsl.d.ts +51 -0
  58. package/dist/services/Repository/dsl.d.ts.map +1 -0
  59. package/dist/services/Repository/dsl.js +55 -0
  60. package/dist/services/Repository/ext.d.ts +310 -0
  61. package/dist/services/Repository/ext.d.ts.map +1 -0
  62. package/dist/services/Repository/ext.js +166 -0
  63. package/dist/services/Repository/service.d.ts +10 -0
  64. package/dist/services/Repository/service.d.ts.map +1 -0
  65. package/dist/services/Repository/service.js +2 -0
  66. package/dist/services/Repository.d.ts +3 -363
  67. package/dist/services/Repository.d.ts.map +1 -1
  68. package/dist/services/Repository.js +4 -217
  69. package/dist/services/RepositoryBase.d.ts +241 -6
  70. package/dist/services/RepositoryBase.d.ts.map +1 -1
  71. package/dist/services/RepositoryBase.js +176 -52
  72. package/dist/services/RequestContextContainer.d.ts +3 -5
  73. package/dist/services/RequestContextContainer.d.ts.map +1 -1
  74. package/dist/services/RequestContextContainer.js +17 -16
  75. package/dist/services/Store/ContextMapContainer.d.ts +2 -5
  76. package/dist/services/Store/ContextMapContainer.d.ts.map +1 -1
  77. package/dist/services/Store/ContextMapContainer.js +7 -8
  78. package/dist/services/Store/Cosmos.js +1 -1
  79. package/dist/services/Store/Disk.js +1 -1
  80. package/dist/services/Store/Memory.d.ts.map +1 -1
  81. package/dist/services/Store/Memory.js +1 -1
  82. package/dist/services/Store/Redis.js +1 -1
  83. package/dist/services/Store/utils.d.ts.map +1 -1
  84. package/dist/services/Store/utils.js +1 -1
  85. package/dist/services/simpledb/cosmosdb.js +1 -1
  86. package/dist/services/simpledb/diskdb.js +1 -1
  87. package/dist/services/simpledb/memdb.js +1 -1
  88. package/dist/services/simpledb/mongodb.js +1 -1
  89. package/dist/services/simpledb/redisdb.js +1 -1
  90. package/package.json +37 -7
@@ -1,791 +1,3 @@
1
- /* eslint-disable @typescript-eslint/no-explicit-any */
2
- // Update = Must return updated items
3
- // Modify = Must `set` updated items, and can return anything.
4
- import type { FixEnv, PureLogT } from "@effect-app/prelude/Pure"
5
- import { Pure } from "@effect-app/prelude/Pure"
6
- import type { InvalidStateError, OptimisticConcurrencyException } from "../errors.js"
7
- import { NotFoundError } from "../errors.js"
8
- import type { Filter, PersistenceModelType } from "../services/Store.js"
9
- import type { RepositoryBaseC } from "./RepositoryBase.js"
10
- import type { QueryBuilder } from "./Store/filterApi/query.js"
11
-
12
- /**
13
- * @tsplus type Repository
14
- */
15
- export interface Repository<
16
- T extends { id: unknown },
17
- PM extends PersistenceModelType<string>,
18
- Evt,
19
- ItemType extends string
20
- > extends RepositoryBaseC<T, PM, Evt, ItemType> {}
21
-
22
- export interface PureDSL<S, S2, W> {
23
- get: ReturnType<typeof Pure.get<S>>
24
- set: typeof Pure.set<S2>
25
- log: (...w: W[]) => PureLogT<W>
26
- }
27
-
28
- export const AnyPureDSL: PureDSL<any, any, any> = {
29
- get: Pure.get(),
30
- set: Pure.set,
31
- log: (...evt: any[]) => Pure.logMany(evt)
32
- }
33
-
34
- /**
35
- * @tsplus fluent Repository get
36
- */
37
- export function get<
38
- T extends { id: unknown },
39
- PM extends PersistenceModelType<string>,
40
- Evt,
41
- ItemType extends string
42
- >(
43
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
44
- id: T["id"]
45
- ) {
46
- return self
47
- .find(id)
48
- .flatMap((_) => _.encaseInEffect(() => new NotFoundError<ItemType>({ type: self.itemType, id })))
49
- }
50
-
51
- /**
52
- * @tsplus getter Repository log
53
- */
54
- export function log<
55
- T extends { id: unknown },
56
- PM extends PersistenceModelType<string>,
57
- Evt,
58
- ItemType extends string
59
- >(_: RepositoryBaseC<T, PM, Evt, ItemType>) {
60
- return (evt: Evt) => AnyPureDSL.log(evt)
61
- }
62
-
63
- /**
64
- * TODO: project inside the db.
65
- * @tsplus fluent Repository projectEffect
66
- */
67
- export function projectEffect<
68
- T extends { id: unknown },
69
- PM extends PersistenceModelType<string>,
70
- Evt,
71
- ItemType extends string,
72
- R,
73
- E,
74
- S = PM
75
- >(
76
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
77
- map: Effect<{
78
- filter?: Filter<PM> | undefined
79
- collect?: ((t: PM) => Option<S>) | undefined
80
- limit?: number | undefined
81
- skip?: number | undefined
82
- }, E, R>
83
- ): Effect<S[], E, R>
84
- export function projectEffect<
85
- T extends { id: unknown },
86
- PM extends PersistenceModelType<string>,
87
- Evt,
88
- ItemType extends string,
89
- R,
90
- E,
91
- U extends keyof PM,
92
- S = PM
93
- >(
94
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
95
- map: Effect<{
96
- filter?: QueryBuilder<PM> | undefined
97
- collect?: ((t: PM) => Option<S>) | undefined
98
- limit?: number | undefined
99
- skip?: number | undefined
100
- }, E, R>
101
- ): Effect<Pick<PM, U>[], E, R>
102
- export function projectEffect<
103
- T extends { id: unknown },
104
- PM extends PersistenceModelType<string>,
105
- Evt,
106
- ItemType extends string,
107
- R,
108
- E,
109
- U extends keyof PM,
110
- S = Pick<PM, U>
111
- >(
112
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
113
- map: Effect<{
114
- filter?: Filter<PM> | undefined
115
- select?: NonEmptyReadonlyArray<U> | undefined
116
- collect?: ((t: PM) => Option<S>) | undefined
117
- limit?: number | undefined
118
- skip?: number | undefined
119
- }, E, R>
120
- ): Effect<S[], E, R> {
121
- // TODO: a projection that gets sent to the db instead.
122
- return map.flatMap((f) =>
123
- self
124
- .utils
125
- .filter(f)
126
- .map((_) => f.collect ? _.filterMap(f.collect) : _ as unknown as S[])
127
- )
128
- }
129
-
130
- /**
131
- * TODO: project inside the db.
132
- * @tsplus fluent Repository project
133
- */
134
- export function project<
135
- T extends { id: unknown },
136
- PM extends PersistenceModelType<string>,
137
- Evt,
138
- ItemType extends string,
139
- S = PM
140
- >(
141
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
142
- map: {
143
- filter?: Filter<PM>
144
- collect?: (t: PM) => Option<S>
145
- limit?: number
146
- skip?: number
147
- }
148
- ): Effect<S[]>
149
- export function project<
150
- T extends { id: unknown },
151
- PM extends PersistenceModelType<string>,
152
- Evt,
153
- ItemType extends string,
154
- U extends keyof PM
155
- >(
156
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
157
- map: {
158
- filter?: QueryBuilder<PM>
159
- select: NonEmptyReadonlyArray<U>
160
- limit?: number
161
- skip?: number
162
- }
163
- ): Effect<Pick<PM, U>[]>
164
- export function project<
165
- T extends { id: unknown },
166
- PM extends PersistenceModelType<string>,
167
- Evt,
168
- ItemType extends string,
169
- U extends keyof PM,
170
- S = Pick<PM, U>
171
- >(
172
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
173
- map: {
174
- filter?: Filter<PM>
175
- select?: NonEmptyReadonlyArray<U>
176
- collect?: (t: Pick<PM, U>) => Option<S>
177
- limit?: number
178
- skip?: number
179
- }
180
- ): Effect<S[]> {
181
- return self.projectEffect(Effect.sync(() => map))
182
- }
183
-
184
- /**
185
- * TODO: count inside the db.
186
- * @tsplus fluent Repository project
187
- */
188
- export function count<
189
- T extends { id: unknown },
190
- PM extends PersistenceModelType<string>,
191
- Evt,
192
- ItemType extends string
193
- >(
194
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
195
- filter?: Filter<PM>
196
- ) {
197
- return self
198
- .projectEffect(Effect.sync(() => ({ filter })))
199
- .map((_) => NonNegativeInt(_.length))
200
- }
201
-
202
- /**
203
- * @tsplus fluent Repository queryEffect
204
- */
205
- export function queryEffect<
206
- T extends { id: unknown },
207
- PM extends PersistenceModelType<string>,
208
- Evt,
209
- ItemType extends string,
210
- R,
211
- E,
212
- S = T
213
- >(
214
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
215
- // TODO: think about collectPM, collectE, and collect(Parsed)
216
- map: Effect<{ filter?: Filter<PM>; collect?: (t: T) => Option<S>; limit?: number; skip?: number }, E, R>
217
- ) {
218
- return map.flatMap((f) =>
219
- (f.filter ? self.utils.filter(f) : self.utils.all)
220
- .flatMap((_) => self.utils.parseMany(_))
221
- .map((_) => f.collect ? _.filterMap(f.collect) : _ as any as S[])
222
- )
223
- }
224
-
225
- /**
226
- * @tsplus fluent Repository queryOneEffect
227
- */
228
- export function queryOneEffect<
229
- T extends { id: unknown },
230
- PM extends PersistenceModelType<string>,
231
- Evt,
232
- ItemType extends string,
233
- R,
234
- E
235
- >(
236
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
237
- // TODO: think about collectPM, collectE, and collect(Parsed)
238
- map: Effect<{ filter?: Filter<PM> }, E, R>
239
- ): Effect<T, E | NotFoundError<ItemType>, R>
240
- export function queryOneEffect<
241
- T extends { id: unknown },
242
- PM extends PersistenceModelType<string>,
243
- Evt,
244
- ItemType extends string,
245
- R,
246
- E,
247
- S = T
248
- >(
249
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
250
- // TODO: think about collectPM, collectE, and collect(Parsed)
251
- map: Effect<{ filter?: Filter<PM>; collect: (t: T) => Option<S> }, E, R>
252
- ): Effect<S, E | NotFoundError<ItemType>, R>
253
- export function queryOneEffect<
254
- T extends { id: unknown },
255
- PM extends PersistenceModelType<string>,
256
- Evt,
257
- ItemType extends string,
258
- R,
259
- E,
260
- S = T
261
- >(
262
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
263
- // TODO: think about collectPM, collectE, and collect(Parsed)
264
- map: Effect<{ filter?: Filter<PM>; collect?: (t: T) => Option<S> }, E, R>
265
- ): Effect<S, E | NotFoundError<ItemType>, R> {
266
- return map.flatMap((f) =>
267
- (f.filter ? self.utils.filter({ filter: f.filter, limit: 1 }) : self.utils.all)
268
- .flatMap((_) => self.utils.parseMany(_))
269
- .flatMap((_) =>
270
- (f.collect ? _.filterMap(f.collect) : _ as any as S[])
271
- .toNonEmpty
272
- .encaseInEffect(() => new NotFoundError<ItemType>({ type: self.itemType, id: f.filter }))
273
- .map((_) => _[0])
274
- )
275
- )
276
- }
277
-
278
- /**
279
- * @tsplus fluent Repository query
280
- */
281
- export function query<
282
- T extends { id: unknown },
283
- PM extends PersistenceModelType<string>,
284
- Evt,
285
- ItemType extends string,
286
- S = T
287
- >(
288
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
289
- // TODO: think about collectPM, collectE, and collect(Parsed)
290
- map: { filter?: Filter<PM>; collect?: (t: T) => Option<S>; limit?: number; skip?: number }
291
- ) {
292
- return self.queryEffect(Effect.sync(() => map))
293
- }
294
-
295
- /**
296
- * @tsplus fluent Repository queryOne
297
- */
298
- export function queryOne<
299
- T extends { id: unknown },
300
- PM extends PersistenceModelType<string>,
301
- Evt,
302
- ItemType extends string,
303
- S = T
304
- >(
305
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
306
- map: { filter?: Filter<PM>; collect: (t: T) => Option<S> }
307
- ): Effect<S, NotFoundError<ItemType>>
308
- export function queryOne<
309
- T extends { id: unknown },
310
- PM extends PersistenceModelType<string>,
311
- Evt,
312
- ItemType extends string
313
- >(
314
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
315
- map: { filter?: Filter<PM> }
316
- ): Effect<T, NotFoundError<ItemType>>
317
- export function queryOne<
318
- T extends { id: unknown },
319
- PM extends PersistenceModelType<string>,
320
- Evt,
321
- ItemType extends string,
322
- S = T
323
- >(
324
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
325
- map: { filter?: Filter<PM>; collect?: (t: T) => Option<S> }
326
- ) {
327
- return self.queryOneEffect(Effect.sync(() => map))
328
- }
329
-
330
- /**
331
- * @tsplus fluent Repository queryAndSaveOnePureEffect
332
- */
333
- export function queryAndSaveOnePureEffect<
334
- T extends { id: unknown },
335
- PM extends PersistenceModelType<string>,
336
- Evt,
337
- ItemType extends string,
338
- R,
339
- E,
340
- S extends T = T
341
- >(
342
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
343
- map: Effect<{ filter: Filter<PM>; collect: (t: T) => Option<S>; limit?: number; skip?: number }, E, R>
344
- ): <R2, A, E2, S2 extends T>(pure: Effect<A, E2, FixEnv<R2, Evt, S, S2>>) => Effect<A, InvalidStateError | OptimisticConcurrencyException | E | E2 | NotFoundError<ItemType>, | R
345
- | Exclude<R2, {
346
- env: PureEnv<Evt, S, S2>
347
- }>>
348
- export function queryAndSaveOnePureEffect<
349
- T extends { id: unknown },
350
- PM extends PersistenceModelType<string>,
351
- Evt,
352
- ItemType extends string,
353
- R,
354
- E
355
- >(
356
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
357
- map: Effect<{ filter: Filter<PM> }, E, R>
358
- ): <R2, A, E2, T2 extends T>(pure: Effect<A, E2, FixEnv<R2, Evt, T, T2>>) => Effect<A, InvalidStateError | OptimisticConcurrencyException | E | E2 | NotFoundError<ItemType>, | R
359
- | Exclude<R2, {
360
- env: PureEnv<Evt, T, T2>
361
- }>>
362
- export function queryAndSaveOnePureEffect(
363
- self: any,
364
- map: any
365
- ) {
366
- return (pure: any) =>
367
- queryOneEffect(self, map)
368
- .flatMap((_) => saveWithPure_(self, _, pure))
369
- }
370
-
371
- /**
372
- * @tsplus fluent Repository queryAndSaveOnePure
373
- */
374
- export function queryAndSaveOnePure<
375
- T extends { id: unknown },
376
- PM extends PersistenceModelType<string>,
377
- Evt,
378
- ItemType extends string,
379
- S extends T = T
380
- >(
381
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
382
- map: { filter: Filter<PM>; collect: (t: T) => Option<S>; limit?: number; skip?: number }
383
- ): <R2, A, E2, S2>(pure: Effect<A, E2, FixEnv<R2, Evt, S, S2>>) => Effect<
384
- A,
385
- InvalidStateError | OptimisticConcurrencyException | E2 | NotFoundError<ItemType>,
386
- Exclude<R2, {
387
- env: PureEnv<Evt, S, S2>
388
- }>
389
- >
390
- export function queryAndSaveOnePure<
391
- T extends { id: unknown },
392
- PM extends PersistenceModelType<string>,
393
- Evt,
394
- ItemType extends string
395
- >(
396
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
397
- map: { filter: Filter<PM> }
398
- ): <R2, A, E2, T2>(pure: Effect<A, E2, FixEnv<R2, Evt, T, T2>>) => Effect<
399
- A,
400
- InvalidStateError | OptimisticConcurrencyException | E2 | NotFoundError<ItemType>,
401
- Exclude<R2, {
402
- env: PureEnv<Evt, T, T2>
403
- }>
404
- >
405
- export function queryAndSaveOnePure(
406
- self: any,
407
- map: { filter: Filter<any>; collect?: any }
408
- ) {
409
- return queryAndSaveOnePureEffect(self, Effect.sync(() => map))
410
- }
411
-
412
- /**
413
- * @tsplus fluent Repository queryAndSavePureEffect
414
- */
415
- export function queryAndSavePureEffect<
416
- T extends { id: unknown },
417
- PM extends PersistenceModelType<string>,
418
- Evt,
419
- ItemType extends string,
420
- R,
421
- E,
422
- S extends T = T
423
- >(
424
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
425
- map: Effect<{ filter: Filter<PM>; collect?: (t: T) => Option<S>; limit?: number; skip?: number }, E, R>
426
- ) {
427
- return <R2, A, E2, S2 extends T>(pure: Effect<A, E2, FixEnv<R2, Evt, S[], S2[]>>) =>
428
- queryEffect(self, map)
429
- .flatMap((_) => self.saveManyWithPure_(_, pure));
430
- }
431
-
432
- /**
433
- * @tsplus fluent Repository queryAndSavePure
434
- */
435
- export function queryAndSavePure<
436
- T extends { id: unknown },
437
- PM extends PersistenceModelType<string>,
438
- Evt,
439
- ItemType extends string,
440
- S extends T = T
441
- >(
442
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
443
- map: { filter: Filter<PM>; collect?: (t: T) => Option<S>; limit?: number; skip?: number }
444
- ) {
445
- return self.queryAndSavePureEffect(Effect.sync(() => map))
446
- }
447
-
448
- /**
449
- * @tsplus getter Repository saveManyWithPure
450
- */
451
- export function saveManyWithPure<
452
- T extends { id: unknown },
453
- PM extends PersistenceModelType<string>,
454
- Evt,
455
- ItemType extends string
456
- >(self: RepositoryBaseC<T, PM, Evt, ItemType>) {
457
- return <R, A, E, S1 extends T, S2 extends T>(pure: Effect<A, E, FixEnv<R, Evt, S1[], S2[]>>) =>
458
- (items: Iterable<S1>) => saveManyWithPure_(self, items, pure);
459
- }
460
-
461
- /**
462
- * @tsplus fluent Repository byIdAndSaveWithPure
463
- */
464
- export function byIdAndSaveWithPure<
465
- T extends { id: unknown },
466
- PM extends PersistenceModelType<string>,
467
- Evt,
468
- ItemType extends string
469
- >(self: RepositoryBaseC<T, PM, Evt, ItemType>, id: T["id"]) {
470
- return <R, A, E, S2 extends T>(pure: Effect<A, E, FixEnv<R, Evt, T, S2>>) =>
471
- get(self, id).flatMap((item) => saveWithPure_(self, item, pure));
472
- }
473
-
474
- /**
475
- * NOTE: it's not as composable, only useful when the request is simple, and only this part needs request args.
476
- * @tsplus getter Repository handleByIdAndSaveWithPure
477
- */
478
- export function handleByIdAndSaveWithPure<
479
- T extends { id: unknown },
480
- PM extends PersistenceModelType<string>,
481
- Evt,
482
- ItemType extends string
483
- >(self: RepositoryBaseC<T, PM, Evt, ItemType>) {
484
- return <Req extends { id: T["id"] }, Context, R, A, E, S2 extends T>(
485
- pure: (req: Req, ctx: Context) => Effect<A, E, FixEnv<R, Evt, T, S2>>
486
- ) =>
487
- (req: Req, ctx: Context) => byIdAndSaveWithPure(self, req.id)(pure(req, ctx));
488
- }
489
-
490
- /**
491
- * @tsplus fluent Repository saveManyWithPure_
492
- */
493
- export function saveManyWithPure_<
494
- R,
495
- T extends { id: unknown },
496
- PM extends PersistenceModelType<string>,
497
- A,
498
- E,
499
- Evt,
500
- S1 extends T,
501
- S2 extends T,
502
- ItemType extends string
503
- >(
504
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
505
- items: Iterable<S1>,
506
- pure: Effect<A, E, FixEnv<R, Evt, S1[], S2[]>>
507
- ) {
508
- return saveAllWithEffectInt(
509
- self,
510
- pure.runTerm([...items])
511
- )
512
- }
513
-
514
- /**
515
- * @tsplus fluent Repository saveWithPure_
516
- */
517
- export function saveWithPure_<
518
- R,
519
- T extends { id: unknown },
520
- PM extends PersistenceModelType<string>,
521
- A,
522
- E,
523
- Evt,
524
- S1 extends T,
525
- S2 extends T,
526
- ItemType extends string
527
- >(
528
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
529
- item: S1,
530
- pure: Effect<A, E, FixEnv<R, Evt, S1, S2>>
531
- ) {
532
- return saveAllWithEffectInt(
533
- self,
534
- pure
535
- .runTerm(item)
536
- .map(([item, events, a]) => [[item], events, a])
537
- )
538
- }
539
-
540
- export function saveAllWithEffectInt<
541
- T extends { id: unknown },
542
- PM extends PersistenceModelType<string>,
543
- P extends T,
544
- Evt,
545
- ItemType extends string,
546
- R,
547
- E,
548
- A
549
- >(
550
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
551
- gen: Effect<readonly [Iterable<P>, Iterable<Evt>, A], E, R>
552
- ) {
553
- return gen
554
- .flatMap(
555
- ([items, events, a]) => self.saveAndPublish(items, events).map(() => a)
556
- )
557
- }
558
-
559
- /**
560
- * @tsplus fluent Repository queryAndSavePureEffectBatched
561
- */
562
- export function queryAndSavePureEffectBatched<
563
- T extends { id: unknown },
564
- PM extends PersistenceModelType<string>,
565
- Evt,
566
- ItemType extends string,
567
- R,
568
- E,
569
- S extends T = T
570
- >(
571
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
572
- // TODO: think about collectPM, collectE, and collect(Parsed)
573
- map: Effect<{ filter: Filter<PM>; collect?: (t: T) => Option<S>; limit?: number; skip?: number }, E, R>,
574
- batchSize = 100
575
- ) {
576
- return <R2, A, E2, S2 extends T>(pure: Effect<A, E2, FixEnv<R2, Evt, S[], S2[]>>) =>
577
- queryEffect(self, map)
578
- .flatMap((_) => self.saveManyWithPureBatched_(_, pure, batchSize));
579
- }
580
-
581
- /**
582
- * @tsplus fluent Repository queryAndSavePureBatched
583
- */
584
- export function queryAndSavePureBatched<
585
- T extends { id: unknown },
586
- PM extends PersistenceModelType<string>,
587
- Evt,
588
- ItemType extends string,
589
- S extends T = T
590
- >(
591
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
592
- // TODO: think about collectPM, collectE, and collect(Parsed)
593
- map: { filter: Filter<PM>; collect?: (t: T) => Option<S>; limit?: number; skip?: number },
594
- batchSize = 100
595
- ) {
596
- return self.queryAndSavePureEffectBatched(Effect.sync(() => map), batchSize)
597
- }
598
-
599
- /**
600
- * @tsplus fluent Repository saveManyWithPureBatched
601
- */
602
- export function saveManyWithPureBatched<
603
- T extends { id: unknown },
604
- PM extends PersistenceModelType<string>,
605
- Evt,
606
- ItemType extends string
607
- >(self: RepositoryBaseC<T, PM, Evt, ItemType>, batchSize = 100) {
608
- return <R, A, E, S1 extends T, S2 extends T>(pure: Effect<A, E, FixEnv<R, Evt, S1[], S2[]>>) =>
609
- (items: Iterable<S1>) => saveManyWithPureBatched_(self, items, pure, batchSize);
610
- }
611
-
612
- /**
613
- * @tsplus fluent Repository saveManyWithPureBatched_
614
- */
615
- export function saveManyWithPureBatched_<
616
- R,
617
- T extends { id: unknown },
618
- PM extends PersistenceModelType<string>,
619
- A,
620
- E,
621
- Evt,
622
- S1 extends T,
623
- S2 extends T,
624
- ItemType extends string
625
- >(
626
- self: RepositoryBaseC<T, PM, Evt, ItemType>,
627
- items: Iterable<S1>,
628
- pure: Effect<A, E, FixEnv<R, Evt, S1[], S2[]>>,
629
- batchSize = 100
630
- ) {
631
- return items
632
- .chunk(batchSize)
633
- .forEachEffect((batch) =>
634
- saveAllWithEffectInt(
635
- self,
636
- pure.runTerm(batch)
637
- )
638
- )
639
- }
640
-
641
- const anyDSL = makeDSL<any, any, any>()
642
-
643
- export type AllDSL<T, Evt> =
644
- & (<R, A, E, S1 extends T, S2 extends T>(
645
- pure: (dsl: PureDSL<S1[], S2[], Evt>) => Effect<A, E, R>
646
- ) => Effect<A, E, FixEnv<R, Evt, S1[], S2[]>>)
647
- & AllDSLExt<T, Evt>
648
-
649
- /**
650
- * @tsplus type DSLExt
651
- */
652
- export interface AllDSLExt<T, Evt> {
653
- modify: <R, E, A, S1 extends T, S2 extends T>(
654
- pure: (items: S1[], dsl: PureDSL<S1[], S2[], Evt>) => Effect<A, E, R>
655
- ) => Effect<A, E, FixEnv<R, Evt, S1[], S2[]>>
656
- update: <R, E, S1 extends T, S2 extends T>(
657
- pure: (items: S1[], log: (...evt: Evt[]) => PureLogT<Evt>) => Effect<S2[], E, R>
658
- ) => Effect<S2[], E, FixEnv<R, Evt, S1[], S2[]>>
659
- }
660
-
661
- export function makeAllDSL<T, Evt>() {
662
- const dsl: AllDSL<T, Evt> = anyDSL
663
- return dsl
664
- }
665
-
666
- export type OneDSL<T, Evt> =
667
- & (<R, A, E, S1 extends T, S2 extends T>(
668
- pure: (dsl: PureDSL<S1, S2, Evt>) => Effect<A, E, FixEnv<R, Evt, S1, S2>>
669
- ) => Effect<A, E, FixEnv<R, Evt, S1, S2>>)
670
- & OneDSLExt<T, Evt>
671
-
672
- /**
673
- * @tsplus type DSLExt
674
- */
675
- export interface OneDSLExt<T, Evt> {
676
- modify: <R, E, A, S1 extends T, S2 extends T>(
677
- pure: (items: S1, dsl: PureDSL<S1, S2, Evt>) => Effect<A, E, FixEnv<R, Evt, S1, S2>>
678
- ) => Effect<A, E, FixEnv<R, Evt, S1, S2> | PureEnvEnv<Evt, S1, S1>>
679
- update: <R, E, S1 extends T, S2 extends T>(
680
- pure: (items: S1, log: (...evt: Evt[]) => PureLogT<Evt>) => Effect<S2, E, FixEnv<R, Evt, S1, S2>>
681
- ) => Effect<S2, E, FixEnv<R, Evt, S1, S2>>
682
- }
683
-
684
- /**
685
- * @tsplus fluent DSLExt updateWith
686
- */
687
- export function updateWithOne<T, Evt, S1 extends T, S2 extends T>(self: OneDSL<T, Evt>, upd: (item: S1) => S2) {
688
- return self.update((_: S1) => Effect.sync(() => upd(_)))
689
- }
690
-
691
- /**
692
- * @tsplus fluent DSLExt updateWith
693
- */
694
- export function updateWith<T, Evt, S1 extends T, S2 extends T>(
695
- self: AllDSL<T, Evt>,
696
- upd: (item: S1[]) => S2[]
697
- ) {
698
- return self.update((_: S1[]) => Effect.sync(() => upd(_)))
699
- }
700
-
701
- export function makeOneDSL<T, Evt>(): OneDSL<T, Evt> {
702
- return anyDSL
703
- }
704
-
705
- export function makeDSL<S1, S2, Evt>() {
706
- const dsl: PureDSL<S1, S2, Evt> = AnyPureDSL
707
-
708
- function modify<
709
- R,
710
- E,
711
- A
712
- >(
713
- pure: (
714
- items: S1,
715
- dsl: PureDSL<S1, S2, Evt>
716
- ) => Effect<A, E, R>
717
- ): Effect<A, E, FixEnv<R, Evt, S1, S2>> {
718
- return dsl.get.flatMap((items) => pure(items, dsl)) as any
719
- }
720
-
721
- function update<
722
- R,
723
- E
724
- >(
725
- pure: (
726
- items: S1,
727
- log: (...evt: Evt[]) => PureLogT<Evt>
728
- ) => Effect<S2, E, R>
729
- ): Effect<S2, E, FixEnv<R, Evt, S1, S2>> {
730
- return dsl.get.flatMap((items) => pure(items, dsl.log).tap(dsl.set)) as any
731
- }
732
-
733
- function withDSL<
734
- R,
735
- A,
736
- E
737
- >(
738
- pure: (dsl: PureDSL<S1, S2, Evt>) => Effect<A, E, R>
739
- ): Effect<A, E, FixEnv<R, Evt, S1, S2>> {
740
- return pure(AnyPureDSL) as any
741
- }
742
-
743
- return Object.assign(
744
- withDSL,
745
- {
746
- modify,
747
- update
748
- }
749
- )
750
- }
751
-
752
- export interface DSLExt<S1, S2, Evt> extends ReturnType<typeof makeDSL<S1, S2, Evt>> {}
753
-
754
- export function ifAny<T, R, E, A>(fn: (items: NonEmptyReadonlyArray<T>) => Effect<A, E, R>) {
755
- return (items: Iterable<T>) => Effect.sync(() => items.toNonEmptyArray).flatMapOpt(fn)
756
- }
757
-
758
- /**
759
- * @tsplus fluent Iterable ifAny
760
- */
761
- export function ifAny_<T, R, E, A>(items: Iterable<T>, fn: (items: NonEmptyReadonlyArray<T>) => Effect<A, E, R>) {
762
- return Effect.sync(() => items.toNonEmptyArray).flatMapOpt(fn)
763
- }
764
-
765
- /**
766
- * @tsplus getter Repository save
767
- */
768
- export function save<
769
- T extends { id: unknown },
770
- PM extends PersistenceModelType<string>,
771
- Evt,
772
- ItemType extends string
773
- >(
774
- self: RepositoryBaseC<T, PM, Evt, ItemType>
775
- ) {
776
- return (...items: NonEmptyArray<T>) => self.saveAndPublish(items)
777
- }
778
-
779
- /**
780
- * @tsplus getter Repository saveWithEvents
781
- */
782
- export function saveWithEvents<
783
- T extends { id: unknown },
784
- PM extends PersistenceModelType<string>,
785
- Evt,
786
- ItemType extends string
787
- >(
788
- self: RepositoryBaseC<T, PM, Evt, ItemType>
789
- ) {
790
- return (events: Iterable<Evt>) => (...items: NonEmptyArray<T>) => self.saveAndPublish(items, events)
791
- }
1
+ export * from "./Repository/dsl.js"
2
+ export * from "./Repository/ext.js"
3
+ export * from "./Repository/service.js"