@eclipse-glsp/server 1.1.0-next.9fd0925.53 → 1.1.0-next.abdebbd.65

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 (218) hide show
  1. package/lib/browser/launch/worker-server-launcher.js +26 -3
  2. package/lib/browser/launch/worker-server-launcher.js.map +1 -1
  3. package/lib/common/actions/action-dispatcher.d.ts +2 -1
  4. package/lib/common/actions/action-dispatcher.d.ts.map +1 -1
  5. package/lib/common/actions/action-dispatcher.js +9 -7
  6. package/lib/common/actions/action-dispatcher.js.map +1 -1
  7. package/lib/common/actions/action-handler-registry.js +4 -4
  8. package/lib/common/actions/action-handler-registry.js.map +1 -1
  9. package/lib/common/actions/client-action-handler.d.ts +17 -8
  10. package/lib/common/actions/client-action-handler.d.ts.map +1 -1
  11. package/lib/common/actions/client-action-handler.js +32 -22
  12. package/lib/common/actions/client-action-handler.js.map +1 -1
  13. package/lib/common/actions/global-action-provider.d.ts +6 -21
  14. package/lib/common/actions/global-action-provider.d.ts.map +1 -1
  15. package/lib/common/actions/global-action-provider.js +17 -22
  16. package/lib/common/actions/global-action-provider.js.map +1 -1
  17. package/lib/common/command/command-stack.js +2 -2
  18. package/lib/common/command/command-stack.js.map +1 -1
  19. package/lib/common/command/command.js +1 -1
  20. package/lib/common/command/command.js.map +1 -1
  21. package/lib/common/command/recording-command.d.ts +1 -1
  22. package/lib/common/command/recording-command.d.ts.map +1 -1
  23. package/lib/common/command/recording-command.js +26 -3
  24. package/lib/common/command/recording-command.js.map +1 -1
  25. package/lib/common/command/undo-redo-action-handler.js +2 -2
  26. package/lib/common/command/undo-redo-action-handler.js.map +1 -1
  27. package/lib/common/di/binding-target.d.ts.map +1 -1
  28. package/lib/common/di/binding-target.js +3 -2
  29. package/lib/common/di/binding-target.js.map +1 -1
  30. package/lib/common/di/client-session-module.d.ts +9 -1
  31. package/lib/common/di/client-session-module.d.ts.map +1 -1
  32. package/lib/common/di/client-session-module.js +9 -9
  33. package/lib/common/di/client-session-module.js.map +1 -1
  34. package/lib/common/di/diagram-module.d.ts +20 -1
  35. package/lib/common/di/diagram-module.d.ts.map +1 -1
  36. package/lib/common/di/diagram-module.js +10 -48
  37. package/lib/common/di/diagram-module.js.map +1 -1
  38. package/lib/common/di/glsp-module.js +2 -2
  39. package/lib/common/di/glsp-module.js.map +1 -1
  40. package/lib/common/di/server-module.d.ts +0 -1
  41. package/lib/common/di/server-module.d.ts.map +1 -1
  42. package/lib/common/di/server-module.js +0 -1
  43. package/lib/common/di/server-module.js.map +1 -1
  44. package/lib/common/diagram/diagram-configuration.js +1 -1
  45. package/lib/common/diagram/diagram-configuration.js.map +1 -1
  46. package/lib/common/diagram/request-type-hints-action-handler.js +2 -2
  47. package/lib/common/diagram/request-type-hints-action-handler.js.map +1 -1
  48. package/lib/common/features/clipboard/request-clipboard-data-action-handler.js +2 -2
  49. package/lib/common/features/clipboard/request-clipboard-data-action-handler.js.map +1 -1
  50. package/lib/common/features/contextactions/command-palette-action-provider.js +2 -2
  51. package/lib/common/features/contextactions/command-palette-action-provider.js.map +1 -1
  52. package/lib/common/features/contextactions/context-actions-provider-registry.js +2 -2
  53. package/lib/common/features/contextactions/context-actions-provider-registry.js.map +1 -1
  54. package/lib/common/features/contextactions/context-menu-item-provider.js +2 -2
  55. package/lib/common/features/contextactions/context-menu-item-provider.js.map +1 -1
  56. package/lib/common/features/contextactions/request-context-actions-handler.js +2 -2
  57. package/lib/common/features/contextactions/request-context-actions-handler.js.map +1 -1
  58. package/lib/common/features/contextactions/tool-palette-item-provider.js +4 -4
  59. package/lib/common/features/contextactions/tool-palette-item-provider.js.map +1 -1
  60. package/lib/common/features/directediting/context-edit-validator-registry.js +2 -2
  61. package/lib/common/features/directediting/context-edit-validator-registry.js.map +1 -1
  62. package/lib/common/features/directediting/label-edit-validator.js +2 -2
  63. package/lib/common/features/directediting/label-edit-validator.js.map +1 -1
  64. package/lib/common/features/directediting/request-edit-validation-handler.js +2 -2
  65. package/lib/common/features/directediting/request-edit-validation-handler.js.map +1 -1
  66. package/lib/common/features/layout/computed-bounds-action-handler.js +2 -2
  67. package/lib/common/features/layout/computed-bounds-action-handler.js.map +1 -1
  68. package/lib/common/features/layout/layout-operation-handler.js +2 -2
  69. package/lib/common/features/layout/layout-operation-handler.js.map +1 -1
  70. package/lib/common/features/model/gmodel-factory.js +2 -2
  71. package/lib/common/features/model/gmodel-factory.js.map +1 -1
  72. package/lib/common/features/model/gmodel-index.js +2 -2
  73. package/lib/common/features/model/gmodel-index.js.map +1 -1
  74. package/lib/common/features/model/gmodel-serializer.js +2 -2
  75. package/lib/common/features/model/gmodel-serializer.js.map +1 -1
  76. package/lib/common/features/model/model-state.js +2 -2
  77. package/lib/common/features/model/model-state.js.map +1 -1
  78. package/lib/common/features/model/model-submission-handler.d.ts +30 -2
  79. package/lib/common/features/model/model-submission-handler.d.ts.map +1 -1
  80. package/lib/common/features/model/model-submission-handler.js +57 -8
  81. package/lib/common/features/model/model-submission-handler.js.map +1 -1
  82. package/lib/common/features/model/request-model-action-handler.d.ts +5 -6
  83. package/lib/common/features/model/request-model-action-handler.d.ts.map +1 -1
  84. package/lib/common/features/model/request-model-action-handler.js +37 -15
  85. package/lib/common/features/model/request-model-action-handler.js.map +1 -1
  86. package/lib/common/features/model/save-model-action-handler.js +2 -2
  87. package/lib/common/features/model/save-model-action-handler.js.map +1 -1
  88. package/lib/common/features/navigation/navigation-target-provider-registry.js +2 -2
  89. package/lib/common/features/navigation/navigation-target-provider-registry.js.map +1 -1
  90. package/lib/common/features/navigation/navigation-target-resolver.js +2 -2
  91. package/lib/common/features/navigation/navigation-target-resolver.js.map +1 -1
  92. package/lib/common/features/navigation/request-navigation-targets-action-handler.js +2 -2
  93. package/lib/common/features/navigation/request-navigation-targets-action-handler.js.map +1 -1
  94. package/lib/common/features/navigation/resolve-navigation-targets-action-handler.js +2 -2
  95. package/lib/common/features/navigation/resolve-navigation-targets-action-handler.js.map +1 -1
  96. package/lib/common/features/popup/request-popup-model-action-handler.js +2 -2
  97. package/lib/common/features/popup/request-popup-model-action-handler.js.map +1 -1
  98. package/lib/common/features/progress/progress-service.d.ts +44 -0
  99. package/lib/common/features/progress/progress-service.d.ts.map +1 -0
  100. package/lib/common/features/progress/progress-service.js +74 -0
  101. package/lib/common/features/progress/progress-service.js.map +1 -0
  102. package/lib/common/features/validation/model-validator.d.ts +47 -2
  103. package/lib/common/features/validation/model-validator.d.ts.map +1 -1
  104. package/lib/common/features/validation/model-validator.js +80 -1
  105. package/lib/common/features/validation/model-validator.js.map +1 -1
  106. package/lib/common/features/validation/request-markers-handler.d.ts +15 -0
  107. package/lib/common/features/validation/request-markers-handler.d.ts.map +1 -1
  108. package/lib/common/features/validation/request-markers-handler.js +5 -11
  109. package/lib/common/features/validation/request-markers-handler.js.map +1 -1
  110. package/lib/common/gmodel/apply-label-edit-operation-handler.js +2 -2
  111. package/lib/common/gmodel/apply-label-edit-operation-handler.js.map +1 -1
  112. package/lib/common/gmodel/change-bounds-operation-handler.js +2 -2
  113. package/lib/common/gmodel/change-bounds-operation-handler.js.map +1 -1
  114. package/lib/common/gmodel/change-routing-points-operation-handler.js +2 -2
  115. package/lib/common/gmodel/change-routing-points-operation-handler.js.map +1 -1
  116. package/lib/common/gmodel/cut-operation-handler.js +2 -2
  117. package/lib/common/gmodel/cut-operation-handler.js.map +1 -1
  118. package/lib/common/gmodel/delete-operation-handler.js +2 -2
  119. package/lib/common/gmodel/delete-operation-handler.js.map +1 -1
  120. package/lib/common/gmodel/gmodel-create-edge-operation-handler.js +2 -2
  121. package/lib/common/gmodel/gmodel-create-edge-operation-handler.js.map +1 -1
  122. package/lib/common/gmodel/gmodel-create-node-operation-handler.js +2 -2
  123. package/lib/common/gmodel/gmodel-create-node-operation-handler.js.map +1 -1
  124. package/lib/common/gmodel/gmodel-diagram-module.js +2 -2
  125. package/lib/common/gmodel/gmodel-diagram-module.js.map +1 -1
  126. package/lib/common/gmodel/gmodel-operation-handler.js +1 -1
  127. package/lib/common/gmodel/gmodel-operation-handler.js.map +1 -1
  128. package/lib/common/gmodel/paste-operation-handler.js +26 -3
  129. package/lib/common/gmodel/paste-operation-handler.js.map +1 -1
  130. package/lib/common/gmodel/reconnect-edge-operation-handler.js +2 -2
  131. package/lib/common/gmodel/reconnect-edge-operation-handler.js.map +1 -1
  132. package/lib/common/launch/glsp-server-launcher.js +2 -2
  133. package/lib/common/launch/glsp-server-launcher.js.map +1 -1
  134. package/lib/common/launch/jsonrpc-server-launcher.js +2 -2
  135. package/lib/common/launch/jsonrpc-server-launcher.js.map +1 -1
  136. package/lib/common/operations/compound-operation-handler.js +6 -11
  137. package/lib/common/operations/compound-operation-handler.js.map +1 -1
  138. package/lib/common/operations/create-operation-handler.js +1 -1
  139. package/lib/common/operations/create-operation-handler.js.map +1 -1
  140. package/lib/common/operations/operation-action-handler.d.ts.map +1 -1
  141. package/lib/common/operations/operation-action-handler.js +3 -3
  142. package/lib/common/operations/operation-action-handler.js.map +1 -1
  143. package/lib/common/operations/operation-handler-registry.js +4 -4
  144. package/lib/common/operations/operation-handler-registry.js.map +1 -1
  145. package/lib/common/operations/operation-handler.js +2 -2
  146. package/lib/common/operations/operation-handler.js.map +1 -1
  147. package/lib/common/protocol/client-action.d.ts +31 -0
  148. package/lib/common/protocol/client-action.d.ts.map +1 -0
  149. package/lib/common/protocol/client-action.js +35 -0
  150. package/lib/common/protocol/client-action.js.map +1 -0
  151. package/lib/common/protocol/glsp-server.d.ts +1 -1
  152. package/lib/common/protocol/glsp-server.d.ts.map +1 -1
  153. package/lib/common/protocol/glsp-server.js +9 -11
  154. package/lib/common/protocol/glsp-server.js.map +1 -1
  155. package/lib/common/session/client-session-factory.js +5 -5
  156. package/lib/common/session/client-session-factory.js.map +1 -1
  157. package/lib/common/session/client-session-manager.js +2 -2
  158. package/lib/common/session/client-session-manager.js.map +1 -1
  159. package/lib/common/utils/args-util.js +2 -2
  160. package/lib/common/utils/args-util.js.map +1 -1
  161. package/lib/common/utils/client-options-util.d.ts +3 -0
  162. package/lib/common/utils/client-options-util.d.ts.map +1 -1
  163. package/lib/common/utils/client-options-util.js +5 -15
  164. package/lib/common/utils/client-options-util.js.map +1 -1
  165. package/lib/common/utils/console-logger.js +2 -2
  166. package/lib/common/utils/console-logger.js.map +1 -1
  167. package/lib/common/utils/logger.d.ts.map +1 -1
  168. package/lib/common/utils/logger.js +5 -4
  169. package/lib/common/utils/logger.js.map +1 -1
  170. package/lib/common/utils/promise-queue.d.ts.map +1 -1
  171. package/lib/common/utils/promise-queue.js +3 -6
  172. package/lib/common/utils/promise-queue.js.map +1 -1
  173. package/lib/common/utils/registry.js +4 -4
  174. package/lib/common/utils/registry.js.map +1 -1
  175. package/lib/node/abstract-json-model-storage.d.ts.map +1 -1
  176. package/lib/node/abstract-json-model-storage.js +33 -4
  177. package/lib/node/abstract-json-model-storage.js.map +1 -1
  178. package/lib/node/di/app-module.js +24 -1
  179. package/lib/node/di/app-module.js.map +1 -1
  180. package/lib/node/gmodel/gmodel-storage.js +2 -2
  181. package/lib/node/gmodel/gmodel-storage.js.map +1 -1
  182. package/lib/node/launch/cli-parser.js +26 -3
  183. package/lib/node/launch/cli-parser.js.map +1 -1
  184. package/lib/node/launch/socket-cli-parser.js +24 -1
  185. package/lib/node/launch/socket-cli-parser.js.map +1 -1
  186. package/lib/node/launch/socket-server-launcher.js +27 -4
  187. package/lib/node/launch/socket-server-launcher.js.map +1 -1
  188. package/lib/node/launch/websocket-server-launcher.js +27 -4
  189. package/lib/node/launch/websocket-server-launcher.js.map +1 -1
  190. package/package.json +6 -5
  191. package/src/common/actions/action-dispatcher.spec.ts +3 -2
  192. package/src/common/actions/action-dispatcher.ts +8 -5
  193. package/src/common/actions/client-action-handler.ts +28 -18
  194. package/src/common/actions/global-action-provider.spec.ts +4 -15
  195. package/src/common/actions/global-action-provider.ts +21 -25
  196. package/src/common/command/recording-command.ts +2 -2
  197. package/src/common/di/binding-target.ts +1 -0
  198. package/src/common/di/client-session-module.ts +17 -10
  199. package/src/common/di/diagram-module.ts +14 -66
  200. package/src/common/di/server-module.ts +0 -1
  201. package/src/common/features/model/model-submission-handler.ts +62 -5
  202. package/src/common/features/model/request-model-action-handler.ts +37 -17
  203. package/src/common/features/progress/progress-service.ts +74 -0
  204. package/src/common/features/validation/model-validator.ts +75 -3
  205. package/src/common/features/validation/request-markers-handler.ts +4 -10
  206. package/src/common/operations/operation-action-handler.ts +2 -2
  207. package/src/common/protocol/client-action.ts +38 -0
  208. package/src/common/protocol/glsp-server.spec.ts +11 -10
  209. package/src/common/protocol/glsp-server.ts +11 -14
  210. package/src/common/session/client-session-factory.spec.ts +2 -2
  211. package/src/common/session/client-session-factory.ts +3 -3
  212. package/src/common/session/client-session-manager.spec.ts +4 -3
  213. package/src/common/utils/args-util.ts +1 -1
  214. package/src/common/utils/client-options-util.ts +8 -0
  215. package/src/common/utils/logger.ts +2 -1
  216. package/src/common/utils/promise-queue.ts +4 -5
  217. package/src/node/abstract-json-model-storage.ts +8 -2
  218. package/src/node/launch/cli-parser.ts +1 -1
