@things-factory/integration-base 7.0.0-alpha.6 → 7.0.0-alpha.8

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.
Files changed (41) hide show
  1. package/dist-server/controllers/index.js +5 -0
  2. package/dist-server/controllers/index.js.map +1 -0
  3. package/dist-server/controllers/scenario-controller.js +87 -0
  4. package/dist-server/controllers/scenario-controller.js.map +1 -0
  5. package/dist-server/engine/connector/oracle-connector.js +113 -17
  6. package/dist-server/engine/connector/oracle-connector.js.map +1 -1
  7. package/dist-server/engine/task/oracle-procedure.js +1 -15
  8. package/dist-server/engine/task/oracle-procedure.js.map +1 -1
  9. package/dist-server/engine/task/utils/headless-pool-for-scenario.js +1 -1
  10. package/dist-server/engine/task/utils/headless-pool-for-scenario.js.map +1 -1
  11. package/dist-server/index.js +1 -0
  12. package/dist-server/index.js.map +1 -1
  13. package/dist-server/restful/unstable/run-scenario.js.map +1 -1
  14. package/dist-server/restful/unstable/start-scenario.js +1 -1
  15. package/dist-server/restful/unstable/start-scenario.js.map +1 -1
  16. package/dist-server/restful/unstable/stop-scenario.js +1 -1
  17. package/dist-server/restful/unstable/stop-scenario.js.map +1 -1
  18. package/dist-server/service/scenario-instance/scenario-instance-mutation.js +4 -71
  19. package/dist-server/service/scenario-instance/scenario-instance-mutation.js.map +1 -1
  20. package/dist-server/service/scenario-instance/scenario-instance-type.js +6 -1
  21. package/dist-server/service/scenario-instance/scenario-instance-type.js.map +1 -1
  22. package/dist-server/tsconfig.tsbuildinfo +1 -1
  23. package/helps/integration/connector/oracle-connector.ja.md +90 -0
  24. package/helps/integration/connector/oracle-connector.ko.md +87 -0
  25. package/helps/integration/connector/oracle-connector.md +46 -25
  26. package/helps/integration/connector/oracle-connector.ms.md +87 -0
  27. package/helps/integration/connector/oracle-connector.zh.md +87 -0
  28. package/openapi/unstable/scenario.yaml +100 -100
  29. package/openapi/unstable.yaml +11 -11
  30. package/package.json +7 -11
  31. package/server/controllers/index.ts +1 -0
  32. package/server/controllers/scenario-controller.ts +116 -0
  33. package/server/engine/connector/oracle-connector.ts +132 -22
  34. package/server/engine/task/oracle-procedure.ts +1 -16
  35. package/server/engine/task/utils/headless-pool-for-scenario.ts +1 -1
  36. package/server/index.ts +1 -0
  37. package/server/restful/unstable/run-scenario.ts +0 -1
  38. package/server/restful/unstable/start-scenario.ts +1 -1
  39. package/server/restful/unstable/stop-scenario.ts +1 -1
  40. package/server/service/scenario-instance/scenario-instance-mutation.ts +10 -121
  41. package/server/service/scenario-instance/scenario-instance-type.ts +11 -8
@@ -2,9 +2,9 @@ paths:
2
2
  /scenario/{scenarioId}:
3
3
  get:
4
4
  tags:
5
- - 'integration'
6
- description: 'Use this call to get information for single integration scenario.'
7
- operationId: 'scenario'
5
+ - integration
6
+ description: Use this call to get information for single integration scenario.
7
+ operationId: scenario
8
8
  parameters:
9
9
  - in: header
10
10
  name: x-things-factory-domain
@@ -12,28 +12,28 @@ paths:
12
12
  type: string
13
13
  required: false
14
14
  description: things-factory subdomain name
15
- - in: 'path'
16
- name: 'scenarioId'
15
+ - in: path
16
+ name: scenarioId
17
17
  required: true
