@theia/plugin-ext 1.45.0 → 1.46.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (291) hide show
  1. package/lib/common/plugin-api-rpc.d.ts +9 -4
  2. package/lib/common/plugin-api-rpc.d.ts.map +1 -1
  3. package/lib/common/plugin-api-rpc.js +3 -1
  4. package/lib/common/plugin-api-rpc.js.map +1 -1
  5. package/lib/common/plugin-ext-api-contribution.d.ts +35 -5
  6. package/lib/common/plugin-ext-api-contribution.d.ts.map +1 -1
  7. package/lib/common/plugin-ext-api-contribution.js.map +1 -1
  8. package/lib/common/plugin-protocol.d.ts +5 -2
  9. package/lib/common/plugin-protocol.d.ts.map +1 -1
  10. package/lib/common/plugin-protocol.js +1 -0
  11. package/lib/common/plugin-protocol.js.map +1 -1
  12. package/lib/common/proxy-handler.d.ts +7 -0
  13. package/lib/common/proxy-handler.d.ts.map +1 -1
  14. package/lib/common/proxy-handler.js +5 -1
  15. package/lib/common/proxy-handler.js.map +1 -1
  16. package/lib/common/rpc-protocol.d.ts +10 -0
  17. package/lib/common/rpc-protocol.d.ts.map +1 -1
  18. package/lib/common/rpc-protocol.js +32 -3
  19. package/lib/common/rpc-protocol.js.map +1 -1
  20. package/lib/hosted/browser/hosted-plugin.d.ts +16 -74
  21. package/lib/hosted/browser/hosted-plugin.d.ts.map +1 -1
  22. package/lib/hosted/browser/hosted-plugin.js +41 -314
  23. package/lib/hosted/browser/hosted-plugin.js.map +1 -1
  24. package/lib/hosted/browser/worker/debug-stub.d.ts +2 -2
  25. package/lib/hosted/browser/worker/debug-stub.d.ts.map +1 -1
  26. package/lib/hosted/browser/worker/debug-stub.js +3 -3
  27. package/lib/hosted/browser/worker/debug-stub.js.map +1 -1
  28. package/lib/hosted/browser/worker/worker-env-ext.d.ts +1 -2
  29. package/lib/hosted/browser/worker/worker-env-ext.d.ts.map +1 -1
  30. package/lib/hosted/browser/worker/worker-env-ext.js +18 -4
  31. package/lib/hosted/browser/worker/worker-env-ext.js.map +1 -1
  32. package/lib/hosted/browser/worker/worker-main.js +20 -32
  33. package/lib/hosted/browser/worker/worker-main.js.map +1 -1
  34. package/lib/hosted/browser/worker/worker-plugin-module.d.ts +5 -0
  35. package/lib/hosted/browser/worker/worker-plugin-module.d.ts.map +1 -0
  36. package/lib/hosted/browser/worker/worker-plugin-module.js +71 -0
  37. package/lib/hosted/browser/worker/worker-plugin-module.js.map +1 -0
  38. package/lib/hosted/common/hosted-plugin.d.ts +97 -0
  39. package/lib/hosted/common/hosted-plugin.d.ts.map +1 -0
  40. package/lib/hosted/common/hosted-plugin.js +408 -0
  41. package/lib/hosted/common/hosted-plugin.js.map +1 -0
  42. package/lib/hosted/node/hosted-plugin-process.d.ts +1 -1
  43. package/lib/hosted/node/hosted-plugin-process.d.ts.map +1 -1
  44. package/lib/hosted/node/hosted-plugin-process.js +2 -2
  45. package/lib/hosted/node/hosted-plugin-process.js.map +1 -1
  46. package/lib/hosted/node/plugin-ext-hosted-backend-module.d.ts.map +1 -1
  47. package/lib/hosted/node/plugin-ext-hosted-backend-module.js +2 -0
  48. package/lib/hosted/node/plugin-ext-hosted-backend-module.js.map +1 -1
  49. package/lib/hosted/node/plugin-host-module.d.ts +5 -0
  50. package/lib/hosted/node/plugin-host-module.d.ts.map +1 -0
  51. package/lib/hosted/node/plugin-host-module.js +68 -0
  52. package/lib/hosted/node/plugin-host-module.js.map +1 -0
  53. package/lib/hosted/node/plugin-host-rpc.d.ts +93 -7
  54. package/lib/hosted/node/plugin-host-rpc.d.ts.map +1 -1
  55. package/lib/hosted/node/plugin-host-rpc.js +202 -53
  56. package/lib/hosted/node/plugin-host-rpc.js.map +1 -1
  57. package/lib/hosted/node/plugin-host.js +6 -5
  58. package/lib/hosted/node/plugin-host.js.map +1 -1
  59. package/lib/hosted/node/plugin-reader.d.ts.map +1 -1
  60. package/lib/hosted/node/plugin-reader.js +3 -0
  61. package/lib/hosted/node/plugin-reader.js.map +1 -1
  62. package/lib/hosted/node/plugin-service.d.ts +8 -0
  63. package/lib/hosted/node/plugin-service.d.ts.map +1 -1
  64. package/lib/hosted/node/plugin-service.js +14 -4
  65. package/lib/hosted/node/plugin-service.js.map +1 -1
  66. package/lib/hosted/node/scanners/file-plugin-uri-factory.js +1 -1
  67. package/lib/hosted/node/scanners/file-plugin-uri-factory.js.map +1 -1
  68. package/lib/hosted/node/scanners/scanner-theia.d.ts +17 -3
  69. package/lib/hosted/node/scanners/scanner-theia.d.ts.map +1 -1
  70. package/lib/hosted/node/scanners/scanner-theia.js +48 -19
  71. package/lib/hosted/node/scanners/scanner-theia.js.map +1 -1
  72. package/lib/main/browser/authentication-main.d.ts.map +1 -1
  73. package/lib/main/browser/authentication-main.js +3 -1
  74. package/lib/main/browser/authentication-main.js.map +1 -1
  75. package/lib/main/browser/env-main.d.ts +1 -10
  76. package/lib/main/browser/env-main.d.ts.map +1 -1
  77. package/lib/main/browser/env-main.js +2 -21
  78. package/lib/main/browser/env-main.js.map +1 -1
  79. package/lib/main/browser/menus/menus-contribution-handler.d.ts.map +1 -1
  80. package/lib/main/browser/menus/menus-contribution-handler.js +6 -3
  81. package/lib/main/browser/menus/menus-contribution-handler.js.map +1 -1
  82. package/lib/main/browser/menus/plugin-menu-command-adapter.js +1 -1
  83. package/lib/main/browser/menus/plugin-menu-command-adapter.js.map +1 -1
  84. package/lib/main/browser/message-registry-main.d.ts +6 -4
  85. package/lib/main/browser/message-registry-main.d.ts.map +1 -1
  86. package/lib/main/browser/message-registry-main.js +7 -19
  87. package/lib/main/browser/message-registry-main.js.map +1 -1
  88. package/lib/main/browser/notebooks/renderers/cell-output-webview.d.ts +1 -0
  89. package/lib/main/browser/notebooks/renderers/cell-output-webview.d.ts.map +1 -1
  90. package/lib/main/browser/notebooks/renderers/cell-output-webview.js +23 -22
  91. package/lib/main/browser/notebooks/renderers/cell-output-webview.js.map +1 -1
  92. package/lib/main/browser/notebooks/renderers/output-webview-internal.d.ts.map +1 -1
  93. package/lib/main/browser/notebooks/renderers/output-webview-internal.js +22 -14
  94. package/lib/main/browser/notebooks/renderers/output-webview-internal.js.map +1 -1
  95. package/lib/main/browser/notebooks/renderers/webview-communication.d.ts +2 -1
  96. package/lib/main/browser/notebooks/renderers/webview-communication.d.ts.map +1 -1
  97. package/lib/main/browser/notification-main.d.ts +2 -14
  98. package/lib/main/browser/notification-main.d.ts.map +1 -1
  99. package/lib/main/browser/notification-main.js +3 -52
  100. package/lib/main/browser/notification-main.js.map +1 -1
  101. package/lib/main/browser/terminal-main.d.ts +1 -1
  102. package/lib/main/browser/terminal-main.d.ts.map +1 -1
  103. package/lib/main/browser/terminal-main.js +2 -2
  104. package/lib/main/browser/terminal-main.js.map +1 -1
  105. package/lib/main/browser/view/plugin-view-registry.d.ts.map +1 -1
  106. package/lib/main/browser/view/plugin-view-registry.js +5 -2
  107. package/lib/main/browser/view/plugin-view-registry.js.map +1 -1
  108. package/lib/main/browser/webview/webview-context-keys.d.ts +5 -1
  109. package/lib/main/browser/webview/webview-context-keys.d.ts.map +1 -1
  110. package/lib/main/browser/webview/webview-context-keys.js +13 -4
  111. package/lib/main/browser/webview/webview-context-keys.js.map +1 -1
  112. package/lib/main/browser/webview/webview-widget-factory.d.ts.map +1 -1
  113. package/lib/main/browser/webview/webview-widget-factory.js +2 -1
  114. package/lib/main/browser/webview/webview-widget-factory.js.map +1 -1
  115. package/lib/main/browser/webview/webview.d.ts +1 -0
  116. package/lib/main/browser/webview/webview.d.ts.map +1 -1
  117. package/lib/main/browser/webview/webview.js +1 -0
  118. package/lib/main/browser/webview/webview.js.map +1 -1
  119. package/lib/main/browser/webviews-main.d.ts.map +1 -1
  120. package/lib/main/browser/webviews-main.js +7 -2
  121. package/lib/main/browser/webviews-main.js.map +1 -1
  122. package/lib/main/common/basic-message-registry-main.d.ts +14 -0
  123. package/lib/main/common/basic-message-registry-main.d.ts.map +1 -0
  124. package/lib/main/common/basic-message-registry-main.js +50 -0
  125. package/lib/main/common/basic-message-registry-main.js.map +1 -0
  126. package/lib/main/common/basic-notification-main.d.ts +19 -0
  127. package/lib/main/common/basic-notification-main.d.ts.map +1 -0
  128. package/lib/main/common/basic-notification-main.js +75 -0
  129. package/lib/main/common/basic-notification-main.js.map +1 -0
  130. package/lib/main/common/env-main.d.ts +11 -0
  131. package/lib/main/common/env-main.d.ts.map +1 -0
  132. package/lib/main/common/env-main.js +40 -0
  133. package/lib/main/common/env-main.js.map +1 -0
  134. package/lib/main/node/handlers/plugin-theia-directory-handler.d.ts +8 -3
  135. package/lib/main/node/handlers/plugin-theia-directory-handler.d.ts.map +1 -1
  136. package/lib/main/node/handlers/plugin-theia-directory-handler.js +38 -20
  137. package/lib/main/node/handlers/plugin-theia-directory-handler.js.map +1 -1
  138. package/lib/main/node/handlers/plugin-theia-file-handler.js +1 -1
  139. package/lib/main/node/handlers/plugin-theia-file-handler.js.map +1 -1
  140. package/lib/main/node/plugin-deployer-impl.d.ts.map +1 -1
  141. package/lib/main/node/plugin-deployer-impl.js +5 -1
  142. package/lib/main/node/plugin-deployer-impl.js.map +1 -1
  143. package/lib/main/node/plugins-key-value-storage.js +1 -1
  144. package/lib/main/node/plugins-key-value-storage.js.map +1 -1
  145. package/lib/plugin/clipboard-ext.d.ts +3 -2
  146. package/lib/plugin/clipboard-ext.d.ts.map +1 -1
  147. package/lib/plugin/clipboard-ext.js +28 -4
  148. package/lib/plugin/clipboard-ext.js.map +1 -1
  149. package/lib/plugin/debug/debug-ext.d.ts +3 -1
  150. package/lib/plugin/debug/debug-ext.d.ts.map +1 -1
  151. package/lib/plugin/debug/debug-ext.js +31 -4
  152. package/lib/plugin/debug/debug-ext.js.map +1 -1
  153. package/lib/plugin/documents.js +2 -2
  154. package/lib/plugin/documents.js.map +1 -1
  155. package/lib/plugin/editors-and-documents.d.ts +1 -2
  156. package/lib/plugin/editors-and-documents.d.ts.map +1 -1
  157. package/lib/plugin/editors-and-documents.js +21 -4
  158. package/lib/plugin/editors-and-documents.js.map +1 -1
  159. package/lib/plugin/env.d.ts +6 -2
  160. package/lib/plugin/env.d.ts.map +1 -1
  161. package/lib/plugin/env.js +37 -4
  162. package/lib/plugin/env.js.map +1 -1
  163. package/lib/plugin/localization-ext.d.ts +3 -2
  164. package/lib/plugin/localization-ext.d.ts.map +1 -1
  165. package/lib/plugin/localization-ext.js +30 -4
  166. package/lib/plugin/localization-ext.js.map +1 -1
  167. package/lib/plugin/message-registry.d.ts +2 -1
  168. package/lib/plugin/message-registry.d.ts.map +1 -1
  169. package/lib/plugin/message-registry.js +28 -4
  170. package/lib/plugin/message-registry.js.map +1 -1
  171. package/lib/plugin/node/debug/debug.spec.js +21 -1
  172. package/lib/plugin/node/debug/debug.spec.js.map +1 -1
  173. package/lib/plugin/node/env-node-ext.d.ts +1 -6
  174. package/lib/plugin/node/env-node-ext.d.ts.map +1 -1
  175. package/lib/plugin/node/env-node-ext.js +18 -10
  176. package/lib/plugin/node/env-node-ext.js.map +1 -1
  177. package/lib/plugin/node/plugin-container-module.d.ts +75 -0
  178. package/lib/plugin/node/plugin-container-module.d.ts.map +1 -0
  179. package/lib/plugin/node/plugin-container-module.js +115 -0
  180. package/lib/plugin/node/plugin-container-module.js.map +1 -0
  181. package/lib/plugin/notebook/notebook-kernels.d.ts.map +1 -1
  182. package/lib/plugin/notebook/notebook-kernels.js +0 -1
  183. package/lib/plugin/notebook/notebook-kernels.js.map +1 -1
  184. package/lib/plugin/plugin-context.d.ts.map +1 -1
  185. package/lib/plugin/plugin-context.js +9 -1
  186. package/lib/plugin/plugin-context.js.map +1 -1
  187. package/lib/plugin/plugin-manager.d.ts +26 -17
  188. package/lib/plugin/plugin-manager.d.ts.map +1 -1
  189. package/lib/plugin/plugin-manager.js +107 -37
  190. package/lib/plugin/plugin-manager.js.map +1 -1
  191. package/lib/plugin/plugin-storage.d.ts +11 -3
  192. package/lib/plugin/plugin-storage.d.ts.map +1 -1
  193. package/lib/plugin/plugin-storage.js +25 -5
  194. package/lib/plugin/plugin-storage.js.map +1 -1
  195. package/lib/plugin/preference-registry.d.ts +3 -2
  196. package/lib/plugin/preference-registry.d.ts.map +1 -1
  197. package/lib/plugin/preference-registry.js +35 -5
  198. package/lib/plugin/preference-registry.js.map +1 -1
  199. package/lib/plugin/preference-registry.spec.js +8 -1
  200. package/lib/plugin/preference-registry.spec.js.map +1 -1
  201. package/lib/plugin/quick-open.js +3 -3
  202. package/lib/plugin/quick-open.js.map +1 -1
  203. package/lib/plugin/secrets-ext.d.ts +16 -7
  204. package/lib/plugin/secrets-ext.d.ts.map +1 -1
  205. package/lib/plugin/secrets-ext.js +23 -3
  206. package/lib/plugin/secrets-ext.js.map +1 -1
  207. package/lib/plugin/terminal-ext.d.ts +1 -1
  208. package/lib/plugin/terminal-ext.d.ts.map +1 -1
  209. package/lib/plugin/terminal-ext.js +26 -6
  210. package/lib/plugin/terminal-ext.js.map +1 -1
  211. package/lib/plugin/types-impl.d.ts +22 -2
  212. package/lib/plugin/types-impl.d.ts.map +1 -1
  213. package/lib/plugin/types-impl.js +22 -6
  214. package/lib/plugin/types-impl.js.map +1 -1
  215. package/lib/plugin/webview-views.d.ts.map +1 -1
  216. package/lib/plugin/webview-views.js +2 -1
  217. package/lib/plugin/webview-views.js.map +1 -1
  218. package/lib/plugin/webviews.d.ts +7 -5
  219. package/lib/plugin/webviews.d.ts.map +1 -1
  220. package/lib/plugin/webviews.js +46 -12
  221. package/lib/plugin/webviews.js.map +1 -1
  222. package/lib/plugin/workspace.d.ts +4 -3
  223. package/lib/plugin/workspace.d.ts.map +1 -1
  224. package/lib/plugin/workspace.js +40 -6
  225. package/lib/plugin/workspace.js.map +1 -1
  226. package/package.json +29 -29
  227. package/src/common/plugin-api-rpc.ts +10 -6
  228. package/src/common/plugin-ext-api-contribution.ts +38 -5
  229. package/src/common/plugin-protocol.ts +7 -2
  230. package/src/common/proxy-handler.ts +14 -1
  231. package/src/common/rpc-protocol.ts +41 -3
  232. package/src/hosted/browser/hosted-plugin.ts +47 -337
  233. package/src/hosted/browser/worker/debug-stub.ts +4 -3
  234. package/src/hosted/browser/worker/worker-env-ext.ts +5 -4
  235. package/src/hosted/browser/worker/worker-main.ts +103 -115
  236. package/src/hosted/browser/worker/worker-plugin-module.ts +73 -0
  237. package/src/hosted/common/hosted-plugin.ts +456 -0
  238. package/src/hosted/node/hosted-plugin-process.ts +4 -4
  239. package/src/hosted/node/plugin-ext-hosted-backend-module.ts +3 -1
  240. package/src/hosted/node/plugin-host-module.ts +69 -0
  241. package/src/hosted/node/plugin-host-rpc.ts +232 -73
  242. package/src/hosted/node/plugin-host.ts +9 -7
  243. package/src/hosted/node/plugin-reader.ts +3 -0
  244. package/src/hosted/node/plugin-service.ts +21 -4
  245. package/src/hosted/node/scanners/file-plugin-uri-factory.ts +1 -1
  246. package/src/hosted/node/scanners/scanner-theia.ts +46 -12
  247. package/src/main/browser/authentication-main.ts +3 -1
  248. package/src/main/browser/env-main.ts +1 -28
  249. package/src/main/browser/menus/menus-contribution-handler.ts +8 -3
  250. package/src/main/browser/menus/plugin-menu-command-adapter.ts +1 -1
  251. package/src/main/browser/message-registry-main.ts +10 -23
  252. package/src/main/browser/notebooks/renderers/cell-output-webview.tsx +26 -24
  253. package/src/main/browser/notebooks/renderers/output-webview-internal.ts +22 -13
  254. package/src/main/browser/notebooks/renderers/webview-communication.ts +2 -1
  255. package/src/main/browser/notification-main.ts +4 -64
  256. package/src/main/browser/terminal-main.ts +2 -2
  257. package/src/main/browser/view/plugin-view-registry.ts +6 -3
  258. package/src/main/browser/webview/webview-context-keys.ts +17 -4
  259. package/src/main/browser/webview/webview-widget-factory.ts +2 -1
  260. package/src/main/browser/webview/webview.ts +2 -0
  261. package/src/main/browser/webviews-main.ts +7 -2
  262. package/src/main/common/basic-message-registry-main.ts +53 -0
  263. package/src/main/common/basic-notification-main.ts +86 -0
  264. package/src/main/common/env-main.ts +44 -0
  265. package/src/main/node/handlers/plugin-theia-directory-handler.ts +38 -16
  266. package/src/main/node/handlers/plugin-theia-file-handler.ts +1 -1
  267. package/src/main/node/plugin-deployer-impl.ts +5 -1
  268. package/src/main/node/plugins-key-value-storage.ts +1 -1
  269. package/src/plugin/clipboard-ext.ts +9 -3
  270. package/src/plugin/debug/debug-ext.ts +11 -2
  271. package/src/plugin/documents.ts +2 -2
  272. package/src/plugin/editors-and-documents.ts +5 -3
  273. package/src/plugin/env.ts +19 -3
  274. package/src/plugin/localization-ext.ts +8 -3
  275. package/src/plugin/message-registry.ts +7 -2
  276. package/src/plugin/node/debug/debug.spec.ts +5 -1
  277. package/src/plugin/node/env-node-ext.ts +5 -10
  278. package/src/plugin/node/plugin-container-module.ts +165 -0
  279. package/src/plugin/notebook/notebook-kernels.ts +0 -1
  280. package/src/plugin/plugin-context.ts +11 -2
  281. package/src/plugin/plugin-manager.ts +99 -45
  282. package/src/plugin/plugin-storage.ts +22 -4
  283. package/src/plugin/preference-registry.spec.ts +6 -1
  284. package/src/plugin/preference-registry.ts +11 -5
  285. package/src/plugin/quick-open.ts +3 -3
  286. package/src/plugin/secrets-ext.ts +25 -5
  287. package/src/plugin/terminal-ext.ts +5 -3
  288. package/src/plugin/types-impl.ts +30 -2
  289. package/src/plugin/webview-views.ts +2 -1
  290. package/src/plugin/webviews.ts +22 -13
  291. package/src/plugin/workspace.ts +14 -4
