@neuralinnovations/dataisland-sdk 0.0.1-dev2 → 0.0.1-dev20

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 (286) hide show
  1. package/LICENSE +201 -0
  2. package/README.md +306 -1
  3. package/dist/index.d.ts +3 -0
  4. package/dist/index.d.ts.map +1 -0
  5. package/dist/index.js +3 -0
  6. package/dist/index.js.map +1 -0
  7. package/dist/package.json +100 -0
  8. package/dist/src/appBuilder.d.ts +44 -0
  9. package/dist/src/appBuilder.d.ts.map +1 -0
  10. package/dist/src/appBuilder.js +10 -0
  11. package/dist/src/appBuilder.js.map +1 -0
  12. package/dist/src/commands/startCommandHandler.d.ts +7 -0
  13. package/dist/src/commands/startCommandHandler.d.ts.map +1 -0
  14. package/dist/src/commands/startCommandHandler.js +17 -0
  15. package/dist/src/commands/startCommandHandler.js.map +1 -0
  16. package/dist/src/context.d.ts +23 -0
  17. package/dist/src/context.d.ts.map +1 -0
  18. package/dist/src/context.js +31 -0
  19. package/dist/src/context.js.map +1 -0
  20. package/dist/src/credentials.d.ts +28 -0
  21. package/dist/src/credentials.d.ts.map +1 -0
  22. package/dist/src/credentials.js +70 -0
  23. package/dist/src/credentials.js.map +1 -0
  24. package/dist/src/dataIslandApp.d.ts +50 -0
  25. package/dist/src/dataIslandApp.d.ts.map +1 -0
  26. package/dist/src/dataIslandApp.js +10 -0
  27. package/dist/src/dataIslandApp.js.map +1 -0
  28. package/dist/src/disposable.d.ts +84 -0
  29. package/dist/src/disposable.d.ts.map +1 -0
  30. package/dist/src/disposable.js +147 -0
  31. package/dist/src/disposable.js.map +1 -0
  32. package/dist/src/dto/accessGroupResponse.d.ts +27 -0
  33. package/dist/src/dto/accessGroupResponse.d.ts.map +1 -0
  34. package/dist/src/dto/accessGroupResponse.js +3 -0
  35. package/dist/src/dto/accessGroupResponse.js.map +1 -0
  36. package/dist/src/dto/chatResponse.d.ts +78 -0
  37. package/dist/src/dto/chatResponse.d.ts.map +1 -0
  38. package/dist/src/dto/chatResponse.js +45 -0
  39. package/dist/src/dto/chatResponse.js.map +1 -0
  40. package/dist/src/dto/userInfoResponse.d.ts +42 -0
  41. package/dist/src/dto/userInfoResponse.d.ts.map +1 -0
  42. package/dist/src/dto/userInfoResponse.js +3 -0
  43. package/dist/src/dto/userInfoResponse.js.map +1 -0
  44. package/dist/src/dto/workspacesResponse.d.ts +43 -0
  45. package/dist/src/dto/workspacesResponse.d.ts.map +1 -0
  46. package/dist/src/dto/workspacesResponse.js +3 -0
  47. package/dist/src/dto/workspacesResponse.js.map +1 -0
  48. package/dist/src/events.d.ts +17 -0
  49. package/dist/src/events.d.ts.map +1 -0
  50. package/dist/src/events.js +52 -0
  51. package/dist/src/events.js.map +1 -0
  52. package/dist/src/index.d.ts +58 -0
  53. package/dist/src/index.d.ts.map +1 -0
  54. package/dist/src/index.js +91 -0
  55. package/dist/src/index.js.map +1 -0
  56. package/dist/src/internal/app.impl.d.ts +28 -0
  57. package/dist/src/internal/app.impl.d.ts.map +1 -0
  58. package/dist/src/internal/app.impl.js +151 -0
  59. package/dist/src/internal/app.impl.js.map +1 -0
  60. package/dist/src/internal/appBuilder.impl.d.ts +27 -0
  61. package/dist/src/internal/appBuilder.impl.d.ts.map +1 -0
  62. package/dist/src/internal/appBuilder.impl.js +71 -0
  63. package/dist/src/internal/appBuilder.impl.js.map +1 -0
  64. package/dist/src/internal/createApp.impl.d.ts +4 -0
  65. package/dist/src/internal/createApp.impl.d.ts.map +1 -0
  66. package/dist/src/internal/createApp.impl.js +11 -0
  67. package/dist/src/internal/createApp.impl.js.map +1 -0
  68. package/dist/src/internal/registry.d.ts +66 -0
  69. package/dist/src/internal/registry.d.ts.map +1 -0
  70. package/dist/src/internal/registry.js +114 -0
  71. package/dist/src/internal/registry.js.map +1 -0
  72. package/dist/src/middleware.d.ts +5 -0
  73. package/dist/src/middleware.d.ts.map +1 -0
  74. package/dist/src/middleware.js +3 -0
  75. package/dist/src/middleware.js.map +1 -0
  76. package/dist/src/services/commandService.d.ts +18 -0
  77. package/dist/src/services/commandService.d.ts.map +1 -0
  78. package/dist/src/services/commandService.js +40 -0
  79. package/dist/src/services/commandService.js.map +1 -0
  80. package/dist/src/services/credentialService.d.ts +9 -0
  81. package/dist/src/services/credentialService.d.ts.map +1 -0
  82. package/dist/src/services/credentialService.js +26 -0
  83. package/dist/src/services/credentialService.js.map +1 -0
  84. package/dist/src/services/middlewareService.d.ts +9 -0
  85. package/dist/src/services/middlewareService.d.ts.map +1 -0
  86. package/dist/src/services/middlewareService.js +34 -0
  87. package/dist/src/services/middlewareService.js.map +1 -0
  88. package/dist/src/services/organizationService.d.ts +10 -0
  89. package/dist/src/services/organizationService.d.ts.map +1 -0
  90. package/dist/src/services/organizationService.js +19 -0
  91. package/dist/src/services/organizationService.js.map +1 -0
  92. package/dist/src/services/requestBuilder.d.ts +17 -0
  93. package/dist/src/services/requestBuilder.d.ts.map +1 -0
  94. package/dist/src/services/requestBuilder.js +104 -0
  95. package/dist/src/services/requestBuilder.js.map +1 -0
  96. package/dist/src/services/responseUtils.d.ts +6 -0
  97. package/dist/src/services/responseUtils.d.ts.map +1 -0
  98. package/dist/src/services/responseUtils.js +32 -0
  99. package/dist/src/services/responseUtils.js.map +1 -0
  100. package/dist/src/services/rpcService.d.ts +77 -0
  101. package/dist/src/services/rpcService.d.ts.map +1 -0
  102. package/dist/src/services/rpcService.js +125 -0
  103. package/dist/src/services/rpcService.js.map +1 -0
  104. package/dist/src/services/service.d.ts +21 -0
  105. package/dist/src/services/service.d.ts.map +1 -0
  106. package/dist/src/services/service.js +41 -0
  107. package/dist/src/services/service.js.map +1 -0
  108. package/dist/src/services/userProfileService.d.ts +8 -0
  109. package/dist/src/services/userProfileService.d.ts.map +1 -0
  110. package/dist/src/services/userProfileService.js +32 -0
  111. package/dist/src/services/userProfileService.js.map +1 -0
  112. package/dist/src/storages/chats/answer.d.ts +40 -0
  113. package/dist/src/storages/chats/answer.d.ts.map +1 -0
  114. package/dist/src/storages/chats/answer.impl.d.ts +24 -0
  115. package/dist/src/storages/chats/answer.impl.d.ts.map +1 -0
  116. package/dist/src/storages/chats/answer.impl.js +130 -0
  117. package/dist/src/storages/chats/answer.impl.js.map +1 -0
  118. package/dist/src/storages/chats/answer.js +14 -0
  119. package/dist/src/storages/chats/answer.js.map +1 -0
  120. package/dist/src/storages/chats/chat.d.ts +39 -0
  121. package/dist/src/storages/chats/chat.d.ts.map +1 -0
  122. package/dist/src/storages/chats/chat.impl.d.ts +24 -0
  123. package/dist/src/storages/chats/chat.impl.d.ts.map +1 -0
  124. package/dist/src/storages/chats/chat.impl.js +98 -0
  125. package/dist/src/storages/chats/chat.impl.js.map +1 -0
  126. package/dist/src/storages/chats/chat.js +12 -0
  127. package/dist/src/storages/chats/chat.js.map +1 -0
  128. package/dist/src/storages/chats/chats.d.ts +40 -0
  129. package/dist/src/storages/chats/chats.d.ts.map +1 -0
  130. package/dist/src/storages/chats/chats.impl.d.ts +18 -0
  131. package/dist/src/storages/chats/chats.impl.d.ts.map +1 -0
  132. package/dist/src/storages/chats/chats.impl.js +102 -0
  133. package/dist/src/storages/chats/chats.impl.js.map +1 -0
  134. package/dist/src/storages/chats/chats.js +16 -0
  135. package/dist/src/storages/chats/chats.js.map +1 -0
  136. package/dist/src/storages/files/file.d.ts +31 -0
  137. package/dist/src/storages/files/file.d.ts.map +1 -0
  138. package/dist/src/storages/files/file.impl.d.ts +21 -0
  139. package/dist/src/storages/files/file.impl.d.ts.map +1 -0
  140. package/dist/src/storages/files/file.impl.js +64 -0
  141. package/dist/src/storages/files/file.impl.js.map +1 -0
  142. package/dist/src/storages/files/file.js +11 -0
  143. package/dist/src/storages/files/file.js.map +1 -0
  144. package/dist/src/storages/files/files.d.ts +34 -0
  145. package/dist/src/storages/files/files.d.ts.map +1 -0
  146. package/dist/src/storages/files/files.impl.d.ts +22 -0
  147. package/dist/src/storages/files/files.impl.d.ts.map +1 -0
  148. package/dist/src/storages/files/files.impl.js +140 -0
  149. package/dist/src/storages/files/files.impl.js.map +1 -0
  150. package/dist/src/storages/files/files.js +20 -0
  151. package/dist/src/storages/files/files.js.map +1 -0
  152. package/dist/src/storages/files/filesPage.d.ts +28 -0
  153. package/dist/src/storages/files/filesPage.d.ts.map +1 -0
  154. package/dist/src/storages/files/filesPage.impl.d.ts +15 -0
  155. package/dist/src/storages/files/filesPage.impl.d.ts.map +1 -0
  156. package/dist/src/storages/files/filesPage.impl.js +38 -0
  157. package/dist/src/storages/files/filesPage.impl.js.map +1 -0
  158. package/dist/src/storages/files/filesPage.js +10 -0
  159. package/dist/src/storages/files/filesPage.js.map +1 -0
  160. package/dist/src/storages/groups/groups.d.ts +91 -0
  161. package/dist/src/storages/groups/groups.d.ts.map +1 -0
  162. package/dist/src/storages/groups/groups.impl.d.ts +58 -0
  163. package/dist/src/storages/groups/groups.impl.d.ts.map +1 -0
  164. package/dist/src/storages/groups/groups.impl.js +275 -0
  165. package/dist/src/storages/groups/groups.impl.js.map +1 -0
  166. package/dist/src/storages/groups/groups.js +26 -0
  167. package/dist/src/storages/groups/groups.js.map +1 -0
  168. package/dist/src/storages/organizations/organization.d.ts +54 -0
  169. package/dist/src/storages/organizations/organization.d.ts.map +1 -0
  170. package/dist/src/storages/organizations/organization.impl.d.ts +32 -0
  171. package/dist/src/storages/organizations/organization.impl.d.ts.map +1 -0
  172. package/dist/src/storages/organizations/organization.impl.js +120 -0
  173. package/dist/src/storages/organizations/organization.impl.js.map +1 -0
  174. package/dist/src/storages/organizations/organization.js +18 -0
  175. package/dist/src/storages/organizations/organization.js.map +1 -0
  176. package/dist/src/storages/organizations/organizations.d.ts +46 -0
  177. package/dist/src/storages/organizations/organizations.d.ts.map +1 -0
  178. package/dist/src/storages/organizations/organizations.impl.d.ts +38 -0
  179. package/dist/src/storages/organizations/organizations.impl.d.ts.map +1 -0
  180. package/dist/src/storages/organizations/organizations.impl.js +151 -0
  181. package/dist/src/storages/organizations/organizations.impl.js.map +1 -0
  182. package/dist/src/storages/organizations/organizations.js +20 -0
  183. package/dist/src/storages/organizations/organizations.js.map +1 -0
  184. package/dist/src/storages/user/userProfile.d.ts +32 -0
  185. package/dist/src/storages/user/userProfile.d.ts.map +1 -0
  186. package/dist/src/storages/user/userProfile.impl.d.ts +13 -0
  187. package/dist/src/storages/user/userProfile.impl.d.ts.map +1 -0
  188. package/dist/src/storages/user/userProfile.impl.js +51 -0
  189. package/dist/src/storages/user/userProfile.impl.js.map +1 -0
  190. package/dist/src/storages/user/userProfile.js +12 -0
  191. package/dist/src/storages/user/userProfile.js.map +1 -0
  192. package/dist/src/storages/workspaces/workspace.d.ts +44 -0
  193. package/dist/src/storages/workspaces/workspace.d.ts.map +1 -0
  194. package/dist/src/storages/workspaces/workspace.impl.d.ts +23 -0
  195. package/dist/src/storages/workspaces/workspace.impl.d.ts.map +1 -0
  196. package/dist/src/storages/workspaces/workspace.impl.js +98 -0
  197. package/dist/src/storages/workspaces/workspace.impl.js.map +1 -0
  198. package/dist/src/storages/workspaces/workspace.js +18 -0
  199. package/dist/src/storages/workspaces/workspace.js.map +1 -0
  200. package/dist/src/storages/workspaces/workspaces.d.ts +47 -0
  201. package/dist/src/storages/workspaces/workspaces.d.ts.map +1 -0
  202. package/dist/src/storages/workspaces/workspaces.impl.d.ts +33 -0
  203. package/dist/src/storages/workspaces/workspaces.impl.d.ts.map +1 -0
  204. package/dist/src/storages/workspaces/workspaces.impl.js +157 -0
  205. package/dist/src/storages/workspaces/workspaces.impl.js.map +1 -0
  206. package/dist/src/storages/workspaces/workspaces.js +19 -0
  207. package/dist/src/storages/workspaces/workspaces.js.map +1 -0
  208. package/dist/src/unitTest.d.ts +12 -0
  209. package/dist/src/unitTest.d.ts.map +1 -0
  210. package/dist/src/unitTest.js +44 -0
  211. package/dist/src/unitTest.js.map +1 -0
  212. package/index.d.ts +1 -0
  213. package/index.js +1 -0
  214. package/package.json +43 -4
  215. package/src/appBuilder.ts +6 -6
  216. package/src/commands/startCommandHandler.ts +2 -2
  217. package/src/context.ts +5 -4
  218. package/src/credentials.ts +29 -7
  219. package/src/{appSdk.ts → dataIslandApp.ts} +7 -7
  220. package/src/disposable.ts +20 -8
  221. package/src/dto/accessGroupResponse.ts +35 -0
  222. package/src/dto/chatResponse.ts +103 -0
  223. package/src/dto/userInfoResponse.ts +15 -3
  224. package/src/dto/workspacesResponse.ts +49 -0
  225. package/src/events.ts +13 -13
  226. package/src/index.ts +41 -20
  227. package/src/internal/app.impl.ts +28 -31
  228. package/src/internal/appBuilder.impl.ts +16 -16
  229. package/src/internal/createApp.impl.ts +5 -5
  230. package/src/internal/registry.ts +54 -6
  231. package/src/services/commandService.ts +3 -3
  232. package/src/services/credentialService.ts +3 -3
  233. package/src/services/middlewareService.ts +4 -4
  234. package/src/services/organizationService.ts +18 -116
  235. package/src/services/requestBuilder.ts +40 -15
  236. package/src/services/responseUtils.ts +32 -0
  237. package/src/services/rpcService.ts +28 -11
  238. package/src/services/service.ts +10 -8
  239. package/src/services/userProfileService.ts +18 -66
  240. package/src/storages/chats/answer.impl.ts +186 -0
  241. package/src/storages/chats/answer.ts +55 -0
  242. package/src/storages/chats/chat.impl.ts +126 -0
  243. package/src/storages/chats/chat.ts +49 -0
  244. package/src/storages/chats/chats.impl.ts +142 -0
  245. package/src/storages/chats/chats.ts +47 -0
  246. package/src/storages/files/file.impl.ts +87 -0
  247. package/src/storages/files/file.ts +40 -0
  248. package/src/storages/files/files.impl.ts +191 -0
  249. package/src/storages/files/files.ts +39 -0
  250. package/src/storages/files/filesPage.impl.ts +37 -0
  251. package/src/storages/files/filesPage.ts +33 -0
  252. package/src/storages/groups/groups.impl.ts +363 -0
  253. package/src/storages/groups/groups.ts +106 -0
  254. package/src/storages/organizations/organization.impl.ts +163 -0
  255. package/src/storages/organizations/organization.ts +67 -0
  256. package/src/storages/organizations/organizations.impl.ts +197 -0
  257. package/src/storages/{organizations.ts → organizations/organizations.ts} +8 -28
  258. package/src/storages/user/userProfile.impl.ts +56 -0
  259. package/src/storages/{userProfile.ts → user/userProfile.ts} +2 -2
  260. package/src/storages/workspaces/workspace.impl.ts +129 -0
  261. package/src/storages/workspaces/workspace.ts +54 -0
  262. package/src/storages/workspaces/workspaces.impl.ts +212 -0
  263. package/src/storages/workspaces/workspaces.ts +53 -0
  264. package/src/unitTest.ts +12 -1
  265. package/.browserslistrc +0 -5
  266. package/.editorconfig +0 -22
  267. package/.eslintrc.json +0 -44
  268. package/.github/workflows/publish-npm.yml +0 -28
  269. package/.prettierignore +0 -1
  270. package/.prettierrc +0 -11
  271. package/.yarnrc +0 -2
  272. package/babel.config.js +0 -6
  273. package/jest.config.ts +0 -199
  274. package/jest.setup.ts +0 -2
  275. package/src/services/organizationImpl.ts +0 -51
  276. package/src/services/organizationsImpl.ts +0 -55
  277. package/src/types.ts +0 -86
  278. package/test/commands.test.ts +0 -24
  279. package/test/disposable.test.ts +0 -39
  280. package/test/events.test.ts +0 -151
  281. package/test/index.test.ts +0 -163
  282. package/test/registry.test.ts +0 -44
  283. package/test/services.test.ts +0 -56
  284. package/test/setup.ts +0 -2
  285. package/test/unitTest.test.ts +0 -21
  286. package/tsconfig.json +0 -31