18
- type: 'string'
18
+ type: string
19
19
  responses:
20
20
  '200':
21
- description: 'OK'
21
+ description: OK
22
22
  '400':
23
- description: 'Bad request is sent'
23
+ description: Bad request is sent
24
24
  '401':
25
- description: 'Authentication Error'
25
+ description: Authentication Error
26
26
  '404':
27
- description: 'Resource not found'
27
+ description: Resource not found
28
28
  '500':
29
- description: 'Server error'
29
+ description: Server error
30
30
 
31
31
  /scenarios:
32
32
  get:
33
33
  tags:
34
- - 'integration'
35
- description: 'Use this API to get a list of integration scenarios.'
36
- operationId: 'scenarios'
34
+ - integration
35
+ description: Use this API to get a list of integration scenarios.
36
+ operationId: scenarios
37
37
  parameters:
38
38
  - in: header
39
39
  name: x-things-factory-domain
@@ -41,34 +41,34 @@ paths:
41
41
  type: string
42
42
  required: false
43
43
  description: things-factory subdomain name
44
- - in: 'query'
45
- name: 'page'
46
- description: 'This integer value is used to specify the maximum number of entries to return in a single "page" of data. Max entries per page is 100.'
47
- type: 'integer'
48
- format: 'uint32'
49
- - in: 'query'
50
- name: 'offset'
51
- description: 'Specifies the starting entry of data to return in the current call. Default is 1. if data is more than one page, the offset can be some entry to start next call.'
52
- type: 'integer'
53
- format: 'uint32'
44
+ - in: query
45
+ name: page
46
+ description: This integer value is used to specify the maximum number of entries to return in a single "page" of data. Max entries per page is 100.
47
+ type: integer
48
+ format: uint32
49
+ - in: query
50
+ name: offset
51
+ description: Specifies the starting entry of data to return in the current call. Default is 1. if data is more than one page, the offset can be some entry to start next call.
52
+ type: integer
53
+ format: uint32
54
54
  responses:
55
55
  '200':
56
- description: 'OK'
56
+ description: OK
57
57
  '400':
58
- description: 'Bad request is sent'
58
+ description: Bad request is sent
59
59
  '401':
60
- description: 'Authentication Error'
60
+ description: Authentication Error
61
61
  '404':
62
- description: 'Resource not found'
62
+ description: Resource not found
63
63
  '500':
64
- description: 'Server error'
64
+ description: Server error
65
65
 
66
66
  /scenario-instance/{instanceName}:
67
67
  get:
68
68
  tags:
69
- - 'integration'
70
- description: 'Use this call to get information for single integration scenario instance.'
71
- operationId: 'scenarioInstance'
69
+ - integration
70
+ description: Use this call to get information for single integration scenario instance.
71
+ operationId: scenarioInstance
72
72
  parameters:
73
73
  - in: header
74
74
  name: x-things-factory-domain
@@ -76,28 +76,28 @@ paths:
76
76
  type: string
77
77
  required: false
78
78
  description: things-factory subdomain name
79
- - in: 'path'
80
- name: 'instanceName'
79
+ - in: path
80
+ name: instanceName
81
81
  required: true
82
- type: 'string'
82
+ type: string
83
83
  responses:
84
84
  '200':
85
- description: 'OK'
85
+ description: OK
86
86
  '400':
87
- description: 'Bad request is sent'
87
+ description: Bad request is sent
88
88
  '401':
89
- description: 'Authentication Error'
89
+ description: Authentication Error
90
90
  '404':
91
- description: 'Resource not found'
91
+ description: Resource not found
92
92
  '500':
93
- description: 'Server error'
93
+ description: Server error
94
94
 
95
95
  /scenario-instances:
96
96
  get:
97
97
  tags:
