@owlmeans/context 0.1.18-rc.3 → 0.1.18-rc.30
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +255 -50
- package/agent-meta/manifest.json +5 -5
- package/agent-meta/skills/owlmeans-context/SKILL.md +25 -0
- package/build/config.d.ts.map +1 -1
- package/build/config.js +0 -2
- package/build/config.js.map +1 -1
- package/build/consts.d.ts +1 -9
- package/build/consts.d.ts.map +1 -1
- package/build/consts.js +0 -9
- package/build/consts.js.map +1 -1
- package/build/context.d.ts.map +1 -1
- package/build/context.js +26 -109
- package/build/context.js.map +1 -1
- package/build/helper.d.ts +0 -1
- package/build/helper.d.ts.map +1 -1
- package/build/helper.js +4 -13
- package/build/helper.js.map +1 -1
- package/build/types.d.ts +21 -23
- package/build/types.d.ts.map +1 -1
- package/build/utils/context.d.ts +2 -7
- package/build/utils/context.d.ts.map +1 -1
- package/build/utils/context.js +0 -11
- package/build/utils/context.js.map +1 -1
- package/build/utils/index.d.ts +0 -1
- package/build/utils/index.d.ts.map +1 -1
- package/build/utils/index.js +0 -1
- package/build/utils/index.js.map +1 -1
- package/package.json +1 -1
- package/src/config.ts +1 -2
- package/src/consts.ts +1 -10
- package/src/context.ts +32 -134
- package/src/helper.ts +4 -18
- package/src/types.ts +22 -26
- package/src/utils/context.ts +2 -20
- package/src/utils/index.ts +0 -1
- package/tests/context.ts +1 -2
- package/tests/service.spec.ts +1 -1
- package/agent-meta/skills/context/SKILL.md +0 -53
- package/build/.gitkeep +0 -0
- package/build/utils/layer.d.ts +0 -6
- package/build/utils/layer.d.ts.map +0 -1
- package/build/utils/layer.js +0 -12
- package/build/utils/layer.js.map +0 -1
- package/src/utils/layer.ts +0 -17
package/src/context.ts
CHANGED
|
@@ -1,19 +1,21 @@
|
|
|
1
|
-
import { ContextStage,
|
|
2
|
-
import type {
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
import {
|
|
1
|
+
import { ContextStage, MiddlewareStage, MiddlewareType } from './consts.js'
|
|
2
|
+
import type {
|
|
3
|
+
BasicConfig, BasicContext, Middleware, BasicEntrypoint, BasicResource, EntrypointReference, Service
|
|
4
|
+
} from './types.js'
|
|
5
|
+
import { applyMiddlewares, getMiddlerwareKey } from './utils/context.js'
|
|
6
6
|
|
|
7
7
|
type Entrypoint = BasicEntrypoint
|
|
8
8
|
|
|
9
9
|
export const makeBasicContext = <C extends BasicConfig>(cfg: C): BasicContext<C> => {
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
10
|
+
/**
|
|
11
|
+
* One flat registry per kind, keyed by alias. Registering an alias twice replaces the
|
|
12
|
+
* earlier entry — application entrypoint lists are routinely spread together and the
|
|
13
|
+
* later declaration is the one the app means.
|
|
14
|
+
*/
|
|
15
|
+
const services: Record<string, Service> = {}
|
|
16
|
+
const entrypoints: Record<string, Entrypoint> = {}
|
|
17
|
+
const resources: Record<string, BasicResource> = {}
|
|
13
18
|
const middlewares: Record<string, Middleware[]> = {}
|
|
14
|
-
const allServices: Record<string, Service> = {}
|
|
15
|
-
const allEntrypoints: Record<string, Entrypoint> = {}
|
|
16
|
-
const allResources: Record<string, BasicResource> = {}
|
|
17
19
|
|
|
18
20
|
let configure: (res: boolean) => void
|
|
19
21
|
let initialize: (resv: boolean) => void
|
|
@@ -21,8 +23,6 @@ export const makeBasicContext = <C extends BasicConfig>(cfg: C): BasicContext<C>
|
|
|
21
23
|
const configured = new Promise<boolean>(resolve => { configure = resolve })
|
|
22
24
|
const initialized = new Promise<boolean>(resolve => { initialize = resolve })
|
|
23
25
|
|
|
24
|
-
// const contexts: Record<string, BasicContext<C>> = {}
|
|
25
|
-
|
|
26
26
|
const inLazyInit = new Set<Service>()
|
|
27
27
|
|
|
28
28
|
const context: BasicContext<C> = {
|
|
@@ -59,7 +59,7 @@ export const makeBasicContext = <C extends BasicConfig>(cfg: C): BasicContext<C>
|
|
|
59
59
|
|
|
60
60
|
await applyMiddlewares<C, BasicContext<C>>(context, middlewares, MiddlewareType.Context, MiddlewareStage.Configuration)
|
|
61
61
|
|
|
62
|
-
await
|
|
62
|
+
await Object.values(services).reduce(
|
|
63
63
|
async (previous, service) => {
|
|
64
64
|
await previous
|
|
65
65
|
if (!service.initialized) {
|
|
@@ -75,12 +75,9 @@ export const makeBasicContext = <C extends BasicConfig>(cfg: C): BasicContext<C>
|
|
|
75
75
|
|
|
76
76
|
await applyMiddlewares<C, BasicContext<C>>(context, middlewares, MiddlewareType.Config, MiddlewareStage.Loading)
|
|
77
77
|
|
|
78
|
-
|
|
79
|
-
await Object.values(resources[context.cfg.layer][id]).reduce(async (previous, resource) => {
|
|
78
|
+
await Object.values(resources).reduce(async (previous, resource) => {
|
|
80
79
|
await previous
|
|
81
|
-
|
|
82
|
-
await resource.init?.()
|
|
83
|
-
}
|
|
80
|
+
await resource.init?.()
|
|
84
81
|
}, Promise.resolve())
|
|
85
82
|
|
|
86
83
|
await applyMiddlewares<C, BasicContext<C>>(context, middlewares, MiddlewareType.Context, MiddlewareStage.Loading)
|
|
@@ -95,24 +92,13 @@ export const makeBasicContext = <C extends BasicConfig>(cfg: C): BasicContext<C>
|
|
|
95
92
|
},
|
|
96
93
|
|
|
97
94
|
registerService: <T>(service: Service) => {
|
|
98
|
-
|
|
99
|
-
service = service.registerContext(context)
|
|
100
|
-
|
|
101
|
-
if (allServices[service.alias] == null) {
|
|
102
|
-
allServices[service.alias] = service
|
|
103
|
-
}
|
|
104
|
-
services[context.cfg.layer][id][service.alias] = service
|
|
95
|
+
services[service.alias] = service.registerContext(context)
|
|
105
96
|
|
|
106
97
|
return context as T
|
|
107
98
|
},
|
|
108
99
|
|
|
109
100
|
registerEntrypoint: <T>(entrypoint: Entrypoint) => {
|
|
110
|
-
|
|
111
|
-
entrypoint = entrypoint.registerContext(context)
|
|
112
|
-
if (allEntrypoints[entrypoint.alias] == null) {
|
|
113
|
-
allEntrypoints[entrypoint.alias] = entrypoint
|
|
114
|
-
}
|
|
115
|
-
entrypoints[context.cfg.layer][id][entrypoint.alias] = entrypoint
|
|
101
|
+
entrypoints[entrypoint.alias] = entrypoint.registerContext(context)
|
|
116
102
|
|
|
117
103
|
return context as T
|
|
118
104
|
},
|
|
@@ -122,19 +108,8 @@ export const makeBasicContext = <C extends BasicConfig>(cfg: C): BasicContext<C>
|
|
|
122
108
|
return context as T
|
|
123
109
|
},
|
|
124
110
|
|
|
125
|
-
/** @deprecated use registerEntrypoint */
|
|
126
|
-
registerModule: <T>(module: BasicModule) => context.registerEntrypoint(module as unknown as Entrypoint) as T,
|
|
127
|
-
|
|
128
|
-
/** @deprecated use registerEntrypoints */
|
|
129
|
-
registerModules: <T>(mods: BasicModule[]) => context.registerEntrypoints(mods as unknown as Entrypoint[]) as T,
|
|
130
|
-
|
|
131
111
|
registerResource: <T>(resource: BasicResource) => {
|
|
132
|
-
|
|
133
|
-
resource = resource.registerContext(context)
|
|
134
|
-
if (allResources[resource.alias] == null) {
|
|
135
|
-
allResources[resource.alias] = resource
|
|
136
|
-
}
|
|
137
|
-
resources[context.cfg.layer][id][resource.alias] = resource
|
|
112
|
+
resources[resource.alias] = resource.registerContext(context)
|
|
138
113
|
|
|
139
114
|
return context as T
|
|
140
115
|
},
|
|
@@ -154,15 +129,9 @@ export const makeBasicContext = <C extends BasicConfig>(cfg: C): BasicContext<C>
|
|
|
154
129
|
},
|
|
155
130
|
|
|
156
131
|
service: <T>(alias: string) => {
|
|
157
|
-
const
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
if (services[context.cfg.layer]?.[id]?.[alias] != null) {
|
|
161
|
-
_service = services[context.cfg.layer][id][alias]
|
|
162
|
-
} else if (services[Layer.Global]?.[id]?.[alias] != null) {
|
|
163
|
-
_service = services[context.cfg.layer][id][alias]
|
|
164
|
-
} else {
|
|
165
|
-
throw new SyntaxError(`Service ${alias} not found in layer ${context.cfg.layer}`)
|
|
132
|
+
const _service = services[alias]
|
|
133
|
+
if (_service == null) {
|
|
134
|
+
throw new SyntaxError(`Service ${alias} not found`)
|
|
166
135
|
}
|
|
167
136
|
if (!_service.initialized) {
|
|
168
137
|
if (_service.lazyInit != null) {
|
|
@@ -179,99 +148,28 @@ export const makeBasicContext = <C extends BasicConfig>(cfg: C): BasicContext<C>
|
|
|
179
148
|
return _service as T
|
|
180
149
|
},
|
|
181
150
|
|
|
182
|
-
entrypoint: <T extends Entrypoint>(
|
|
183
|
-
const
|
|
184
|
-
if (entrypoints[
|
|
185
|
-
return entrypoints[
|
|
151
|
+
entrypoint: <T extends Entrypoint>(reference: EntrypointReference<T> | string) => {
|
|
152
|
+
const alias = typeof reference === 'string' ? reference : reference.alias
|
|
153
|
+
if (entrypoints[alias] != null) {
|
|
154
|
+
return entrypoints[alias] as T
|
|
186
155
|
}
|
|
187
156
|
throw new SyntaxError(`Entrypoint ${alias} not found`)
|
|
188
157
|
},
|
|
189
158
|
|
|
190
|
-
/** @deprecated use entrypoint */
|
|
191
|
-
module: <T>(alias: string) => context.entrypoint<any>(alias) as T,
|
|
192
|
-
|
|
193
159
|
resource: <T extends BasicResource>(alias: string) => {
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
const resource = resources[context.cfg.layer][id][alias] as T
|
|
197
|
-
|
|
198
|
-
return resource
|
|
160
|
+
if (resources[alias] != null) {
|
|
161
|
+
return resources[alias] as T
|
|
199
162
|
}
|
|
200
163
|
throw new SyntaxError(`Resource ${alias} not found`)
|
|
201
164
|
},
|
|
202
165
|
|
|
203
|
-
entrypoints: <T extends Entrypoint>() =>
|
|
204
|
-
const id = initializeLayer(entrypoints, context.cfg.layer, context.cfg.layerId)
|
|
205
|
-
return Object.values(entrypoints[context.cfg.layer][id]) as T[]
|
|
206
|
-
},
|
|
207
|
-
|
|
208
|
-
/** @deprecated use entrypoints */
|
|
209
|
-
modules: <T>() => context.entrypoints<any>() as T[],
|
|
210
|
-
|
|
211
|
-
/**
|
|
212
|
-
* @TODO Unfortunatly module cloning between contexts is quite unstable.
|
|
213
|
-
* And it looks like in some cases it relies on modules that aren't really clonned.
|
|
214
|
-
* The problem is that the not cloned modules are changing their context accross all context
|
|
215
|
-
* layers and we can't rely on such behaviour.
|
|
216
|
-
* So we disabled context update as a whole and all functionality that relies on it
|
|
217
|
-
* cause in curent release mixed tenancy is not in use in any project and it looks like
|
|
218
|
-
* there is no short term plans to use it some way.
|
|
219
|
-
*/
|
|
220
|
-
updateContext: async <T>(_id?: string, _layer?: Layer) => {
|
|
221
|
-
return context as T
|
|
222
|
-
|
|
223
|
-
// const index = layersOrder.indexOf(context.cfg.layer)
|
|
224
|
-
// layer = layer ?? (layersOrder[index + 1] != null ? layersOrder[index + 1] : undefined)
|
|
225
|
-
// if (layer == null) {
|
|
226
|
-
// throw new SyntaxError("There is no next layer to switch to")
|
|
227
|
-
// }
|
|
228
|
-
|
|
229
|
-
// if ([Layer.Entity, Layer.User].includes(layer) && id == null) {
|
|
230
|
-
// throw new SyntaxError(`Cannot switch to layer ${layer} without id`)
|
|
231
|
-
// }
|
|
232
|
-
|
|
233
|
-
// id = initializeLayer(resources, layer, id)
|
|
234
|
-
|
|
235
|
-
// // Cache initalized context layers
|
|
236
|
-
// const key = `${layer}:${id}`
|
|
237
|
-
// if (key in contexts) {
|
|
238
|
-
// return contexts[key] as T
|
|
239
|
-
// }
|
|
240
|
-
|
|
241
|
-
// const _config: C = JSON.parse(JSON.stringify(context.cfg))
|
|
242
|
-
// _config.layer = layer
|
|
243
|
-
// _config.ready = false
|
|
244
|
-
// _config.layerId = id
|
|
245
|
-
// // @TODO we need to make a rule to store all makeContext methods after they are applied
|
|
246
|
-
// const _context = context.makeContext != null ? context.makeContext(_config) : makeBasicContext(_config)
|
|
247
|
-
|
|
248
|
-
// Object.values(middlewares).flatMap(middlewares => middlewares)
|
|
249
|
-
// .forEach(middleware => _context.registerMiddleware(middleware))
|
|
250
|
-
|
|
251
|
-
// await applyMiddlewares<C, BasicContext<C>>(_context, middlewares, MiddlewareType.Config, MiddlewareStage.Switching, { layer, id })
|
|
252
|
-
|
|
253
|
-
// Object.values(allServices).forEach(service => _context.registerService(service))
|
|
254
|
-
|
|
255
|
-
// Object.values(allEntrypoints).forEach(ep => _context.registerEntrypoint(ep))
|
|
256
|
-
|
|
257
|
-
// Object.values(allResources).forEach(resource => _context.registerResource(resource))
|
|
258
|
-
|
|
259
|
-
// await applyMiddlewares<C, BasicContext<C>>(_context, middlewares, MiddlewareType.Context, MiddlewareStage.Switching, { layer, id })
|
|
260
|
-
|
|
261
|
-
// _context.stage = ContextStage.Loading
|
|
262
|
-
// await _context.configure().init()
|
|
263
|
-
|
|
264
|
-
// return (contexts[key] = _context) as T
|
|
265
|
-
},
|
|
266
|
-
|
|
267
|
-
hasResource: alias => allResources[alias] != null,
|
|
166
|
+
entrypoints: <T extends Entrypoint>() => Object.values(entrypoints) as T[],
|
|
268
167
|
|
|
269
|
-
|
|
168
|
+
hasResource: alias => resources[alias] != null,
|
|
270
169
|
|
|
271
|
-
|
|
170
|
+
hasService: alias => services[alias] != null,
|
|
272
171
|
|
|
273
|
-
|
|
274
|
-
hasModule: alias => context.hasEntrypoint(alias),
|
|
172
|
+
hasEntrypoint: alias => entrypoints[alias] != null,
|
|
275
173
|
}
|
|
276
174
|
|
|
277
175
|
return context
|
package/src/helper.ts
CHANGED
|
@@ -1,21 +1,14 @@
|
|
|
1
|
-
import { Layer } from './consts.js'
|
|
2
1
|
import type { Contextual, BasicContext, BasicConfig } from './types.js'
|
|
3
2
|
|
|
4
3
|
export const appendContextual = <T extends Contextual>(alias: string, contextual: Partial<T>): T => {
|
|
5
4
|
contextual.alias = alias
|
|
6
5
|
contextual.registerContext = <T, C extends BasicConfig>(context: BasicContext<C>) => {
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
? contextual.reinitializeContext(context) : contextual
|
|
11
|
-
|
|
12
|
-
// We do NOT update context when it's the same contextual with already set context
|
|
13
|
-
// Actuall we just do not need to switch context in many on the level of context consumer
|
|
14
|
-
if (_contextual.ctx == null) {
|
|
15
|
-
_contextual.ctx = context
|
|
6
|
+
// A contextual binds to exactly one context — the first one that registers it.
|
|
7
|
+
if (contextual.ctx == null) {
|
|
8
|
+
contextual.ctx = context
|
|
16
9
|
}
|
|
17
10
|
|
|
18
|
-
return
|
|
11
|
+
return contextual as T
|
|
19
12
|
}
|
|
20
13
|
|
|
21
14
|
contextual.assertCtx = (
|
|
@@ -25,10 +18,6 @@ export const appendContextual = <T extends Contextual>(alias: string, contextual
|
|
|
25
18
|
return contextual as T
|
|
26
19
|
}
|
|
27
20
|
|
|
28
|
-
// export type UpdContextType<C extends Config, T extends Context<C>, ExtraType> = T & ExtraType
|
|
29
|
-
|
|
30
|
-
// export type UpdConfigType<T extends Config, ExtraType> = T & ExtraType
|
|
31
|
-
|
|
32
21
|
/**
|
|
33
22
|
* @throws {SyntaxError}
|
|
34
23
|
*/
|
|
@@ -38,6 +27,3 @@ export const assertContext = <C extends BasicConfig, T extends BasicContext<C>>(
|
|
|
38
27
|
}
|
|
39
28
|
return ctx as T
|
|
40
29
|
}
|
|
41
|
-
|
|
42
|
-
export const isContextWithoutIds = <C extends BasicConfig, T extends BasicContext<C>>(context: T): boolean =>
|
|
43
|
-
[Layer.System, Layer.Global, Layer.Service].includes(context.cfg.layer)
|
package/src/types.ts
CHANGED
|
@@ -1,13 +1,11 @@
|
|
|
1
|
-
import type { AppType, ContextStage,
|
|
1
|
+
import type { AppType, ContextStage, MiddlewareStage, MiddlewareType, CONFIG_RECORD } from './consts.js'
|
|
2
2
|
|
|
3
3
|
export interface BasicConfig {
|
|
4
4
|
ready: boolean
|
|
5
5
|
service: string
|
|
6
6
|
// Is used as username of the service (e.g. for looking up for autehntication keys)
|
|
7
7
|
alias?: string
|
|
8
|
-
layer: Layer
|
|
9
8
|
type: AppType
|
|
10
|
-
layerId?: string
|
|
11
9
|
services?: Record<string, Object>
|
|
12
10
|
[CONFIG_RECORD]?: ConfigRecord[]
|
|
13
11
|
debug?: {
|
|
@@ -31,13 +29,11 @@ interface ConfigRecordItem extends Record<
|
|
|
31
29
|
export interface Contextual {
|
|
32
30
|
ctx?: BasicContext<any>
|
|
33
31
|
alias: string
|
|
34
|
-
reinitializeContext?: <T extends Contextual>(context: BasicContext<any>) => T // This method is a fix to replace context inside closed scope
|
|
35
32
|
registerContext: <T extends Contextual, C extends BasicConfig>(context: BasicContext<C>) => T
|
|
36
33
|
assertCtx: <C extends BasicConfig, T extends BasicContext<C>>(location?: string) => T
|
|
37
34
|
}
|
|
38
35
|
|
|
39
36
|
export interface Service extends Contextual {
|
|
40
|
-
layers?: Layer[]
|
|
41
37
|
initialized: boolean
|
|
42
38
|
init?: () => Promise<void>
|
|
43
39
|
lazyInit?: () => Promise<void>
|
|
@@ -56,17 +52,22 @@ export interface LazyService extends Service {
|
|
|
56
52
|
|
|
57
53
|
export interface BasicEntrypoint extends Contextual {
|
|
58
54
|
_entrypoint: true
|
|
59
|
-
_module: true
|
|
60
55
|
}
|
|
61
56
|
|
|
62
|
-
/**
|
|
63
|
-
|
|
64
|
-
|
|
57
|
+
/**
|
|
58
|
+
* A stable reference to an entrypoint registered in a context.
|
|
59
|
+
*
|
|
60
|
+
* Contract packages use this instead of exporting raw alias strings. The optional type member is
|
|
61
|
+
* deliberately phantom: it lets `context.entrypoint(protocol)` infer the context-bound module
|
|
62
|
+
* without changing the wire alias or adding registry-wide declaration merging.
|
|
63
|
+
*/
|
|
64
|
+
export interface EntrypointReference<T extends BasicEntrypoint = BasicEntrypoint> {
|
|
65
|
+
readonly alias: string
|
|
66
|
+
readonly entrypointType?: T
|
|
65
67
|
}
|
|
66
68
|
|
|
67
69
|
export interface BasicResource extends Contextual {
|
|
68
|
-
|
|
69
|
-
init?: () => Promise<void> // After context switch the resource should be able to reinitialize
|
|
70
|
+
init?: () => Promise<void>
|
|
70
71
|
}
|
|
71
72
|
|
|
72
73
|
export interface Middleware {
|
|
@@ -75,6 +76,12 @@ export interface Middleware {
|
|
|
75
76
|
apply: <C extends BasicConfig, T extends BasicContext<C>>(context: T, args?: Record<string, string | undefined>) => Promise<void>
|
|
76
77
|
}
|
|
77
78
|
|
|
79
|
+
/**
|
|
80
|
+
* The DI container. One context is built per process by one factory: a layer specific
|
|
81
|
+
* factory composes the layer below it and then `append*` mixins register what the
|
|
82
|
+
* application needs. There is no child context and nothing is stored for re-creation —
|
|
83
|
+
* a service, a resource and an entrypoint each bind to exactly one context.
|
|
84
|
+
*/
|
|
78
85
|
export interface BasicContext<C extends BasicConfig> {
|
|
79
86
|
cfg: C
|
|
80
87
|
stage: ContextStage
|
|
@@ -82,7 +89,6 @@ export interface BasicContext<C extends BasicConfig> {
|
|
|
82
89
|
waitForInitialized: () => Promise<boolean>
|
|
83
90
|
configure: <T extends BasicContext<C>>() => T
|
|
84
91
|
init: <T extends BasicContext<C>>() => Promise<T>
|
|
85
|
-
updateContext: <T extends BasicContext<C>>(id?: string, to?: Layer) => Promise<T>
|
|
86
92
|
registerService: <T extends BasicContext<C>>(service: Service) => T
|
|
87
93
|
registerEntrypoint: <T extends BasicContext<C>>(entrypoint: BasicEntrypoint) => T
|
|
88
94
|
registerEntrypoints: <T extends BasicContext<C>>(entrypoints: BasicEntrypoint[]) => T
|
|
@@ -91,24 +97,14 @@ export interface BasicContext<C extends BasicConfig> {
|
|
|
91
97
|
|
|
92
98
|
get config(): Promise<C>
|
|
93
99
|
service: <T extends Service>(alias: string) => T
|
|
94
|
-
entrypoint:
|
|
100
|
+
entrypoint: {
|
|
101
|
+
<T extends BasicEntrypoint>(reference: EntrypointReference<T>): T
|
|
102
|
+
<T extends BasicEntrypoint>(reference: EntrypointReference | string): T
|
|
103
|
+
}
|
|
95
104
|
resource: <T extends BasicResource>(alias: string) => T
|
|
96
105
|
hasResource: (alias: string) => boolean
|
|
97
106
|
hasService: (alias: string) => boolean
|
|
98
107
|
hasEntrypoint: (alias: string) => boolean
|
|
99
108
|
|
|
100
109
|
entrypoints: <T extends BasicEntrypoint>() => T[]
|
|
101
|
-
|
|
102
|
-
/** @deprecated use registerEntrypoint */
|
|
103
|
-
registerModule: <T extends BasicContext<C>>(module: BasicModule) => T
|
|
104
|
-
/** @deprecated use registerEntrypoints */
|
|
105
|
-
registerModules: <T extends BasicContext<C>>(modules: BasicModule[]) => T
|
|
106
|
-
/** @deprecated use entrypoint */
|
|
107
|
-
module: <T extends BasicModule>(alias: string) => T
|
|
108
|
-
/** @deprecated use hasEntrypoint */
|
|
109
|
-
hasModule: (alias: string) => boolean
|
|
110
|
-
/** @deprecated use entrypoints */
|
|
111
|
-
modules: <T extends BasicModule>() => T[]
|
|
112
|
-
|
|
113
|
-
makeContext?: <T extends BasicContext<C>>(cfg: C) => T
|
|
114
110
|
}
|
package/src/utils/context.ts
CHANGED
|
@@ -1,28 +1,10 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import type { BasicConfig, BasicContext, Middleware
|
|
3
|
-
import type { InLayer } from './layer.js'
|
|
1
|
+
import type { MiddlewareStage, MiddlewareType } from '../consts.js'
|
|
2
|
+
import type { BasicConfig, BasicContext, Middleware } from '../types.js'
|
|
4
3
|
|
|
5
4
|
export const getMiddlerwareKey = (middleware: Middleware) => createMiddlewareKey(middleware.type, middleware.stage)
|
|
6
5
|
|
|
7
6
|
export const createMiddlewareKey = (type: MiddlewareType, stage: MiddlewareStage) => `${type}:${stage}`
|
|
8
7
|
|
|
9
|
-
export const isLayerIherited = (current: Layer, parent: Layer): boolean =>
|
|
10
|
-
(current === parent) || (layersOrder.indexOf(parent) > layersOrder.indexOf(current))
|
|
11
|
-
|
|
12
|
-
export const isResourceAvailable = (resource: BasicResource, layer: Layer) =>
|
|
13
|
-
resource.layers == null || resource.layers.some(_layer => isLayerIherited(_layer, layer))
|
|
14
|
-
|
|
15
|
-
export const layersOrder = [
|
|
16
|
-
Layer.System,
|
|
17
|
-
Layer.Global,
|
|
18
|
-
Layer.Service,
|
|
19
|
-
Layer.Entity,
|
|
20
|
-
Layer.User
|
|
21
|
-
]
|
|
22
|
-
|
|
23
|
-
export const getAllServices = (services: InLayer<Record<string, Service>>, layer: Layer, id: string) =>
|
|
24
|
-
services?.[layer]?.[id] != null ? Object.values(services[layer][id]) : []
|
|
25
|
-
|
|
26
8
|
export const applyMiddlewares = <C extends BasicConfig, T extends BasicContext<C>>(
|
|
27
9
|
context: T,
|
|
28
10
|
middlewares: Record<string, Middleware[]>,
|
package/src/utils/index.ts
CHANGED
package/tests/context.ts
CHANGED
|
@@ -1,10 +1,9 @@
|
|
|
1
|
-
import { AppType,
|
|
1
|
+
import { AppType, makeBasicContext } from '@owlmeans/context'
|
|
2
2
|
import type { BasicConfig, BasicContext } from '@owlmeans/context'
|
|
3
3
|
|
|
4
4
|
const baseConfig = (): BasicConfig => ({
|
|
5
5
|
ready: false,
|
|
6
6
|
service: 'test-context',
|
|
7
|
-
layer: Layer.Service,
|
|
8
7
|
type: AppType.Backend,
|
|
9
8
|
})
|
|
10
9
|
|
package/tests/service.spec.ts
CHANGED
|
@@ -5,7 +5,7 @@ import { makeTestCtx } from './context.js'
|
|
|
5
5
|
describe('@owlmeans/context — service registration', () => {
|
|
6
6
|
test('registers a service and resolves it by alias after initialization', async () => {
|
|
7
7
|
const ctx = makeTestCtx()
|
|
8
|
-
const stub = createService('alpha', {
|
|
8
|
+
const stub = createService('alpha', {})
|
|
9
9
|
ctx.registerService(stub)
|
|
10
10
|
expect(ctx.hasService('alpha')).toBe(true)
|
|
11
11
|
ctx.configure()
|
|
@@ -1,53 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: context
|
|
3
|
-
description: How to use @owlmeans/context — base context (DI container) factory, registerService(), service<T>() lookups, entrypoint<ClientEntrypoint<T>>() resolution. Auto-invoked when importing context primitives or building a makeContext factory.
|
|
4
|
-
user-invocable: false
|
|
5
|
-
---
|
|
6
|
-
<!-- AUTO-GENERATED — do not edit. Regenerate via sync-agent-meta. -->
|
|
7
|
-
|
|
8
|
-
# @owlmeans/context
|
|
9
|
-
|
|
10
|
-
**Layer:** Core
|
|
11
|
-
**Install:** `"@owlmeans/context": "^0.1.18-rc.0"` in `dependencies`
|
|
12
|
-
|
|
13
|
-
## Key Exports
|
|
14
|
-
|
|
15
|
-
| Export | Description |
|
|
16
|
-
|--------|-------------|
|
|
17
|
-
| `Context<C>` types | Generic context interface (typed by Config) |
|
|
18
|
-
| `makeBasicContext` | Low-level factory — usually you extend a layer-specific factory instead |
|
|
19
|
-
| `registerService` (method) | Add a service to the DI container |
|
|
20
|
-
| `service<T>(alias)` (method) | Resolve a service by alias |
|
|
21
|
-
| `entrypoint<ClientEntrypoint<T>>(alias)` (method) | Resolve an entrypoint to call cross-service |
|
|
22
|
-
| `Service` types | Service interface and lifecycle |
|
|
23
|
-
| Constants | Built-in service/entrypoint aliases |
|
|
24
|
-
|
|
25
|
-
## Usage
|
|
26
|
-
|
|
27
|
-
Always extend a layer-specific factory (`@owlmeans/server-context`, `@owlmeans/web-panel`, etc.) rather than calling the basic factory directly. Always reassign `context.makeContext` so child contexts inherit the typed factory:
|
|
28
|
-
|
|
29
|
-
```typescript
|
|
30
|
-
import { makeBackendContext } from '@owlmeans/server-context'
|
|
31
|
-
|
|
32
|
-
export const makeContext = <C extends Config, T extends Context<C>>(cfg: C): T => {
|
|
33
|
-
const context = makeBackendContext<C, T>(cfg)
|
|
34
|
-
context.registerService(makeMyService())
|
|
35
|
-
context.makeContext = makeContext as typeof context.makeContext
|
|
36
|
-
return context
|
|
37
|
-
}
|
|
38
|
-
```
|
|
39
|
-
|
|
40
|
-
Resolve services and call cross-service entrypoints from a handler:
|
|
41
|
-
|
|
42
|
-
```typescript
|
|
43
|
-
const someService = ctx.service<MyService>(MY_SERVICE_ALIAS)
|
|
44
|
-
|
|
45
|
-
const [response] = await ctx.entrypoint<ClientEntrypoint<ResponseType>>(
|
|
46
|
-
externalService.action.alias
|
|
47
|
-
).call({ body: { ... } })
|
|
48
|
-
```
|
|
49
|
-
|
|
50
|
-
## Depends On
|
|
51
|
-
|
|
52
|
-
- `@owlmeans/config` — context is parameterized by a Config
|
|
53
|
-
- `@owlmeans/entrypoint` — `ClientEntrypoint<T>` type for cross-service calls
|
package/build/.gitkeep
DELETED
|
File without changes
|
package/build/utils/layer.d.ts
DELETED
|
@@ -1,6 +0,0 @@
|
|
|
1
|
-
import { Layer } from '../consts';
|
|
2
|
-
export interface InLayer<T> extends Record<Layer, Record<string, T>> {
|
|
3
|
-
}
|
|
4
|
-
export declare const initializeLayer: <T>(inLayer: InLayer<T>, layer: Layer, id: string | undefined) => string;
|
|
5
|
-
export declare const DEFAULT = "default";
|
|
6
|
-
//# sourceMappingURL=layer.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"layer.d.ts","sourceRoot":"","sources":["../../src/utils/layer.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,MAAM,WAAW,CAAA;AAEjC,MAAM,WAAW,OAAO,CAAC,CAAC,CAAE,SAAQ,MAAM,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC;CAAI;AAExE,eAAO,MAAM,eAAe,GAAI,CAAC,WAAW,OAAO,CAAC,CAAC,CAAC,SAAS,KAAK,MAAM,MAAM,GAAG,SAAS,KAAG,MAU9F,CAAA;AAED,eAAO,MAAM,OAAO,YAAY,CAAA"}
|
package/build/utils/layer.js
DELETED
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
export const initializeLayer = (inLayer, layer, id) => {
|
|
2
|
-
if (inLayer[layer] == null) {
|
|
3
|
-
inLayer[layer] = {};
|
|
4
|
-
}
|
|
5
|
-
id = id ?? DEFAULT;
|
|
6
|
-
if (inLayer[layer][id] == null) {
|
|
7
|
-
inLayer[layer][id] = {};
|
|
8
|
-
}
|
|
9
|
-
return id;
|
|
10
|
-
};
|
|
11
|
-
export const DEFAULT = 'default';
|
|
12
|
-
//# sourceMappingURL=layer.js.map
|
package/build/utils/layer.js.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"layer.js","sourceRoot":"","sources":["../../src/utils/layer.ts"],"names":[],"mappings":"AAIA,MAAM,CAAC,MAAM,eAAe,GAAG,CAAI,OAAmB,EAAE,KAAY,EAAE,EAAsB,EAAU,EAAE;IACtG,IAAI,OAAO,CAAC,KAAK,CAAC,IAAI,IAAI,EAAE,CAAC;QAC3B,OAAO,CAAC,KAAK,CAAC,GAAG,EAAE,CAAA;IACrB,CAAC;IACD,EAAE,GAAG,EAAE,IAAI,OAAO,CAAA;IAClB,IAAI,OAAO,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,IAAI,IAAI,EAAE,CAAC;QAC/B,OAAO,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,GAAG,EAAO,CAAA;IAC9B,CAAC;IAED,OAAO,EAAE,CAAA;AACX,CAAC,CAAA;AAED,MAAM,CAAC,MAAM,OAAO,GAAG,SAAS,CAAA"}
|
package/src/utils/layer.ts
DELETED
|
@@ -1,17 +0,0 @@
|
|
|
1
|
-
import { Layer } from '../consts'
|
|
2
|
-
|
|
3
|
-
export interface InLayer<T> extends Record<Layer, Record<string, T>> { }
|
|
4
|
-
|
|
5
|
-
export const initializeLayer = <T>(inLayer: InLayer<T>, layer: Layer, id: string | undefined): string => {
|
|
6
|
-
if (inLayer[layer] == null) {
|
|
7
|
-
inLayer[layer] = {}
|
|
8
|
-
}
|
|
9
|
-
id = id ?? DEFAULT
|
|
10
|
-
if (inLayer[layer][id] == null) {
|
|
11
|
-
inLayer[layer][id] = {} as T
|
|
12
|
-
}
|
|
13
|
-
|
|
14
|
-
return id
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
export const DEFAULT = 'default'
|