@@ -14,10 +14,15 @@
14
14
  // SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
15
15
  // *****************************************************************************
16
16
 
17
+ /* eslint-disable @typescript-eslint/no-explicit-any */
18
+
17
19
  import { dynamicRequire, removeFromCache } from '@theia/core/lib/node/dynamic-require';
18
- import { PluginManagerExtImpl } from '../../plugin/plugin-manager';
19
- import { LocalizationExt, MAIN_RPC_CONTEXT, Plugin, PluginAPIFactory } from '../../common/plugin-api-rpc';
20
- import { PluginMetadata } from '../../common/plugin-protocol';
20
+ import { ContainerModule, inject, injectable, postConstruct, unmanaged } from '@theia/core/shared/inversify';
21
+ import { AbstractPluginManagerExtImpl, PluginHost, PluginManagerExtImpl } from '../../plugin/plugin-manager';
22
+ import { MAIN_RPC_CONTEXT, Plugin, PluginAPIFactory, PluginManager,
23
+ LocalizationExt
24
+ } from '../../common/plugin-api-rpc';
25
+ import { PluginMetadata, PluginModel } from '../../common/plugin-protocol';
21
26
  import { createAPIFactory } from '../../plugin/plugin-context';
22
27
  import { EnvExtImpl } from '../../plugin/env';