98
- - 'integration'
99
- description: 'Use this API to get a list of integration scenario instances.'
100
- operationId: 'scenarioInstances'
98
+ - integration
99
+ description: Use this API to get a list of integration scenario instances.
100
+ operationId: scenarioInstances
101
101
  parameters:
102
102
  - in: header
103
103
  name: x-things-factory-domain
@@ -105,34 +105,34 @@ paths:
105
105
  type: string
106
106
  required: false
107
107
  description: things-factory subdomain name
108
- - in: 'query'
109
- name: 'page'
110
- description: 'This integer value is used to specify the maximum number of entries to return in a single "page" of data. Max entries per page is 100.'
111
- type: 'integer'
112
- format: 'uint32'
113
- - in: 'query'
114
- name: 'offset'
115
- description: 'Specifies the starting entry of data to return in the current call. Default is 1. if data is more than one page, the offset can be some entry to start next call.'
116
- type: 'integer'
117
- format: 'uint32'
108
+ - in: query
109
+ name: page
110
+ description: This integer value is used to specify the maximum number of entries to return in a single "page" of data. Max entries per page is 100.
111
+ type: integer
112
+ format: uint32
113
+ - in: query
114
+ name: offset
115
+ description: Specifies the starting entry of data to return in the current call. Default is 1. if data is more than one page, the offset can be some entry to start next call.
116
+ type: integer
117
+ format: uint32
118
118
  responses:
119
119
  '200':
120
- description: 'OK'
120
+ description: OK
121
121
  '400':
122
- description: 'Bad request is sent'
122
+ description: Bad request is sent
123
123
  '401':
124
- description: 'Authentication Error'
124
+ description: Authentication Error
125
125
  '404':
126
- description: 'Resource not found'
126
+ description: Resource not found
127
127
  '500':
128
- description: 'Server error'
128
+ description: Server error
129
129
 
130
130
  /run-scenario/{scenarioName}:
131
131
  post:
132
132
  tags:
133
- - 'integration'
134
- description: 'Use this call to run scenario as standalone.'
135
- operationId: 'runScenario'
133
+ - integration
134
+ description: Use this call to run scenario as standalone.
135
+ operationId: runScenario
136
136
  requestBody:
137
137
  content:
138
138
  application/json:
@@ -140,11 +140,11 @@ paths:
140
140
  type: object
141
141
  properties:
142
142
  instanceName:
143
- type: 'string'
144
- description: 'Scenario Instance Name to identify new scenario instance to run'
143
+ type: string
144
+ description: Scenario Instance Name to identify new scenario instance to run
145
145
  variables:
146
- type: 'object'
147
- description: 'Input parameters for the new scenario instance to run'
146
+ type: object
147
+ description: Input parameters for the new scenario instance to run
148
148
  parameters:
149
149
  - in: header
150
150
  name: x-things-factory-domain
@@ -152,28 +152,28 @@ paths:
152
152
  type: string
153
153
  required: false
154
154
  description: things-factory subdomain name
155
- - in: 'path'
156
- name: 'scenarioName'
155
+ - in: path
156
+ name: scenarioName
157
157
  required: true
158
- type: 'string'
158
+ type: string
159
159
  responses:
160
160
  '200':
161
- description: 'OK'
161
+ description: OK
162
162
  '400':
163
- description: 'Bad request is sent'
163
+ description: Bad request is sent
164
164
  '401':
165
- description: 'Authentication Error'
165
+ description: Authentication Error
166
166
  '404':
167
- description: 'Resource not found'
167
+ description: Resource not found
168
168
  '500':
169
- description: 'Server error'
169
+ description: Server error
170
170
 
171
171
  /start-scenario/{scenarioName}:
172
172
  post:
173
173
  tags:
174
- - 'integration'
175
- description: 'Use this call to start scenario as a given instance name.'
176
- operationId: 'startScenario'
174
+ - integration
175
+ description: Use this call to start scenario as a given instance name.
176
+ operationId: startScenario
177
177
  requestBody:
