@effect-app/infra 0.73.0 → 0.74.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/CHANGELOG.md +20 -0
- package/_cjs/RequestContext.cjs +2 -4
- package/_cjs/RequestContext.cjs.map +1 -1
- package/_cjs/api/authorization.jwt.cjs +1 -2
- package/_cjs/api/authorization.jwt.cjs.map +1 -1
- package/_cjs/api/codec.cjs +4 -3
- package/_cjs/api/codec.cjs.map +1 -1
- package/_cjs/api/defaultErrorHandler.cjs +6 -8
- package/_cjs/api/defaultErrorHandler.cjs.map +1 -1
- package/_cjs/api/express/makeJsonSchema.test.cjs +2 -2
- package/_cjs/api/express/makeJsonSchema.test.cjs.map +1 -1
- package/_cjs/api/express/schema/jwt.cjs +8 -10
- package/_cjs/api/express/schema/jwt.cjs.map +1 -1
- package/_cjs/api/express/schema/requestHandler.cjs +7 -6
- package/_cjs/api/express/schema/requestHandler.cjs.map +1 -1
- package/_cjs/api/express/schema/routing.cjs +20 -5
- package/_cjs/api/express/schema/routing.cjs.map +1 -1
- package/_cjs/api/reportError.cjs +7 -8
- package/_cjs/api/reportError.cjs.map +1 -1
- package/_cjs/api/routing.cjs +26 -25
- package/_cjs/api/routing.cjs.map +1 -1
- package/_cjs/api/setupRequest.cjs +3 -4
- package/_cjs/api/setupRequest.cjs.map +1 -1
- package/_cjs/api/writeDocs.cjs +3 -4
- package/_cjs/api/writeDocs.cjs.map +1 -1
- package/_cjs/errorReporter.cjs +10 -11
- package/_cjs/errorReporter.cjs.map +1 -1
- package/_cjs/errors.cjs +1 -1
- package/_cjs/errors.cjs.map +1 -1
- package/_cjs/filter.cjs +14 -28
- package/_cjs/filter.cjs.map +1 -1
- package/_cjs/instrument.cjs +1 -2
- package/_cjs/instrument.cjs.map +1 -1
- package/_cjs/logger/jsonLogger.cjs +17 -12
- package/_cjs/logger/jsonLogger.cjs.map +1 -1
- package/_cjs/logger/logFmtLogger.cjs +7 -6
- package/_cjs/logger/logFmtLogger.cjs.map +1 -1
- package/_cjs/rateLimit.cjs +13 -5
- package/_cjs/rateLimit.cjs.map +1 -1
- package/_cjs/services/Emailer/Sendgrid.cjs +10 -9
- package/_cjs/services/Emailer/Sendgrid.cjs.map +1 -1
- package/_cjs/services/Emailer/fake.cjs +3 -3
- package/_cjs/services/Emailer/fake.cjs.map +1 -1
- package/_cjs/services/Operations/live.cjs +4 -6
- package/_cjs/services/Operations/live.cjs.map +1 -1
- package/_cjs/services/Operations/service.cjs +5 -7
- package/_cjs/services/Operations/service.cjs.map +1 -1
- package/_cjs/services/QueueMaker/errors.cjs +5 -3
- package/_cjs/services/QueueMaker/errors.cjs.map +1 -1
- package/_cjs/services/QueueMaker/memQueue.cjs +5 -6
- package/_cjs/services/QueueMaker/memQueue.cjs.map +1 -1
- package/_cjs/services/QueueMaker/sbqueue.cjs +9 -10
- package/_cjs/services/QueueMaker/sbqueue.cjs.map +1 -1
- package/_cjs/services/QueueMaker/service.cjs +1 -2
- package/_cjs/services/QueueMaker/service.cjs.map +1 -1
- package/_cjs/services/Repository.cjs +18 -30
- package/_cjs/services/Repository.cjs.map +1 -1
- package/_cjs/services/RepositoryBase.cjs +7 -5
- package/_cjs/services/RepositoryBase.cjs.map +1 -1
- package/_cjs/services/RequestContextContainer.cjs +1 -2
- package/_cjs/services/RequestContextContainer.cjs.map +1 -1
- package/_cjs/services/Store/Cosmos.cjs +68 -58
- package/_cjs/services/Store/Cosmos.cjs.map +1 -1
- package/_cjs/services/Store/Disk.cjs +2 -1
- package/_cjs/services/Store/Disk.cjs.map +1 -1
- package/_cjs/services/Store/Memory.cjs +15 -19
- package/_cjs/services/Store/Memory.cjs.map +1 -1
- package/_cjs/services/Store/Redis.cjs +2 -1
- package/_cjs/services/Store/Redis.cjs.map +1 -1
- package/_cjs/services/Store/index.cjs +4 -3
- package/_cjs/services/Store/index.cjs.map +1 -1
- package/_cjs/services/Store/service.cjs +1 -2
- package/_cjs/services/Store/service.cjs.map +1 -1
- package/_cjs/services/simpledb/cosmosdb.cjs +25 -23
- package/_cjs/services/simpledb/cosmosdb.cjs.map +1 -1
- package/_cjs/services/simpledb/diskdb.cjs +16 -7
- package/_cjs/services/simpledb/diskdb.cjs.map +1 -1
- package/_cjs/services/simpledb/memdb.cjs +1 -1
- package/_cjs/services/simpledb/memdb.cjs.map +1 -1
- package/_cjs/services/simpledb/mongodb.cjs +26 -22
- package/_cjs/services/simpledb/mongodb.cjs.map +1 -1
- package/_cjs/services/simpledb/redisdb.cjs +35 -28
- package/_cjs/services/simpledb/redisdb.cjs.map +1 -1
- package/_cjs/services/simpledb/simpledb.cjs +25 -17
- package/_cjs/services/simpledb/simpledb.cjs.map +1 -1
- package/_cjs/test.arbs.cjs +5 -4
- package/_cjs/test.arbs.cjs.map +1 -1
- package/_src/api/defaultErrorHandler.ts +33 -37
- package/_src/api/express/makeJsonSchema.test.ts +2 -2
- package/_src/api/express/routing.ts.bak +1 -1
- package/_src/api/express/schema/routing.ts +20 -20
- package/_src/api/reportError.ts +15 -19
- package/_src/api/routing.ts +96 -95
- package/_src/api/setupRequest.ts +4 -6
- package/_src/api/writeDocs.ts +1 -1
- package/_src/errorReporter.ts +25 -29
- package/_src/errors.ts +1 -1
- package/_src/instrument.ts +4 -5
- package/_src/logger/jsonLogger.ts +5 -6
- package/_src/logger/logFmtLogger.ts +5 -4
- package/_src/rateLimit.ts +10 -9
- package/_src/services/Emailer/Sendgrid.ts +3 -3
- package/_src/services/Emailer/fake.ts +1 -1
- package/_src/services/Operations/live.ts +1 -1
- package/_src/services/Operations/service.ts +32 -38
- package/_src/services/QueueMaker/errors.ts +1 -2
- package/_src/services/QueueMaker/memQueue.ts +1 -1
- package/_src/services/QueueMaker/sbqueue.ts +3 -3
- package/_src/services/Repository.ts +10 -13
- package/_src/services/RepositoryBase.ts +10 -8
- package/_src/services/Store/Cosmos.ts +66 -62
- package/_src/services/Store/Memory.ts +1 -1
- package/_src/services/simpledb/cosmosdb.ts +45 -43
- package/_src/services/simpledb/diskdb.ts +9 -10
- package/_src/services/simpledb/mongodb.ts +33 -31
- package/_src/services/simpledb/redisdb.ts +42 -40
- package/_src/services/simpledb/simpledb.ts +6 -7
- package/dist/RequestContext.d.ts +4 -4
- package/dist/RequestContext.js +5 -3
- package/dist/api/defaultErrorHandler.d.ts.map +1 -1
- package/dist/api/defaultErrorHandler.js +7 -9
- package/dist/api/express/schema/routing.js +21 -6
- package/dist/api/reportError.d.ts.map +1 -1
- package/dist/api/reportError.js +9 -10
- package/dist/api/routing.d.ts +1 -1
- package/dist/api/routing.d.ts.map +1 -1
- package/dist/api/routing.js +35 -33
- package/dist/api/setupRequest.d.ts.map +1 -1
- package/dist/api/setupRequest.js +4 -5
- package/dist/api/writeDocs.js +4 -5
- package/dist/errorReporter.d.ts.map +1 -1
- package/dist/errorReporter.js +11 -12
- package/dist/errors.js +2 -2
- package/dist/instrument.d.ts.map +1 -1
- package/dist/instrument.js +2 -3
- package/dist/logger/jsonLogger.d.ts +1 -1
- package/dist/logger/jsonLogger.d.ts.map +1 -1
- package/dist/logger/jsonLogger.js +9 -11
- package/dist/logger/logFmtLogger.d.ts +1 -1
- package/dist/logger/logFmtLogger.d.ts.map +1 -1
- package/dist/logger/logFmtLogger.js +5 -4
- package/dist/rateLimit.d.ts.map +1 -1
- package/dist/rateLimit.js +6 -6
- package/dist/services/Emailer/Sendgrid.d.ts +1 -1
- package/dist/services/Emailer/Sendgrid.d.ts.map +1 -1
- package/dist/services/Emailer/Sendgrid.js +11 -10
- package/dist/services/Emailer/fake.js +4 -3
- package/dist/services/Emailer/service.d.ts +1 -1
- package/dist/services/Operations/live.js +5 -6
- package/dist/services/Operations/service.d.ts.map +1 -1
- package/dist/services/Operations/service.js +8 -9
- package/dist/services/QueueMaker/errors.d.ts.map +1 -1
- package/dist/services/QueueMaker/errors.js +2 -2
- package/dist/services/QueueMaker/memQueue.js +6 -7
- package/dist/services/QueueMaker/sbqueue.js +10 -11
- package/dist/services/Repository.d.ts +19 -18
- package/dist/services/Repository.d.ts.map +1 -1
- package/dist/services/Repository.js +8 -9
- package/dist/services/RepositoryBase.d.ts +7 -7
- package/dist/services/RepositoryBase.d.ts.map +1 -1
- package/dist/services/RepositoryBase.js +5 -4
- package/dist/services/Store/Cosmos.d.ts +1 -1
- package/dist/services/Store/Cosmos.d.ts.map +1 -1
- package/dist/services/Store/Cosmos.js +64 -55
- package/dist/services/Store/Disk.d.ts +1 -1
- package/dist/services/Store/Disk.d.ts.map +1 -1
- package/dist/services/Store/Disk.js +3 -2
- package/dist/services/Store/Memory.js +13 -14
- package/dist/services/Store/Redis.d.ts +1 -1
- package/dist/services/Store/Redis.d.ts.map +1 -1
- package/dist/services/Store/Redis.js +3 -2
- package/dist/services/Store/index.d.ts +1 -1
- package/dist/services/Store/index.d.ts.map +1 -1
- package/dist/services/Store/index.js +5 -4
- package/dist/services/Store/service.d.ts +1 -1
- package/dist/services/simpledb/cosmosdb.d.ts.map +1 -1
- package/dist/services/simpledb/cosmosdb.js +29 -27
- package/dist/services/simpledb/diskdb.d.ts.map +1 -1
- package/dist/services/simpledb/diskdb.js +10 -4
- package/dist/services/simpledb/memdb.d.ts +2 -2
- package/dist/services/simpledb/memdb.js +1 -1
- package/dist/services/simpledb/mongodb.d.ts.map +1 -1
- package/dist/services/simpledb/mongodb.js +18 -15
- package/dist/services/simpledb/redisdb.d.ts.map +1 -1
- package/dist/services/simpledb/redisdb.js +30 -23
- package/dist/services/simpledb/simpledb.d.ts.map +1 -1
- package/dist/services/simpledb/simpledb.js +16 -12
- package/package.json +22 -22
- package/tsconfig.json +1 -1
|
@@ -20,18 +20,16 @@ export abstract class Operations extends TagClass<OperationsId, Operations>() {
|
|
|
20
20
|
* @tsplus getter effect/io/Effect forkOperation
|
|
21
21
|
*/
|
|
22
22
|
export function forkOperation<R, E, A>(self: Effect<R, E, A>) {
|
|
23
|
-
return
|
|
24
|
-
Operations
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
)
|
|
34
|
-
)
|
|
23
|
+
return Operations.flatMap(
|
|
24
|
+
(Operations) =>
|
|
25
|
+
Scope
|
|
26
|
+
.make()
|
|
27
|
+
.flatMap((scope) =>
|
|
28
|
+
Operations
|
|
29
|
+
.register
|
|
30
|
+
.extend(scope)
|
|
31
|
+
.tap(() => self.use(scope).forkDaemonReportRequestUnexpected)
|
|
32
|
+
)
|
|
35
33
|
)
|
|
36
34
|
}
|
|
37
35
|
|
|
@@ -39,25 +37,23 @@ export function forkOperation<R, E, A>(self: Effect<R, E, A>) {
|
|
|
39
37
|
* @tsplus getter function forkOperation
|
|
40
38
|
*/
|
|
41
39
|
export function forkOperationFunction<R, E, A, Inp>(fnc: (inp: Inp) => Effect<R, E, A>) {
|
|
42
|
-
return (inp: Inp) =>
|
|
40
|
+
return (inp: Inp) => fnc(inp).forkOperation
|
|
43
41
|
}
|
|
44
42
|
|
|
45
43
|
/**
|
|
46
44
|
* @tsplus static effect/io/Effect.Ops forkOperation
|
|
47
45
|
*/
|
|
48
46
|
export function forkOperation2<R, E, A>(self: (opId: OperationId) => Effect<R, E, A>) {
|
|
49
|
-
return
|
|
50
|
-
Operations
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
)
|
|
60
|
-
)
|
|
47
|
+
return Operations.flatMap(
|
|
48
|
+
(Operations) =>
|
|
49
|
+
Scope
|
|
50
|
+
.make()
|
|
51
|
+
.flatMap((scope) =>
|
|
52
|
+
Operations
|
|
53
|
+
.register
|
|
54
|
+
.extend(scope)
|
|
55
|
+
.tap((id) => self(id).use(scope).forkDaemonReportRequestUnexpected)
|
|
56
|
+
)
|
|
61
57
|
)
|
|
62
58
|
}
|
|
63
59
|
|
|
@@ -68,18 +64,16 @@ export function forkOperationWithEffect<R, R2, E, E2, A, A2>(
|
|
|
68
64
|
self: (id: OperationId) => Effect<R, E, A>,
|
|
69
65
|
fnc: (id: OperationId) => Effect<R2, E2, A2>
|
|
70
66
|
) {
|
|
71
|
-
return
|
|
72
|
-
Operations
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
)
|
|
83
|
-
)
|
|
67
|
+
return Operations.flatMap(
|
|
68
|
+
(Operations) =>
|
|
69
|
+
Scope
|
|
70
|
+
.make()
|
|
71
|
+
.flatMap((scope) =>
|
|
72
|
+
Operations
|
|
73
|
+
.register
|
|
74
|
+
.extend(scope)
|
|
75
|
+
.tap((opId) => self(opId).use(scope).forkDaemonReportRequestUnexpected)
|
|
76
|
+
.tap((opId) => fnc(opId).interruptible.forkScoped.extend(scope))
|
|
77
|
+
)
|
|
84
78
|
)
|
|
85
79
|
}
|
|
@@ -42,8 +42,7 @@ export function reportNonInterruptedFailure(context?: Record<string, unknown>) {
|
|
|
42
42
|
.exit
|
|
43
43
|
.flatMap((result) =>
|
|
44
44
|
result.match(
|
|
45
|
-
(cause) => report(cause).map(() => result),
|
|
46
|
-
() => Effect(result)
|
|
45
|
+
{ onFailure: (cause) => report(cause).map(() => result), onSuccess: () => Effect(result) }
|
|
47
46
|
)
|
|
48
47
|
)
|
|
49
48
|
}
|
|
@@ -66,7 +66,7 @@ export function makeMemQueue<
|
|
|
66
66
|
.flatMap(({ body, meta }) =>
|
|
67
67
|
Effect
|
|
68
68
|
.logDebug(`$$ [${queueDrainName}] Processing incoming message`)
|
|
69
|
-
.apply(Effect.
|
|
69
|
+
.apply(Effect.annotateLogs({ body: body.$$.pretty, meta: meta.$$.pretty }))
|
|
70
70
|
.tap(() => restoreFromRequestContext)
|
|
71
71
|
.zipRight(handleEvent(body))
|
|
72
72
|
.apply(silenceAndReportError)
|
|
@@ -58,7 +58,7 @@ export function makeServiceBusQueue<
|
|
|
58
58
|
.flatMap(({ body, meta }) =>
|
|
59
59
|
Effect
|
|
60
60
|
.logDebug(`$$ [${queueDrainName}] Processing incoming message`)
|
|
61
|
-
.apply(Effect.
|
|
61
|
+
.apply(Effect.annotateLogs({ body: body.$$.pretty, meta: meta.$$.pretty }))
|
|
62
62
|
.tap(() => restoreFromRequestContext)
|
|
63
63
|
.zipRight(handleEvent(body))
|
|
64
64
|
.orDie
|
|
@@ -80,10 +80,10 @@ export function makeServiceBusQueue<
|
|
|
80
80
|
|
|
81
81
|
return yield* $(
|
|
82
82
|
subscribe({
|
|
83
|
-
processMessage: (x) => processMessage(x.body).uninterruptible
|
|
83
|
+
processMessage: (x) => processMessage(x.body).uninterruptible,
|
|
84
84
|
processError: (err) => Effect(captureException(err.error))
|
|
85
85
|
})
|
|
86
|
-
.
|
|
86
|
+
.provide(receiverLayer)
|
|
87
87
|
)
|
|
88
88
|
}),
|
|
89
89
|
|
|
@@ -9,6 +9,7 @@ import { ContextMap } from "../services/Store.js"
|
|
|
9
9
|
import type { Filter } from "../services/Store.js"
|
|
10
10
|
import type { RequestContextContainer } from "./RequestContextContainer.js"
|
|
11
11
|
|
|
12
|
+
export type RequestCTX = ContextMap | RequestContextContainer
|
|
12
13
|
/**
|
|
13
14
|
* @tsplus type Repository
|
|
14
15
|
*/
|
|
@@ -19,16 +20,16 @@ export interface Repository<
|
|
|
19
20
|
ItemType extends string
|
|
20
21
|
> {
|
|
21
22
|
itemType: ItemType
|
|
22
|
-
find: (id: T["id"]) => Effect<
|
|
23
|
+
find: (id: T["id"]) => Effect<RequestCTX, never, Option<T>>
|
|
23
24
|
all: Effect<ContextMap, never, T[]>
|
|
24
25
|
saveAndPublish: (
|
|
25
26
|
items: Iterable<T>,
|
|
26
27
|
events?: Iterable<Evt>
|
|
27
|
-
) => Effect<
|
|
28
|
+
) => Effect<RequestCTX, InvalidStateError | OptimisticConcurrencyException, void>
|
|
28
29
|
removeAndPublish: (
|
|
29
30
|
items: Iterable<T>,
|
|
30
31
|
events?: Iterable<Evt>
|
|
31
|
-
) => Effect<
|
|
32
|
+
) => Effect<RequestCTX, never, void>
|
|
32
33
|
utils: {
|
|
33
34
|
mapReverse: (
|
|
34
35
|
pm: PM,
|
|
@@ -271,10 +272,8 @@ export function queryAndSavePureEffect<
|
|
|
271
272
|
map: Effect<R, E, { filter: Filter<PM>; collect?: (t: T) => Option<S>; limit?: number; skip?: number }>
|
|
272
273
|
) {
|
|
273
274
|
return <R2, A, E2, S2 extends T>(pure: Effect<FixEnv<R2, Evt, S[], S2[]>, E2, A>) =>
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
.flatMap(restore((_) => self.saveManyWithPure_(_, pure)))
|
|
277
|
-
)
|
|
275
|
+
queryEffect(self, map)
|
|
276
|
+
.flatMap((_) => self.saveManyWithPure_(_, pure))
|
|
278
277
|
}
|
|
279
278
|
|
|
280
279
|
/**
|
|
@@ -401,12 +400,10 @@ export function saveAllWithEffectInt<
|
|
|
401
400
|
self: Repository<T, PM, Evt, ItemType>,
|
|
402
401
|
gen: Effect<R, E, readonly [Iterable<P>, Iterable<Evt>, A]>
|
|
403
402
|
) {
|
|
404
|
-
return
|
|
405
|
-
|
|
406
|
-
.
|
|
407
|
-
|
|
408
|
-
)
|
|
409
|
-
)
|
|
403
|
+
return gen
|
|
404
|
+
.flatMap(
|
|
405
|
+
([items, events, a]) => self.saveAndPublish(items, events).map(() => a)
|
|
406
|
+
)
|
|
410
407
|
}
|
|
411
408
|
|
|
412
409
|
/**
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { ParserEnv } from "@effect-app/schema/custom/Parser"
|
|
2
|
-
import type { Repository } from "./Repository.js"
|
|
2
|
+
import type { Repository, RequestCTX } from "./Repository.js"
|
|
3
3
|
import type { RequestContextContainer } from "./RequestContextContainer.js"
|
|
4
4
|
import { ContextMap, StoreMaker } from "./Store.js"
|
|
5
5
|
import type { Filter, StoreConfig, Where } from "./Store.js"
|
|
@@ -94,7 +94,7 @@ export function makeRepo<
|
|
|
94
94
|
const mkStore = makeStore<PM>()(name, schema, mapTo)
|
|
95
95
|
|
|
96
96
|
function make(
|
|
97
|
-
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<
|
|
97
|
+
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<RequestCTX, never, void>,
|
|
98
98
|
makeInitial?: Effect<never, never, readonly T[]>,
|
|
99
99
|
config?: Omit<StoreConfig<PM>, "partitionValue"> & {
|
|
100
100
|
partitionValue?: (a: PM) => string
|
|
@@ -110,7 +110,9 @@ export function makeRepo<
|
|
|
110
110
|
})
|
|
111
111
|
)
|
|
112
112
|
|
|
113
|
-
const
|
|
113
|
+
const parse = EParserFor(schema).condemnDie
|
|
114
|
+
|
|
115
|
+
const all = allE.flatMap((_) => _.forEachEffect((_) => parse(_)))
|
|
114
116
|
|
|
115
117
|
function findE(id: T["id"]) {
|
|
116
118
|
return store
|
|
@@ -311,7 +313,7 @@ export const RepositoryBaseImpl = <Service>() => {
|
|
|
311
313
|
mapTo: (e: E, etag: string | undefined) => PM
|
|
312
314
|
): (abstract new() => Repository<T, PM, Evt, ItemType>) & Tag<Service, Service> & {
|
|
313
315
|
make(
|
|
314
|
-
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<
|
|
316
|
+
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<RequestCTX, never, void>,
|
|
315
317
|
makeInitial?: Effect<never, never, readonly T[]>,
|
|
316
318
|
config?: Omit<StoreConfig<PM>, "partitionValue"> & {
|
|
317
319
|
partitionValue?: (a: PM) => string
|
|
@@ -345,14 +347,14 @@ export const RepositoryDefaultImpl = <Service>() => {
|
|
|
345
347
|
impl: Repository<T, PM, Evt, ItemType>
|
|
346
348
|
): Repository<T, PM, Evt, ItemType>
|
|
347
349
|
make(
|
|
348
|
-
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<
|
|
350
|
+
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<RequestCTX, never, void>,
|
|
349
351
|
makeInitial?: Effect<never, never, readonly T[]>,
|
|
350
352
|
config?: Omit<StoreConfig<PM>, "partitionValue"> & {
|
|
351
353
|
partitionValue?: (a: PM) => string
|
|
352
354
|
}
|
|
353
355
|
): Effect<StoreMaker, never, Repository<T, PM, Evt, ItemType>>
|
|
354
356
|
toLayer(
|
|
355
|
-
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<
|
|
357
|
+
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<RequestCTX, never, void>,
|
|
356
358
|
makeInitial?: Effect<never, never, readonly T[]>,
|
|
357
359
|
config?: Omit<StoreConfig<PM>, "partitionValue"> & {
|
|
358
360
|
partitionValue?: (a: PM) => string
|
|
@@ -366,7 +368,7 @@ export const RepositoryDefaultImpl = <Service>() => {
|
|
|
366
368
|
} => {
|
|
367
369
|
return class extends RepositoryBaseImpl<Service>()<PM, Evt>()(itemType, schema, mapFrom, mapTo) {
|
|
368
370
|
static toLayer(
|
|
369
|
-
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<
|
|
371
|
+
publishEvents: (evt: NonEmptyReadonlyArray<Evt>) => Effect<RequestCTX, never, void>,
|
|
370
372
|
makeInitial?: Effect<never, never, readonly T[]>,
|
|
371
373
|
config?: Omit<StoreConfig<PM>, "partitionValue"> & {
|
|
372
374
|
partitionValue?: (a: PM) => string
|
|
@@ -383,6 +385,6 @@ export const RepositoryDefaultImpl = <Service>() => {
|
|
|
383
385
|
super()
|
|
384
386
|
Object.assign(this, impl)
|
|
385
387
|
}
|
|
386
|
-
}
|
|
388
|
+
} as any // TODO: seems to be a compiler bug, it somehow says its missing toLayer and repo...
|
|
387
389
|
}
|
|
388
390
|
}
|
|
@@ -53,25 +53,26 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
53
53
|
(x) =>
|
|
54
54
|
[
|
|
55
55
|
x,
|
|
56
|
-
Option.fromNullable(x._etag).match(
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
56
|
+
Option.fromNullable(x._etag).match({
|
|
57
|
+
onNone: () => ({
|
|
58
|
+
operationType: "Create" as const,
|
|
59
|
+
resourceBody: {
|
|
60
|
+
...omit(x, "_etag"),
|
|
61
|
+
_partitionKey: config?.partitionValue(x)
|
|
62
|
+
} as any,
|
|
63
|
+
partitionKey: config?.partitionValue(x)
|
|
64
|
+
}),
|
|
65
|
+
onSome: (eTag) => ({
|
|
66
|
+
operationType: "Replace" as const,
|
|
67
|
+
id: x.id,
|
|
68
|
+
resourceBody: {
|
|
69
|
+
...omit(x, "_etag"),
|
|
70
|
+
_partitionKey: config?.partitionValue(x)
|
|
71
|
+
} as any,
|
|
72
|
+
ifMatch: eTag,
|
|
73
|
+
partitionKey: config?.partitionValue(x)
|
|
74
|
+
})
|
|
75
|
+
}
|
|
75
76
|
)
|
|
76
77
|
] as const
|
|
77
78
|
)
|
|
@@ -122,7 +123,7 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
122
123
|
return batchResult.flat() as unknown as NonEmptyReadonlyArray<PM>
|
|
123
124
|
})
|
|
124
125
|
.instrument("cosmos.bulkSet")
|
|
125
|
-
.
|
|
126
|
+
.annotateLogs("cosmos.db", containerId)
|
|
126
127
|
|
|
127
128
|
const batchSet = (items: NonEmptyReadonlyArray<PM>) => {
|
|
128
129
|
return Effect
|
|
@@ -131,23 +132,24 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
131
132
|
(x) =>
|
|
132
133
|
[
|
|
133
134
|
x,
|
|
134
|
-
Option.fromNullable(x._etag).match(
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
135
|
+
Option.fromNullable(x._etag).match({
|
|
136
|
+
onNone: () => ({
|
|
137
|
+
operationType: "Create" as const,
|
|
138
|
+
resourceBody: {
|
|
139
|
+
...omit(x, "_etag"),
|
|
140
|
+
_partitionKey: config?.partitionValue(x)
|
|
141
|
+
} as any
|
|
142
|
+
}),
|
|
143
|
+
onSome: (eTag) => ({
|
|
144
|
+
operationType: "Replace" as const,
|
|
145
|
+
id: x.id,
|
|
146
|
+
resourceBody: {
|
|
147
|
+
...omit(x, "_etag"),
|
|
148
|
+
_partitionKey: config?.partitionValue(x)
|
|
149
|
+
} as any,
|
|
150
|
+
ifMatch: eTag
|
|
151
|
+
})
|
|
152
|
+
}
|
|
151
153
|
)
|
|
152
154
|
] as const
|
|
153
155
|
)
|
|
@@ -185,7 +187,7 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
185
187
|
)
|
|
186
188
|
})
|
|
187
189
|
.instrument("cosmos.batchSet")
|
|
188
|
-
.
|
|
190
|
+
.annotateLogs("cosmos.db", containerId)
|
|
189
191
|
}
|
|
190
192
|
|
|
191
193
|
const s: Store<PM, Id> = {
|
|
@@ -204,7 +206,7 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
204
206
|
)
|
|
205
207
|
)
|
|
206
208
|
.instrument("cosmos.all")
|
|
207
|
-
.
|
|
209
|
+
.annotateLogs("cosmos.db", containerId),
|
|
208
210
|
filterJoinSelect: <T extends object>(
|
|
209
211
|
filter: FilterJoinSelect,
|
|
210
212
|
cursor?: { skip?: number; limit?: number }
|
|
@@ -236,7 +238,7 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
236
238
|
return v
|
|
237
239
|
})
|
|
238
240
|
.instrument("cosmos.filterJoinSelect")
|
|
239
|
-
.
|
|
241
|
+
.annotateLogs("cosmos.db", containerId),
|
|
240
242
|
/**
|
|
241
243
|
* May return duplicate results for "join_find", when matching more than once.
|
|
242
244
|
*/
|
|
@@ -277,7 +279,7 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
277
279
|
)
|
|
278
280
|
))
|
|
279
281
|
.instrument("cosmos.filter")
|
|
280
|
-
.
|
|
282
|
+
.annotateLogs("cosmos.db", containerId)
|
|
281
283
|
},
|
|
282
284
|
find: (id) =>
|
|
283
285
|
Effect
|
|
@@ -288,30 +290,32 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
288
290
|
.then(({ resource }) => Option.fromNullable(resource))
|
|
289
291
|
)
|
|
290
292
|
.instrument("cosmos.find")
|
|
291
|
-
.
|
|
293
|
+
.annotateLogs("cosmos.db", containerId),
|
|
292
294
|
set: (e) =>
|
|
293
295
|
Option
|
|
294
296
|
.fromNullable(e._etag)
|
|
295
297
|
.match(
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
298
|
+
{
|
|
299
|
+
onNone: () =>
|
|
300
|
+
Effect.promise(() =>
|
|
301
|
+
container.items.create({
|
|
302
|
+
...e,
|
|
303
|
+
_partitionKey: config?.partitionValue(e)
|
|
304
|
+
})
|
|
305
|
+
),
|
|
306
|
+
onSome: (eTag) =>
|
|
307
|
+
Effect.promise(() =>
|
|
308
|
+
container.item(e.id, config?.partitionValue(e)).replace(
|
|
309
|
+
{ ...e, _partitionKey: config?.partitionValue(e) },
|
|
310
|
+
{
|
|
311
|
+
accessCondition: {
|
|
312
|
+
type: "IfMatch",
|
|
313
|
+
condition: eTag
|
|
314
|
+
}
|
|
311
315
|
}
|
|
312
|
-
|
|
316
|
+
)
|
|
313
317
|
)
|
|
314
|
-
|
|
318
|
+
}
|
|
315
319
|
)
|
|
316
320
|
.flatMap((x) => {
|
|
317
321
|
if (x.statusCode === 412 || x.statusCode === 404) {
|
|
@@ -330,14 +334,14 @@ export function makeCosmosStore({ prefix }: StorageConfig) {
|
|
|
330
334
|
})
|
|
331
335
|
})
|
|
332
336
|
.instrument("cosmos.set")
|
|
333
|
-
.
|
|
337
|
+
.annotateLogs("cosmos.db", containerId),
|
|
334
338
|
batchSet,
|
|
335
339
|
bulkSet,
|
|
336
340
|
remove: (e: PM) =>
|
|
337
341
|
Effect
|
|
338
342
|
.promise(() => container.item(e.id, config?.partitionValue(e)).delete())
|
|
339
343
|
.instrument("cosmos.remove")
|
|
340
|
-
.
|
|
344
|
+
.annotateLogs("cosmos.db", containerId)
|
|
341
345
|
}
|
|
342
346
|
|
|
343
347
|
// handle mock data
|
|
@@ -390,7 +394,7 @@ function logQuery(q: {
|
|
|
390
394
|
}) {
|
|
391
395
|
return Effect
|
|
392
396
|
.logDebug("cosmos query")
|
|
393
|
-
.apply(Effect.
|
|
397
|
+
.apply(Effect.annotateLogs({
|
|
394
398
|
query: q.query,
|
|
395
399
|
parameters: JSON.stringify(
|
|
396
400
|
q.parameters.reduce((acc, v) => {
|
|
@@ -31,7 +31,7 @@ export const restoreFromRequestContext = RequestContextContainer.get.flatMap((ct
|
|
|
31
31
|
function logQuery(filter: any, cursor: any) {
|
|
32
32
|
return Effect
|
|
33
33
|
.logDebug("mem query")
|
|
34
|
-
.apply(Effect.
|
|
34
|
+
.apply(Effect.annotateLogs({
|
|
35
35
|
query: JSON.stringify(filter, undefined, 2),
|
|
36
36
|
cursor: JSON.stringify(
|
|
37
37
|
cursor,
|
|
@@ -90,51 +90,53 @@ WHERE (
|
|
|
90
90
|
|
|
91
91
|
yield* $(
|
|
92
92
|
currentVersion.match(
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
93
|
+
{
|
|
94
|
+
onNone: () =>
|
|
95
|
+
Effect
|
|
96
|
+
.tryPromise(() =>
|
|
97
|
+
db.container(type).items.create({
|
|
98
|
+
id: record.id,
|
|
99
|
+
timestamp: new Date(),
|
|
100
|
+
data
|
|
101
|
+
})
|
|
102
|
+
)
|
|
103
|
+
.asUnit
|
|
104
|
+
.orDie,
|
|
105
|
+
onSome: (currentVersion) =>
|
|
106
|
+
Effect
|
|
107
|
+
.tryPromise(() =>
|
|
108
|
+
db
|
|
109
|
+
.container(type)
|
|
110
|
+
.item(record.id)
|
|
111
|
+
.replace(
|
|
112
|
+
{
|
|
113
|
+
id: record.id,
|
|
114
|
+
timestamp: new Date(),
|
|
115
|
+
data
|
|
116
|
+
},
|
|
117
|
+
{
|
|
118
|
+
accessCondition: {
|
|
119
|
+
type: "IfMatch",
|
|
120
|
+
condition: currentVersion
|
|
121
|
+
}
|
|
120
122
|
}
|
|
121
|
-
}
|
|
122
|
-
)
|
|
123
|
-
)
|
|
124
|
-
.orDie
|
|
125
|
-
.flatMap((x) => {
|
|
126
|
-
if (x.statusCode === 412) {
|
|
127
|
-
return Effect.fail(new OptimisticLockException(type, record.id))
|
|
128
|
-
}
|
|
129
|
-
if (x.statusCode > 299 || x.statusCode < 200) {
|
|
130
|
-
return Effect.die(
|
|
131
|
-
new CosmosDbOperationError(
|
|
132
|
-
"not able to update record: " + x.statusCode
|
|
133
123
|
)
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
124
|
+
)
|
|
125
|
+
.orDie
|
|
126
|
+
.flatMap((x) => {
|
|
127
|
+
if (x.statusCode === 412) {
|
|
128
|
+
return Effect.fail(new OptimisticLockException(type, record.id))
|
|
129
|
+
}
|
|
130
|
+
if (x.statusCode > 299 || x.statusCode < 200) {
|
|
131
|
+
return Effect.die(
|
|
132
|
+
new CosmosDbOperationError(
|
|
133
|
+
"not able to update record: " + x.statusCode
|
|
134
|
+
)
|
|
135
|
+
)
|
|
136
|
+
}
|
|
137
|
+
return Effect.unit
|
|
138
|
+
})
|
|
139
|
+
}
|
|
138
140
|
)
|
|
139
141
|
)
|
|
140
142
|
return { version, data: record } as CachedRecord<A>
|
|
@@ -78,10 +78,10 @@ export function createContext<TKey extends string, EA, A extends DBRecord<TKey>>
|
|
|
78
78
|
function lockRecordOnDisk(type: string) {
|
|
79
79
|
return (id: string) =>
|
|
80
80
|
lockFile(getFilename(type, id))
|
|
81
|
-
.mapBoth(
|
|
82
|
-
(err) => new CouldNotAquireDbLockException(type, id, err as Error),
|
|
83
|
-
(release) => ({ release })
|
|
84
|
-
)
|
|
81
|
+
.mapBoth({
|
|
82
|
+
onFailure: (err) => new CouldNotAquireDbLockException(type, id, err as Error),
|
|
83
|
+
onSuccess: (release) => ({ release })
|
|
84
|
+
})
|
|
85
85
|
.acquireRelease(
|
|
86
86
|
(l) => l.release
|
|
87
87
|
)
|
|
@@ -90,10 +90,10 @@ export function createContext<TKey extends string, EA, A extends DBRecord<TKey>>
|
|
|
90
90
|
function lockIndexOnDisk(type: string) {
|
|
91
91
|
return (id: string) =>
|
|
92
92
|
lockFile(getIdxName(type, id))
|
|
93
|
-
.mapBoth(
|
|
94
|
-
(err) => new CouldNotAquireDbLockException(type, id, err as Error),
|
|
95
|
-
(release) => ({ release })
|
|
96
|
-
)
|
|
93
|
+
.mapBoth({
|
|
94
|
+
onFailure: (err) => new CouldNotAquireDbLockException(type, id, err as Error),
|
|
95
|
+
onSuccess: (release) => ({ release })
|
|
96
|
+
})
|
|
97
97
|
.acquireRelease(
|
|
98
98
|
(l) => l.release
|
|
99
99
|
)
|
|
@@ -121,8 +121,7 @@ export function createContext<TKey extends string, EA, A extends DBRecord<TKey>>
|
|
|
121
121
|
return tryRead(getIdxName(type, index.doc)).map(
|
|
122
122
|
(_) =>
|
|
123
123
|
_.match(
|
|
124
|
-
() => ({} as Record<string, TKey>),
|
|
125
|
-
(x) => JSON.parse(x) as Record<string, TKey>
|
|
124
|
+
{ onNone: () => ({} as Record<string, TKey>), onSome: (x) => JSON.parse(x) as Record<string, TKey> }
|
|
126
125
|
)
|
|
127
126
|
)
|
|
128
127
|
}
|