@weave-js/core 0.10.0 → 0.12.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/.eslintrc.js +1 -1
- package/jest.config.js +1 -1
- package/lib/ExtendableError.js +33 -0
- package/lib/broker/context.js +58 -46
- package/lib/broker/{default-options.js → defaultOptions.js} +31 -13
- package/lib/broker/index.js +273 -251
- package/lib/buildRuntime.js +70 -0
- package/lib/cache/adapters/base.js +119 -0
- package/lib/cache/adapters/inMemory.js +154 -0
- package/lib/cache/adapters/inMemoryLru.js +140 -0
- package/lib/cache/adapters/index.js +10 -0
- package/lib/cache/getCacheKeyByObject.js +31 -0
- package/lib/cache/getPropertyFromDataOrMetadata.js +20 -0
- package/lib/cache/lock.js +34 -11
- package/lib/constants.js +11 -8
- package/lib/{error-handler.js → errorHandler.js} +8 -8
- package/lib/errors.js +46 -39
- package/lib/helper/{define-action.js → defineAction.js} +5 -3
- package/lib/helper/{define-broker-options.js → defineBrokerOptions.js} +4 -2
- package/lib/helper/{define-service.js → defineService.js} +6 -3
- package/lib/index.js +25 -22
- package/lib/logger/base.js +38 -29
- package/lib/logger/format/asHumanReadable.js +15 -14
- package/lib/logger/format/asJson.js +10 -10
- package/lib/logger/format/index.js +3 -3
- package/lib/logger/index.js +28 -25
- package/lib/logger/levels.js +23 -22
- package/lib/logger/tools.js +17 -13
- package/lib/logger/utils/colorize.js +23 -23
- package/lib/logger/utils/format.js +89 -65
- package/lib/metrics/common.js +47 -47
- package/lib/metrics/constants.js +44 -44
- package/lib/metrics/exporter/base.js +8 -8
- package/lib/metrics/exporter/event.js +20 -20
- package/lib/metrics/exporter/index.js +15 -15
- package/lib/metrics/index.js +2 -2
- package/lib/metrics/types/base.js +20 -20
- package/lib/metrics/types/counter.js +6 -6
- package/lib/metrics/types/gauge.js +24 -24
- package/lib/metrics/types/histogram.js +26 -26
- package/lib/metrics/types/index.js +6 -6
- package/lib/metrics/types/info.js +17 -17
- package/lib/middlewares/action-hooks/index.js +82 -34
- package/lib/middlewares/bulkhead/index.js +34 -33
- package/lib/middlewares/cache/index.js +106 -0
- package/lib/middlewares/circuit-breaker/index.js +85 -60
- package/lib/middlewares/context-tracker/index.js +39 -39
- package/lib/middlewares/error-handler/index.js +14 -14
- package/lib/middlewares/index.js +3 -2
- package/lib/middlewares/metrics/getMiddlewareWrapper.js +17 -17
- package/lib/middlewares/metrics/index.js +29 -29
- package/lib/middlewares/retry/index.js +15 -15
- package/lib/middlewares/timeout/index.js +18 -18
- package/lib/middlewares/tracing/index.js +50 -37
- package/lib/middlewares/tracing/tags.js +43 -0
- package/lib/middlewares/validator/index.js +32 -32
- package/lib/registry/{action-endpoint.js → actionEndpoint.js} +8 -8
- package/lib/registry/collections/{action-collection.js → actionCollection.js} +39 -35
- package/lib/registry/collections/{endpoint-collection.js → endpointCollection.js} +64 -65
- package/lib/registry/collections/{event-collection.js → eventCollection.js} +65 -69
- package/lib/registry/collections/{node-collection.js → nodeCollection.js} +45 -45
- package/lib/registry/collections/{service-collection.js → serviceCollection.js} +61 -55
- package/lib/registry/eventEndpoint.js +26 -0
- package/lib/registry/load-balancer/base.js +3 -3
- package/lib/registry/load-balancer/index.js +7 -7
- package/lib/registry/node.js +27 -27
- package/lib/registry/registry.js +147 -163
- package/lib/registry/service/parseAction.js +16 -16
- package/lib/registry/service/parseEvent.js +18 -18
- package/lib/registry/service/reduceMixins.js +10 -10
- package/lib/registry/service/service.js +72 -72
- package/lib/registry/{service-item.js → serviceItem.js} +21 -21
- package/lib/runtime/{init-action-invoker.js → initActionInvoker.js} +21 -21
- package/lib/runtime/initCache.js +19 -0
- package/lib/runtime/{init-context-factory.js → initContextFactory.js} +22 -22
- package/lib/runtime/{init-eventbus.js → initEventbus.js} +54 -53
- package/lib/runtime/{init-logger.js → initLogger.js} +11 -11
- package/lib/runtime/{init-metrics.js → initMetrics.js} +55 -54
- package/lib/runtime/{init-middleware-manager.js → initMiddlewareManager.js} +21 -21
- package/lib/runtime/{init-registry.js → initRegistry.js} +6 -6
- package/lib/runtime/initServiceManager.js +145 -0
- package/lib/runtime/{init-tracing.js → initTracing.js} +25 -24
- package/lib/runtime/{init-transport.js → initTransport.js} +5 -5
- package/lib/runtime/{init-uuid-factory.js → initUuidFactory.js} +4 -4
- package/lib/runtime/{init-validator.js → initValidator.js} +5 -5
- package/lib/tracing/collectors/base.js +29 -37
- package/lib/tracing/collectors/event.js +33 -33
- package/lib/tracing/collectors/index.js +16 -16
- package/lib/tracing/span.js +34 -32
- package/lib/tracing/time.js +8 -8
- package/lib/transport/InboundTransformStream.js +75 -0
- package/lib/transport/adapters/adapteBase.js +107 -0
- package/lib/transport/adapters/adapters.js +4 -4
- package/lib/transport/adapters/dummy/index.js +19 -19
- package/lib/transport/adapters/fromURI.js +13 -13
- package/lib/transport/adapters/getAdapterByName.js +5 -5
- package/lib/transport/adapters/index.js +12 -12
- package/lib/transport/adapters/tcp/discovery/codec.js +4 -4
- package/lib/transport/adapters/tcp/discovery/index.js +90 -76
- package/lib/transport/adapters/tcp/index.js +180 -175
- package/lib/transport/adapters/tcp/tcp-messagetypes.js +7 -7
- package/lib/transport/adapters/tcp/tcpReader.js +39 -38
- package/lib/transport/adapters/tcp/tcpWriteStream.js +26 -26
- package/lib/transport/adapters/tcp/tcpWriter.js +58 -58
- package/lib/transport/adapters/tcp/utils.js +12 -12
- package/lib/transport/createMessage.js +11 -0
- package/lib/transport/createTransport.js +377 -334
- package/lib/transport/errorPayloadFactory.js +15 -0
- package/lib/transport/messageHandlers.js +517 -0
- package/lib/transport/messageTypes.js +23 -0
- package/lib/types.js +95 -71
- package/lib/utils/index.js +2 -2
- package/lib/utils/options.js +47 -45
- package/lib/utils/{restore-error.js → restoreError.js} +4 -4
- package/package.json +6 -12
- package/CHANGELOG.md +0 -1334
- package/lib/build-runtime.js +0 -70
- package/lib/cache/base.js +0 -142
- package/lib/cache/index.js +0 -48
- package/lib/cache/memory.js +0 -121
- package/lib/middlewares/tracing/buildTags.js +0 -17
- package/lib/new-errors.js +0 -25
- package/lib/registry/event-endpoint.js +0 -26
- package/lib/runtime/init-cache.js +0 -10
- package/lib/runtime/init-service-manager.js +0 -128
- package/lib/tracing/collectors/console.js +0 -34
- package/lib/tracing/index.js +0 -3
- package/lib/tracing/tracer.js +0 -64
- package/lib/transport/adapters/adapter-base.js +0 -92
- package/lib/transport/message-handlers.js +0 -448
- package/lib/transport/message-types.js +0 -59
- package/lib/transport/message.js +0 -16
package/lib/registry/registry.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
// @ts-check
|
|
2
2
|
/*
|
|
3
|
-
* Author: Kevin Ries (kevin@
|
|
3
|
+
* Author: Kevin Ries (kevin.ries@fachwerk.io)
|
|
4
4
|
* -----
|
|
5
5
|
* Copyright 2021 Fachwerk
|
|
6
6
|
*/
|
|
@@ -18,18 +18,18 @@
|
|
|
18
18
|
* @typedef {import('../types.js').ServiceChangedDelegate} ServiceChangedDelegate
|
|
19
19
|
*/
|
|
20
20
|
|
|
21
|
-
const { safeCopy } = require('@weave-js/utils')
|
|
21
|
+
const { safeCopy } = require('@weave-js/utils');
|
|
22
22
|
|
|
23
23
|
// own packages
|
|
24
|
-
const { createNodeCollection } = require('./collections/
|
|
25
|
-
const { createServiceCollection } = require('./collections/
|
|
26
|
-
const { createActionCollection } = require('./collections/
|
|
27
|
-
const { createEventCollection } = require('./collections/
|
|
28
|
-
const { createActionEndpoint } = require('./
|
|
29
|
-
const { createNode } = require('./node')
|
|
30
|
-
const { WeaveServiceNotFoundError, WeaveServiceNotAvailableError } = require('../errors')
|
|
24
|
+
const { createNodeCollection } = require('./collections/nodeCollection');
|
|
25
|
+
const { createServiceCollection } = require('./collections/serviceCollection');
|
|
26
|
+
const { createActionCollection } = require('./collections/actionCollection');
|
|
27
|
+
const { createEventCollection } = require('./collections/eventCollection');
|
|
28
|
+
const { createActionEndpoint } = require('./actionEndpoint');
|
|
29
|
+
const { createNode } = require('./node');
|
|
30
|
+
const { WeaveServiceNotFoundError, WeaveServiceNotAvailableError } = require('../errors');
|
|
31
31
|
|
|
32
|
-
const noop = () => {}
|
|
32
|
+
const noop = () => {};
|
|
33
33
|
|
|
34
34
|
/**
|
|
35
35
|
* Registry factory
|
|
@@ -37,7 +37,7 @@ const noop = () => {}
|
|
|
37
37
|
* @returns {Registry} Registry
|
|
38
38
|
*/
|
|
39
39
|
exports.createRegistry = (runtime) => {
|
|
40
|
-
const { middlewareHandler } = runtime
|
|
40
|
+
const { middlewareHandler } = runtime;
|
|
41
41
|
|
|
42
42
|
/**
|
|
43
43
|
* @type {Registry}
|
|
@@ -47,277 +47,267 @@ exports.createRegistry = (runtime) => {
|
|
|
47
47
|
log: runtime.createLogger('REGISTRY'),
|
|
48
48
|
/**
|
|
49
49
|
* Initialize the registry
|
|
50
|
-
* @param {
|
|
51
|
-
* @param {MiddlewareHandler} middlewareHandler Middleware handler
|
|
52
|
-
* @param {ServiceChangedDelegate} serviceChanged Service changed delegate
|
|
50
|
+
* @param {Runtime} runtime Runtime
|
|
53
51
|
* @returns {void}
|
|
54
52
|
*/
|
|
55
53
|
init (runtime) {
|
|
56
|
-
/**
|
|
57
|
-
* @type {Broker}
|
|
58
|
-
*/
|
|
59
|
-
|
|
60
|
-
/**
|
|
61
|
-
* @type {MiddlewareHandler}
|
|
62
|
-
*/
|
|
63
|
-
|
|
64
|
-
/**
|
|
65
|
-
* @type {ServiceChangedDelegate}
|
|
66
|
-
*/
|
|
67
|
-
|
|
68
54
|
// init collections
|
|
69
|
-
this.nodeCollection = createNodeCollection(this)
|
|
70
|
-
this.serviceCollection = createServiceCollection(this)
|
|
71
|
-
this.actionCollection = createActionCollection(this)
|
|
72
|
-
this.eventCollection = createEventCollection(this)
|
|
55
|
+
this.nodeCollection = createNodeCollection(this);
|
|
56
|
+
this.serviceCollection = createServiceCollection(this);
|
|
57
|
+
this.actionCollection = createActionCollection(this);
|
|
58
|
+
this.eventCollection = createEventCollection(this);
|
|
73
59
|
|
|
74
60
|
// register an event handler for "$broker.started".
|
|
75
61
|
runtime.bus.on('$broker.started', () => {
|
|
76
62
|
if (this.nodeCollection.localNode) {
|
|
77
|
-
this.generateLocalNodeInfo(true)
|
|
63
|
+
this.generateLocalNodeInfo(true);
|
|
78
64
|
}
|
|
79
|
-
})
|
|
65
|
+
});
|
|
80
66
|
},
|
|
81
67
|
onRegisterLocalAction: noop,
|
|
82
68
|
onRegisterRemoteAction: noop,
|
|
83
69
|
checkActionVisibility (action, node) {
|
|
84
|
-
if (
|
|
85
|
-
|
|
70
|
+
if (
|
|
71
|
+
typeof action.visibility === 'undefined' ||
|
|
72
|
+
action.visibility === 'public' ||
|
|
73
|
+
action.visibility === 'published'
|
|
74
|
+
) {
|
|
75
|
+
return true;
|
|
86
76
|
}
|
|
87
77
|
|
|
78
|
+
// Only callable from local services.
|
|
88
79
|
if (action.visibility === 'protected' && node.isLocal) {
|
|
89
|
-
return true
|
|
80
|
+
return true;
|
|
90
81
|
}
|
|
91
82
|
|
|
92
|
-
return false
|
|
83
|
+
return false;
|
|
93
84
|
},
|
|
94
85
|
registerLocalService (serviceSpecification) {
|
|
95
86
|
if (!this.serviceCollection.has(serviceSpecification.name, serviceSpecification.version, runtime.nodeId)) {
|
|
96
|
-
const service = this.serviceCollection.add(this.nodeCollection.localNode, serviceSpecification.name, serviceSpecification.version, serviceSpecification.settings)
|
|
87
|
+
const service = this.serviceCollection.add(this.nodeCollection.localNode, serviceSpecification.name, serviceSpecification.version, serviceSpecification.settings);
|
|
97
88
|
|
|
98
89
|
if (serviceSpecification.actions) {
|
|
99
|
-
this.registerActions(this.nodeCollection.localNode, service, serviceSpecification.actions)
|
|
90
|
+
this.registerActions(this.nodeCollection.localNode, service, serviceSpecification.actions);
|
|
100
91
|
}
|
|
101
92
|
|
|
102
93
|
if (serviceSpecification.events) {
|
|
103
|
-
this.registerEvents(this.nodeCollection.localNode, service, serviceSpecification.events)
|
|
94
|
+
this.registerEvents(this.nodeCollection.localNode, service, serviceSpecification.events);
|
|
104
95
|
}
|
|
105
96
|
|
|
106
|
-
this.nodeCollection.localNode.services.push(service)
|
|
97
|
+
this.nodeCollection.localNode.services.push(service);
|
|
107
98
|
|
|
108
|
-
this.generateLocalNodeInfo(runtime.state.isStarted)
|
|
99
|
+
this.generateLocalNodeInfo(runtime.state.isStarted);
|
|
109
100
|
|
|
110
101
|
if (serviceSpecification.version) {
|
|
111
|
-
this.log.info(`Service '${service.name}' (v${serviceSpecification.version}) registered.`)
|
|
102
|
+
this.log.info(`Service '${service.name}' (v${serviceSpecification.version}) registered.`);
|
|
112
103
|
} else {
|
|
113
|
-
this.log.info(`Service '${service.name}' registered.`)
|
|
104
|
+
this.log.info(`Service '${service.name}' registered.`);
|
|
114
105
|
}
|
|
115
106
|
|
|
116
|
-
runtime.services.serviceChanged(true)
|
|
107
|
+
runtime.services.serviceChanged(true);
|
|
117
108
|
}
|
|
118
109
|
},
|
|
119
110
|
registerRemoteServices (node, services) {
|
|
120
111
|
services.forEach((service) => {
|
|
121
112
|
// todo: handle events
|
|
122
|
-
let oldActions
|
|
123
|
-
let oldEvents
|
|
124
|
-
let svc = this.serviceCollection.get(node.id, service.name, service.version)
|
|
113
|
+
let oldActions;
|
|
114
|
+
let oldEvents;
|
|
115
|
+
let svc = this.serviceCollection.get(node.id, service.name, service.version);
|
|
125
116
|
|
|
126
117
|
if (!svc) {
|
|
127
|
-
svc = this.serviceCollection.add(node, service.name, service.version, service.settings)
|
|
118
|
+
svc = this.serviceCollection.add(node, service.name, service.version, service.settings);
|
|
128
119
|
} else {
|
|
129
120
|
// Update existing service with new actions
|
|
130
|
-
oldActions = Object.assign({}, svc.actions)
|
|
131
|
-
oldEvents = Object.assign({}, svc.events)
|
|
132
|
-
svc.update(service)
|
|
121
|
+
oldActions = Object.assign({}, svc.actions);
|
|
122
|
+
oldEvents = Object.assign({}, svc.events);
|
|
123
|
+
svc.update(service);
|
|
133
124
|
}
|
|
134
125
|
|
|
135
126
|
if (service.actions) {
|
|
136
|
-
this.registerActions(node, svc, service.actions)
|
|
127
|
+
this.registerActions(node, svc, service.actions);
|
|
137
128
|
}
|
|
138
129
|
|
|
139
130
|
if (service.events) {
|
|
140
|
-
this.registerEvents(node, svc, service.events)
|
|
131
|
+
this.registerEvents(node, svc, service.events);
|
|
141
132
|
}
|
|
142
133
|
|
|
143
134
|
if (oldActions) {
|
|
144
|
-
// this.deregisterAction()
|
|
145
135
|
Object.keys(oldActions).forEach(actionName => {
|
|
146
136
|
if (!service.actions[actionName]) {
|
|
147
|
-
this.actionCollection.remove(actionName, node)
|
|
137
|
+
this.actionCollection.remove(actionName, node);
|
|
148
138
|
}
|
|
149
|
-
})
|
|
139
|
+
});
|
|
150
140
|
}
|
|
151
141
|
|
|
152
142
|
if (oldEvents) {
|
|
153
143
|
Object.keys(oldEvents).forEach(eventName => {
|
|
154
144
|
if (!service.actions[eventName]) {
|
|
155
|
-
this.eventCollection.remove(eventName, node)
|
|
145
|
+
this.eventCollection.remove(eventName, node);
|
|
156
146
|
}
|
|
157
|
-
})
|
|
147
|
+
});
|
|
158
148
|
}
|
|
159
|
-
})
|
|
149
|
+
});
|
|
160
150
|
|
|
161
151
|
// remove old services
|
|
162
|
-
const oldServices = Array.from(this.serviceCollection.services)
|
|
163
|
-
oldServices.forEach((
|
|
164
|
-
if (
|
|
152
|
+
const oldServices = Array.from(this.serviceCollection.services);
|
|
153
|
+
oldServices.forEach((oldService) => {
|
|
154
|
+
if (oldService.node.id !== node.id) {
|
|
155
|
+
return;
|
|
156
|
+
}
|
|
165
157
|
|
|
166
|
-
let isExisting = false
|
|
158
|
+
let isExisting = false;
|
|
167
159
|
|
|
160
|
+
// check if the old service exists in the new services.
|
|
168
161
|
services.forEach((svc) => {
|
|
169
|
-
if (
|
|
170
|
-
isExisting = true
|
|
162
|
+
if (oldService.equals(svc.name, svc.version)) {
|
|
163
|
+
isExisting = true;
|
|
171
164
|
}
|
|
172
|
-
})
|
|
165
|
+
});
|
|
173
166
|
|
|
174
167
|
if (!isExisting) {
|
|
175
|
-
this.deregisterService(
|
|
168
|
+
this.deregisterService(oldService.name, oldService.version, node.id);
|
|
176
169
|
}
|
|
177
|
-
})
|
|
170
|
+
});
|
|
178
171
|
|
|
179
|
-
runtime.services.serviceChanged(false)
|
|
172
|
+
runtime.services.serviceChanged(false);
|
|
180
173
|
},
|
|
181
174
|
registerEvents (node, service, events) {
|
|
182
175
|
Object.keys(events).forEach((key) => {
|
|
183
|
-
const event = events[key]
|
|
176
|
+
const event = events[key];
|
|
184
177
|
|
|
185
178
|
if (node.isLocal) {
|
|
186
|
-
event.handler = middlewareHandler.wrapHandler('localEvent', event.handler, event) // this.onRegisterLocalEvent(event)
|
|
179
|
+
event.handler = middlewareHandler.wrapHandler('localEvent', event.handler, event); // this.onRegisterLocalEvent(event)
|
|
187
180
|
}
|
|
188
181
|
|
|
189
|
-
this.eventCollection.add(node, service, event)
|
|
190
|
-
service.addEvent(event)
|
|
191
|
-
})
|
|
182
|
+
this.eventCollection.add(node, service, event);
|
|
183
|
+
service.addEvent(event);
|
|
184
|
+
});
|
|
192
185
|
},
|
|
193
186
|
registerActions (node, service, actions) {
|
|
194
187
|
Object.keys(actions).forEach((key) => {
|
|
195
|
-
const action = actions[key]
|
|
188
|
+
const action = actions[key];
|
|
196
189
|
|
|
197
190
|
if (!this.checkActionVisibility(action, node)) {
|
|
198
|
-
return
|
|
191
|
+
return;
|
|
199
192
|
}
|
|
200
193
|
|
|
201
194
|
if (node.isLocal) {
|
|
202
|
-
action.handler = middlewareHandler.wrapHandler('localAction', action.handler, action)
|
|
195
|
+
action.handler = middlewareHandler.wrapHandler('localAction', action.handler, action);
|
|
203
196
|
} else {
|
|
204
|
-
action.handler = middlewareHandler.wrapHandler('remoteAction', runtime.transport.
|
|
197
|
+
action.handler = middlewareHandler.wrapHandler('remoteAction', runtime.transport.sendRequest.bind(runtime.transport), action);
|
|
205
198
|
}
|
|
206
199
|
|
|
207
|
-
this.actionCollection.add(node, service, action)
|
|
200
|
+
this.actionCollection.add(node, service, action);
|
|
208
201
|
|
|
209
|
-
service.addAction(action)
|
|
210
|
-
})
|
|
211
|
-
},
|
|
212
|
-
getActionList (options) {
|
|
213
|
-
return this.actionCollection.list(options)
|
|
202
|
+
service.addAction(action);
|
|
203
|
+
});
|
|
214
204
|
},
|
|
215
205
|
deregisterService (name, version, nodeId) {
|
|
216
|
-
this.serviceCollection.remove(nodeId || runtime.nodeId, name, version)
|
|
206
|
+
this.serviceCollection.remove(nodeId || runtime.nodeId, name, version);
|
|
217
207
|
|
|
218
|
-
// It must be a local service
|
|
208
|
+
// It must be a local service if there is no node ID.
|
|
219
209
|
if (!nodeId) {
|
|
220
|
-
const serviceToRemove = this.nodeCollection.localNode.services.find(service => service.name === name)
|
|
221
|
-
this.nodeCollection.localNode.services.splice(this.nodeCollection.localNode.services.indexOf(serviceToRemove), 1)
|
|
210
|
+
const serviceToRemove = this.nodeCollection.localNode.services.find(service => service.name === name);
|
|
211
|
+
this.nodeCollection.localNode.services.splice(this.nodeCollection.localNode.services.indexOf(serviceToRemove), 1);
|
|
222
212
|
}
|
|
223
213
|
|
|
224
214
|
if (!nodeId || nodeId === runtime.nodeId) {
|
|
225
|
-
this.generateLocalNodeInfo(true)
|
|
215
|
+
this.generateLocalNodeInfo(true);
|
|
226
216
|
}
|
|
227
217
|
},
|
|
228
218
|
deregisterServiceByNodeId (nodeId) {
|
|
229
|
-
return this.serviceCollection.removeAllByNodeId(nodeId)
|
|
219
|
+
return this.serviceCollection.removeAllByNodeId(nodeId);
|
|
230
220
|
},
|
|
231
221
|
hasService (serviceName, version, nodeId) {
|
|
232
|
-
return this.serviceCollection.has(serviceName, version, nodeId)
|
|
222
|
+
return this.serviceCollection.has(serviceName, version, nodeId);
|
|
233
223
|
},
|
|
234
224
|
getNextAvailableActionEndpoint (actionName, opts = {}) {
|
|
235
225
|
// Handle direct endpoint call.
|
|
236
226
|
if (typeof actionName !== 'string') {
|
|
237
|
-
return actionName
|
|
227
|
+
return actionName;
|
|
238
228
|
} else {
|
|
239
229
|
// check if the action call is intended for a specific remote node
|
|
240
230
|
if (opts.nodeId) {
|
|
241
|
-
const endpoint = this.getActionEndpointByNodeId(actionName, opts.nodeId)
|
|
231
|
+
const endpoint = this.getActionEndpointByNodeId(actionName, opts.nodeId);
|
|
242
232
|
|
|
243
233
|
// no endpoint for this action & node ID found
|
|
244
234
|
if (!endpoint) {
|
|
245
|
-
this.log.warn(`Service "${actionName}" is not registered on node ${opts.nodeId}.`)
|
|
246
|
-
return new WeaveServiceNotFoundError({ actionName, nodeId: opts.nodeId })
|
|
235
|
+
this.log.warn(`Service "${actionName}" is not registered on node ${opts.nodeId}.`);
|
|
236
|
+
return new WeaveServiceNotFoundError({ actionName, nodeId: opts.nodeId });
|
|
247
237
|
}
|
|
248
238
|
|
|
249
|
-
return endpoint
|
|
239
|
+
return endpoint;
|
|
250
240
|
} else {
|
|
251
|
-
const endpointList = this.getActionEndpoints(actionName)
|
|
241
|
+
const endpointList = this.getActionEndpoints(actionName);
|
|
252
242
|
|
|
253
243
|
if (!endpointList) {
|
|
254
|
-
this.log.warn(`Service "${actionName}" is not registered.`)
|
|
255
|
-
return new WeaveServiceNotFoundError({ actionName })
|
|
244
|
+
this.log.warn(`Service "${actionName}" is not registered.`);
|
|
245
|
+
return new WeaveServiceNotFoundError({ actionName });
|
|
256
246
|
}
|
|
257
247
|
|
|
258
|
-
const endpoint = endpointList.getNextAvailableEndpoint()
|
|
248
|
+
const endpoint = endpointList.getNextAvailableEndpoint();
|
|
259
249
|
|
|
260
250
|
if (!endpoint) {
|
|
261
|
-
this.log.warn(`Service "${actionName}" is not available.`)
|
|
262
|
-
return new WeaveServiceNotAvailableError({ actionName })
|
|
251
|
+
this.log.warn(`Service "${actionName}" is not available.`);
|
|
252
|
+
return new WeaveServiceNotAvailableError({ actionName });
|
|
263
253
|
}
|
|
264
254
|
|
|
265
|
-
return endpoint
|
|
255
|
+
return endpoint;
|
|
266
256
|
}
|
|
267
257
|
}
|
|
268
258
|
},
|
|
269
259
|
getActionEndpointByNodeId (actionName, nodeId) {
|
|
270
|
-
const endpointList = this.getActionEndpoints(actionName)
|
|
260
|
+
const endpointList = this.getActionEndpoints(actionName);
|
|
271
261
|
if (endpointList) {
|
|
272
|
-
return endpointList.getByNodeId(nodeId)
|
|
262
|
+
return endpointList.getByNodeId(nodeId);
|
|
273
263
|
}
|
|
274
|
-
return null
|
|
264
|
+
return null;
|
|
275
265
|
},
|
|
276
266
|
getActionEndpoints (actionName) {
|
|
277
|
-
return this.actionCollection.get(actionName)
|
|
267
|
+
return this.actionCollection.get(actionName);
|
|
278
268
|
},
|
|
279
269
|
createPrivateActionEndpoint (action) {
|
|
280
|
-
return createActionEndpoint(runtime, this.nodeCollection.localNode, action.service, action)
|
|
270
|
+
return createActionEndpoint(runtime, this.nodeCollection.localNode, action.service, action);
|
|
281
271
|
},
|
|
282
272
|
getLocalActionEndpoint (actionName) {
|
|
283
|
-
const endpointList = this.getActionEndpoints(actionName)
|
|
273
|
+
const endpointList = this.getActionEndpoints(actionName);
|
|
284
274
|
|
|
285
275
|
if (!endpointList) {
|
|
286
|
-
this.log.warn(`Service "${actionName}" is not registered localy.`)
|
|
287
|
-
runtime.handleError(new WeaveServiceNotFoundError({ actionName }))
|
|
276
|
+
this.log.warn(`Service "${actionName}" is not registered localy.`);
|
|
277
|
+
runtime.handleError(new WeaveServiceNotFoundError({ actionName }));
|
|
288
278
|
}
|
|
289
279
|
|
|
290
|
-
const endpoint = endpointList.getNextLocalEndpoint()
|
|
280
|
+
const endpoint = endpointList.getNextLocalEndpoint();
|
|
291
281
|
|
|
292
282
|
if (!endpoint) {
|
|
293
|
-
this.log.warn(`Service "${actionName}" is not available localy.`)
|
|
294
|
-
runtime.handleError(new WeaveServiceNotAvailableError({ actionName }))
|
|
283
|
+
this.log.warn(`Service "${actionName}" is not available localy.`);
|
|
284
|
+
runtime.handleError(new WeaveServiceNotAvailableError({ actionName }));
|
|
295
285
|
}
|
|
296
286
|
|
|
297
|
-
return endpoint
|
|
287
|
+
return endpoint;
|
|
298
288
|
},
|
|
299
289
|
getNodeInfo (nodeId) {
|
|
300
|
-
const node = this.nodeCollection.get(nodeId)
|
|
290
|
+
const node = this.nodeCollection.get(nodeId);
|
|
301
291
|
|
|
302
292
|
if (!node) {
|
|
303
|
-
return null
|
|
293
|
+
return null;
|
|
304
294
|
}
|
|
305
295
|
|
|
306
|
-
return node.info
|
|
296
|
+
return node.info;
|
|
307
297
|
},
|
|
308
298
|
getLocalNodeInfo (forceGenerateInfo) {
|
|
309
299
|
if (forceGenerateInfo || !this.nodeCollection.localNode.info) {
|
|
310
|
-
return this.generateLocalNodeInfo()
|
|
300
|
+
return this.generateLocalNodeInfo();
|
|
311
301
|
}
|
|
312
302
|
|
|
313
|
-
return this.nodeCollection.localNode.info
|
|
303
|
+
return this.nodeCollection.localNode.info;
|
|
314
304
|
},
|
|
315
305
|
generateLocalNodeInfo (incrementSequence = false) {
|
|
316
|
-
const { client, IPList, sequence } = this.nodeCollection.localNode
|
|
317
|
-
const nodeInfo = { client, IPList, sequence }
|
|
306
|
+
const { client, IPList, sequence } = this.nodeCollection.localNode;
|
|
307
|
+
const nodeInfo = { client, IPList, sequence };
|
|
318
308
|
|
|
319
309
|
if (incrementSequence) {
|
|
320
|
-
this.nodeCollection.localNode.sequence
|
|
310
|
+
this.nodeCollection.localNode.sequence++;
|
|
321
311
|
}
|
|
322
312
|
|
|
323
313
|
if (runtime.state.isStarted) {
|
|
@@ -327,86 +317,80 @@ exports.createRegistry = (runtime) => {
|
|
|
327
317
|
withEvents: true,
|
|
328
318
|
withNodeService: runtime.options.registry.publishNodeService,
|
|
329
319
|
withSettings: true
|
|
330
|
-
})
|
|
320
|
+
});
|
|
331
321
|
} else {
|
|
332
|
-
nodeInfo.services = []
|
|
322
|
+
nodeInfo.services = [];
|
|
333
323
|
}
|
|
334
324
|
|
|
335
|
-
this.nodeCollection.localNode.info = safeCopy(nodeInfo)
|
|
336
|
-
return this.nodeCollection.localNode.info
|
|
325
|
+
this.nodeCollection.localNode.info = safeCopy(nodeInfo);
|
|
326
|
+
return this.nodeCollection.localNode.info;
|
|
337
327
|
},
|
|
338
328
|
processNodeInfo (payload) {
|
|
339
329
|
/**
|
|
340
330
|
* @type {string}
|
|
341
331
|
*/
|
|
342
|
-
const nodeId = payload.sender
|
|
332
|
+
const nodeId = payload.sender;
|
|
343
333
|
|
|
344
334
|
/**
|
|
345
335
|
* @type {Node}
|
|
346
336
|
*/
|
|
347
|
-
let node = this.nodeCollection.get(nodeId)
|
|
337
|
+
let node = this.nodeCollection.get(nodeId);
|
|
348
338
|
|
|
349
339
|
/**
|
|
350
340
|
* @type {boolean}
|
|
351
341
|
*/
|
|
352
|
-
let isNew = false
|
|
342
|
+
let isNew = false;
|
|
353
343
|
|
|
354
344
|
/**
|
|
355
345
|
* @type {boolean}
|
|
356
346
|
*/
|
|
357
|
-
let isReconnected = false
|
|
347
|
+
let isReconnected = false;
|
|
358
348
|
|
|
359
349
|
// There is no node with the specified ID. It must therefore be a new node.
|
|
360
350
|
if (!node) {
|
|
361
|
-
isNew = true
|
|
362
|
-
node = createNode(nodeId)
|
|
363
|
-
this.nodeCollection.add(nodeId, node)
|
|
351
|
+
isNew = true;
|
|
352
|
+
node = createNode(nodeId);
|
|
353
|
+
this.nodeCollection.add(nodeId, node);
|
|
364
354
|
} else if (!node.isAvailable) {
|
|
365
355
|
// Node exists, but is marked as unavailable. It must therefore be a reconnected node.
|
|
366
|
-
isReconnected = true
|
|
367
|
-
node.isAvailable = true
|
|
368
|
-
node.lastHeartbeatTime = Date.now()
|
|
356
|
+
isReconnected = true;
|
|
357
|
+
node.isAvailable = true;
|
|
358
|
+
node.lastHeartbeatTime = Date.now();
|
|
369
359
|
}
|
|
370
360
|
|
|
371
361
|
// todo: Handle multiple nodes with the same ID.
|
|
372
|
-
const
|
|
362
|
+
const updateNecessary = node.update(payload, isReconnected);
|
|
373
363
|
|
|
374
|
-
if (
|
|
375
|
-
this.registerRemoteServices(node, node.services)
|
|
364
|
+
if (updateNecessary && node.services) {
|
|
365
|
+
this.registerRemoteServices(node, node.services);
|
|
376
366
|
}
|
|
377
367
|
|
|
378
368
|
if (isNew) {
|
|
379
|
-
runtime.eventBus.broadcastLocal('$node.connected', { node, isReconnected })
|
|
380
|
-
this.log.info(`Node "${node.id}" connected!`)
|
|
369
|
+
runtime.eventBus.broadcastLocal('$node.connected', { node, isReconnected });
|
|
370
|
+
this.log.info(`Node "${node.id}" connected!`);
|
|
381
371
|
} else if (isReconnected) {
|
|
382
|
-
runtime.eventBus.broadcastLocal('$node.connected', { node, isReconnected })
|
|
383
|
-
this.log.info(`Node "${node.id}" reconnected!`)
|
|
372
|
+
runtime.eventBus.broadcastLocal('$node.connected', { node, isReconnected });
|
|
373
|
+
this.log.info(`Node "${node.id}" reconnected!`);
|
|
384
374
|
} else {
|
|
385
|
-
runtime.eventBus.broadcastLocal('$node.updated', { node, isReconnected })
|
|
386
|
-
this.log.info(`Node "${node.id}" updated!`)
|
|
375
|
+
runtime.eventBus.broadcastLocal('$node.updated', { node, isReconnected });
|
|
376
|
+
this.log.info(`Node "${node.id}" updated!`);
|
|
387
377
|
}
|
|
388
378
|
},
|
|
389
379
|
nodeDisconnected (nodeId, isUnexpected) {
|
|
390
|
-
const node = this.nodeCollection.get(nodeId)
|
|
380
|
+
const node = this.nodeCollection.get(nodeId);
|
|
391
381
|
if (node && node.isAvailable) {
|
|
392
|
-
this.deregisterServiceByNodeId(node.id)
|
|
393
|
-
node.disconnected(isUnexpected)
|
|
394
|
-
runtime.eventBus.broadcastLocal('$node.disconnected', { nodeId, isUnexpected })
|
|
395
|
-
this.log.warn(`Nodes "${node.id}"${isUnexpected ? ' unexpectedly' : ''} disconnected.`)
|
|
382
|
+
this.deregisterServiceByNodeId(node.id);
|
|
383
|
+
node.disconnected(isUnexpected);
|
|
384
|
+
runtime.eventBus.broadcastLocal('$node.disconnected', { nodeId, isUnexpected });
|
|
385
|
+
this.log.warn(`Nodes "${node.id}"${isUnexpected ? ' unexpectedly' : ''} disconnected.`);
|
|
396
386
|
}
|
|
397
387
|
},
|
|
398
388
|
removeNode (nodeId) {
|
|
399
|
-
this.nodeCollection.remove(nodeId)
|
|
400
|
-
runtime.eventBus.broadcastLocal('$node.removed', { nodeId })
|
|
401
|
-
this.log.warn(`Node "${nodeId}" removed.`)
|
|
402
|
-
},
|
|
403
|
-
getNodeList (options) {
|
|
404
|
-
return this.nodeCollection.list(options)
|
|
405
|
-
},
|
|
406
|
-
getServiceList (options) {
|
|
407
|
-
return this.serviceCollection.list(options)
|
|
389
|
+
this.nodeCollection.remove(nodeId);
|
|
390
|
+
runtime.eventBus.broadcastLocal('$node.removed', { nodeId });
|
|
391
|
+
this.log.warn(`Node "${nodeId}" removed.`);
|
|
408
392
|
}
|
|
409
|
-
}
|
|
393
|
+
};
|
|
410
394
|
|
|
411
|
-
return registry
|
|
412
|
-
}
|
|
395
|
+
return registry;
|
|
396
|
+
};
|
|
@@ -1,36 +1,36 @@
|
|
|
1
|
-
const { isFunction, clone, wrapHandler, isObject, promisify } = require('@weave-js/utils')
|
|
2
|
-
const { WeaveError } = require('../../errors')
|
|
1
|
+
const { isFunction, clone, wrapHandler, isObject, promisify } = require('@weave-js/utils');
|
|
2
|
+
const { WeaveError } = require('../../errors');
|
|
3
3
|
|
|
4
4
|
module.exports.parseAction = (runtime, service, actionDefinition, name) => {
|
|
5
|
-
let action = actionDefinition
|
|
5
|
+
let action = actionDefinition;
|
|
6
6
|
|
|
7
7
|
// if the handler is a method (short form), we wrap the method in our handler object.
|
|
8
8
|
if (isFunction(actionDefinition)) {
|
|
9
|
-
action = wrapHandler(actionDefinition)
|
|
9
|
+
action = wrapHandler(actionDefinition);
|
|
10
10
|
} else if (isObject(actionDefinition)) {
|
|
11
|
-
action = clone(actionDefinition)
|
|
11
|
+
action = clone(actionDefinition);
|
|
12
12
|
} else {
|
|
13
|
-
runtime.handleError(new WeaveError(`Invalid action definition in "${name}" on service "${service.name}".`))
|
|
13
|
+
runtime.handleError(new WeaveError(`Invalid action definition in "${name}" on service "${service.name}".`));
|
|
14
14
|
}
|
|
15
15
|
|
|
16
|
-
const handler = action.handler
|
|
16
|
+
const handler = action.handler;
|
|
17
17
|
|
|
18
18
|
// Action handler has to be a function
|
|
19
19
|
if (!isFunction(handler)) {
|
|
20
|
-
runtime.handleError(new WeaveError(`Missing action handler in "${name}" on service "${service.name}".`))
|
|
20
|
+
runtime.handleError(new WeaveError(`Missing action handler in "${name}" on service "${service.name}".`));
|
|
21
21
|
}
|
|
22
22
|
|
|
23
|
-
action.name = service.name + '.' + (action.name || name)
|
|
24
|
-
action.shortName = name
|
|
23
|
+
action.name = service.name + '.' + (action.name || name);
|
|
24
|
+
action.shortName = name;
|
|
25
25
|
|
|
26
26
|
// if this is a versioned service. The action name is prefixed with the version number.
|
|
27
27
|
if (service.version) {
|
|
28
|
-
action.name = `v${service.version}.${action.name}
|
|
28
|
+
action.name = `v${service.version}.${action.name}`;
|
|
29
29
|
}
|
|
30
30
|
|
|
31
|
-
action.service = service
|
|
32
|
-
action.version = service.version
|
|
33
|
-
action.handler = promisify(handler.bind(service))
|
|
31
|
+
action.service = service;
|
|
32
|
+
action.version = service.version;
|
|
33
|
+
action.handler = promisify(handler.bind(service));
|
|
34
34
|
|
|
35
|
-
return action
|
|
36
|
-
}
|
|
35
|
+
return action;
|
|
36
|
+
};
|
|
@@ -1,45 +1,45 @@
|
|
|
1
|
-
const { isFunction, clone, wrapHandler, isObject, promisify } = require('@weave-js/utils')
|
|
2
|
-
const { WeaveError } = require('../../errors')
|
|
1
|
+
const { isFunction, clone, wrapHandler, isObject, promisify } = require('@weave-js/utils');
|
|
2
|
+
const { WeaveError } = require('../../errors');
|
|
3
3
|
|
|
4
4
|
module.exports.parseEvent = (runtime, service, eventDefinition, name) => {
|
|
5
|
-
let event
|
|
5
|
+
let event;
|
|
6
6
|
|
|
7
7
|
// if the handler is a method (short form), we wrap the method in our handler object.
|
|
8
8
|
if (isFunction(eventDefinition)) {
|
|
9
|
-
event = wrapHandler(eventDefinition)
|
|
9
|
+
event = wrapHandler(eventDefinition);
|
|
10
10
|
} else if (isObject(eventDefinition)) {
|
|
11
|
-
event = clone(eventDefinition)
|
|
11
|
+
event = clone(eventDefinition);
|
|
12
12
|
} else {
|
|
13
|
-
runtime.handleError(new WeaveError(`Invalid event definition "${name}" on service "${service.name}".`))
|
|
13
|
+
runtime.handleError(new WeaveError(`Invalid event definition "${name}" on service "${service.name}".`));
|
|
14
14
|
}
|
|
15
15
|
|
|
16
16
|
// Event handler has to be a function
|
|
17
17
|
if (!isFunction(event.handler) && !Array.isArray(event.handler)) {
|
|
18
|
-
runtime.handleError(new WeaveError(`Missing event handler for "${name}" on service "${service.name}".`))
|
|
18
|
+
runtime.handleError(new WeaveError(`Missing event handler for "${name}" on service "${service.name}".`));
|
|
19
19
|
}
|
|
20
20
|
|
|
21
|
-
event.service = service
|
|
21
|
+
event.service = service;
|
|
22
22
|
|
|
23
|
-
let handler
|
|
23
|
+
let handler;
|
|
24
24
|
if (isFunction(event.handler)) {
|
|
25
|
-
handler = promisify(event.handler.bind(service))
|
|
25
|
+
handler = promisify(event.handler.bind(service));
|
|
26
26
|
} else if (Array.isArray(event.handler)) {
|
|
27
27
|
handler = event.handler.map(h => {
|
|
28
|
-
return promisify(h.bind(service))
|
|
29
|
-
})
|
|
28
|
+
return promisify(h.bind(service));
|
|
29
|
+
});
|
|
30
30
|
}
|
|
31
31
|
|
|
32
32
|
if (!event.name) {
|
|
33
|
-
event.name = name
|
|
33
|
+
event.name = name;
|
|
34
34
|
}
|
|
35
35
|
|
|
36
36
|
if (isFunction(handler)) {
|
|
37
|
-
event.handler = (context) => handler(context)
|
|
37
|
+
event.handler = (context) => handler(context);
|
|
38
38
|
} else if (Array.isArray(handler)) {
|
|
39
|
-
event.handler = (context) => Promise.all(handler.map(h => h(context)))
|
|
39
|
+
event.handler = (context) => Promise.all(handler.map(h => h(context)));
|
|
40
40
|
}
|
|
41
41
|
|
|
42
|
-
event.service = service
|
|
42
|
+
event.service = service;
|
|
43
43
|
|
|
44
|
-
return event
|
|
45
|
-
}
|
|
44
|
+
return event;
|
|
45
|
+
};
|