178
178
  content:
179
179
  application/json:
@@ -181,11 +181,11 @@ paths:
181
181
  type: object
182
182
  properties:
183
183
  instanceName:
184
- type: 'string'
185
- description: 'Scenario Instance Name to identify new scenario instance to start'
184
+ type: string
185
+ description: Scenario Instance Name to identify new scenario instance to start
186
186
  variables:
187
- type: 'object'
188
- description: 'Input parameters for the new scenario instance to start'
187
+ type: object
188
+ description: Input parameters for the new scenario instance to start
189
189
  parameters:
190
190
  - in: header
191
191
  name: x-things-factory-domain
@@ -193,28 +193,28 @@ paths:
193
193
  type: string
194
194
  required: false
195
195
  description: things-factory subdomain name
196
- - in: 'path'
197
- name: 'scenarioName'
196
+ - in: path
197
+ name: scenarioName
198
198
  required: true
199
- type: 'string'
199
+ type: string
200
200
  responses:
201
201
  '200':
202
- description: 'OK'
202
+ description: OK
203
203
  '400':
204
- description: 'Bad request is sent'
204
+ description: Bad request is sent
205
205
  '401':
206
- description: 'Authentication Error'
206
+ description: Authentication Error
207
207
  '404':
208
- description: 'Resource not found'
208
+ description: Resource not found
209
209
  '500':
210
- description: 'Server error'
210
+ description: Server error
211
211
 
212
212
  /stop-scenario/{instanceName}:
213
213
  post:
214
214
  tags:
215
- - 'integration'
216
- description: 'Use this call to stop scenario running as a given instance name.'
217
- operationId: 'stopScenario'
215
+ - integration
216
+ description: Use this call to stop scenario running as a given instance name.
217
+ operationId: stopScenario
218
218
  parameters:
219
219
  - in: header
220
220
  name: x-things-factory-domain
@@ -222,19 +222,19 @@ paths:
222
222
  type: string
223
223
  required: false
224
224
  description: things-factory subdomain name
225
- - in: 'path'
226
- name: 'instanceName'
225
+ - in: path
226
+ name: instanceName
227
227
  required: true
228
- type: 'string'
229
- description: 'scenario instance name to be stopped'
228
+ type: string
229
+ description: scenario instance name to be stopped
230
230
  responses:
231
231
  '200':
232
- description: 'OK'
232
+ description: OK
233
233
  '400':
234
- description: 'Bad request is sent'
234
+ description: Bad request is sent
235
235
  '401':
236
- description: 'Authentication Error'
236
+ description: Authentication Error
237
237
  '404':
238
- description: 'Resource not found'
238
+ description: Resource not found
239
239
  '500':
240
- description: 'Server error'
240
+ description: Server error
@@ -3,22 +3,22 @@ info:
3
3
  description: >
4
4
  For the latest release information please check our [release notes](https://developer.myoperato.com/release_notes).
5
5
  The Integration API exposes integrations endpoint and related functions.
6
- version: 'unstable'
7
- title: 'Integration'
8
- termsOfService: 'https://myoperato.com/terms/'
6
+ version: unstable
7
+ title: Integration
8
+ termsOfService: https://myoperato.com/terms/
9
9
  contact:
10
- email: 'heartyoh@hatiolab.com'
10
+ email: heartyoh@hatiolab.com
11
11
  license:
12
12
  name: MIT
13
13
  url: http://mit-license.org/
14
14
  tags:
15
- - name: 'integration'
16
- description: 'API to integrate with other systems'
15
+ - name: integration
16
+ description: API to integrate with other systems
17
17
  schemes:
18
- - 'https'
19
- - 'http'
18
+ - https
19
+ - http
20
20
  servers:
21
- - url: '/api/unstable/'
21
+ - url: /api/unstable/
22
22
 
23
23
  components:
24
24
  securitySchemes:
@@ -37,5 +37,5 @@ responses:
37
37
  description: Unauthorized
38
38
 
39
39
  externalDocs:
40
- description: 'Find out about our release notes'
41
- url: 'https://developer.myoperato.com/release_notes'
40
+ description: Find out about our release notes
41
+ url: https://developer.myoperato.com/release_notes
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@things-factory/integration-base",
3
- "version": "7.0.0-alpha.6",
3
+ "version": "7.0.0-alpha.8",
4
4
  "main": "dist-server/index.js",
5
5
  "browser": "client/index.js",
6
6
  "things-factory": true,
@@ -26,26 +26,22 @@
26
26
  },