23
28
  import { PreferenceRegistryExtImpl } from '../../plugin/preference-registry';
@@ -26,95 +31,139 @@ import { DebugExtImpl } from '../../plugin/debug/debug-ext';
26
31
  import { EditorsAndDocumentsExtImpl } from '../../plugin/editors-and-documents';
27
32
  import { WorkspaceExtImpl } from '../../plugin/workspace';
28
33
  import { MessageRegistryExt } from '../../plugin/message-registry';
29
- import { EnvNodeExtImpl } from '../../plugin/node/env-node-ext';
30
34
  import { ClipboardExt } from '../../plugin/clipboard-ext';
31
35
  import { loadManifest } from './plugin-manifest-loader';
32
36
  import { KeyValueStorageProxy } from '../../plugin/plugin-storage';
33
37
  import { WebviewsExtImpl } from '../../plugin/webviews';
34
38
  import { TerminalServiceExtImpl } from '../../plugin/terminal-ext';
35
39
  import { SecretsExtImpl } from '../../plugin/secrets-ext';
36
- import { BackendInitializationFn } from '../../common';
37
40
  import { connectProxyResolver } from './plugin-host-proxy';
38
41
  import { LocalizationExtImpl } from '../../plugin/localization-ext';
42
+ import { RPCProtocol, ProxyIdentifier } from '../../common/rpc-protocol';
43
+ import { PluginApiCache } from '../../plugin/node/plugin-container-module';
44
+
45
+ /**
46
+ * The full set of all possible `Ext` interfaces that a plugin manager can support.
47
+ */
48
+ export interface ExtInterfaces {
49
+ envExt: EnvExtImpl,
50
+ storageExt: KeyValueStorageProxy,
51
+ debugExt: DebugExtImpl,
52
+ editorsAndDocumentsExt: EditorsAndDocumentsExtImpl,
53
+ messageRegistryExt: MessageRegistryExt,
54
+ workspaceExt: WorkspaceExtImpl,
55
+ preferenceRegistryExt: PreferenceRegistryExtImpl,
56
+ clipboardExt: ClipboardExt,
57
+ webviewExt: WebviewsExtImpl,
58
+ terminalServiceExt: TerminalServiceExtImpl,
59
+ secretsExt: SecretsExtImpl,
60
+ localizationExt: LocalizationExtImpl
61
+ }
62
+
63
+ /**
64
+ * The RPC proxy identifier keys to set in the RPC object to register our `Ext` interface implementations.
65
+ */
66
+ export type RpcKeys<EXT extends Partial<ExtInterfaces>> = Partial<Record<keyof EXT, ProxyIdentifier<any>>> & {
67
+ $pluginManager: ProxyIdentifier<any>;
68
+ };
69
+
70
+ export const PluginContainerModuleLoader = Symbol('PluginContainerModuleLoader');
71
+ /**
72
+ * A function that loads a `PluginContainerModule` exported by a plugin's entry-point
73
+ * script, returning the per-`Container` cache of its exported API instances if the
74
+ * module has an API factory registered.
75
+ */
76
+ export type PluginContainerModuleLoader = (module: ContainerModule) => PluginApiCache<object> | undefined;
39
77
 
