@live-change/framework 0.8.31 → 0.8.33
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/lib/App.js +33 -22
- package/lib/definition/ServiceDefinition.js +2 -2
- package/lib/processors/crudGenerator.js +1 -3
- package/lib/runtime/Service.js +4 -4
- package/lib/runtime/TriggerHandler.js +4 -2
- package/lib/utils/CommandQueue.js +6 -6
- package/lib/utils/validators.js +1 -1
- package/package.json +4 -4
package/lib/App.js
CHANGED
|
@@ -181,15 +181,14 @@ class App {
|
|
|
181
181
|
if(!(serviceDefinition instanceof ServiceDefinition))
|
|
182
182
|
serviceDefinition = new ServiceDefinition(serviceDefinition)
|
|
183
183
|
let service = new Service(serviceDefinition, this)
|
|
184
|
-
await service.start(config)
|
|
185
|
-
console.log("service started", serviceDefinition.name, "!")
|
|
186
|
-
await this.profileLog.end(profileOp)
|
|
187
|
-
this.startedServices[serviceDefinition.name] = service
|
|
188
|
-
|
|
189
184
|
for(const viewName in serviceDefinition.views) {
|
|
190
185
|
const viewDefinition = serviceDefinition.views[viewName]
|
|
191
186
|
if(viewDefinition.global) this.globalViews[viewName] = service.views[viewName]
|
|
192
187
|
}
|
|
188
|
+
await service.start(config)
|
|
189
|
+
console.log("service started", serviceDefinition.name, "!")
|
|
190
|
+
await this.profileLog.end(profileOp)
|
|
191
|
+
this.startedServices[serviceDefinition.name] = service
|
|
193
192
|
|
|
194
193
|
return service
|
|
195
194
|
}
|
|
@@ -234,20 +233,26 @@ class App {
|
|
|
234
233
|
return definition
|
|
235
234
|
}
|
|
236
235
|
|
|
237
|
-
async trigger(data) {
|
|
236
|
+
async trigger(trigger, data) {
|
|
237
|
+
if(!trigger) throw new Error("trigger must have type")
|
|
238
|
+
if(typeof trigger !== 'object') throw new Error("trigger must be object")
|
|
239
|
+
if(typeof trigger.type !== 'string') throw new Error("trigger type must be string")
|
|
240
|
+
if(!data) throw new Error("trigger must have data")
|
|
241
|
+
if(typeof data !== 'object') throw new Error("trigger must be object")
|
|
242
|
+
if(trigger.service) return await this.triggerService(trigger, data, true)
|
|
238
243
|
if(this.shortTriggers) {
|
|
239
|
-
const triggers = this.triggerRoutes[
|
|
244
|
+
const triggers = this.triggerRoutes[trigger.type] /// TODO: check if it is right
|
|
240
245
|
return await Promise.all(triggers.map(t => t.execute(data)))
|
|
241
246
|
}
|
|
242
247
|
const profileOp = await this.profileLog.begin({
|
|
243
|
-
operation: "callTrigger", triggerType:
|
|
248
|
+
operation: "callTrigger", triggerType: trigger.type, id: data.id, by: data.by
|
|
244
249
|
})
|
|
245
250
|
const routes = await this.dao.get(['database', 'tableRange', this.databaseName, 'triggerRoutes',
|
|
246
|
-
{ gte:
|
|
247
|
-
console.log("TRIGGER ROUTES",
|
|
251
|
+
{ gte: trigger.type+'=', lte: trigger.type+'=\xFF\xFF\xFF\xFF' }])
|
|
252
|
+
console.log("TRIGGER ROUTES", trigger.type, '=>', routes)
|
|
248
253
|
let promises = []
|
|
249
254
|
for(const route of routes) {
|
|
250
|
-
promises.push(this.triggerService(route.service, { ...data }, true))
|
|
255
|
+
promises.push(this.triggerService({ ...trigger, service: route.service }, { ...data }, true))
|
|
251
256
|
}
|
|
252
257
|
const promise = Promise.all(promises)
|
|
253
258
|
await this.profileLog.endPromise(profileOp, promise)
|
|
@@ -256,31 +261,37 @@ class App {
|
|
|
256
261
|
return result
|
|
257
262
|
}
|
|
258
263
|
|
|
259
|
-
async triggerService(
|
|
264
|
+
async triggerService(trigger, data, returnArray = false) {
|
|
265
|
+
if(!trigger.service) throw new Error("trigger must have service")
|
|
266
|
+
if(typeof trigger !== 'object') throw new Error("trigger must be object")
|
|
267
|
+
if(typeof trigger.service !== 'string') throw new Error("trigger service must be string")
|
|
268
|
+
if(typeof trigger.type !== 'string') throw new Error("trigger type must be string")
|
|
269
|
+
trigger.data = data
|
|
270
|
+
if(!trigger.data) throw new Error("trigger must have data")
|
|
271
|
+
if(typeof trigger.data !== 'object') throw new Error("trigger must be object")
|
|
260
272
|
if(this.shortTriggers) {
|
|
261
|
-
const service = this.startedServices[service]
|
|
262
|
-
const triggers = service.triggers[
|
|
273
|
+
const service = this.startedServices[trigger.service]
|
|
274
|
+
const triggers = service.triggers[trigger.type]
|
|
263
275
|
if(!triggers) return []
|
|
264
276
|
const result = await Promise.all(triggers.map(t => t.execute(data)))
|
|
265
277
|
if(!returnArray && Array.isArray(result) && result.length === 1) return result[0]
|
|
266
278
|
return result
|
|
267
279
|
}
|
|
268
|
-
if(!
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
if(!data.timestamp) data.timestamp = (new Date()).toISOString()
|
|
280
|
+
if(!trigger.id) trigger.id = this.generateUid()
|
|
281
|
+
trigger.state = 'new'
|
|
282
|
+
if(!trigger.timestamp) trigger.timestamp = (new Date()).toISOString()
|
|
272
283
|
|
|
273
284
|
const profileOp = await this.profileLog.begin({
|
|
274
|
-
operation: "callTriggerService", triggerType:
|
|
285
|
+
operation: "callTriggerService", triggerType: trigger.type, service: trigger.service, triggerId: trigger.id, by: data.by
|
|
275
286
|
})
|
|
276
287
|
|
|
277
288
|
const triggersTable = this.splitCommands ? `${this.name}_triggers` : 'triggers'
|
|
278
289
|
const objectObservable = this.dao.observable(
|
|
279
|
-
['database', 'tableObject', this.databaseName, triggersTable,
|
|
290
|
+
['database', 'tableObject', this.databaseName, triggersTable, trigger.id],
|
|
280
291
|
ReactiveDao.ObservableValue
|
|
281
292
|
)
|
|
282
|
-
await this.dao.request(['database', 'update', this.databaseName, triggersTable,
|
|
283
|
-
{ op: 'reverseMerge', value:
|
|
293
|
+
await this.dao.request(['database', 'update', this.databaseName, triggersTable, trigger.id, [
|
|
294
|
+
{ op: 'reverseMerge', value: trigger }
|
|
284
295
|
]])
|
|
285
296
|
let observer
|
|
286
297
|
const promise = new Promise((resolve, reject) => {
|
|
@@ -202,9 +202,9 @@ class ServiceDefinition {
|
|
|
202
202
|
}
|
|
203
203
|
}
|
|
204
204
|
|
|
205
|
-
callTrigger(data) {
|
|
205
|
+
callTrigger(trigger, data) {
|
|
206
206
|
if(!this._runtime) throw new Error("triggers can be called only on runtime")
|
|
207
|
-
this._runtime.trigger(data)
|
|
207
|
+
this._runtime.trigger(trigger, data)
|
|
208
208
|
}
|
|
209
209
|
|
|
210
210
|
computeChanges( oldModuleParam ) {
|
|
@@ -143,9 +143,7 @@ export default function(service, app) {
|
|
|
143
143
|
...writeOptions,
|
|
144
144
|
execute: async function (props, {service}, emit) {
|
|
145
145
|
if(crud.deleteTrigger || crud.triggers) {
|
|
146
|
-
|
|
147
|
-
trig[idName] = props[idName]
|
|
148
|
-
await service.trigger(trig)
|
|
146
|
+
await service.trigger({ type: genName("Deleted") }, { [idName] : props[idName ] })
|
|
149
147
|
}
|
|
150
148
|
emit({
|
|
151
149
|
...props,
|
package/lib/runtime/Service.js
CHANGED
|
@@ -93,12 +93,12 @@ class Service {
|
|
|
93
93
|
console.log("Service", this.definition.name, "started")
|
|
94
94
|
}
|
|
95
95
|
|
|
96
|
-
async trigger(
|
|
97
|
-
return this.app.trigger(
|
|
96
|
+
async trigger(...args) {
|
|
97
|
+
return this.app.trigger(...args)
|
|
98
98
|
}
|
|
99
99
|
|
|
100
|
-
async triggerService(
|
|
101
|
-
return this.app.triggerService(
|
|
100
|
+
async triggerService(...args) {
|
|
101
|
+
return this.app.triggerService(...args)
|
|
102
102
|
}
|
|
103
103
|
|
|
104
104
|
}
|
|
@@ -16,17 +16,19 @@ class TriggerHandler {
|
|
|
16
16
|
}
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
-
async doExecute(
|
|
19
|
+
async doExecute(trig, emit) {
|
|
20
20
|
//console.log("PARAMETERS", JSON.stringify(parameters), "DEFN", this.definition.properties)
|
|
21
|
+
const parameters = trig.data
|
|
21
22
|
const preparedParams = await prepareParameters(parameters, this.definition.properties, this.service)
|
|
22
23
|
//console.log("PREP PARAMS", preparedParams)
|
|
23
24
|
|
|
24
25
|
let resultPromise = this.definition.execute({
|
|
25
26
|
...preparedParams
|
|
26
27
|
}, {
|
|
28
|
+
...trig,
|
|
27
29
|
action: this,
|
|
28
30
|
service: this.service,
|
|
29
|
-
trigger: (...args) => this.service.trigger(...args) /// TODO: collect call traces
|
|
31
|
+
trigger: (...args) => this.service.trigger(...args) /// TODO: collect call traces,
|
|
30
32
|
}, emit)
|
|
31
33
|
|
|
32
34
|
resultPromise = resultPromise.then(async result => {
|
|
@@ -59,7 +59,7 @@ class CommandQueue {
|
|
|
59
59
|
}
|
|
60
60
|
async handleCommand(command) {
|
|
61
61
|
//console.log("COMMNAD HANDLE!", command)
|
|
62
|
-
if(command.state
|
|
62
|
+
if(command.state !== 'new') return
|
|
63
63
|
if(this.commandsStarted.has(command.id)) return
|
|
64
64
|
this.commandsStarted.set(command.id, command)
|
|
65
65
|
const started = new Date()
|
|
@@ -69,7 +69,7 @@ class CommandQueue {
|
|
|
69
69
|
let commandHandlers = this.commandTypeHandlers.get(command.type) || []
|
|
70
70
|
for(let handler of commandHandlers) {
|
|
71
71
|
result = handler(command)
|
|
72
|
-
if(result
|
|
72
|
+
if(result !== 'ignored') {
|
|
73
73
|
handled = true
|
|
74
74
|
break
|
|
75
75
|
}
|
|
@@ -77,7 +77,7 @@ class CommandQueue {
|
|
|
77
77
|
if(!handled) {
|
|
78
78
|
for(let handler of this.allCommandHandlers) {
|
|
79
79
|
const result = handler(command)
|
|
80
|
-
if(result
|
|
80
|
+
if(result !== 'ignored') {
|
|
81
81
|
handled = true
|
|
82
82
|
break
|
|
83
83
|
}
|
|
@@ -104,7 +104,7 @@ class CommandQueue {
|
|
|
104
104
|
// hold it for one second in case of delayed event:
|
|
105
105
|
setTimeout(() => this.commandsStarted.delete(command.id), 1000)
|
|
106
106
|
}).catch(async error => {
|
|
107
|
-
|
|
107
|
+
const result = await this.connection.request(['database', 'update'], this.database, this.tableName, command.id, [
|
|
108
108
|
{
|
|
109
109
|
op: 'merge', property: null,
|
|
110
110
|
value: { state: 'failed', error: (error && (error.stack || error.message)) || error }
|
|
@@ -112,13 +112,13 @@ class CommandQueue {
|
|
|
112
112
|
])
|
|
113
113
|
// hold it for one second in case of delayed event:
|
|
114
114
|
setTimeout(() => this.commandsStarted.delete(command.id), 1000)
|
|
115
|
+
return result
|
|
115
116
|
})
|
|
116
117
|
} catch(e) {
|
|
117
118
|
console.error(`COMMAND ${JSON.stringify(command, null, " ")} HANDLING ERROR`, e, ' => STOPPING!')
|
|
118
|
-
this.dispose()
|
|
119
|
+
await this.dispose()
|
|
119
120
|
throw e
|
|
120
121
|
}
|
|
121
|
-
return 'ok'
|
|
122
122
|
}
|
|
123
123
|
set(value) {
|
|
124
124
|
if(this.resolveStart) {
|
package/lib/utils/validators.js
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@live-change/framework",
|
|
3
|
-
"version": "0.8.
|
|
3
|
+
"version": "0.8.33",
|
|
4
4
|
"description": "Live Change Framework - ultimate solution for real time mobile/web apps",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"scripts": {
|
|
@@ -22,8 +22,8 @@
|
|
|
22
22
|
},
|
|
23
23
|
"homepage": "https://github.com/live-change/live-change-stack",
|
|
24
24
|
"devDependencies": {
|
|
25
|
-
"@live-change/dao": "^0.8.
|
|
26
|
-
"@live-change/uid": "^0.8.
|
|
25
|
+
"@live-change/dao": "^0.8.33",
|
|
26
|
+
"@live-change/uid": "^0.8.33"
|
|
27
27
|
},
|
|
28
|
-
"gitHead": "
|
|
28
|
+
"gitHead": "98ff6f9c09e5fc1f408010df6cc8038eff571276"
|
|
29
29
|
}
|