27
27
  "dependencies": {
28
28
  "@apollo/client": "^3.6.9",
29
- "@things-factory/api": "^7.0.0-alpha.6",
30
- "@things-factory/auth-base": "^7.0.0-alpha.6",
29
+ "@things-factory/api": "^7.0.0-alpha.8",
30
+ "@things-factory/auth-base": "^7.0.0-alpha.8",
31
31
  "@things-factory/env": "^7.0.0-alpha.0",
32
- "@things-factory/oauth2-client": "^7.0.0-alpha.6",
33
- "@things-factory/scheduler-client": "^7.0.0-alpha.6",
34
- "@things-factory/shell": "^7.0.0-alpha.6",
32
+ "@things-factory/oauth2-client": "^7.0.0-alpha.8",
33
+ "@things-factory/scheduler-client": "^7.0.0-alpha.8",
34
+ "@things-factory/shell": "^7.0.0-alpha.8",
35
35
  "@things-factory/utils": "^7.0.0-alpha.0",
36
36
  "async-mqtt": "^2.5.0",
37
37
  "chance": "^1.1.11",
38
38
  "cross-fetch": "^3.0.4",
39
39
  "ieee754": "^1.2.1",
40
40
  "moment-timezone": "^0.5.40",
41
- "mssql": "^8.1.2",
42
41
  "node-fetch": "^2.6.0",
43
42
  "promise-socket": "^7.0.0",
44
43
  "readline": "^1.3.0",
45
44
  "vm2": "3.9.11"
46
45
  },
47
- "devDependencies": {
48
- "@types/cron": "^2.0.1"
49
- },
50
- "gitHead": "cf46b4e03d6312f7ccb366a3c9fc2df16c68b7fa"
46
+ "gitHead": "b4981ea2721e7eaf4dbd618b6c77316ebc000ee5"
51
47
  }
