@toa.io/boot 0.2.0-dev.3 → 0.2.1-dev.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/package.json +8 -7
- package/src/bindings/broadcast.js +7 -0
- package/src/bindings/factory.js +6 -2
- package/src/bindings/index.js +2 -0
- package/src/bindings/produce.js +3 -2
- package/src/bridge.js +5 -5
- package/src/cascade.js +2 -2
- package/src/component.js +33 -0
- package/src/composition.js +18 -11
- package/src/context.js +6 -3
- package/src/deployment.js +9 -4
- package/src/discovery.js +1 -0
- package/src/emission.js +4 -2
- package/src/exposition.js +1 -1
- package/src/extensions/aspects.js +27 -0
- package/src/extensions/component.js +19 -0
- package/src/extensions/context.js +19 -0
- package/src/extensions/emitter.js +20 -0
- package/src/extensions/index.js +19 -0
- package/src/extensions/instances.js +6 -0
- package/src/extensions/load.js +27 -0
- package/src/extensions/receiver.js +20 -0
- package/src/extensions/resolve.js +27 -0
- package/src/extensions/storage.js +19 -0
- package/src/extensions/tenants.js +27 -0
- package/src/images.js +1 -1
- package/src/index.js +3 -4
- package/src/manifest.js +16 -2
- package/src/operation.js +3 -10
- package/src/receivers.js +8 -5
- package/src/remote.js +7 -2
- package/src/storage.js +14 -3
- package/types/composition.d.ts +19 -0
- package/types/index.d.ts +3 -0
- package/types/manifest.d.ts +8 -0
- package/LICENSE +0 -22
- package/src/extensions.js +0 -25
- package/src/runtime.js +0 -25
package/package.json
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@toa.io/boot",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.1-dev.0",
|
|
4
4
|
"description": "Toa Boot",
|
|
5
5
|
"author": "temich <tema.gurtovoy@gmail.com>",
|
|
6
6
|
"homepage": "https://github.com/toa-io/toa#readme",
|
|
7
7
|
"main": "src/index.js",
|
|
8
|
+
"types": "types/index.d.ts",
|
|
8
9
|
"repository": {
|
|
9
10
|
"type": "git",
|
|
10
11
|
"url": "git+https://github.com/toa-io/toa.git"
|
|
@@ -19,12 +20,12 @@
|
|
|
19
20
|
"test": "echo \"Error: run tests from root\" && exit 1"
|
|
20
21
|
},
|
|
21
22
|
"dependencies": {
|
|
22
|
-
"@toa.io/
|
|
23
|
-
"@toa.io/
|
|
24
|
-
"@toa.io/
|
|
25
|
-
"@toa.io/
|
|
26
|
-
"@toa.io/schema": "
|
|
23
|
+
"@toa.io/core": "*",
|
|
24
|
+
"@toa.io/filesystem": "*",
|
|
25
|
+
"@toa.io/generic": "*",
|
|
26
|
+
"@toa.io/norm": "*",
|
|
27
|
+
"@toa.io/schema": "*",
|
|
27
28
|
"clone-deep": "4.0.1"
|
|
28
29
|
},
|
|
29
|
-
"gitHead": "
|
|
30
|
+
"gitHead": "2be07592325b2e4dc823e81d882a4e50bf50de24"
|
|
30
31
|
}
|
package/src/bindings/factory.js
CHANGED
|
@@ -1,11 +1,15 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
let instances = {}
|
|
4
4
|
|
|
5
5
|
const factory = (binding) => {
|
|
6
|
-
if (
|
|
6
|
+
if (instances[binding] === undefined) instances[binding] = new (require(binding).Factory)()
|
|
7
7
|
|
|
8
8
|
return instances[binding]
|
|
9
9
|
}
|
|
10
10
|
|
|
11
|
+
// for testing purposes
|
|
12
|
+
const reset = () => (instances = {})
|
|
13
|
+
|
|
11
14
|
exports.factory = factory
|
|
15
|
+
exports.reset = reset
|
package/src/bindings/index.js
CHANGED
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
|
+
const { broadcast } = require('./broadcast')
|
|
3
4
|
const { consume } = require('./consume')
|
|
4
5
|
const { emit } = require('./emit')
|
|
5
6
|
const { produce } = require('./produce')
|
|
6
7
|
const { receive } = require('./receive')
|
|
7
8
|
|
|
9
|
+
exports.broadcast = broadcast
|
|
8
10
|
exports.consume = consume
|
|
9
11
|
exports.emit = emit
|
|
10
12
|
exports.produce = produce
|
package/src/bindings/produce.js
CHANGED
|
@@ -3,13 +3,14 @@
|
|
|
3
3
|
const { LOOP } = require('./constants')
|
|
4
4
|
const { factory } = require('./factory')
|
|
5
5
|
|
|
6
|
-
const produce = (
|
|
7
|
-
factory.producer(
|
|
6
|
+
const produce = (component, operations) => group(operations, (factory, endpoints) =>
|
|
7
|
+
factory.producer(component.locator, endpoints, component))
|
|
8
8
|
|
|
9
9
|
const group = (operations, callback) => {
|
|
10
10
|
const map = {}
|
|
11
11
|
|
|
12
12
|
for (const [endpoint, operation] of Object.entries(operations)) {
|
|
13
|
+
// noinspection JSUnresolvedVariable
|
|
13
14
|
const bindings = global.TOA_INTEGRATION_BINDINGS_LOOP_DISABLED
|
|
14
15
|
? operation.bindings
|
|
15
16
|
: [LOOP].concat(operation.bindings)
|
package/src/bridge.js
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
|
-
const
|
|
4
|
-
const
|
|
3
|
+
const algorithm = (bridge, path, endpoint, context) => {
|
|
4
|
+
const algorithm = resolve(bridge).algorithm(path, endpoint, context)
|
|
5
5
|
|
|
6
|
-
|
|
6
|
+
algorithm.depends(context)
|
|
7
7
|
|
|
8
|
-
return
|
|
8
|
+
return algorithm
|
|
9
9
|
}
|
|
10
10
|
|
|
11
11
|
const event = (bridge, path, label) => resolve(bridge).event(path, label)
|
|
@@ -23,6 +23,6 @@ const resolve = (bridge) => {
|
|
|
23
23
|
return factories[bridge]
|
|
24
24
|
}
|
|
25
25
|
|
|
26
|
-
exports.
|
|
26
|
+
exports.algorithm = algorithm
|
|
27
27
|
exports.event = event
|
|
28
28
|
exports.receiver = receiver
|
package/src/cascade.js
CHANGED
|
@@ -10,7 +10,7 @@ const cascade = (manifest, endpoint, definition, context) => {
|
|
|
10
10
|
if (definition.forward) endpoint = definition.forward
|
|
11
11
|
|
|
12
12
|
if (definition.bridge) {
|
|
13
|
-
const bridge = boot.bridge.
|
|
13
|
+
const bridge = boot.bridge.algorithm(definition.bridge, manifest.path, endpoint, context)
|
|
14
14
|
|
|
15
15
|
bridges.unshift(bridge)
|
|
16
16
|
}
|
|
@@ -22,7 +22,7 @@ const cascade = (manifest, endpoint, definition, context) => {
|
|
|
22
22
|
|
|
23
23
|
if (operation === undefined) continue
|
|
24
24
|
|
|
25
|
-
const bridge = boot.bridge.
|
|
25
|
+
const bridge = boot.bridge.algorithm(operation.bridge, prototype.path, endpoint, context)
|
|
26
26
|
|
|
27
27
|
bridges.unshift(bridge)
|
|
28
28
|
}
|
package/src/component.js
ADDED
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { remap } = require('@toa.io/generic')
|
|
4
|
+
const { Component, Locator, State, entities } = require('@toa.io/core')
|
|
5
|
+
const { Schema } = require('@toa.io/schema')
|
|
6
|
+
|
|
7
|
+
const boot = require('./index')
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* @param {toa.norm.Component} manifest
|
|
11
|
+
* @returns {Promise<toa.core.Component>}
|
|
12
|
+
*/
|
|
13
|
+
const component = async (manifest) => {
|
|
14
|
+
const locator = new Locator(manifest.name, manifest.namespace)
|
|
15
|
+
const storage = boot.storage(locator, manifest.entity.storage)
|
|
16
|
+
const context = await boot.context(manifest)
|
|
17
|
+
const emission = boot.emission(manifest.events, locator)
|
|
18
|
+
const schema = new Schema(manifest.entity.schema)
|
|
19
|
+
const entity = new entities.Factory(schema)
|
|
20
|
+
const state = new State(storage, entity, emission, manifest.entity.initialized)
|
|
21
|
+
|
|
22
|
+
const operations = remap(manifest.operations, (definition, endpoint) =>
|
|
23
|
+
boot.operation(manifest, endpoint, definition, context, state))
|
|
24
|
+
|
|
25
|
+
const component = new Component(locator, operations)
|
|
26
|
+
|
|
27
|
+
if (storage) component.depends(storage)
|
|
28
|
+
if (emission) component.depends(emission)
|
|
29
|
+
|
|
30
|
+
return boot.extensions.component(component)
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
exports.component = component
|
package/src/composition.js
CHANGED
|
@@ -5,25 +5,32 @@ const { Composition } = require('@toa.io/core')
|
|
|
5
5
|
const boot = require('./index')
|
|
6
6
|
|
|
7
7
|
async function composition (paths, options) {
|
|
8
|
-
|
|
8
|
+
options = Object.assign({}, options, EXTENSIONS)
|
|
9
9
|
|
|
10
|
+
/** @type {toa.norm.Component[]} */
|
|
10
11
|
const manifests = await Promise.all(paths.map((path) => boot.manifest(path, options)))
|
|
11
|
-
|
|
12
|
+
|
|
13
|
+
boot.extensions.load(manifests, options.extensions)
|
|
14
|
+
|
|
15
|
+
/** @type {toa.core.Connector[]} */
|
|
16
|
+
const tenants = await Promise.all(manifests.map(boot.extensions.tenants))
|
|
17
|
+
|
|
12
18
|
const expositions = await Promise.all(manifests.map(boot.discovery.expose))
|
|
13
|
-
const runtimes = await Promise.all(manifests.map(boot.runtime))
|
|
14
19
|
|
|
15
|
-
|
|
16
|
-
|
|
20
|
+
/** @type {toa.core.Component[]} */
|
|
21
|
+
const components = await Promise.all(manifests.map(boot.component))
|
|
22
|
+
|
|
23
|
+
const producers = components.map((component, index) =>
|
|
24
|
+
boot.bindings.produce(component, manifests[index].operations))
|
|
17
25
|
|
|
18
|
-
const receivers = await Promise.all(
|
|
19
|
-
boot.receivers(manifests[index],
|
|
26
|
+
const receivers = await Promise.all(components.map((component, index) =>
|
|
27
|
+
boot.receivers(manifests[index], component)))
|
|
20
28
|
|
|
21
|
-
return new Composition(expositions.flat(), producers.flat(), receivers.flat(),
|
|
29
|
+
return new Composition(expositions.flat(), producers.flat(), receivers.flat(), tenants.flat())
|
|
22
30
|
}
|
|
23
31
|
|
|
24
|
-
const
|
|
25
|
-
|
|
26
|
-
if (options.bindings === null) options.bindings = []
|
|
32
|
+
const EXTENSIONS = {
|
|
33
|
+
extensions: ['@toa.io/extensions.sampling']
|
|
27
34
|
}
|
|
28
35
|
|
|
29
36
|
exports.composition = composition
|
package/src/context.js
CHANGED
|
@@ -6,9 +6,10 @@ const boot = require('./index')
|
|
|
6
6
|
|
|
7
7
|
const context = async (manifest) => {
|
|
8
8
|
const local = await boot.remote(manifest.locator, manifest)
|
|
9
|
+
const aspects = boot.extensions.aspects(manifest)
|
|
9
10
|
|
|
10
|
-
const lookup = async (
|
|
11
|
-
const locator = new Locator(
|
|
11
|
+
const lookup = async (namespace, name) => {
|
|
12
|
+
const locator = new Locator(name, namespace)
|
|
12
13
|
const remote = await boot.remote(locator)
|
|
13
14
|
|
|
14
15
|
await remote.connect()
|
|
@@ -16,7 +17,9 @@ const context = async (manifest) => {
|
|
|
16
17
|
return remote
|
|
17
18
|
}
|
|
18
19
|
|
|
19
|
-
|
|
20
|
+
const context = new Context(local, lookup, aspects)
|
|
21
|
+
|
|
22
|
+
return boot.extensions.context(context)
|
|
20
23
|
}
|
|
21
24
|
|
|
22
25
|
exports.context = context
|
package/src/deployment.js
CHANGED
|
@@ -1,13 +1,18 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
3
|
const { deployment: { Factory } } = require('@toa.io/operations')
|
|
4
|
-
const { context: load } = require('@toa.io/
|
|
4
|
+
const { context: load } = require('@toa.io/norm')
|
|
5
5
|
|
|
6
|
-
|
|
7
|
-
|
|
6
|
+
/**
|
|
7
|
+
* @param {string} path
|
|
8
|
+
* @param {string} [environment]
|
|
9
|
+
* @returns {Promise<toa.deployment.Operator>}
|
|
10
|
+
*/
|
|
11
|
+
const deployment = async (path, environment) => {
|
|
12
|
+
const context = await load(path, environment)
|
|
8
13
|
const factory = new Factory(context)
|
|
9
14
|
|
|
10
|
-
return factory.
|
|
15
|
+
return factory.operator()
|
|
11
16
|
}
|
|
12
17
|
|
|
13
18
|
exports.deployment = deployment
|
package/src/discovery.js
CHANGED
package/src/emission.js
CHANGED
|
@@ -3,15 +3,17 @@
|
|
|
3
3
|
const { Emission, Event } = require('@toa.io/core')
|
|
4
4
|
|
|
5
5
|
const boot = require('./index')
|
|
6
|
+
const extensions = require('./extensions')
|
|
6
7
|
|
|
7
8
|
const emission = (definitions, locator) => {
|
|
8
9
|
if (definitions === undefined) return
|
|
9
10
|
|
|
10
11
|
const events = Object.entries(definitions).map(([label, definition]) => {
|
|
11
|
-
const
|
|
12
|
+
const emitter = boot.bindings.emit(definition.binding, locator, label)
|
|
13
|
+
const decorator = extensions.emitter(emitter, label)
|
|
12
14
|
const bridge = boot.bridge.event(definition.bridge, definition.path, label)
|
|
13
15
|
|
|
14
|
-
return new Event(definition,
|
|
16
|
+
return new Event(definition, decorator, bridge)
|
|
15
17
|
})
|
|
16
18
|
|
|
17
19
|
return new Emission(events)
|
package/src/exposition.js
CHANGED
|
@@ -5,7 +5,7 @@ const { Exposition, Locator } = require('@toa.io/core')
|
|
|
5
5
|
const boot = require('./index')
|
|
6
6
|
|
|
7
7
|
const exposition = async (manifest) => {
|
|
8
|
-
const locator = new Locator()
|
|
8
|
+
const locator = new Locator('', '')
|
|
9
9
|
const exposition = new Exposition(locator, manifest)
|
|
10
10
|
const producers = boot.bindings.expose(exposition)
|
|
11
11
|
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { resolve } = require('./resolve')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.norm.Component} manifest
|
|
7
|
+
* @returns {toa.core.extensions.Aspect[]}
|
|
8
|
+
*/
|
|
9
|
+
const aspects = (manifest) => {
|
|
10
|
+
const aspects = []
|
|
11
|
+
|
|
12
|
+
if (manifest.extensions === undefined) return aspects
|
|
13
|
+
|
|
14
|
+
for (const [name, declaration] of Object.entries(manifest.extensions)) {
|
|
15
|
+
const factory = resolve(name, manifest.path)
|
|
16
|
+
|
|
17
|
+
if (factory.aspect === undefined) continue
|
|
18
|
+
|
|
19
|
+
const aspect = factory.aspect(manifest.locator, declaration)
|
|
20
|
+
|
|
21
|
+
aspects.push(aspect)
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
return aspects
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
exports.aspects = aspects
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { instances } = require('./instances')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.core.Component} component
|
|
7
|
+
* @returns {toa.core.Component}
|
|
8
|
+
*/
|
|
9
|
+
const component = (component) => {
|
|
10
|
+
let decorated = component
|
|
11
|
+
|
|
12
|
+
for (const factory of Object.values(instances)) {
|
|
13
|
+
if (factory.component !== undefined) decorated = factory.component(decorated)
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
return decorated
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
exports.component = component
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { instances } = require('./instances')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.core.Context} component
|
|
7
|
+
* @returns {toa.core.Context}
|
|
8
|
+
*/
|
|
9
|
+
const context = (component) => {
|
|
10
|
+
let decorated = component
|
|
11
|
+
|
|
12
|
+
for (const factory of Object.values(instances)) {
|
|
13
|
+
if (factory.context !== undefined) decorated = factory.context(decorated)
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
return decorated
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
exports.context = context
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { instances } = require('./instances')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.core.bindings.Emitter} emitter
|
|
7
|
+
* @param {string} label
|
|
8
|
+
* @returns {toa.core.bindings.Emitter}
|
|
9
|
+
*/
|
|
10
|
+
const emitter = (emitter, label) => {
|
|
11
|
+
let decorated = emitter
|
|
12
|
+
|
|
13
|
+
for (const factory of Object.values(instances)) {
|
|
14
|
+
if (factory.emitter !== undefined) decorated = factory.emitter(decorated, label)
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
return decorated
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
exports.emitter = emitter
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { aspects } = require('./aspects')
|
|
4
|
+
const { component } = require('./component')
|
|
5
|
+
const { context } = require('./context')
|
|
6
|
+
const { emitter } = require('./emitter')
|
|
7
|
+
const { load } = require('./load')
|
|
8
|
+
const { receiver } = require('./receiver')
|
|
9
|
+
const { storage } = require('./storage')
|
|
10
|
+
const { tenants } = require('./tenants')
|
|
11
|
+
|
|
12
|
+
exports.aspects = aspects
|
|
13
|
+
exports.component = component
|
|
14
|
+
exports.context = context
|
|
15
|
+
exports.emitter = emitter
|
|
16
|
+
exports.load = load
|
|
17
|
+
exports.receiver = receiver
|
|
18
|
+
exports.storage = storage
|
|
19
|
+
exports.tenants = tenants
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { resolve } = require('./resolve')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.norm.Component[]} manifests
|
|
7
|
+
* @param {string[]} defaults
|
|
8
|
+
*/
|
|
9
|
+
const load = (manifests, defaults) => {
|
|
10
|
+
scan(manifests)
|
|
11
|
+
defaults.map((name) => resolve(name))
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* @param {toa.norm.Component[]} manifests
|
|
16
|
+
*/
|
|
17
|
+
const scan = (manifests) => {
|
|
18
|
+
for (const manifest of manifests) {
|
|
19
|
+
if (manifest.extensions === undefined) continue
|
|
20
|
+
|
|
21
|
+
for (const name of Object.keys(manifest.extensions)) {
|
|
22
|
+
resolve(name, manifest.path)
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
exports.load = load
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { instances } = require('./instances')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.core.Receiver} receiver
|
|
7
|
+
* @param {toa.core.Locator} locator
|
|
8
|
+
* @returns {toa.core.Receiver}
|
|
9
|
+
*/
|
|
10
|
+
const receiver = (receiver, locator) => {
|
|
11
|
+
let decorated = receiver
|
|
12
|
+
|
|
13
|
+
for (const factory of Object.values(instances)) {
|
|
14
|
+
if (factory.receiver !== undefined) decorated = factory.receiver(decorated, locator)
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
return decorated
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
exports.receiver = receiver
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { directory: { find } } = require('@toa.io/filesystem')
|
|
4
|
+
const boot = require('../..')
|
|
5
|
+
|
|
6
|
+
const { instances } = require('./instances')
|
|
7
|
+
|
|
8
|
+
/**
|
|
9
|
+
* @param {string} reference
|
|
10
|
+
* @param {string} base
|
|
11
|
+
* @returns {toa.core.extensions.Factory}
|
|
12
|
+
*/
|
|
13
|
+
const resolve = (reference, base = process.cwd()) => {
|
|
14
|
+
const path = find(reference, base)
|
|
15
|
+
|
|
16
|
+
if (instances[path] === undefined) instances[path] = create(path)
|
|
17
|
+
|
|
18
|
+
return instances[path]
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
const create = (path) => {
|
|
22
|
+
const { Factory } = require(path)
|
|
23
|
+
|
|
24
|
+
return new Factory(boot)
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
exports.resolve = resolve
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { instances } = require('./instances')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.core.Storage} storage
|
|
7
|
+
* @returns {toa.core.Storage}
|
|
8
|
+
*/
|
|
9
|
+
const storage = (storage) => {
|
|
10
|
+
let decorated = storage
|
|
11
|
+
|
|
12
|
+
for (const factory of Object.values(instances)) {
|
|
13
|
+
if (factory.storage !== undefined) decorated = factory.storage(decorated)
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
return decorated
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
exports.storage = storage
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
'use strict'
|
|
2
|
+
|
|
3
|
+
const { resolve } = require('./resolve')
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.norm.Component} manifest
|
|
7
|
+
* @returns {toa.core.Connector[]}
|
|
8
|
+
*/
|
|
9
|
+
const tenants = (manifest) => {
|
|
10
|
+
const tenants = []
|
|
11
|
+
|
|
12
|
+
if (manifest.extensions === undefined) return tenants
|
|
13
|
+
|
|
14
|
+
for (const [name, declaration] of Object.entries(manifest.extensions)) {
|
|
15
|
+
const factory = resolve(name, manifest.path)
|
|
16
|
+
|
|
17
|
+
if (factory.tenant === undefined) continue
|
|
18
|
+
|
|
19
|
+
const tenant = factory.tenant(manifest.locator, declaration)
|
|
20
|
+
|
|
21
|
+
tenants.push(tenant)
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
return tenants
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
exports.tenants = tenants
|
package/src/images.js
CHANGED
package/src/index.js
CHANGED
|
@@ -2,37 +2,36 @@
|
|
|
2
2
|
|
|
3
3
|
const { call } = require('./call')
|
|
4
4
|
const { cascade } = require('./cascade')
|
|
5
|
+
const { component } = require('./component')
|
|
5
6
|
const { composition } = require('./composition')
|
|
6
7
|
const { context } = require('./context')
|
|
7
8
|
const { deployment } = require('./deployment')
|
|
8
9
|
const { emission } = require('./emission')
|
|
9
10
|
const { exposition } = require('./exposition')
|
|
10
|
-
const { extensions } = require('./extensions')
|
|
11
11
|
const { images } = require('./images')
|
|
12
12
|
const { manifest } = require('./manifest')
|
|
13
13
|
const { operation } = require('./operation')
|
|
14
14
|
const { receivers } = require('./receivers')
|
|
15
15
|
const { remote } = require('./remote')
|
|
16
|
-
const { runtime } = require('./runtime')
|
|
17
16
|
const { storage } = require('./storage')
|
|
18
17
|
|
|
19
18
|
exports.bindings = require('./bindings')
|
|
20
19
|
exports.bridge = require('./bridge')
|
|
21
20
|
exports.contract = require('./contract')
|
|
22
21
|
exports.discovery = require('./discovery')
|
|
22
|
+
exports.extensions = require('./extensions')
|
|
23
23
|
|
|
24
24
|
exports.call = call
|
|
25
25
|
exports.cascade = cascade
|
|
26
|
+
exports.component = component
|
|
26
27
|
exports.composition = composition
|
|
27
28
|
exports.context = context
|
|
28
29
|
exports.deployment = deployment
|
|
29
30
|
exports.emission = emission
|
|
30
31
|
exports.exposition = exposition
|
|
31
|
-
exports.extensions = extensions
|
|
32
32
|
exports.images = images
|
|
33
33
|
exports.manifest = manifest
|
|
34
34
|
exports.operation = operation
|
|
35
35
|
exports.receivers = receivers
|
|
36
36
|
exports.remote = remote
|
|
37
|
-
exports.runtime = runtime
|
|
38
37
|
exports.storage = storage
|
package/src/manifest.js
CHANGED
|
@@ -1,8 +1,11 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
|
-
const {
|
|
3
|
+
const { component: load } = require('@toa.io/norm')
|
|
4
4
|
const { Locator } = require('@toa.io/core')
|
|
5
5
|
|
|
6
|
+
/**
|
|
7
|
+
* @type {toa.boot.Manifest}
|
|
8
|
+
*/
|
|
6
9
|
const manifest = async (path, options) => {
|
|
7
10
|
const manifest = await load(path)
|
|
8
11
|
|
|
@@ -10,9 +13,20 @@ const manifest = async (path, options) => {
|
|
|
10
13
|
for (const operation of Object.values(manifest.operations)) {
|
|
11
14
|
operation.bindings = options.bindings
|
|
12
15
|
}
|
|
16
|
+
|
|
17
|
+
const check = (binding) => require(binding).properties?.async === true
|
|
18
|
+
const asyncBinding = options.bindings.find(check)
|
|
19
|
+
|
|
20
|
+
if (asyncBinding === undefined) throw new Error('Bindings override must contain at least one async binding')
|
|
21
|
+
|
|
22
|
+
for (const event of Object.values(manifest.events)) event.binding = asyncBinding
|
|
23
|
+
|
|
24
|
+
if (manifest.receivers) {
|
|
25
|
+
for (const receiver of Object.values(manifest.receivers)) receiver.binding = asyncBinding
|
|
26
|
+
}
|
|
13
27
|
}
|
|
14
28
|
|
|
15
|
-
manifest.locator = new Locator(manifest)
|
|
29
|
+
manifest.locator = new Locator(manifest.name, manifest.namespace)
|
|
16
30
|
|
|
17
31
|
return manifest
|
|
18
32
|
}
|
package/src/operation.js
CHANGED
|
@@ -1,23 +1,16 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
|
-
const { Transition, Observation, Assignment,
|
|
4
|
-
const { Schema } = require('@toa.io/schema')
|
|
3
|
+
const { Transition, Observation, Assignment, Query } = require('@toa.io/core')
|
|
5
4
|
|
|
6
5
|
const boot = require('./index')
|
|
7
6
|
|
|
8
|
-
const operation = (manifest, endpoint, definition, context,
|
|
7
|
+
const operation = (manifest, endpoint, definition, context, scope) => {
|
|
9
8
|
const cascade = boot.cascade(manifest, endpoint, definition, context)
|
|
10
9
|
const contract = boot.contract.reply(definition.output, definition.error)
|
|
11
|
-
const schema = new Schema(manifest.entity.schema)
|
|
12
|
-
const entity = new entities.Factory(schema)
|
|
13
|
-
const subject = new State(storage, entity, emission, manifest.entity.initialized)
|
|
14
10
|
const query = new Query(manifest.entity.schema.properties)
|
|
15
|
-
|
|
16
|
-
subject.query = subject[definition.subject]
|
|
17
|
-
|
|
18
11
|
const Type = TYPES[definition.type]
|
|
19
12
|
|
|
20
|
-
return new Type(cascade,
|
|
13
|
+
return new Type(cascade, scope, contract, query, definition)
|
|
21
14
|
}
|
|
22
15
|
|
|
23
16
|
const TYPES = {
|
package/src/receivers.js
CHANGED
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
const { Receiver, Locator } = require('@toa.io/core')
|
|
4
4
|
|
|
5
5
|
const boot = require('./index')
|
|
6
|
+
const extensions = require('./extensions')
|
|
6
7
|
|
|
7
8
|
const receivers = async (manifest, runtime) => {
|
|
8
9
|
if (manifest.receivers === undefined) return []
|
|
@@ -13,20 +14,22 @@ const receivers = async (manifest, runtime) => {
|
|
|
13
14
|
const local = await boot.remote(manifest.locator, manifest)
|
|
14
15
|
const bridge = boot.bridge.receiver(definition.bridge, manifest.path, label)
|
|
15
16
|
const receiver = new Receiver(definition, local, bridge)
|
|
17
|
+
const decorator = extensions.receiver(receiver, manifest.locator)
|
|
16
18
|
|
|
17
19
|
let transport = definition.binding
|
|
18
|
-
|
|
19
|
-
const
|
|
20
|
+
|
|
21
|
+
const [namespace, name, endpoint] = label.split('.')
|
|
22
|
+
const remote = new Locator(name, namespace)
|
|
20
23
|
|
|
21
24
|
if (transport === undefined) {
|
|
22
25
|
const discovery = await boot.discovery.discovery()
|
|
23
|
-
const { events } = await discovery.lookup(
|
|
26
|
+
const { events } = await discovery.lookup(remote)
|
|
24
27
|
|
|
25
28
|
transport = events[endpoint].binding
|
|
26
29
|
}
|
|
27
30
|
|
|
28
|
-
const { id } = new Locator(manifest)
|
|
29
|
-
const binding = boot.bindings.receive(transport,
|
|
31
|
+
const { id } = new Locator(manifest.name, manifest.namespace)
|
|
32
|
+
const binding = boot.bindings.receive(transport, remote, endpoint, id, decorator)
|
|
30
33
|
|
|
31
34
|
binding.depends(runtime)
|
|
32
35
|
receivers.push(binding)
|
package/src/remote.js
CHANGED
|
@@ -1,11 +1,16 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
3
|
const { Remote } = require('@toa.io/core')
|
|
4
|
-
const { remap } = require('@toa.io/
|
|
4
|
+
const { remap } = require('@toa.io/generic')
|
|
5
5
|
|
|
6
6
|
const boot = require('./index')
|
|
7
7
|
|
|
8
|
-
|
|
8
|
+
/**
|
|
9
|
+
* @param {toa.core.Locator} locator
|
|
10
|
+
* @param {toa.norm.Component} manifest
|
|
11
|
+
* @returns {Promise<Remote>}
|
|
12
|
+
*/
|
|
13
|
+
const remote = async (locator, manifest = undefined) => {
|
|
9
14
|
const discovery = await boot.discovery.discovery()
|
|
10
15
|
|
|
11
16
|
if (manifest === undefined) manifest = await discovery.lookup(locator)
|
package/src/storage.js
CHANGED
|
@@ -1,9 +1,20 @@
|
|
|
1
1
|
'use strict'
|
|
2
2
|
|
|
3
|
-
const
|
|
4
|
-
const { Storage } = require(storage)
|
|
3
|
+
const extensions = require('./extensions')
|
|
5
4
|
|
|
6
|
-
|
|
5
|
+
/**
|
|
6
|
+
* @param {toa.core.Locator} locator
|
|
7
|
+
* @param {string} provider
|
|
8
|
+
* @returns {toa.core.Storage}
|
|
9
|
+
*/
|
|
10
|
+
const storage = (locator, provider) => {
|
|
11
|
+
const { Factory } = require(provider)
|
|
12
|
+
|
|
13
|
+
/** @type {toa.core.storages.Factory} */
|
|
14
|
+
const factory = new Factory()
|
|
15
|
+
const storage = factory.storage(locator)
|
|
16
|
+
|
|
17
|
+
return extensions.storage(storage)
|
|
7
18
|
}
|
|
8
19
|
|
|
9
20
|
exports.storage = storage
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import * as _core from '@toa.io/core/types'
|
|
2
|
+
|
|
3
|
+
declare namespace toa.boot {
|
|
4
|
+
|
|
5
|
+
namespace composition {
|
|
6
|
+
|
|
7
|
+
type Options = {
|
|
8
|
+
bindings?: string[]
|
|
9
|
+
extensions?: string[]
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
type Composition = (paths: string[], options: composition.Options) => Promise<_core.Connector>
|
|
15
|
+
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
export type Options = toa.boot.composition.Options
|
|
19
|
+
export type Composition = toa.boot.Composition
|
package/types/index.d.ts
ADDED
package/LICENSE
DELETED
|
@@ -1,22 +0,0 @@
|
|
|
1
|
-
Copyright (c) 2020-present Artem Gurtovoi
|
|
2
|
-
|
|
3
|
-
MIT License
|
|
4
|
-
|
|
5
|
-
Permission is hereby granted, free of charge, to any person obtaining
|
|
6
|
-
a copy of this software and associated documentation files (the
|
|
7
|
-
"Software"), to deal in the Software without restriction, including
|
|
8
|
-
without limitation the rights to use, copy, modify, merge, publish,
|
|
9
|
-
distribute, sublicense, and/or sell copies of the Software, and to
|
|
10
|
-
permit persons to whom the Software is furnished to do so, subject to
|
|
11
|
-
the following conditions:
|
|
12
|
-
|
|
13
|
-
The above copyright notice and this permission notice shall be
|
|
14
|
-
included in all copies or substantial portions of the Software.
|
|
15
|
-
|
|
16
|
-
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
17
|
-
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
18
|
-
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
|
19
|
-
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
|
20
|
-
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
|
21
|
-
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
|
22
|
-
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
package/src/extensions.js
DELETED
|
@@ -1,25 +0,0 @@
|
|
|
1
|
-
'use strict'
|
|
2
|
-
|
|
3
|
-
const extensions = (manifest) => {
|
|
4
|
-
if (manifest.extensions === undefined) return
|
|
5
|
-
|
|
6
|
-
const extensions = []
|
|
7
|
-
|
|
8
|
-
for (const [key, value] of Object.entries(manifest.extensions)) {
|
|
9
|
-
extensions.push(extension(key, value, manifest))
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
return extensions
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
const extension = (name, definition, manifest) => {
|
|
16
|
-
if (factories[name] === undefined) {
|
|
17
|
-
factories[name] = new (require(name).Factory)()
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
return factories[name].connector(manifest.locator, definition)
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
const factories = {}
|
|
24
|
-
|
|
25
|
-
exports.extensions = extensions
|
package/src/runtime.js
DELETED
|
@@ -1,25 +0,0 @@
|
|
|
1
|
-
'use strict'
|
|
2
|
-
|
|
3
|
-
const { remap } = require('@toa.io/gears')
|
|
4
|
-
const { Runtime, Locator } = require('@toa.io/core')
|
|
5
|
-
|
|
6
|
-
const boot = require('./index')
|
|
7
|
-
|
|
8
|
-
const runtime = async (manifest) => {
|
|
9
|
-
const locator = new Locator(manifest)
|
|
10
|
-
const storage = boot.storage(locator, manifest.entity.storage)
|
|
11
|
-
const context = await boot.context(manifest)
|
|
12
|
-
const emission = boot.emission(manifest.events, locator)
|
|
13
|
-
|
|
14
|
-
const operations = remap(manifest.operations, (definition, endpoint) =>
|
|
15
|
-
boot.operation(manifest, endpoint, definition, context, storage, emission))
|
|
16
|
-
|
|
17
|
-
const runtime = new Runtime(locator, operations)
|
|
18
|
-
|
|
19
|
-
if (storage) runtime.depends(storage)
|
|
20
|
-
if (emission) runtime.depends(emission)
|
|
21
|
-
|
|
22
|
-
return runtime
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
exports.runtime = runtime
|