40
78
  /**
41
79
  * Handle the RPC calls.
80
+ *
81
+ * @template PM is the plugin manager (ext) type
82
+ * @template PAF is the plugin API factory type
83
+ * @template EXT is the type identifying the `Ext` interfaces supported by the plugin manager
42
84
  */
43
- export class PluginHostRPC {
85
+ @injectable()
86
+ export abstract class AbstractPluginHostRPC<PM extends AbstractPluginManagerExtImpl<any>, PAF, EXT extends Partial<ExtInterfaces>> {
87
+
88
+ @inject(RPCProtocol)
89
+ protected readonly rpc: any;
44
90
 
45
- private apiFactory: PluginAPIFactory;
91
+ @inject(PluginContainerModuleLoader)
92
+ protected readonly loadContainerModule: PluginContainerModuleLoader;
46
93
 
47
- private pluginManager: PluginManagerExtImpl;
94
+ @inject(AbstractPluginManagerExtImpl)
95
+ protected readonly pluginManager: PM;
48
96
 
49
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
50
- constructor(protected readonly rpc: any) {
97
+ protected readonly banner: string;
98
+
99
+ protected apiFactory: PAF;
100
+
101
+ constructor(
102
+ @unmanaged() name: string,
103
+ @unmanaged() private readonly backendInitPath: string | undefined,
104
+ @unmanaged() private readonly extRpc: RpcKeys<EXT>) {
105
+ this.banner = `${name}(${process.pid}):`;
51
106
  }
52
107
 
108
+ @postConstruct()
53
109
  initialize(): void {
54
- const envExt = new EnvNodeExtImpl(this.rpc);
55
- const storageProxy = new KeyValueStorageProxy(this.rpc);
56
- const debugExt = new DebugExtImpl(this.rpc);
57
- const editorsAndDocumentsExt = new EditorsAndDocumentsExtImpl(this.rpc);
58
- const messageRegistryExt = new MessageRegistryExt(this.rpc);
59
- const workspaceExt = new WorkspaceExtImpl(this.rpc, editorsAndDocumentsExt, messageRegistryExt);
60
- const preferenceRegistryExt = new PreferenceRegistryExtImpl(this.rpc, workspaceExt);
61
- const clipboardExt = new ClipboardExt(this.rpc);
62
- const webviewExt = new WebviewsExtImpl(this.rpc, workspaceExt);
63
- const terminalService = new TerminalServiceExtImpl(this.rpc);
64
- const secretsExt = new SecretsExtImpl(this.rpc);
65
- const localizationExt = new LocalizationExtImpl(this.rpc);
66
- this.pluginManager = this.createPluginManager(envExt, terminalService, storageProxy, preferenceRegistryExt, webviewExt, secretsExt, localizationExt, this.rpc);
67
- this.rpc.set(MAIN_RPC_CONTEXT.HOSTED_PLUGIN_MANAGER_EXT, this.pluginManager);
68
- this.rpc.set(MAIN_RPC_CONTEXT.EDITORS_AND_DOCUMENTS_EXT, editorsAndDocumentsExt);
69
- this.rpc.set(MAIN_RPC_CONTEXT.WORKSPACE_EXT, workspaceExt);
70
- this.rpc.set(MAIN_RPC_CONTEXT.PREFERENCE_REGISTRY_EXT, preferenceRegistryExt);
71
- this.rpc.set(MAIN_RPC_CONTEXT.STORAGE_EXT, storageProxy);
72
- this.rpc.set(MAIN_RPC_CONTEXT.WEBVIEWS_EXT, webviewExt);
73
- this.rpc.set(MAIN_RPC_CONTEXT.SECRETS_EXT, secretsExt);
74
-
75
- this.apiFactory = createAPIFactory(
76
- this.rpc,
77
- this.pluginManager,
78
- envExt,
79
- debugExt,
80
- preferenceRegistryExt,
81
- editorsAndDocumentsExt,
82
- workspaceExt,
83
- messageRegistryExt,
84
- clipboardExt,
85
- webviewExt,
86
- localizationExt
87
- );
88
- connectProxyResolver(workspaceExt, preferenceRegistryExt);
110
+ this.pluginManager.setPluginHost(this.createPluginHost());
111
+
112
+ const extInterfaces = this.createExtInterfaces();
113
+ this.registerExtInterfaces(extInterfaces);
114
+
115
+ this.apiFactory = this.createAPIFactory(extInterfaces);
116
+
117
+ this.loadContainerModule(new ContainerModule(bind => bind(PluginManager).toConstantValue(this.pluginManager)));
89
118
  }
90
119
 
91
120
  async terminate(): Promise<void> {
92
121
  await this.pluginManager.terminate();
93
122
  }
94
123
 
124
+ protected abstract createAPIFactory(extInterfaces: EXT): PAF;
125
+
126
+ protected abstract createExtInterfaces(): EXT;
127
+
128
+ protected registerExtInterfaces(extInterfaces: EXT): void {
129
+ for (const _key in this.extRpc) {
130
+ if (Object.hasOwnProperty.call(this.extRpc, _key)) {
131
+ const key = _key as keyof ExtInterfaces;
132
+ // In case of present undefineds
133
+ if (extInterfaces[key]) {
134
+ this.rpc.set(this.extRpc[key], extInterfaces[key]);
135
+ }
136
+ }
137
+ }
138
+ this.rpc.set(this.extRpc.$pluginManager, this.pluginManager);
139
+ }
140
+
95
141
  initContext(contextPath: string, plugin: Plugin): void {
96
142
  const { name, version } = plugin.rawModel;
97
- console.debug('PLUGIN_HOST(' + process.pid + '): initializing(' + name + '@' + version + ' with ' + contextPath + ')');
143
+ console.debug(this.banner, 'initializing(' + name + '@' + version + ' with ' + contextPath + ')');
98
144
  try {
99
- const backendInit = dynamicRequire<{ doInitialization: BackendInitializationFn }>(contextPath);
145
+ type BackendInitFn = (pluginApiFactory: PAF, plugin: Plugin) => void;
146
+ const backendInit = dynamicRequire<{ doInitialization: BackendInitFn }>(contextPath);
100
147
  backendInit.doInitialization(this.apiFactory, plugin);
101
148
  } catch (e) {
102
149
  console.error(e);
103
150
  }
104
151
  }
105
152
 
106
- createPluginManager(
107
- envExt: EnvExtImpl, terminalService: TerminalServiceExtImpl, storageProxy: KeyValueStorageProxy,
108
- preferencesManager: PreferenceRegistryExtImpl, webview: WebviewsExtImpl, secretsExt: SecretsExtImpl, localization: LocalizationExt,
109
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
110
- rpc: any
111
- ): PluginManagerExtImpl {
153
+ protected getBackendPluginPath(pluginModel: PluginModel): string | undefined {
154
+ return pluginModel.entryPoint.backend;
155
+ }
156
+
157
+ /**
158
+ * Create the {@link PluginHost} that is required by my plugin manager ext interface to delegate
159
+ * critical behaviour such as loading and initializing plugins to me.
160
+ */
161
+ createPluginHost(): PluginHost {
112
162
  const { extensionTestsPath } = process.env;
113
163
  const self = this;
114
- const pluginManager = new PluginManagerExtImpl({
115
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
164
+ return {
116
165
  loadPlugin(plugin: Plugin): any {
117
- console.debug('PLUGIN_HOST(' + process.pid + '): PluginManagerExtImpl/loadPlugin(' + plugin.pluginPath + ')');
166
+ console.debug(self.banner, 'PluginManagerExtImpl/loadPlugin(' + plugin.pluginPath + ')');
118
167
  // cleaning the cache for all files of that plug-in.
119
168
  // this prevents a memory leak on plugin host restart. See for reference:
120
169
  // https://github.com/eclipse-theia/theia/pull/4931
@@ -125,7 +174,7 @@ export class PluginHostRPC {
125
174
  }
126
175
  },
127
176
  async init(raw: PluginMetadata[]): Promise<[Plugin[], Plugin[]]> {
128
- console.log('PLUGIN_HOST(' + process.pid + '): PluginManagerExtImpl/init()');
177
+ console.log(self.banner, 'PluginManagerExtImpl/init()');
129
178
  const result: Plugin[] = [];
130
179
  const foreign: Plugin[] = [];
131
180
  for (const plg of raw) {
@@ -146,14 +195,16 @@ export class PluginHostRPC {
146
195
  isUnderDevelopment: !!plg.isUnderDevelopment
147
196
  });
148
197
  } else {
198
+ // Headless and backend plugins are, for now, very similar
149
199
  let backendInitPath = pluginLifecycle.backendInitPath;
150
200
  // if no init path, try to init as regular Theia plugin
151
- if (!backendInitPath) {
152
- backendInitPath = __dirname + '/scanners/backend-init-theia.js';
201
+ if (!backendInitPath && self.backendInitPath) {
202
+ backendInitPath = __dirname + self.backendInitPath;
153
203
  }
154
204
 
205
+ const pluginPath = self.getBackendPluginPath(pluginModel);
155
206
  const plugin: Plugin = {
156
- pluginPath: pluginModel.entryPoint.backend!,
207
+ pluginPath,
157
208
  pluginFolder: pluginModel.packagePath,
158
209
  pluginUri: pluginModel.packageUri,
159
210
  model: pluginModel,
@@ -162,30 +213,30 @@ export class PluginHostRPC {
162
213
  isUnderDevelopment: !!plg.isUnderDevelopment
163
214
  };
164
215
 
165
- self.initContext(backendInitPath, plugin);
166
-
216
+ if (backendInitPath) {
217
+ self.initContext(backendInitPath, plugin);
218
+ } else {
219
+ const { name, version } = plugin.rawModel;
220
+ console.debug(self.banner, 'initializing(' + name + '@' + version + ' without any default API)');
221
+ }
167
222
  result.push(plugin);
168
223
  }
169
224
  } catch (e) {
170
- console.error(`Failed to initialize ${plg.model.id} plugin.`, e);
225
+ console.error(self.banner, `Failed to initialize ${plg.model.id} plugin.`, e);
171
226
  }
172
227
  }
173
228
  return [result, foreign];
174
229
  },
175
230
  initExtApi(extApi: ExtPluginApi[]): void {
176
231
  for (const api of extApi) {
177
- if (api.backendInitPath) {
178
- try {
179
- const extApiInit = dynamicRequire<{ provideApi: ExtPluginApiBackendInitializationFn }>(api.backendInitPath);
180
- extApiInit.provideApi(rpc, pluginManager);
181
- } catch (e) {
182
- console.error(e);
183
- }
232
+ try {
233
+ self.initExtApi(api);
234
+ } catch (e) {
235
+ console.error(e);
184
236
  }
185
237
  }
186
238
  },
187
239
  loadTests: extensionTestsPath ? async () => {
188
- /* eslint-disable @typescript-eslint/no-explicit-any */
189
240
  // Require the test runner via node require from the provided path
190
241
  let testRunner: any;
191
242
  let requireError: Error | undefined;
@@ -212,7 +263,115 @@ export class PluginHostRPC {
212
263
  `Path ${extensionTestsPath} does not point to a valid extension test runner.`
213
264
  );
214
265
  } : undefined
215
- }, envExt, terminalService, storageProxy, secretsExt, preferencesManager, webview, localization, rpc);
216
- return pluginManager;
266
+ };
267
+ }
268
+
269
+ /**
270
+ * Initialize the end of the given provided extension API applicable to the current plugin host.
271
+ * Errors should be propagated to the caller.
272
+ *
273
+ * @param extApi the extension API to initialize, if appropriate
274
+ * @throws if any error occurs in initializing the extension API
275
+ */
276
+ protected abstract initExtApi(extApi: ExtPluginApi): void;
277
+ }
278
+
279
+ /**
280
+ * The RPC handler for frontend-connection-scoped plugins (Theia and VSCode plugins).
281
+ */
282
+ @injectable()
283
+ export class PluginHostRPC extends AbstractPluginHostRPC<PluginManagerExtImpl, PluginAPIFactory, ExtInterfaces> {
284
+ @inject(EnvExtImpl)
285
+ protected readonly envExt: EnvExtImpl;
286
+
287
+ @inject(LocalizationExt)
288
+ protected readonly localizationExt: LocalizationExtImpl;
289
+
290
+ @inject(KeyValueStorageProxy)
291
+ protected readonly keyValueStorageProxy: KeyValueStorageProxy;
292
+
293
+ @inject(DebugExtImpl)
294
+ protected readonly debugExt: DebugExtImpl;
295
+
296
+ @inject(EditorsAndDocumentsExtImpl)
297
+ protected readonly editorsAndDocumentsExt: EditorsAndDocumentsExtImpl;
298
+
299
+ @inject(MessageRegistryExt)
300
+ protected readonly messageRegistryExt: MessageRegistryExt;
301
+
302
+ @inject(WorkspaceExtImpl)
303
+ protected readonly workspaceExt: WorkspaceExtImpl;
304
+
305
+ @inject(PreferenceRegistryExtImpl)
306
+ protected readonly preferenceRegistryExt: PreferenceRegistryExtImpl;
307
+
308
+ @inject(ClipboardExt)
309
+ protected readonly clipboardExt: ClipboardExt;
310
+
311
+ @inject(WebviewsExtImpl)
312
+ protected readonly webviewExt: WebviewsExtImpl;
313
+
314
+ @inject(TerminalServiceExtImpl)
315
+ protected readonly terminalServiceExt: TerminalServiceExtImpl;
316
+
317
+ @inject(SecretsExtImpl)
318
+ protected readonly secretsExt: SecretsExtImpl;
319
+
320
+ constructor() {
321
+ super('PLUGIN_HOST', '/scanners/backend-init-theia.js',
322
+ {
323
+ $pluginManager: MAIN_RPC_CONTEXT.HOSTED_PLUGIN_MANAGER_EXT,
324
+ editorsAndDocumentsExt: MAIN_RPC_CONTEXT.EDITORS_AND_DOCUMENTS_EXT,
325
+ workspaceExt: MAIN_RPC_CONTEXT.WORKSPACE_EXT,
326
+ preferenceRegistryExt: MAIN_RPC_CONTEXT.PREFERENCE_REGISTRY_EXT,
327
+ storageExt: MAIN_RPC_CONTEXT.STORAGE_EXT,
328
+ webviewExt: MAIN_RPC_CONTEXT.WEBVIEWS_EXT,
329
+ secretsExt: MAIN_RPC_CONTEXT.SECRETS_EXT
330
+ }
331
+ );
332
+ }
333
+
334
+ protected createExtInterfaces(): ExtInterfaces {
335
+ connectProxyResolver(this.workspaceExt, this.preferenceRegistryExt);
336
+ return {
337
+ envExt: this.envExt,
338
+ storageExt: this.keyValueStorageProxy,
339
+ debugExt: this.debugExt,
340
+ editorsAndDocumentsExt: this.editorsAndDocumentsExt,
341
+ messageRegistryExt: this.messageRegistryExt,
342
+ workspaceExt: this.workspaceExt,
343
+ preferenceRegistryExt: this.preferenceRegistryExt,
344
+ clipboardExt: this.clipboardExt,
345
+ webviewExt: this.webviewExt,
346
+ terminalServiceExt: this.terminalServiceExt,
347
+ secretsExt: this.secretsExt,
348
+ localizationExt: this.localizationExt
349
+ };
350
+ }
351
+
352
+ protected createAPIFactory(extInterfaces: ExtInterfaces): PluginAPIFactory {
353
+ const {
354
+ envExt, debugExt, preferenceRegistryExt, editorsAndDocumentsExt, workspaceExt,
355
+ messageRegistryExt, clipboardExt, webviewExt, localizationExt
356
+ } = extInterfaces;
357
+ return createAPIFactory(this.rpc, this.pluginManager, envExt, debugExt, preferenceRegistryExt,
358
+ editorsAndDocumentsExt, workspaceExt, messageRegistryExt, clipboardExt, webviewExt,
359
+ localizationExt);
360
+ }
361
+
362
+ protected initExtApi(extApi: ExtPluginApi): void {
363
+ interface PluginExports {
364
+ containerModule?: ContainerModule;
365
+ provideApi?: ExtPluginApiBackendInitializationFn;
366
+ }
367
+ if (extApi.backendInitPath) {
368
+ const { containerModule, provideApi } = dynamicRequire<PluginExports>(extApi.backendInitPath);
369
+ if (containerModule) {
370
+ this.loadContainerModule(containerModule);
371
+ }
372
+ if (provideApi) {
373
+ provideApi(this.rpc, this.pluginManager);
374
+ }
375
+ }
217
376
  }
218
377
  }
@@ -14,10 +14,11 @@
14
14
  // SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
15
15
  // *****************************************************************************
16
16
  import '@theia/core/shared/reflect-metadata';
17
- import { ConnectionClosedError, RPCProtocolImpl } from '../../common/rpc-protocol';
17
+ import { Container } from '@theia/core/shared/inversify';
18
+ import { ConnectionClosedError, RPCProtocol } from '../../common/rpc-protocol';
18
19
  import { ProcessTerminatedMessage, ProcessTerminateMessage } from './hosted-plugin-protocol';
19
20
  import { PluginHostRPC } from './plugin-host-rpc';
20
- import { IPCChannel } from '@theia/core/lib/node';
21
+ import pluginHostModule from './plugin-host-module';
21
22
 
22
23
  console.log('PLUGIN_HOST(' + process.pid + ') starting instance');
23
24
 
@@ -74,8 +75,12 @@ process.on('rejectionHandled', (promise: Promise<any>) => {
74
75
  });
75
76
 
76
77
  let terminating = false;
77
- const channel = new IPCChannel();
78
- const rpc = new RPCProtocolImpl(channel);
78
+
79
+ const container = new Container();
80
+ container.load(pluginHostModule);
81
+
82
+ const rpc: RPCProtocol = container.get(RPCProtocol);
83
+ const pluginHostRPC = container.get(PluginHostRPC);
79
84
 
80
85
  process.on('message', async (message: string) => {
81
86
  if (terminating) {
@@ -103,6 +108,3 @@ process.on('message', async (message: string) => {
103
108
  console.error(e);
104
109
  }
105
110
  });
106
-
107
- const pluginHostRPC = new PluginHostRPC(rpc);
108
- pluginHostRPC.initialize();
@@ -108,6 +108,9 @@ export class HostedPluginReader implements BackendApplicationContribution {
108
108
  if (pluginMetadata.model.entryPoint.backend) {
109
109
  pluginMetadata.model.entryPoint.backend = path.resolve(plugin.packagePath, pluginMetadata.model.entryPoint.backend);
110
110
  }
111
+ if (pluginMetadata.model.entryPoint.headless) {
112
+ pluginMetadata.model.entryPoint.headless = path.resolve(plugin.packagePath, pluginMetadata.model.entryPoint.headless);
113
+ }
111
114
  if (pluginMetadata) {
112
115
  // Add post processor
113
116
  if (this.metadataProcessors) {
@@ -13,7 +13,7 @@
13
13
  //
14
14
  // SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
15
15
  // *****************************************************************************
16
- import { injectable, inject, named, postConstruct } from '@theia/core/shared/inversify';
16
+ import { injectable, inject, named, optional, postConstruct } from '@theia/core/shared/inversify';
17
17
  import { HostedPluginServer, HostedPluginClient, PluginDeployer, GetDeployedPluginsParams, DeployedPlugin, PluginIdentifiers } from '../../common/plugin-protocol';
18
18
  import { HostedPluginSupport } from './hosted-plugin';
19
19
  import { ILogger, Disposable, ContributionProvider, DisposableCollection } from '@theia/core';
@@ -23,6 +23,14 @@ import { PluginDeployerImpl } from '../../main/node/plugin-deployer-impl';
23
23
  import { HostedPluginLocalizationService } from './hosted-plugin-localization-service';
24
24
  import { PluginUninstallationManager } from '../../main/node/plugin-uninstallation-manager';
25
25
 
26
+ export const BackendPluginHostableFilter = Symbol('BackendPluginHostableFilter');
27
+ /**
28
+ * A filter matching backend plugins that are hostable in my plugin host process.
29
+ * Only if at least one backend plugin is deployed that matches my filter will I
30
+ * start the host process.
31
+ */
32
+ export type BackendPluginHostableFilter = (plugin: DeployedPlugin) => boolean;
33
+
26
34
  @injectable()
27
35
  export class HostedPluginServerImpl implements HostedPluginServer {
28
36
  @inject(ILogger)
@@ -43,6 +51,10 @@ export class HostedPluginServerImpl implements HostedPluginServer {
43
51
 
44
52
  @inject(PluginUninstallationManager) protected readonly uninstallationManager: PluginUninstallationManager;
45
53
 
54
+ @inject(BackendPluginHostableFilter)
55
+ @optional()
56
+ protected backendPluginHostableFilter: BackendPluginHostableFilter;
57
+
46
58
  protected client: HostedPluginClient | undefined;
47
59
  protected toDispose = new DisposableCollection();
48
60
 
@@ -63,6 +75,10 @@ export class HostedPluginServerImpl implements HostedPluginServer {
63
75
 
64
76
  @postConstruct()
65
77
  protected init(): void {
78
+ if (!this.backendPluginHostableFilter) {
79
+ this.backendPluginHostableFilter = () => true;
80
+ }
81
+
66
82
  this.toDispose.pushAll([
67
83
  this.pluginDeployer.onDidDeploy(() => this.client?.onDidDeploy()),
68
84
  this.uninstallationManager.onDidChangeUninstalledPlugins(currentUninstalled => {
@@ -90,8 +106,9 @@ export class HostedPluginServerImpl implements HostedPluginServer {
90
106
  }
91
107
 
92
108
  async getDeployedPluginIds(): Promise<PluginIdentifiers.VersionedId[]> {
93
- const backendMetadata = await this.deployerHandler.getDeployedBackendPluginIds();
94
- if (backendMetadata.length > 0) {
109
+ const backendPlugins = (await this.deployerHandler.getDeployedBackendPlugins())
110
+ .filter(this.backendPluginHostableFilter);
111
+ if (backendPlugins.length > 0) {
95
112
  this.hostedPlugin.runPluginServer();
96
113
  }
97
114
  const plugins = new Set<PluginIdentifiers.VersionedId>();
@@ -103,7 +120,7 @@ export class HostedPluginServerImpl implements HostedPluginServer {
103
120
  }
104
121
  };
105
122
  addIds(await this.deployerHandler.getDeployedFrontendPluginIds());
106
- addIds(backendMetadata);
123
+ addIds(await this.deployerHandler.getDeployedBackendPluginIds());
107
124
  addIds(await this.hostedPlugin.getExtraDeployedPluginIds());
108
125
  return Array.from(plugins);
109
126
  }
@@ -17,7 +17,7 @@
17
17
  import { injectable } from '@theia/core/shared/inversify';
18
18
  import * as path from 'path';
19
19
  import URI from '@theia/core/lib/common/uri';
20
- import { FileUri } from '@theia/core/lib/node/file-uri';
20
+ import { FileUri } from '@theia/core/lib/common/file-uri';
21
21
  import { PluginPackage } from '../../../common';
22
22
  import { PluginUriFactory } from './plugin-uri-factory';
23
23
  /**
@@ -62,7 +62,9 @@ import {
62
62
  Translation,
63
63
  PluginIdentifiers,
64
64
  TerminalProfile,
65
- PluginIconContribution
65
+ PluginIconContribution,
66
+ PluginEntryPoint,
67
+ PluginPackageContribution
66
68
  } from '../../../common/plugin-protocol';
67
69
  import { promises as fs } from 'fs';
68
70
  import * as path from 'path';
@@ -87,17 +89,19 @@ function getFileExtension(filePath: string): string {
87
89
  return index === -1 ? '' : filePath.substring(index + 1);
88
90
  }
89
91
 
90
- @injectable()
91
- export class TheiaPluginScanner implements PluginScanner {
92
+ type PluginPackageWithContributes = PluginPackage & { contributes: PluginPackageContribution };
92
93
 
93
- private readonly _apiType: PluginEngine = 'theiaPlugin';
94
+ @injectable()
95
+ export abstract class AbstractPluginScanner implements PluginScanner {
94
96
 
95
97
  @inject(GrammarsReader)
96
- private readonly grammarsReader: GrammarsReader;
98
+ protected readonly grammarsReader: GrammarsReader;
97
99
 
98
100
  @inject(PluginUriFactory)
99
101
  protected readonly pluginUriFactory: PluginUriFactory;
100
102
 
103
+ constructor(private readonly _apiType: PluginEngine, private readonly _backendInitPath?: string) { }
104
+
101
105
  get apiType(): PluginEngine {
102
106
  return this._apiType;
103
107
  }
@@ -119,22 +123,25 @@ export class TheiaPluginScanner implements PluginScanner {
119
123
  type: this._apiType,
120
124
  version: plugin.engines[this._apiType]
121
125
  },
122
- entryPoint: {
123
- frontend: plugin.theiaPlugin!.frontend,
124
- backend: plugin.theiaPlugin!.backend
125
- }
126
+ entryPoint: this.getEntryPoint(plugin)
126
127
  };
127
128
  return result;
128
129
  }
129
130
 
131
+ protected abstract getEntryPoint(plugin: PluginPackage): PluginEntryPoint;
132
+
130
133
  getLifecycle(plugin: PluginPackage): PluginLifecycle {
131
- return {
134
+ const result: PluginLifecycle = {
132
135
  startMethod: 'start',
133
136
  stopMethod: 'stop',
134
137
  frontendModuleName: buildFrontendModuleName(plugin),
135
-
136
- backendInitPath: path.join(__dirname, 'backend-init-theia')
137
138
  };
139
+
140
+ if (this._backendInitPath) {
141
+ result.backendInitPath = path.join(__dirname, this._backendInitPath);
142
+ }
143
+
144
+ return result;
138
145
  }
139
146
 
140
147
  getDependencies(rawPlugin: PluginPackage): Map<string, string> | undefined {
@@ -155,6 +162,33 @@ export class TheiaPluginScanner implements PluginScanner {
155
162
  return contributions;
156
163
  }
157
164
 
165
+ return this.readContributions(rawPlugin as PluginPackageWithContributes, contributions);
166
+ }
167
+
168
+ protected async readContributions(rawPlugin: PluginPackageWithContributes, contributions: PluginContribution): Promise<PluginContribution> {
169
+ return contributions;
170
+ }
171
+
172
+ }
173
+
174
+ @injectable()
175
+ export class TheiaPluginScanner extends AbstractPluginScanner {
176
+ constructor() {
177
+ super('theiaPlugin', 'backend-init-theia');
178
+ }
179
+
180
+ protected getEntryPoint(plugin: PluginPackage): PluginEntryPoint {
181
+ const result: PluginEntryPoint = {
182
+ frontend: plugin.theiaPlugin!.frontend,
183
+ backend: plugin.theiaPlugin!.backend
184
+ };
185
+ if (plugin.theiaPlugin?.headless) {
186
+ result.headless = plugin.theiaPlugin.headless;
187
+ }
188
+ return result;
189
+ }
190
+
191
+ protected override async readContributions(rawPlugin: PluginPackageWithContributes, contributions: PluginContribution): Promise<PluginContribution> {
158
192
  try {
159
193
  if (rawPlugin.contributes.configuration) {
160
194
  const configurations = Array.isArray(rawPlugin.contributes.configuration) ? rawPlugin.contributes.configuration : [rawPlugin.contributes.configuration];
@@ -361,7 +361,9 @@ export class AuthenticationProviderImpl implements AuthenticationProvider {
361
361
 
362
362
  removeSession(sessionId: string): Thenable<void> {
363
363
  return this.proxy.$removeSession(this.id, sessionId)
364
- .then(() => { this.messageService.info('Successfully signed out.'); });
364
+ .then(() => {
365
+ this.messageService.info(nls.localizeByDefault('Successfully signed out.'));
366
+ });
365
367
  }
366
368
  }
367
369