@@ -13,60 +13,56 @@
13
13
  *
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
+ import { distinctAdd } from '@eclipse-glsp/protocol';
16
17
  import { Container, ContainerModule, inject, injectable } from 'inversify';
17
- import { ClientActionKinds, DiagramModules, InjectionContainer } from '../di/service-identifiers';
18
+ import { createClientSessionModule } from '../di/client-session-module';
19
+ import { DiagramModules, InjectionContainer } from '../di/service-identifiers';
18
20
  import { ClientSessionInitializer } from '../session/client-session-initializer';
19
21
  import { ActionHandlerRegistry } from './action-handler-registry';
20
- import { ClientActionHandler } from './client-action-handler';
21
22
 
22
23
  export const GlobalActionProvider = Symbol('GlobalActionProvider');
23
24
 
25
+ /**
26
+ * Provides a map of handled action kinds grouped by `diagramType`
27
+ */
24
28
  export interface GlobalActionProvider {
25
- readonly serverActionKinds: Map<string, string[]>;
26
- readonly clientActionKinds: Map<string, string[]>;
29
+ readonly actionKinds: Map<string, string[]>;
27
30
  }
28
31
 
29
32
  @injectable()
30
33
  export class DefaultGlobalActionProvider implements GlobalActionProvider {
31
- public readonly serverActionKinds: Map<string, string[]>;
32
- public readonly clientActionKinds: Map<string, string[]>;
34
+ public readonly actionKinds: Map<string, string[]>;
33
35
 
34
36
  constructor(
35
37
  @inject(InjectionContainer) serverContainer: Container,
36
38
  @inject(DiagramModules) diagramModules: Map<string, ContainerModule[]>
37
39
  ) {
38
- this.serverActionKinds = new Map();
39
- this.clientActionKinds = new Map();
40
+ this.actionKinds = new Map();
40
41
  diagramModules.forEach((modules, diagramType) => {
41
42
  const container = this.createDiagramContainer(serverContainer, modules);
42
43
  const initializers = container.getAll<ClientSessionInitializer>(ClientSessionInitializer);
43
44
  initializers.forEach(service => service.initialize());
44
- this.loadServerActionKinds(diagramType, container);
45
- this.loadClientActionKinds(diagramType, container);
45
+ this.loadActionKinds(diagramType, container);
46
46
  container.unbindAll();
47
47
  });
48
48
  }
49
49
 
50
50
  createDiagramContainer(serverContainer: Container, modules: ContainerModule[]): Container {
51
51
  const container = serverContainer.createChild();
52
- container.load(...modules);
52
+ const clientSessionModule = createClientSessionModule({
53
+ clientId: 'tempId',
54
+ // eslint-disable-next-line @typescript-eslint/no-empty-function
55
+ glspClient: { process: () => {} },
56
+ clientActionKinds: []
57
+ });
58
+ container.load(...modules, clientSessionModule);
53
59
  return container;
54
60
  }
55
61
 
56
- loadServerActionKinds(diagramType: string, diagramContainer: Container): void {
62
+ loadActionKinds(diagramType: string, diagramContainer: Container): void {
57
63
  const handlerRegistry = diagramContainer.get<ActionHandlerRegistry>(ActionHandlerRegistry);
58
- const diagramServerActions = this.serverActionKinds.get(diagramType) ?? [];
59
- handlerRegistry
60
- .getAll()
61
- .filter(handler => !(handler instanceof ClientActionHandler))
62
- .forEach(handler => diagramServerActions.push(...handler.actionKinds));
63
- this.serverActionKinds.set(diagramType, [...new Set(diagramServerActions)]);
64
- }
65
-
66
- loadClientActionKinds(diagramType: string, diagramContainer: Container): void {
67
- const clientActionKinds = diagramContainer.getAll<string>(ClientActionKinds);
68
- const diagramClientActions = this.clientActionKinds.get(diagramType) ?? [];
69
- diagramClientActions.push(...clientActionKinds);
70
- this.clientActionKinds.set(diagramType, diagramClientActions);
64
+ const diagramServerActions = this.actionKinds.get(diagramType) ?? [];
65
+ handlerRegistry.getAll().forEach(handler => distinctAdd(diagramServerActions, ...handler.actionKinds));
66
+ this.actionKinds.set(diagramType, diagramServerActions);
71
67
  }
72
68
  }
@@ -111,8 +111,8 @@ export class GModelRecordingCommand extends AbstractRecordingCommand<GModelRootS
111
111
  return this.serializer.createSchema(this.modelState.root);
112
112
  }