@@ -0,0 +1 @@
1
+ export * from './scenario-controller'
@@ -0,0 +1,116 @@
1
+ import { getRepository, Domain, GraphqlLocalClient } from '@things-factory/shell'
2
+ import { PrivilegeObject, checkPermission } from '@things-factory/auth-base'
3
+
4
+ import { ScenarioEngine } from '../engine/scenario-engine'
5
+ import { Scenario } from '../service/scenario/scenario'
6
+ import { ScenarioInstance } from '../service/scenario-instance/scenario-instance-type'
7
+ import { Step } from '../service/step/step-type'
8
+
9
+ const debug = require('debug')('things-factory:integration-base:controller:run-scenario')
10
+
11
+ async function findScenario(scenarioName: string, domain: Domain): Promise<{ name: string; steps: Step[]; domain: Domain; privilege?: PrivilegeObject }> {
12
+ var repository = getRepository(Scenario)
13
+
14
+ var scenario = await repository.findOne({
15
+ where: { domain: { id: domain.id }, name: scenarioName },
16
+ relations: ['domain', 'steps', 'creator', 'updater']
17
+ })
18
+
19
+ if (!scenario && domain.parentId) {
20
+ scenario = await repository.findOne({
21
+ where: { domain: { id: domain.parentId }, name: scenarioName },
22
+ relations: ['domain', 'steps', 'creator', 'updater']
23
+ })
24
+ }
25
+
26
+ return scenario as any
27
+ }
28
+
29
+ export async function runScenario(instanceName: string, scenarioName: string, variables: any, context: ResolverContext): Promise<ScenarioInstance> {
30
+ const { domain, user, lng, unsafeIP, prohibitedPrivileges } = context.state
31
+
32
+ debug('runScenario', scenarioName, instanceName, variables)
33
+
34
+ var scenario = await findScenario(scenarioName, domain)
35
+
36
+ if (!scenario) {
37
+ throw new Error(
38
+ context.t('error.scenario not found', {
39
+ scenario: scenarioName
40
+ })
41
+ )
42
+ }
43
+
44
+ if (!(await checkPermission(scenario.privilege, user, domain, unsafeIP, prohibitedPrivileges))) {
45
+ const { category, privilege } = scenario.privilege || {}
46
+ throw new Error(`Unauthorized! ${category && privilege ? category + ':' + privilege + ' privilege' : 'ownership granted'} required`)
47
+ }
48
+
49
+ /* 시나리오 인스턴스를 생성한다. */
50
+ instanceName = instanceName || scenarioName + '-' + String(Date.now())
51
+ var instance = new ScenarioInstance(instanceName, scenario, {
52
+ domain,
53
+ user,
54
+ lng,
55
+ variables,
56
+ client: GraphqlLocalClient.client
57
+ })
58
+
59
+ await instance.run()
60
+
61
+ return instance
62
+ }
63
+
64
+ export async function startScenario(instanceName: string, scenarioName: string, variables: any, context: ResolverContext): Promise<ScenarioInstance> {
65
+ const { domain, user, lng, unsafeIP, prohibitedPrivileges } = context.state
66
+
67
+ debug('startScenario', instanceName, scenarioName, variables)
68
+
69
+ var scenario = await findScenario(scenarioName, domain)
70
+
71
+ if (!scenario) {
72
+ throw new Error(
73
+ context.t('error.scenario not found', {
74
+ scenario: scenarioName
75
+ })
76
+ )
77
+ }
78
+
79
+ if (!(await checkPermission(scenario.privilege, user, domain, unsafeIP, prohibitedPrivileges))) {
80
+ const { category, privilege } = scenario.privilege || {}
81
+ throw new Error(`Unauthorized! ${category && privilege ? category + ':' + privilege + ' privilege' : 'ownership granted'} required`)
82
+ }
83
+
84
+ instanceName = instanceName || scenarioName
85
+ return await ScenarioEngine.load(instanceName, scenario, { domain, user, lng, variables })
86
+ }
87
+
88
+ export async function stopScenario(instanceName: string, context: ResolverContext): Promise<ScenarioInstance | undefined> {
89
+ const { domain, user, unsafeIP, prohibitedPrivileges } = context.state
90
+
91
+ debug('stopScenario', instanceName)
92
+
93
+ runScenario
94
+
95
+ var scenarioInstance = ScenarioEngine.getScenarioInstance(domain, instanceName)
96
+
97
+ if (!scenarioInstance) {
98
+ debug('stopScenario', `ScenarioInstance(${instanceName}) Not Found.`)
99
+ throw new Error(
100
+ context.t('error.scenario instance not found', {
101
+ instance: instanceName
102
+ })
103
+ )
104
+ }
105
+
106
+ var scenario = await findScenario(scenarioInstance.scenarioName, domain)
107
+
108
+ if (!(await checkPermission(scenario.privilege, user, domain, unsafeIP, prohibitedPrivileges))) {
109
+ const { category, privilege } = scenario.privilege || {}
110
+ throw new Error(`Unauthorized! ${category && privilege ? category + ':' + privilege + ' privilege' : 'ownership granted'} required`)
111
+ }
112
+
113
+ await ScenarioEngine.unload(domain, instanceName)
114
+
115
+ return scenarioInstance
116
+ }