@@ -0,0 +1,40 @@
1
+ import { FileProgressDto } from "../../dto/workspacesResponse"
2
+ import { EventDispatcher } from "../../events"
3
+ import { FilesEvent } from "./files"
4
+
5
+ export type FileId = string
6
+
7
+ /**
8
+ * File.
9
+ */
10
+ export abstract class File extends EventDispatcher<
11
+ FilesEvent,
12
+ File
13
+ > {
14
+ /**
15
+ * File id.
16
+ */
17
+ abstract get id(): FileId
18
+
19
+ /**
20
+ * File name.
21
+ */
22
+ abstract get name(): string
23
+
24
+ /**
25
+ * File date added.
26
+ */
27
+ abstract get createdAt(): number
28
+
29
+ abstract get status(): FileProgressDto
30
+
31
+ /**
32
+ * Get temporary url.
33
+ */
34
+ abstract url(): Promise<string>
35
+
36
+ /**
37
+ * Get file status.
38
+ */
39
+ abstract updateStatus(): Promise<void>
40
+ }
@@ -0,0 +1,191 @@
1
+ import { Context } from "../../context"
2
+ import { FileDto, FileListResponse } from "../../dto/workspacesResponse"
3
+ import { RpcService } from "../../services/rpcService"
4
+ import { FileImpl } from "./file.impl"
5
+ import { Files, FilesEvent, UploadFile } from "./files"
6
+ import { WorkspaceImpl } from "../workspaces/workspace.impl"
7
+ import { ResponseUtils } from "../../services/responseUtils"
8
+ import { File } from "./file"
9
+ import { FilesPage } from "./filesPage"
10
+ import { FilesPageImpl } from "./filesPage.impl"
11
+
12
+ export class FilesImpl extends Files {
13
+ constructor(
14
+ private readonly workspace: WorkspaceImpl,
15
+ private readonly context: Context
16
+ ) {
17
+ super()
18
+ }
19
+
20
+ // Object used as files page data, returned by "query"
21
+ public filesList?: FilesPage
22
+
23
+ async upload(files: any[]): Promise<File[]> {
24
+ const loaded_files = []
25
+ for ( const file of files ){
26
+ loaded_files.push(await this.internalUpload(file))
27
+ }
28
+ return loaded_files
29
+ }
30
+
31
+ async delete(ids: string[]): Promise<void> {
32
+ for ( const id of ids ){
33
+ await this.internalDeleteFile(id)
34
+ }
35
+ }
36
+
37
+ async query(query: string, page: number, limit: number): Promise<FilesPage> {
38
+ return await this.internalQuery(query, page, limit)
39
+ }
40
+
41
+ //----------------------------------------------------------------------------
42
+ // INTERNALS
43
+ //----------------------------------------------------------------------------
44
+
45
+ /**
46
+ * Delete file.
47
+ * @param id
48
+ */
49
+ async internalDeleteFile(id: string): Promise<void> {
50
+ if (id === undefined || id === null) {
51
+ throw new Error("File delete, id is undefined or null")
52
+ }
53
+ if (id.length === 0 || id.trim().length === 0) {
54
+ throw new Error("File delete, id is empty")
55
+ }
56
+
57
+ const response = await this.context
58
+ .resolve(RpcService)
59
+ ?.requestBuilder("/api/v1/Files")
60
+ .searchParam("id", id)
61
+ .sendDelete()
62
+ if (ResponseUtils.isFail(response)) {
63
+ await ResponseUtils.throwError(`File ${id} delete, failed`, response)
64
+ }
65
+ const file = <FileImpl>this.filesList!.files.find(f => f.id === id)
66
+ const index = this.filesList!.files.indexOf(file)
67
+ if (index < 0) {
68
+ throw new Error("File delete, index is not found")
69
+ }
70
+
71
+ // remove file from collection
72
+ this.filesList!.files.splice(index, 1)
73
+
74
+ // dispatch event, file removed
75
+ this.dispatch({
76
+ type: FilesEvent.REMOVED,
77
+ data: file
78
+ })
79
+
80
+ // dispose file
81
+ file.dispose()
82
+ }
83
+
84
+ async internalQuery(
85
+ query: string,
86
+ page: number,
87
+ limit: number
88
+ ): Promise<FilesPage> {
89
+
90
+ // check page
91
+ if (page === undefined || page === null) {
92
+ throw new Error("File fetch, page is undefined or null")
93
+ }
94
+ if (page < 0) {
95
+ throw new Error("File fetch, page is negative")
96
+ }
97
+
98
+ // check limit
99
+ if (limit === undefined || limit === null) {
100
+ throw new Error("File fetch, limit is undefined or null")
101
+ }
102
+ if (limit === 0) {
103
+ throw new Error("File fetch, limit is 0")
104
+ }
105
+
106
+ // send request to the server
107
+ const response = await this.context
108
+ .resolve(RpcService)
109
+ ?.requestBuilder("api/v1/Files/list")
110
+ .searchParam("workspaceId", this.workspace.id)
111
+ .searchParam("organizationId", this.workspace.organization.id)
112
+ .searchParam("query", query)
113
+ .searchParam("page", page.toString())
114
+ .searchParam("limit", limit.toString())
115
+ .sendGet()
116
+
117
+ // check response status
118
+ if (ResponseUtils.isFail(response)) {
119
+ await ResponseUtils.throwError(
120
+ `Files fetch query:${query}, page:${page}, limit:${limit}, failed`,
121
+ response
122
+ )
123
+ }
124
+
125
+ // parse files from the server's response
126
+ const files = (await response!.json()) as FileListResponse
127
+
128
+ // create files list
129
+ const filesList = new FilesPageImpl()
130
+ filesList.total = files.totalFilesCount
131
+ filesList.filesPerPage = files.filesPerPage
132
+ filesList.page = page
133
+
134
+ // init files from the server's response
135
+ for (const fl of files.files) {
136
+
137
+ // create file implementation
138
+ const file = new FileImpl(this.context).initFrom(fl)
139
+
140
+ // add file to the collection
141
+ filesList.files.push(file)
142
+ }
143
+
144
+ // set files list
145
+ this.filesList = filesList
146
+
147
+ return filesList
148
+ }
149
+
150
+ async internalUpload(file: UploadFile): Promise<File> {
151
+ // check file
152
+ if (file === undefined || file === null) {
153
+ throw new Error("File upload, file is undefined or null")
154
+ }
155
+
156
+ // form data to send
157
+ const form = new FormData()
158
+ form.append("organizationId", this.workspace.organization.id)
159
+ form.append("workspaceId", this.workspace.id)
160
+ form.append("name", file.name)
161
+ form.append("file", file, file.name)
162
+
163
+ // send request to the server
164
+ const response = await this.context
165
+ .resolve(RpcService)
166
+ ?.requestBuilder("api/v1/Files")
167
+ .sendPostFormData(form)
168
+
169
+ // check response status
170
+ if (ResponseUtils.isFail(response)) {
171
+ await ResponseUtils.throwError(`File upload ${file.name}`, response)
172
+ }
173
+
174
+ // parse file from the server's response
175
+ const result = (await response!.json()).file as FileDto
176
+
177
+ // create file implementation
178
+ const fileImpl = new FileImpl(this.context).initFrom(result)
179
+
180
+ // TODO: why is this here?
181
+ this.filesList?.files.push(fileImpl)
182
+
183
+ // dispatch event, file added
184
+ this.dispatch({
185
+ type: FilesEvent.ADDED,
186
+ data: fileImpl
187
+ })
188
+
189
+ return fileImpl
190
+ }
191
+ }
@@ -0,0 +1,39 @@
1
+ import { EventDispatcher } from "../../events"
2
+ import { File, FileId } from "./file"
3
+ import { FilesPage } from "./filesPage"
4
+
5
+ /**
6
+ * Files event.
7
+ */
8
+ export enum FilesEvent {
9
+ ADDED = "added",
10
+ REMOVED = "removed",
11
+ UPDATED = "updated"
12
+ }
13
+
14
+ /**
15
+ * Upload file.
16
+ */
17
+ export type UploadFile = globalThis.File
18
+
19
+ /**
20
+ * Files storage.
21
+ */
22
+ export abstract class Files extends EventDispatcher<FilesEvent, File> {
23
+ /**
24
+ * Upload file.
25
+ */
26
+ abstract upload(files: UploadFile[]): Promise<File[]>
27
+
28
+ /**
29
+ * Delete files.
30
+ * @param ids
31
+ */
32
+ abstract delete(ids: FileId[]): Promise<void>
33
+
34
+ /**
35
+ * Query files.
36
+ */
37
+ abstract query(query: string, page: number, limit: number): Promise<FilesPage>
38
+ }
39
+
@@ -0,0 +1,37 @@
1
+ import { FilesPage } from "./filesPage"
2
+ import { Disposable } from "../../disposable"
3
+ import { File } from "./file"
4
+
5
+ export class FilesPageImpl extends FilesPage implements Disposable {
6
+ private _isDisposed: boolean = false
7
+
8
+ public files: File[] = []
9
+ public total: number = 0
10
+ public filesPerPage: number = 0
11
+ public page: number = 0
12
+
13
+ get pages(): number {
14
+ return Math.ceil(Math.max(this.total / this.filesPerPage, 1.0))
15
+ }
16
+
17
+ get isDisposed(): boolean {
18
+ return this._isDisposed
19
+ }
20
+
21
+ dispose(): void {
22
+ this._isDisposed = true
23
+ }
24
+
25
+ equals(other?: FilesPage | null): boolean {
26
+ if (other === undefined) return false
27
+ if (other === null) return false
28
+ if (other === this) return true
29
+ return (
30
+ other.pages === this.pages &&
31
+ other.total === this.total &&
32
+ other.page === this.page &&
33
+ (other.files === this.files ||
34
+ other.files.every((file, index) => file.id === this.files[index].id))
35
+ )
36
+ }
37
+ }
@@ -0,0 +1,33 @@
1
+ import { File } from "./file"
2
+
3
+ /**
4
+ * Files page.
5
+ */
6
+ export abstract class FilesPage {
7
+
8
+ /**
9
+ * Get files.
10
+ */
11
+ abstract get files(): File[]
12
+
13
+ /**
14
+ * Get pages count.
15
+ */
16
+ abstract get pages(): number
17
+
18
+ /**
19
+ * Get total count.
20
+ */
21
+ abstract get total(): number
22
+
23
+ /**
24
+ * Get current page.
25
+ */
26
+ abstract get page(): number
27
+
28
+ /**
29
+ * Equals.
30
+ * @param other
31
+ */
32
+ abstract equals(other?: FilesPage | null): boolean
33
+ }
@@ -0,0 +1,363 @@
1
+ import { Context } from "../../context"
2
+ import { Disposable } from "../../disposable"
3
+ import {
4
+ AccessGroupDto,
5
+ AccessGroupResponse,
6
+ AccessGroupsResponse
7
+ } from "../../dto/accessGroupResponse"
8
+ import { UserDto } from "../../dto/userInfoResponse"
9
+ import { WorkspaceDto, WorkspacesResponse } from "../../dto/workspacesResponse"
10
+ import { RpcService } from "../../services/rpcService"
11
+ import { Group, GroupEvent, GroupId, Groups } from "./groups"
12
+ import { OrganizationImpl } from "../organizations/organization.impl"
13
+ import { ResponseUtils } from "../../services/responseUtils"
14
+ import { Organization } from "../organizations/organization"
15
+ import { UserId } from "../user/userProfile"
16
+
17
+ export class GroupImpl extends Group implements Disposable {
18
+ private _isDisposed: boolean = false
19
+ private _content?: AccessGroupDto
20
+ private _members?: UserDto[]
21
+
22
+ constructor(
23
+ private readonly context: Context,
24
+ public readonly organization: Organization
25
+ ) {
26
+ super()
27
+ }
28
+
29
+ async initFrom(id: GroupId): Promise<Group> {
30
+ await this.reloadGroup(id)
31
+ return this
32
+ }
33
+
34
+ async reloadGroup(id: GroupId): Promise<void> {
35
+ // fetch group
36
+ const response = await this.context.resolve(RpcService)
37
+ ?.requestBuilder("api/v1/AccessGroups")
38
+ .searchParam("groupId", id)
39
+ .sendGet()
40
+
41
+ // check response status
42
+ if (ResponseUtils.isFail(response)) {
43
+ await ResponseUtils.throwError(`Failed to get group: ${id}, organization: ${this.organization.id}`, response)
44
+ }
45
+
46
+ // parse group from the server's response
47
+ const group = (await response!.json()) as AccessGroupResponse
48
+ // init group
49
+ this._content = group.group
50
+ this._members = group.members
51
+ }
52
+
53
+ get id(): GroupId {
54
+ if (this._content) {
55
+ return this._content.id
56
+ }
57
+ throw new Error("Access group is not loaded.")
58
+ }
59
+
60
+ get group(): AccessGroupDto {
61
+ if (this._content) {
62
+ return this._content
63
+ }
64
+ throw new Error("Access group is not loaded.")
65
+ }
66
+
67
+ async getWorkspaces(): Promise<WorkspaceDto[]> {
68
+ // fetch workspaces
69
+ const response = await this.context.resolve(RpcService)
70
+ ?.requestBuilder("api/v1/Organizations/workspaces")
71
+ .searchParam("id", this.id)
72
+ .sendGet()
73
+
74
+ if (ResponseUtils.isFail(response)) {
75
+ await ResponseUtils.throwError(`Failed to get workspaces for group: ${this.id}, organization: ${this.organization.id}`, response)
76
+ }
77
+
78
+ // parse workspaces from the server's response
79
+ const workspaces = (await response!.json()) as WorkspacesResponse
80
+
81
+ return workspaces.workspaces
82
+ }
83
+
84
+ get members(): UserDto[] {
85
+ if (this._members) {
86
+ return this._members
87
+ }
88
+ throw new Error("Access group is not loaded.")
89
+ }
90
+
91
+ async setName(name: string): Promise<void> {
92
+ if (name === undefined || name === null) {
93
+ throw new Error("Groups change, name is undefined or null")
94
+ }
95
+ if (name.length === 0 || name.trim().length === 0) {
96
+ throw new Error("Groups change, name is empty")
97
+ }
98
+ // send request to the server
99
+ const response = await this.context
100
+ .resolve(RpcService)
101
+ ?.requestBuilder("api/v1/AccessGroups/name")
102
+ .sendPutJson({
103
+ groupId: this.id,
104
+ name: name
105
+ })
106
+
107
+ // check response status
108
+ if (ResponseUtils.isFail(response)) {
109
+ await ResponseUtils.throwError(`Failed to change group name, group: ${this.id}, organization: ${this.organization.id}`, response)
110
+ }
111
+
112
+ if (this._content) {
113
+ this._content.name = name
114
+ }
115
+ }
116
+
117
+ async setPermits(permits: { isAdmin: boolean }): Promise<void> {
118
+ // send request to the server
119
+ const response = await this.context
120
+ .resolve(RpcService)
121
+ ?.requestBuilder("api/v1/AccessGroups/permits")
122
+ .sendPutJson({
123
+ groupId: this.id,
124
+ permits: permits
125
+ })
126
+
127
+ if (ResponseUtils.isFail(response)) {
128
+ await ResponseUtils.throwError(`Failed to change group permits, group: ${this.id}, organization: ${this.organization.id}`, response)
129
+ }
130
+ }
131
+
132
+ async setWorkspaces(workspaces: string[]): Promise<void> {
133
+ if (workspaces === null || workspaces === undefined) {
134
+ throw new Error("Group add workspaces, workspaces is undefined or null")
135
+ }
136
+
137
+ // send request to the server
138
+ const response = await this.context
139
+ .resolve(RpcService)
140
+ ?.requestBuilder("api/v1/AccessGroups/workspaces")
141
+ .sendPutJson({
142
+ groupId: this.id,
143
+ actualWorkspaceIds: workspaces
144
+ })
145
+
146
+ if (ResponseUtils.isFail(response)) {
147
+ await ResponseUtils.throwError(`Failed to set workspaces for group: ${this.id}, organization: ${this.organization.id}`, response)
148
+ }
149
+ }
150
+
151
+ async setMembersIds(members: UserId[]) {
152
+ if (members === null || members === undefined) {
153
+ throw new Error("Group setMembersIds, members is undefined or null")
154
+ }
155
+
156
+ // send request to the server
157
+ const response = await this.context
158
+ .resolve(RpcService)
159
+ ?.requestBuilder("api/v1/AccessGroups/members")
160
+ .sendPutJson({
161
+ groupId: this.id,
162
+ memberIds: members
163
+ })
164
+
165
+ if (ResponseUtils.isFail(response)) {
166
+ await ResponseUtils.throwError(`Failed to set members for group: ${this.id}, organization: ${this.organization.id}`, response)
167
+ }
168
+
169
+ // reload group
170
+ await this.reloadGroup(this.id)
171
+ }
172
+
173
+ async removeMembers(members: UserId[]): Promise<void> {
174
+ // check members
175
+ if (members === null || members === undefined) {
176
+ throw new Error("Group removeMembers, members is undefined or null")
177
+ }
178
+
179
+ // make set of members
180
+ const groupMembers = new Set(this.members.map(m => m.id))
181
+
182
+ // check argument
183
+ if (!members.every(m => groupMembers.has(m))) {
184
+ const notExistingMembers = members.filter(memberId => !groupMembers.has(memberId))
185
+ throw new Error(`Group removeMembers, members contains not existing members: ${notExistingMembers}`)
186
+ }
187
+
188
+ // remove members
189
+ for (const id of members) {
190
+ groupMembers.delete(id)
191
+ }
192
+
193
+ // send request to the server
194
+ await this.setMembersIds(Array.from(groupMembers))
195
+ }
196
+
197
+ get isDisposed(): boolean {
198
+ return this._isDisposed
199
+ }
200
+
201
+ dispose(): void {
202
+ this._isDisposed = true
203
+ }
204
+ }
205
+
206
+ export class GroupsImpl extends Groups {
207
+
208
+ private _groups: Group[] = []
209
+
210
+ constructor(
211
+ public readonly organization: OrganizationImpl,
212
+ private readonly context: Context
213
+ ) {
214
+ super()
215
+ }
216
+
217
+ get collection(): readonly Group[] {
218
+ return this._groups
219
+ }
220
+
221
+ async initialize() {
222
+ await this.internalInit()
223
+ }
224
+
225
+ async create(name: string, permits: {
226
+ isAdmin: boolean
227
+ }, memberIds: string[]): Promise<Group> {
228
+ return await this.internalCreate(name, permits, memberIds)
229
+ }
230
+
231
+ get(id: GroupId): Group | undefined {
232
+ return this._groups.find(group => group.id === id)
233
+ }
234
+
235
+ async delete(id: GroupId): Promise<void> {
236
+ return await this.internalDeleteGroup(id)
237
+ }
238
+
239
+ //----------------------------------------------------------------------------
240
+ // INTERNALS
241
+ //----------------------------------------------------------------------------
242
+
243
+ /**
244
+ * Init access groups.
245
+ */
246
+ async internalInit(): Promise<void> {
247
+ // fetch groups
248
+ const response = await this.context.resolve(RpcService)
249
+ ?.requestBuilder("api/v1/Organizations/access_groups")
250
+ .searchParam("id", this.organization.id)
251
+ .sendGet()
252
+
253
+ // check response status
254
+ if (ResponseUtils.isFail(response)) {
255
+ await ResponseUtils.throwError(`Failed to get groups for organization: ${this.organization.id}`, response)
256
+ }
257
+
258
+ // parse groups from the server's response
259
+ const groups = (await response!.json()) as AccessGroupsResponse
260
+
261
+ // init groups
262
+ for (const gr of groups.groups) {
263
+ // create group implementation
264
+ const group = await new GroupImpl(this.context, this.organization).initFrom(gr.id)
265
+
266
+ // add group to the collection
267
+ this._groups.push(group)
268
+
269
+ // dispatch event
270
+ this.dispatch({
271
+ type: GroupEvent.ADDED,
272
+ data: group
273
+ })
274
+ }
275
+ }
276
+
277
+ async internalCreate(name: string, permits: {
278
+ isAdmin: boolean
279
+ }, memberIds: string[]): Promise<Group> {
280
+ if (name === undefined || name === null) {
281
+ throw new Error("Group create, name is undefined or null")
282
+ }
283
+ if (name.length === 0 || name.trim().length === 0) {
284
+ throw new Error("Group create, name is empty")
285
+ }
286
+
287
+ // send request to the server
288
+ const response = await this.context
289
+ .resolve(RpcService)
290
+ ?.requestBuilder("api/v1/AccessGroups")
291
+ .sendPostJson({
292
+ name: name,
293
+ organizationId: this.organization.id,
294
+ permits: permits,
295
+ memberIds: memberIds
296
+ })
297
+
298
+ // check response status
299
+ if (ResponseUtils.isFail(response)) {
300
+ await ResponseUtils.throwError(`Failed to create group, organization: ${this.organization.id}`, response)
301
+ }
302
+ // parse group from the server's response
303
+ const content = (await response!.json()) as AccessGroupResponse
304
+
305
+ // create group implementation
306
+ const group = await new GroupImpl(this.context, this.organization).initFrom(content.group.id)
307
+
308
+ // add group to the collection
309
+ this._groups.push(group)
310
+
311
+ // dispatch event
312
+ this.dispatch({
313
+ type: GroupEvent.ADDED,
314
+ data: group
315
+ })
316
+
317
+ return group
318
+ }
319
+
320
+ /**
321
+ * Delete group.
322
+ * @param id
323
+ */
324
+ async internalDeleteGroup(id: GroupId): Promise<void> {
325
+ if (id === undefined || id === null) {
326
+ throw new Error("Group delete, id is undefined or null")
327
+ }
328
+ if (id.length === 0 || id.trim().length === 0) {
329
+ throw new Error("Group delete, id is empty")
330
+ }
331
+
332
+ // send request to the server
333
+ const response = await this.context
334
+ .resolve(RpcService)
335
+ ?.requestBuilder("/api/v1/AccessGroups")
336
+ .searchParam("groupId", id)
337
+ .sendDelete()
338
+
339
+ // check response status
340
+ if (ResponseUtils.isFail(response)) {
341
+ await ResponseUtils.throwError(`Failed to delete group: ${id}, organization: ${this.organization.id}`, response)
342
+ }
343
+
344
+ // delete group from collection
345
+ const group = <GroupImpl>this._groups.find(f => f.id === id)
346
+ const index = this._groups.indexOf(group)
347
+ if (index < 0) {
348
+ throw new Error("Group delete, index is not found")
349
+ }
350
+
351
+ // remove group from collection
352
+ this._groups.splice(index, 1)
353
+
354
+ // dispatch event, group removed
355
+ this.dispatch({
356
+ type: GroupEvent.REMOVED,
357
+ data: group
358
+ })
359
+
360
+ // dispose group
361
+ group.dispose()
362
+ }
363
+ }