113
113
 
114
- protected override applyPatch(rootSchema: GModelRootSchema, patch: jsonPatch.Operation[]): MaybePromise<void> {
115
- super.applyPatch(rootSchema, patch);
114
+ protected override async applyPatch(rootSchema: GModelRootSchema, patch: jsonPatch.Operation[]): Promise<void> {
115
+ await super.applyPatch(rootSchema, patch);
116
116
  const newRoot = this.serializer.createRoot(rootSchema);
117
117
  this.modelState.updateRoot(newRoot);
118
118
  }
@@ -152,6 +152,7 @@ namespace NoOPSyntax {
152
152
  };
153
153
  const syntax = {
154
154
  onActivation: noOpReturn,
155
+ onDeactivation: noOpReturn,
155
156
  when: noOpReturn,
156
157
  whenAnyAncestorIs: noOpReturn,
157
158
  whenAnyAncestorMatches: noOpReturn,
@@ -13,17 +13,24 @@
13
13
  *
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
- import { GLSPClientProxy } from '@eclipse-glsp/protocol';
16
+ import { GLSPClientProxy, bindOrRebind } from '@eclipse-glsp/protocol';
17
17
  import { ContainerModule } from 'inversify';
18
- import { ClientId } from './service-identifiers';
18
+ import { ClientActionKinds, ClientId } from './service-identifiers';
19
19
 
20
- export function createClientSessionModule(clientId: string, glspClient: GLSPClientProxy): ContainerModule {
21
- return new ContainerModule((bind, _unbind, isBound, rebind) => {
22
- if (isBound(ClientId)) {
23
- rebind(ClientId).toConstantValue(clientId);
24
- } else {
25
- bind(ClientId).toConstantValue(clientId);
26
- }
27
- bind(GLSPClientProxy).toConstantValue(glspClient);
20
+ export interface ClientSessionModuleOptions {
21
+ clientId: string;
22
+ glspClient: GLSPClientProxy;
23
+ clientActionKinds: string[];
24
+ }
25
+
26
+ /**
27
+ * Creates the DI module that binds client session specific configuration
28
+ */
29
+ export function createClientSessionModule(options: ClientSessionModuleOptions): ContainerModule {
30
+ return new ContainerModule((bind, unbind, isBound, rebind) => {
31
+ const context = { bind, unbind, isBound, rebind };
32
+ bindOrRebind(context, ClientId).toConstantValue(options.clientId);
33
+ bind(GLSPClientProxy).toConstantValue(options.glspClient);
34
+ bind(ClientActionKinds).toConstantValue(new Set(options.clientActionKinds));
28
35
  });
29
36
  }
@@ -13,41 +13,11 @@
13
13
  *
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
- import {
17
- CenterAction,
18
- DeleteMarkersAction,
19
- ExportSvgAction,
20
- FitToScreenAction,
21
- NavigateToExternalTargetAction,
22
- NavigateToTargetAction,
23
- RequestBoundsAction,
24
- SelectAction,
25
- SelectAllAction,
26
- ServerMessageAction,
27
- ServerStatusAction,
28
- SetBoundsAction,
29
- SetClipboardDataAction,
30
- SetContextActions,
31
- SetDirtyStateAction,
32
- SetEditModeAction,
33
- SetEditValidationResultAction,
34
- SetMarkersAction,
35
- SetModelAction,
36
- SetNavigationTargetsAction,
37
- SetPopupModelAction,
38
- SetResolvedNavigationTargetAction,
39
- SetTypeHintsAction,
40
- SetViewportAction,
41
- SourceModelChangedAction,
42
- TriggerEdgeCreationAction,
43
- TriggerNodeCreationAction,
44
- UpdateModelAction
45
- } from '@eclipse-glsp/protocol';
46
16
  import { interfaces } from 'inversify';
47
17
  import { ActionDispatcher, DefaultActionDispatcher } from '../actions/action-dispatcher';
48
18
  import { ActionHandlerConstructor, ActionHandlerFactory } from '../actions/action-handler';
49
19
  import { ActionHandlerRegistry, ActionHandlerRegistryInitializer } from '../actions/action-handler-registry';
50
- import { ClientActionHandler } from '../actions/client-action-handler';
20
+ import { ClientActionForwarder } from '../actions/client-action-handler';
51
21
  import { CommandStack, DefaultCommandStack } from '../command/command-stack';
52
22
  import { UndoRedoActionHandler } from '../command/undo-redo-action-handler';
53
23
  import { DiagramConfiguration } from '../diagram/diagram-configuration';
@@ -86,6 +56,7 @@ import { RequestNavigationTargetsActionHandler } from '../features/navigation/re
86
56
  import { ResolveNavigationTargetsActionHandler } from '../features/navigation/resolve-navigation-targets-action-handler';
87
57
  import { PopupModelFactory } from '../features/popup/popup-model-factory';
88
58
  import { RequestPopupModelActionHandler } from '../features/popup/request-popup-model-action-handler';
59
+ import { DefaultProgressService, ProgressService } from '../features/progress/progress-service';
89
60
  import { ModelValidator } from '../features/validation/model-validator';
90
61
  import { RequestMarkersHandler } from '../features/validation/request-markers-handler';
91
62
  import { CompoundOperationHandler } from '../operations/compound-operation-handler';
@@ -93,11 +64,10 @@ import { OperationActionHandler } from '../operations/operation-action-handler';
93
64
  import { OperationHandlerConstructor, OperationHandlerFactory } from '../operations/operation-handler';
94
65
  import { OperationHandlerRegistry, OperationHandlerRegistryInitializer } from '../operations/operation-handler-registry';
95
66
  import { ClientSessionInitializer } from '../session/client-session-initializer';
96
- import { applyBindingTarget, applyOptionalBindingTarget, BindingTarget } from './binding-target';
67
+ import { BindingTarget, applyBindingTarget, applyOptionalBindingTarget } from './binding-target';
97
68
  import { GLSPModule } from './glsp-module';
98
69
  import { InstanceMultiBinding, MultiBinding } from './multi-binding';
99
70
  import {
100
- ClientActionKinds,
101
71
  ClientId,
102
72
  ContextActionsProviders,
103
73
  ContextEditValidators,
@@ -133,6 +103,7 @@ import {
133
103
  * - {@link ContextActionsProviders} as {@link ClassMultiBinding<ContextActionsProvider>} (empty)
134
104
  * - {@link ContextActionsProviderRegistry}
135
105
  * - {@link ActionDispatcher}
106
+ * - {@link ProgressService}
136
107
  * - {@link ClientActionKinds} as {@link InstanceMultiBinding<string>}
137
108
  * - {@link ActionHandler} as {@link InstanceMultiBinding<ActionHandlerConstructor>}
138
109
  * - {@link ActionHandlerFactory}
@@ -162,6 +133,7 @@ export abstract class DiagramModule extends GLSPModule {
162
133
  applyBindingTarget(context, DiagramType, this.bindDiagramType());
163
134
  applyBindingTarget(context, ClientId, this.bindClientId());
164
135
  applyBindingTarget(context, DiagramConfiguration, this.bindDiagramConfiguration()).inSingletonScope();
136
+ applyBindingTarget(context, ClientActionForwarder, this.bindClientActionForwarder()).inSingletonScope();
165
137
 
166
138
  // Model-related bindings
167
139
  applyBindingTarget(context, GModelSerializer, this.bindGModelSerializer()).inSingletonScope();
@@ -186,7 +158,6 @@ export abstract class DiagramModule extends GLSPModule {
186
158
 
187
159
  // Action & operation related bindings
188
160
  applyBindingTarget(context, ActionDispatcher, this.bindActionDispatcher()).inSingletonScope();
189
- this.configureMultiBinding(new InstanceMultiBinding<string>(ClientActionKinds), binding => this.configureClientActions(binding));
190
161
  this.configureMultiBinding(new InstanceMultiBinding<ActionHandlerConstructor>(ActionHandlerConstructor), binding =>
191
162
  this.configureActionHandlers(binding)
192
163
  );
@@ -217,6 +188,7 @@ export abstract class DiagramModule extends GLSPModule {
217
188
  this.configureMultiBinding(new MultiBinding<ClientSessionInitializer>(ClientSessionInitializer), binding =>
218
189
  this.configureClientSessionInitializers(binding)
219
190
  );
191
+ applyBindingTarget(context, ProgressService, this.bindProgressService()).inSingletonScope();
220
192
  applyOptionalBindingTarget(context, PopupModelFactory, this.bindPopupModelFactory());
221
193
  applyOptionalBindingTarget(context, LayoutEngine, this.bindLayoutEngine?.());
222
194
  }
@@ -227,7 +199,6 @@ export abstract class DiagramModule extends GLSPModule {
227
199
  }
228
200
 
229
201
  protected configureActionHandlers(binding: InstanceMultiBinding<ActionHandlerConstructor>): void {
230
- binding.add(ClientActionHandler);
231
202
  binding.add(RequestModelActionHandler);
232
203
  binding.add(RequestContextActionsHandler);
233
204
  binding.add(RequestTypeHintsActionHandler);
@@ -254,6 +225,10 @@ export abstract class DiagramModule extends GLSPModule {
254
225
  return DefaultGModelSerializer;
255
226
  }
256
227
 
228
+ protected bindClientActionForwarder(): BindingTarget<ClientActionForwarder> {
229
+ return ClientActionForwarder;
230
+ }
231
+
257
232
  protected bindGModelIndex(): BindingTarget<GModelIndex> {
258
233
  return GModelIndex;
259
234
  }
@@ -308,6 +283,10 @@ export abstract class DiagramModule extends GLSPModule {
308
283
  binding.add(LayoutOperationHandler);
309
284
  }
310
285
 
286
+ protected bindProgressService(): BindingTarget<ProgressService> {
287
+ return DefaultProgressService;
288
+ }
289
+
311
290
  protected configureContextActionProviders(binding: MultiBinding<ContextActionsProvider>): void {
312
291
  // empty as default
313
292
  }
@@ -320,37 +299,6 @@ export abstract class DiagramModule extends GLSPModule {
320
299
  // empty as default
321
300
  }
322
301
 
323
- protected configureClientActions(binding: InstanceMultiBinding<string>): void {
324
- binding.add(CenterAction.KIND);
325
- binding.add(ExportSvgAction.KIND);
326
- binding.add(DeleteMarkersAction.KIND);
327
- binding.add(FitToScreenAction.KIND);
328
- binding.add(SourceModelChangedAction.KIND);
329
- binding.add(NavigateToTargetAction.KIND);
330
- binding.add(NavigateToExternalTargetAction.KIND);
331
- binding.add(RequestBoundsAction.KIND);
332
- binding.add(SelectAction.KIND);
333
- binding.add(SelectAllAction.KIND);
334
- binding.add(ServerMessageAction.KIND);
335
- binding.add(SetBoundsAction.KIND);
336
- binding.add(SetClipboardDataAction.KIND);
337
- binding.add(SetContextActions.KIND);
338
- binding.add(SetDirtyStateAction.KIND);
339
- binding.add(SetEditModeAction.KIND);
340
- binding.add(SetEditValidationResultAction.KIND);
341
- binding.add(SetMarkersAction.KIND);
342
- binding.add(SetModelAction.KIND);
343
- binding.add(SetNavigationTargetsAction.KIND);
344
- binding.add(SetPopupModelAction.KIND);
345
- binding.add(SetResolvedNavigationTargetAction.KIND);
346
- binding.add(SetTypeHintsAction.KIND);
347
- binding.add(SetViewportAction.KIND);
348
- binding.add(ServerStatusAction.KIND);
349
- binding.add(TriggerNodeCreationAction.KIND);
350
- binding.add(TriggerEdgeCreationAction.KIND);
351
- binding.add(UpdateModelAction.KIND);
352
- }
353
-
354
302
  protected bindContextActionsProviderRegistry(): BindingTarget<ContextActionsProviderRegistry> {
355
303
  return ContextActionsProviderRegistry;
356
304
  }
@@ -41,7 +41,6 @@ import { DiagramModules, InjectionContainer } from './service-identifiers';
41
41
  * * {@link ClientSessionFactory}
42
42
  * * {@link ClientSessionManager}
43
43
  * * {@link GlobalActionProvider}
44
- * * {@link GLSPClientProxy}
45
44
  *
46
45
  */
47
46
  export class ServerModule extends GLSPModule {
@@ -17,20 +17,34 @@ import { GModelRootSchema } from '@eclipse-glsp/graph';
17
17
  import {
18
18
  Action,
19
19
  DirtyStateChangeReason,
20
+ MarkersReason,
20
21
  MaybePromise,
21
22
  RequestBoundsAction,
23
+ RequestModelAction,
22
24
  SetDirtyStateAction,
25
+ SetMarkersAction,
23
26
  SetModelAction,
24
27
  UpdateModelAction
25
28
  } from '@eclipse-glsp/protocol';
29
+
26
30
  import { inject, injectable, optional } from 'inversify';
27
31
  import { CommandStack } from '../../command/command-stack';
28
32
  import { DiagramConfiguration, ServerLayoutKind } from '../../diagram/diagram-configuration';
29
33
  import { LayoutEngine } from '../layout/layout-engine';
34
+ import { ModelValidator } from '../validation/model-validator';
30
35
  import { GModelFactory } from './gmodel-factory';
31
36
  import { GModelSerializer } from './gmodel-serializer';
32
37
  import { ModelState } from './model-state';
33
38
 
39
+ /**
40
+ * Helper class that provides utility methods to handle model updates i.e.
41
+ * submit a new model to the client. In addition, to the core model update action this class
42
+ * also takes care of related behavior like dirty state handling, validation and client/server side layouting.
43
+ * Note that the submissions handler is only responsible for deriving the set of actions that comprise a model update
44
+ * but does not actually dispatch them. The returned actions should be either manually dispatched
45
+ * to the `ActionDispatcher`, or simply returned as the result of an
46
+ * `ActionHandler.execute` method.
47
+ */
34
48
  @injectable()
35
49
  export class ModelSubmissionHandler {
36
50
  @inject(DiagramConfiguration)
@@ -52,8 +66,38 @@ export class ModelSubmissionHandler {
52
66
  @inject(CommandStack)
53
67
  protected commandStack: CommandStack;
54
68
 
69
+ @inject(ModelValidator)
70
+ @optional()
71
+ protected validator?: ModelValidator;
72
+
73
+ protected requestModelAction?: RequestModelAction;
74
+
55
75
  /**
56
- * Returns a list of actions to update the client-side model, based on the specified <code>modelState</code>.
76
+ * Returns a list of actions to submit the initial revision of the client-side model, based on the injected
77
+ * {@link GModelState}. Typically this method is invoked by the {@link RequestModelActionHandler} when the diagram
78
+ * is (re)loaded.
79
+ * <p>
80
+ * These actions are not processed by this {@link ModelSubmissionHandler}, but should be either manually dispatched
81
+ * to the {@link ActionDispatcher}, or simply returned as the result of an
82
+ * {@link ActionHandler#execute(Action)} method.
83
+ * </p>
84
+ *
85
+ * @param requestAction The {@link RequestModelAction} that triggere the initial model update
86
+ * @return A list of actions to be processed in order to submit the intial model.
87
+ *
88
+ */
89
+ submitInitialModel(requestAction: RequestModelAction): MaybePromise<Action[]> {
90
+ /*
91
+ * In the default update action flow a `RequestModelAction` does not directly trigger a `SetModelAction` response
92
+ * (RequestModelAction (C) -> RequestBoundsAction (S) -> ComputedBoundsAction (C) -> SetModelACtion (S)
93
+ * Therefore we temporarily store the action later retrival
94
+ */
95
+ this.requestModelAction = requestAction;
96
+ return this.submitModel();
97
+ }
98
+
99
+ /**
100
+ * Returns a list of actions to update the client-side model, based on the injected {@link ModelState}
57
101
  *
58
102
  * These actions are not processed by this {@link ModelSubmissionHandler}, but should be either manually dispatched
59
103
  * to the `ActionDispatcher`, or simply returned as the result of an `ActionHandler.execute()` method.
@@ -63,13 +107,15 @@ export class ModelSubmissionHandler {
63
107
  */
64
108
  submitModel(reason?: DirtyStateChangeReason): MaybePromise<Action[]> {
65
109
  this.modelFactory.createModel();
66
- this.modelState.root.revision = (this.modelState.root.revision ?? 0) + 1;
110
+
111
+ const revision = this.requestModelAction ? 0 : this.modelState.root.revision! + 1;
112
+ this.modelState.root.revision = revision;
67
113
  const root = this.serializeGModel();
68
114
 
69
115
  if (this.diagramConfiguration.needsClientLayout) {
70
116
  return [RequestBoundsAction.create(root), SetDirtyStateAction.create(this.commandStack.isDirty, { reason })];
71
117
  }
72
- return [SetModelAction.create(root)];
118
+ return this.submitModelDirectly(reason);
73
119
  }
74
120
 
75
121
  /**
@@ -94,16 +140,27 @@ export class ModelSubmissionHandler {
94
140
  }
95
141
  const result: Action[] = [];
96
142
  result.push(
97
- root.revision === 0
98
- ? SetModelAction.create(root)
143
+ this.requestModelAction
144
+ ? this.createSetModeAction(root)
99
145
  : UpdateModelAction.create(root, { animate: this.diagramConfiguration.animatedUpdate })
100
146
  );
101
147
  if (!this.diagramConfiguration.needsClientLayout) {
102
148
  result.push(SetDirtyStateAction.create(this.commandStack.isDirty, { reason }));
103
149
  }
150
+ if (this.validator) {
151
+ const markers = await this.validator.validate([this.modelState.root], MarkersReason.LIVE);
152
+ result.push(SetMarkersAction.create(markers, { reason: MarkersReason.LIVE }));
153
+ }
104
154
  return result;
105
155
  }
106
156
 
157
+ protected createSetModeAction(newRoot: GModelRootSchema): SetModelAction {
158
+ const responseId = this.requestModelAction?.requestId ?? '';
159
+ const response = SetModelAction.create(newRoot, { responseId });
160
+ this.requestModelAction = undefined;
161
+ return response;
162
+ }
163
+
107
164
  protected serializeGModel(): GModelRootSchema {
108
165
  return this.serializer.createSchema(this.modelState.root);
109
166
  }
@@ -13,11 +13,13 @@
13
13
  *
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
- import { Action, RequestModelAction, ServerMessageAction, ServerStatusAction } from '@eclipse-glsp/protocol';
16
+ import { Action, RequestModelAction, StatusAction } from '@eclipse-glsp/protocol';
17
17
  import { inject, injectable } from 'inversify';
18
18
  import { ActionDispatcher } from '../../actions/action-dispatcher';
19
19
  import { ActionHandler } from '../../actions/action-handler';
20
+ import { ClientOptionsUtil } from '../../utils/client-options-util';
20
21
  import { Logger } from '../../utils/logger';
22
+ import { ProgressMonitor, ProgressService } from '../progress/progress-service';
21
23
  import { ModelState } from './model-state';
22
24
  import { ModelSubmissionHandler } from './model-submission-handler';
23
25
  import { SourceModelStorage } from './source-model-storage';
@@ -41,27 +43,45 @@ export class RequestModelActionHandler implements ActionHandler {
41
43
  @inject(ModelSubmissionHandler)
42
44
  protected submissionHandler: ModelSubmissionHandler;
43
45
 
46
+ @inject(ProgressService)
47
+ protected progressService: ProgressService;
48
+
44
49
  async execute(action: RequestModelAction): Promise<Action[]> {
45
50
  this.logger.debug('Execute RequestModelAction:', action);
46
51
  this.modelState.setAll(action.options ?? {});
47
52
 
48
- this.notifyClient('Model loading in progress');
49
- await this.sourceModelStorage.loadSourceModel(action);
50
- // Clear the previous notification.
51
- this.notifyClient();
52
- return this.submissionHandler.submitModel();
53
+ const isReconnecting = ClientOptionsUtil.isReconnecting(action.options);
54
+
55
+ const progress = this.reportModelLoading('Model loading in progress');
56
+
57
+ if (isReconnecting) {
58
+ await this.handleReconnect(action);
59
+ } else {
60
+ await this.sourceModelStorage.loadSourceModel(action);
61
+ }
62
+ this.reportModelLoadingFinished(progress);
63
+
64
+ return this.submissionHandler.submitInitialModel(action);
65
+ }
66
+
67
+ protected async handleReconnect(action: RequestModelAction): Promise<void> {
68
+ const oldModelRoot = this.modelState.root;
69
+ if (oldModelRoot) {
70
+ // decrease revision by one, as each submit will increase it by one;
71
+ // the next save would produce warning that source model was changed otherwise
72
+ this.modelState.root.revision = (this.modelState.root.revision ?? 0) - 1;
73
+ } else {
74
+ await this.sourceModelStorage.loadSourceModel(action);
75
+ }
76
+ }
77
+
78
+ protected reportModelLoading(message: string): ProgressMonitor {
79
+ this.actionDispatcher.dispatch(StatusAction.create(message, { severity: 'INFO' }));
80
+ return this.progressService.start(message);
53
81
  }
54
82
 
55
- /**
56
- * Send a message and status notification with the given message to the client.
57
- * An empty message is an indication for the client to clear previously received notifications.
58
- * @param message The message that should be sent to the client
59
- */
60
- protected notifyClient(message = ''): void {
61
- const severity = message.length > 0 ? 'INFO' : 'NONE';
62
- this.actionDispatcher.dispatchAll(
63
- ServerMessageAction.create(message, { severity }),
64
- ServerStatusAction.create(message, { severity })
65
- );
83
+ protected reportModelLoadingFinished(monitor: ProgressMonitor): void {
84
+ this.actionDispatcher.dispatch(StatusAction.create('', { severity: 'NONE' }));
85
+ monitor.end();
66
86
  }
67
87
  }
@@ -0,0 +1,74 @@
1
+ /********************************************************************************
2
+ * Copyright (c) 2023 EclipseSource and others.
3
+ *
4
+ * This program and the accompanying materials are made available under the
5
+ * terms of the Eclipse Public License v. 2.0 which is available at
6
+ * http://www.eclipse.org/legal/epl-2.0.
7
+ *
8
+ * This Source Code may also be made available under the following Secondary
9
+ * Licenses when the conditions for such availability set forth in the Eclipse
10
+ * Public License v. 2.0 are satisfied: GNU General Public License, version 2
11
+ * with the GNU Classpath Exception which is available at
12
+ * https://www.gnu.org/software/classpath/license.html.
13
+ *
14
+ * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
+ ********************************************************************************/
16
+ import { EndProgressAction, StartProgressAction, UpdateProgressAction } from '@eclipse-glsp/protocol';
17
+ import { inject, injectable } from 'inversify';
18
+ import * as uuid from 'uuid';
19
+ import { ActionDispatcher } from '../../actions/action-dispatcher';
20
+
21
+ export const ProgressService = Symbol('ProgressService');
22
+
23
+ /**
24
+ * Service for starting and monitoring progress reporting to the client.
25
+ */
26
+ export interface ProgressService {
27
+ /**
28
+ * Start a progress reporting.
29
+ * @param title The title shown in the UI for the progress reporting.
30
+ * @param options Additional optional options for the progress reporting.
31
+ * @returns a monitor to update and end the progress reporting later.
32
+ */
33
+ start(title: string, options?: ProgressOptions): ProgressMonitor;
34
+ }
35
+
36
+ /**
37
+ * Optional progress reporting options.
38
+ */
39
+ export interface ProgressOptions {
40
+ /** A message shown in the UI. */
41
+ message?: string;
42
+ /* The percentage (value range: 0 to 100) to show in the progress reporting. */
43
+ percentage?: number;
44
+ }
45
+
46
+ /**
47
+ * The monitor of a progress reporting, which can be used to update and end the reporting.
48
+ */
49
+ export interface ProgressMonitor {
50
+ /**
51
+ * Updates an ongoing progress reporting.
52
+ * @param options Updated message and/or percentage (value range: 0 to 100).
53
+ */
54
+ update(options: { message?: string; percentage?: number }): void;
55
+ /**
56
+ * Ends an ongoing progress reporting.
57
+ */
58
+ end(): void;
59
+ }
60
+
61
+ @injectable()
62
+ export class DefaultProgressService implements ProgressService {
63
+ @inject(ActionDispatcher)
64
+ protected actionDispatcher: ActionDispatcher;
65
+
66
+ start(title: string, options?: ProgressOptions): ProgressMonitor {
67
+ const progressId = uuid.v4();
68
+ this.actionDispatcher.dispatch(StartProgressAction.create({ progressId, title, ...options }));
69
+ return {
70
+ update: updateOptions => this.actionDispatcher.dispatch(UpdateProgressAction.create(progressId, updateOptions)),
71
+ end: () => this.actionDispatcher.dispatch(EndProgressAction.create(progressId))
72
+ };
73
+ }
74
+ }