@theia/plugin-ext 1.34.0-next.7 → 1.34.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 (175) hide show
  1. package/lib/common/plugin-api-rpc.d.ts +30 -10
  2. package/lib/common/plugin-api-rpc.d.ts.map +1 -1
  3. package/lib/common/plugin-api-rpc.js +23 -11
  4. package/lib/common/plugin-api-rpc.js.map +1 -1
  5. package/lib/common/plugin-protocol.d.ts +15 -0
  6. package/lib/common/plugin-protocol.d.ts.map +1 -1
  7. package/lib/common/plugin-protocol.js.map +1 -1
  8. package/lib/common/rpc-protocol.d.ts.map +1 -1
  9. package/lib/common/rpc-protocol.js +3 -4
  10. package/lib/common/rpc-protocol.js.map +1 -1
  11. package/lib/common/types.d.ts +1 -1
  12. package/lib/common/types.d.ts.map +1 -1
  13. package/lib/common/types.js +2 -3
  14. package/lib/common/types.js.map +1 -1
  15. package/lib/hosted/browser/hosted-plugin.d.ts +1 -0
  16. package/lib/hosted/browser/hosted-plugin.d.ts.map +1 -1
  17. package/lib/hosted/browser/hosted-plugin.js +3 -0
  18. package/lib/hosted/browser/hosted-plugin.js.map +1 -1
  19. package/lib/hosted/node/hosted-plugin-localization-service.d.ts.map +1 -1
  20. package/lib/hosted/node/hosted-plugin-localization-service.js +2 -2
  21. package/lib/hosted/node/hosted-plugin-localization-service.js.map +1 -1
  22. package/lib/hosted/node/plugin-host.d.ts +1 -1
  23. package/lib/hosted/node/plugin-host.d.ts.map +1 -1
  24. package/lib/hosted/node/plugin-host.js +1 -2
  25. package/lib/hosted/node/plugin-host.js.map +1 -1
  26. package/lib/hosted/node/scanners/scanner-theia.d.ts +2 -1
  27. package/lib/hosted/node/scanners/scanner-theia.d.ts.map +1 -1
  28. package/lib/hosted/node/scanners/scanner-theia.js +13 -0
  29. package/lib/hosted/node/scanners/scanner-theia.js.map +1 -1
  30. package/lib/main/browser/authentication-main.js +1 -1
  31. package/lib/main/browser/authentication-main.js.map +1 -1
  32. package/lib/main/browser/commands.js +1 -1
  33. package/lib/main/browser/commands.js.map +1 -1
  34. package/lib/main/browser/debug/debug-main.d.ts.map +1 -1
  35. package/lib/main/browser/debug/debug-main.js +1 -0
  36. package/lib/main/browser/debug/debug-main.js.map +1 -1
  37. package/lib/main/browser/dialogs-main.d.ts.map +1 -1
  38. package/lib/main/browser/dialogs-main.js +2 -1
  39. package/lib/main/browser/dialogs-main.js.map +1 -1
  40. package/lib/main/browser/menus/plugin-menu-command-adapter.d.ts +2 -2
  41. package/lib/main/browser/menus/plugin-menu-command-adapter.d.ts.map +1 -1
  42. package/lib/main/browser/menus/plugin-menu-command-adapter.js +6 -2
  43. package/lib/main/browser/menus/plugin-menu-command-adapter.js.map +1 -1
  44. package/lib/main/browser/menus/vscode-theia-menu-mappings.d.ts +2 -2
  45. package/lib/main/browser/menus/vscode-theia-menu-mappings.d.ts.map +1 -1
  46. package/lib/main/browser/menus/vscode-theia-menu-mappings.js +6 -0
  47. package/lib/main/browser/menus/vscode-theia-menu-mappings.js.map +1 -1
  48. package/lib/main/browser/plugin-contribution-handler.d.ts +6 -0
  49. package/lib/main/browser/plugin-contribution-handler.d.ts.map +1 -1
  50. package/lib/main/browser/plugin-contribution-handler.js +35 -0
  51. package/lib/main/browser/plugin-contribution-handler.js.map +1 -1
  52. package/lib/main/browser/plugin-ext-frontend-module.d.ts.map +1 -1
  53. package/lib/main/browser/plugin-ext-frontend-module.js +8 -3
  54. package/lib/main/browser/plugin-ext-frontend-module.js.map +1 -1
  55. package/lib/main/browser/plugin-terminal-registry.d.ts +5 -0
  56. package/lib/main/browser/plugin-terminal-registry.d.ts.map +1 -0
  57. package/lib/main/browser/plugin-terminal-registry.js +35 -0
  58. package/lib/main/browser/plugin-terminal-registry.js.map +1 -0
  59. package/lib/main/browser/scm-main.d.ts +1 -0
  60. package/lib/main/browser/scm-main.d.ts.map +1 -1
  61. package/lib/main/browser/scm-main.js +7 -0
  62. package/lib/main/browser/scm-main.js.map +1 -1
  63. package/lib/main/browser/terminal-main.d.ts +10 -4
  64. package/lib/main/browser/terminal-main.d.ts.map +1 -1
  65. package/lib/main/browser/terminal-main.js +51 -25
  66. package/lib/main/browser/terminal-main.js.map +1 -1
  67. package/lib/main/browser/view/dnd-file-content-store.d.ts +8 -0
  68. package/lib/main/browser/view/dnd-file-content-store.d.ts.map +1 -0
  69. package/lib/main/browser/view/dnd-file-content-store.js +52 -0
  70. package/lib/main/browser/view/dnd-file-content-store.js.map +1 -0
  71. package/lib/main/browser/view/plugin-view-registry.d.ts.map +1 -1
  72. package/lib/main/browser/view/plugin-view-registry.js +1 -1
  73. package/lib/main/browser/view/plugin-view-registry.js.map +1 -1
  74. package/lib/main/browser/view/tree-view-decorator-service.d.ts +2 -4
  75. package/lib/main/browser/view/tree-view-decorator-service.d.ts.map +1 -1
  76. package/lib/main/browser/view/tree-view-decorator-service.js +1 -2
  77. package/lib/main/browser/view/tree-view-decorator-service.js.map +1 -1
  78. package/lib/main/browser/view/tree-view-widget.d.ts +25 -9
  79. package/lib/main/browser/view/tree-view-widget.d.ts.map +1 -1
  80. package/lib/main/browser/view/tree-view-widget.js +184 -38
  81. package/lib/main/browser/view/tree-view-widget.js.map +1 -1
  82. package/lib/main/browser/view/tree-views-main.d.ts +5 -2
  83. package/lib/main/browser/view/tree-views-main.d.ts.map +1 -1
  84. package/lib/main/browser/view/tree-views-main.js +16 -2
  85. package/lib/main/browser/view/tree-views-main.js.map +1 -1
  86. package/lib/main/browser/webview/webview.d.ts +1 -1
  87. package/lib/main/browser/webview/webview.d.ts.map +1 -1
  88. package/lib/main/browser/webview/webview.js +7 -2
  89. package/lib/main/browser/webview/webview.js.map +1 -1
  90. package/lib/main/node/handlers/plugin-theia-directory-handler.d.ts +1 -1
  91. package/lib/main/node/handlers/plugin-theia-directory-handler.d.ts.map +1 -1
  92. package/lib/plugin/debug/debug-ext.d.ts +3 -0
  93. package/lib/plugin/debug/debug-ext.d.ts.map +1 -1
  94. package/lib/plugin/debug/debug-ext.js +10 -0
  95. package/lib/plugin/debug/debug-ext.js.map +1 -1
  96. package/lib/plugin/languages/code-action.d.ts.map +1 -1
  97. package/lib/plugin/languages/code-action.js +8 -8
  98. package/lib/plugin/languages/code-action.js.map +1 -1
  99. package/lib/plugin/plugin-context.d.ts.map +1 -1
  100. package/lib/plugin/plugin-context.js +8 -0
  101. package/lib/plugin/plugin-context.js.map +1 -1
  102. package/lib/plugin/plugin-manager.d.ts.map +1 -1
  103. package/lib/plugin/plugin-manager.js +1 -0
  104. package/lib/plugin/plugin-manager.js.map +1 -1
  105. package/lib/plugin/preference-registry.d.ts.map +1 -1
  106. package/lib/plugin/preference-registry.js +4 -2
  107. package/lib/plugin/preference-registry.js.map +1 -1
  108. package/lib/plugin/quick-open.d.ts +3 -0
  109. package/lib/plugin/quick-open.d.ts.map +1 -1
  110. package/lib/plugin/quick-open.js +7 -0
  111. package/lib/plugin/quick-open.js.map +1 -1
  112. package/lib/plugin/scm.d.ts +3 -0
  113. package/lib/plugin/scm.d.ts.map +1 -1
  114. package/lib/plugin/scm.js +7 -0
  115. package/lib/plugin/scm.js.map +1 -1
  116. package/lib/plugin/tabs.js +2 -2
  117. package/lib/plugin/tabs.js.map +1 -1
  118. package/lib/plugin/terminal-ext.d.ts +9 -1
  119. package/lib/plugin/terminal-ext.d.ts.map +1 -1
  120. package/lib/plugin/terminal-ext.js +63 -7
  121. package/lib/plugin/terminal-ext.js.map +1 -1
  122. package/lib/plugin/tree/tree-views.d.ts +13 -7
  123. package/lib/plugin/tree/tree-views.d.ts.map +1 -1
  124. package/lib/plugin/tree/tree-views.js +93 -24
  125. package/lib/plugin/tree/tree-views.js.map +1 -1
  126. package/lib/plugin/type-converters.d.ts +4 -0
  127. package/lib/plugin/type-converters.d.ts.map +1 -1
  128. package/lib/plugin/type-converters.js +48 -46
  129. package/lib/plugin/type-converters.js.map +1 -1
  130. package/lib/plugin/type-converters.spec.js +19 -0
  131. package/lib/plugin/type-converters.spec.js.map +1 -1
  132. package/lib/plugin/types-impl.d.ts +61 -6
  133. package/lib/plugin/types-impl.d.ts.map +1 -1
  134. package/lib/plugin/types-impl.js +117 -17
  135. package/lib/plugin/types-impl.js.map +1 -1
  136. package/package.json +26 -26
  137. package/src/common/plugin-api-rpc.ts +36 -18
  138. package/src/common/plugin-protocol.ts +18 -0
  139. package/src/common/rpc-protocol.ts +2 -3
  140. package/src/common/types.ts +4 -4
  141. package/src/hosted/browser/hosted-plugin.ts +4 -0
  142. package/src/hosted/node/hosted-plugin-localization-service.ts +3 -3
  143. package/src/hosted/node/plugin-host.ts +1 -2
  144. package/src/hosted/node/scanners/scanner-theia.ts +15 -1
  145. package/src/main/browser/authentication-main.ts +1 -1
  146. package/src/main/browser/commands.ts +1 -1
  147. package/src/main/browser/debug/debug-main.ts +1 -0
  148. package/src/main/browser/dialogs-main.ts +2 -1
  149. package/src/main/browser/menus/plugin-menu-command-adapter.ts +7 -4
  150. package/src/main/browser/menus/vscode-theia-menu-mappings.ts +6 -0
  151. package/src/main/browser/plugin-contribution-handler.ts +35 -0
  152. package/src/main/browser/plugin-ext-frontend-module.ts +10 -4
  153. package/src/main/browser/plugin-terminal-registry.ts +27 -0
  154. package/src/main/browser/scm-main.ts +10 -0
  155. package/src/main/browser/terminal-main.ts +55 -25
  156. package/src/main/browser/view/dnd-file-content-store.ts +42 -0
  157. package/src/main/browser/view/plugin-view-registry.ts +4 -1
  158. package/src/main/browser/view/tree-view-decorator-service.ts +4 -5
  159. package/src/main/browser/view/tree-view-widget.tsx +189 -35
  160. package/src/main/browser/view/tree-views-main.ts +20 -4
  161. package/src/main/browser/webview/pre/main.js +112 -111
  162. package/src/main/browser/webview/webview.ts +7 -3
  163. package/src/plugin/debug/debug-ext.ts +12 -0
  164. package/src/plugin/languages/code-action.ts +8 -8
  165. package/src/plugin/plugin-context.ts +16 -3
  166. package/src/plugin/plugin-manager.ts +1 -0
  167. package/src/plugin/preference-registry.ts +4 -2
  168. package/src/plugin/quick-open.ts +10 -0
  169. package/src/plugin/scm.ts +11 -0
  170. package/src/plugin/tabs.ts +2 -2
  171. package/src/plugin/terminal-ext.ts +68 -8
  172. package/src/plugin/tree/tree-views.ts +98 -31
  173. package/src/plugin/type-converters.spec.ts +20 -0
  174. package/src/plugin/type-converters.ts +51 -50
  175. package/src/plugin/types-impl.ts +143 -21
@@ -67,78 +67,78 @@
67
67
  };
68
68
 
69
69
  const defaultCssRules = `
70
- body {
71
- background-color: var(--vscode-editor-background);
72
- color: var(--vscode-editor-foreground);
73
- font-family: var(--vscode-font-family);
74
- font-weight: var(--vscode-font-weight);
75
- font-size: var(--vscode-font-size);
76
- margin: 0;
77
- padding: 0 20px;
78
- }
79
-
80
- img {
81
- max-width: 100%;
82
- max-height: 100%;
83
- }
84
-
85
- a {
86
- color: var(--vscode-textLink-foreground);
87
- }
88
-
89
- a:hover {
90
- color: var(--vscode-textLink-activeForeground);
91
- }
92
-
93
- a:focus,
94
- input:focus,
95
- select:focus,
96
- textarea:focus {
97
- outline: 1px solid -webkit-focus-ring-color;
98
- outline-offset: -1px;
99
- }
100
-
101
- code {
102
- color: var(--vscode-textPreformat-foreground);
103
- }
104
-
105
- blockquote {
106
- background: var(--vscode-textBlockQuote-background);
107
- border-color: var(--vscode-textBlockQuote-border);
108
- }
109
-
110
- kbd {
111
- color: var(--vscode-editor-foreground);
112
- border-radius: 3px;
113
- vertical-align: middle;
114
- padding: 1px 3px;
115
-
116
- background-color: hsla(0,0%,50%,.17);
117
- border: 1px solid rgba(71,71,71,.4);
118
- border-bottom-color: rgba(88,88,88,.4);
119
- box-shadow: inset 0 -1px 0 rgba(88,88,88,.4);
120
- }
121
- .vscode-light kbd {
122
- background-color: hsla(0,0%,87%,.5);
123
- border: 1px solid hsla(0,0%,80%,.7);
124
- border-bottom-color: hsla(0,0%,73%,.7);
125
- box-shadow: inset 0 -1px 0 hsla(0,0%,73%,.7);
126
- }
127
-
128
- ::-webkit-scrollbar {
129
- width: 10px;
130
- height: 10px;
131
- }
132
-
133
- ::-webkit-scrollbar-thumb {
134
- background-color: var(--vscode-scrollbarSlider-background);
135
- }
136
- ::-webkit-scrollbar-thumb:hover {
137
- background-color: var(--vscode-scrollbarSlider-hoverBackground);
138
- }
139
- ::-webkit-scrollbar-thumb:active {
140
- background-color: var(--vscode-scrollbarSlider-activeBackground);
141
- }`;
70
+ body {
71
+ background-color: var(--vscode-editor-background);
72
+ color: var(--vscode-editor-foreground);
73
+ font-family: var(--vscode-font-family);
74
+ font-weight: var(--vscode-font-weight);
75
+ font-size: var(--vscode-font-size);
76
+ margin: 0;
77
+ padding: 0 20px;
78
+ }
79
+
80
+ img {
81
+ max-width: 100%;
82
+ max-height: 100%;
83
+ }
84
+
85
+ a {
86
+ color: var(--vscode-textLink-foreground);
87
+ }
88
+
89
+ a:hover {
90
+ color: var(--vscode-textLink-activeForeground);
91
+ }
92
+
93
+ a:focus,
94
+ input:focus,
95
+ select:focus,
96
+ textarea:focus {
97
+ outline: 1px solid -webkit-focus-ring-color;
98
+ outline-offset: -1px;
99
+ }
100
+
101
+ code {
102
+ color: var(--vscode-textPreformat-foreground);
103
+ }
104
+
105
+ blockquote {
106
+ background: var(--vscode-textBlockQuote-background);
107
+ border-color: var(--vscode-textBlockQuote-border);
108
+ }
109
+
110
+ kbd {
111
+ color: var(--vscode-editor-foreground);
112
+ border-radius: 3px;
113
+ vertical-align: middle;
114
+ padding: 1px 3px;
115
+
116
+ background-color: hsla(0,0%,50%,.17);
117
+ border: 1px solid rgba(71,71,71,.4);
118
+ border-bottom-color: rgba(88,88,88,.4);
119
+ box-shadow: inset 0 -1px 0 rgba(88,88,88,.4);
120
+ }
121
+ .vscode-light kbd {
122
+ background-color: hsla(0,0%,87%,.5);
123
+ border: 1px solid hsla(0,0%,80%,.7);
124
+ border-bottom-color: hsla(0,0%,73%,.7);
125
+ box-shadow: inset 0 -1px 0 hsla(0,0%,73%,.7);
126
+ }
127
+
128
+ ::-webkit-scrollbar {
129
+ width: 10px;
130
+ height: 10px;
131
+ }
132
+
133
+ ::-webkit-scrollbar-thumb {
134
+ background-color: var(--vscode-scrollbarSlider-background);
135
+ }
136
+ ::-webkit-scrollbar-thumb:hover {
137
+ background-color: var(--vscode-scrollbarSlider-hoverBackground);
138
+ }
139
+ ::-webkit-scrollbar-thumb:active {
140
+ background-color: var(--vscode-scrollbarSlider-activeBackground);
141
+ }`;
142
142
 
143
143
  /**
144
144
  * @param {*} [state]
@@ -146,38 +146,38 @@
146
146
  */
147
147
  function getVsCodeApiScript(state) {
148
148
  return `
149
- const acquireVsCodeApi = (function() {
150
- const originalPostMessage = window.parent.postMessage.bind(window.parent);
151
- const targetOrigin = '*';
152
- let acquired = false;
153
-
154
- let state = ${state ? `JSON.parse(${JSON.stringify(state)})` : undefined};
155
-
156
- return () => {
157
- if (acquired) {
158
- throw new Error('An instance of the VS Code API has already been acquired');
159
- }
160
- acquired = true;
161
- return Object.freeze({
162
- postMessage: function(msg) {
163
- return originalPostMessage({ command: 'onmessage', data: msg }, targetOrigin);
164
- },
165
- setState: function(newState) {
166
- state = newState;
167
- originalPostMessage({ command: 'do-update-state', data: JSON.stringify(newState) }, targetOrigin);
168
- return newState;
169
- },
170
- getState: function() {
171
- return state;
172
- }
173
- });
174
- };
175
- })();
176
- const acquireTheiaApi = acquireVsCodeApi;
177
- delete window.parent;
178
- delete window.top;
179
- delete window.frameElement;
180
- `;
149
+ const acquireVsCodeApi = (function() {
150
+ const originalPostMessage = window.parent.postMessage.bind(window.parent);
151
+ const targetOrigin = '*';
152
+ let acquired = false;
153
+
154
+ let state = ${state ? `JSON.parse(${JSON.stringify(state)})` : undefined};
155
+
156
+ return () => {
157
+ if (acquired) {
158
+ throw new Error('An instance of the VS Code API has already been acquired');
159
+ }
160
+ acquired = true;
161
+ return Object.freeze({
162
+ postMessage: function(msg) {
163
+ return originalPostMessage({ command: 'onmessage', data: msg }, targetOrigin);
164
+ },
165
+ setState: function(newState) {
166
+ state = newState;
167
+ originalPostMessage({ command: 'do-update-state', data: JSON.stringify(newState) }, targetOrigin);
168
+ return newState;
169
+ },
170
+ getState: function() {
171
+ return state;
172
+ }
173
+ });
174
+ };
175
+ })();
176
+ const acquireTheiaApi = acquireVsCodeApi;
177
+ delete window.parent;
178
+ delete window.top;
179
+ delete window.frameElement;
180
+ `;
181
181
  }
182
182
 
183
183
  /**
@@ -381,20 +381,21 @@
381
381
 
382
382
  applyStyles(newDocument, newDocument.body);
383
383
 
384
+ const sameOrigin = '\'self\''; // see: https://content-security-policy.com/self/
384
385
  // Check for CSP
385
386
  const csp = newDocument.querySelector('meta[http-equiv="Content-Security-Policy"]');
386
- if (!csp) {
387
- host.postMessage('no-csp-found');
388
- } else {
389
- // Rewrite vscode-resource in csp
390
- if (data.endpoint) {
387
+ if (csp !== null) {
388
+ const cspContent = csp.getAttribute('content');
389
+ if (cspContent !== null) {
390
+ // Rewrite vscode-resource in csp
391
391
  try {
392
- const endpointUrl = new URL(data.endpoint);
393
- csp.setAttribute('content', csp.getAttribute('content').replace(/(?:vscode|theia)-resource:(?=(\s|;|$))/g, endpointUrl.origin));
392
+ csp.setAttribute('content', cspContent.replace(/(vscode-webview-resource|vscode-resource):(?=(\s|;|$))/g, sameOrigin));
394
393
  } catch (e) {
395
394
  console.error('Could not rewrite csp');
396
395
  }
397
396
  }
397
+ } else {
398
+ host.postMessage('no-csp-found');
398
399
  }
399
400
 
400
401
  // set DOCTYPE for newDocument explicitly as DOMParser.parseFromString strips it off
@@ -76,7 +76,7 @@ export interface WebviewContentOptions {
76
76
  readonly allowForms?: boolean;
77
77
  readonly localResourceRoots?: ReadonlyArray<string>;
78
78
  readonly portMapping?: ReadonlyArray<WebviewPortMapping>;
79
- readonly enableCommandUris?: boolean;
79
+ readonly enableCommandUris?: boolean | readonly string[];
80
80
  }
81
81
 
82
82
  @injectable()
@@ -450,8 +450,12 @@ export class WebviewWidget extends BaseWidget implements StatefulWidget, Extract
450
450
  }
451
451
  return link;
452
452
  }
453
- if (!!this.contentOptions.enableCommandUris && link.scheme === Schemes.command) {
454
- return link;
453
+ if (link.scheme === Schemes.command) {
454
+ if (Array.isArray(this.contentOptions.enableCommandUris) && this.contentOptions.enableCommandUris.some(value => value === link.path.toString())) {
455
+ return link;
456
+ } else if (this.contentOptions.enableCommandUris === true) {
457
+ return link;
458
+ }
455
459
  }
456
460
  return undefined;
457
461
  }
@@ -67,6 +67,7 @@ export class DebugExtImpl implements DebugExt {
67
67
  private readonly onDidChangeBreakpointsEmitter = new Emitter<theia.BreakpointsChangeEvent>();
68
68
  private readonly onDidChangeActiveDebugSessionEmitter = new Emitter<theia.DebugSession | undefined>();
69
69
  private readonly onDidTerminateDebugSessionEmitter = new Emitter<theia.DebugSession>();
70
+ private readonly onDidCreateDebugSessionEmitter = new Emitter<theia.DebugSession>();
70
71
  private readonly onDidStartDebugSessionEmitter = new Emitter<theia.DebugSession>();
71
72
  private readonly onDidReceiveDebugSessionCustomEmitter = new Emitter<theia.DebugSessionCustomEvent>();
72
73
 
@@ -131,6 +132,10 @@ export class DebugExtImpl implements DebugExt {
131
132
  return this.onDidTerminateDebugSessionEmitter.event;
132
133
  }
133
134
 
135
+ get onDidCreateDebugSession(): theia.Event<theia.DebugSession> {
136
+ return this.onDidCreateDebugSessionEmitter.event;
137
+ }
138
+
134
139
  get onDidStartDebugSession(): theia.Event<theia.DebugSession> {
135
140
  return this.onDidStartDebugSessionEmitter.event;
136
141
  }
@@ -253,6 +258,13 @@ export class DebugExtImpl implements DebugExt {
253
258
  }
254
259
 
255
260
  async $sessionDidCreate(sessionId: string): Promise<void> {
261
+ const session = this.sessions.get(sessionId);
262
+ if (session) {
263
+ this.onDidCreateDebugSessionEmitter.fire(session);
264
+ }
265
+ }
266
+
267
+ async $sessionDidStart(sessionId: string): Promise<void> {
256
268
  const session = this.sessions.get(sessionId);
257
269
  if (session) {
258
270
  this.onDidStartDebugSessionEmitter.fire(session);
@@ -24,6 +24,7 @@ import { Diagnostics } from './diagnostics';
24
24
  import { CodeActionKind } from '../types-impl';
25
25
  import { CommandRegistryImpl } from '../command-registry';
26
26
  import { DisposableCollection } from '@theia/core/lib/common/disposable';
27
+ import { isObject } from '@theia/core/lib/common';
27
28
 
28
29
  export class CodeActionAdapter {
29
30
 
@@ -147,16 +148,15 @@ export class CodeActionAdapter {
147
148
  }
148
149
 
149
150
  private static _isCommand(arg: unknown): arg is theia.Command {
150
- return !!arg && typeof arg === 'object' && typeof (arg as theia.Command).command === 'string';
151
+ return isObject<theia.Command>(arg) && typeof arg.command === 'string';
151
152
  }
152
153
 
153
- private static _isSelection(obj: unknown): obj is Selection {
154
- const selection = obj as Selection;
155
- return !!obj && typeof obj === 'object'
156
- && typeof selection.selectionStartLineNumber === 'number'
157
- && typeof selection.selectionStartColumn === 'number'
158
- && typeof selection.positionLineNumber === 'number'
159
- && typeof selection.positionColumn === 'number';
154
+ private static _isSelection(arg: unknown): arg is Selection {
155
+ return isObject<Selection>(arg)
156
+ && typeof arg.selectionStartLineNumber === 'number'
157
+ && typeof arg.selectionStartColumn === 'number'
158
+ && typeof arg.positionLineNumber === 'number'
159
+ && typeof arg.positionColumn === 'number';
160
160
  }
161
161
 
162
162
  }
@@ -61,6 +61,7 @@ import {
61
61
  CompletionItemKind,
62
62
  CompletionList,
63
63
  TextEdit,
64
+ SnippetTextEdit,
64
65
  CompletionTriggerKind,
65
66
  Diagnostic,
66
67
  DiagnosticRelatedInformation,
@@ -92,6 +93,8 @@ import {
92
93
  CodeActionTriggerKind,
93
94
  TextDocumentSaveReason,
94
95
  CodeAction,
96
+ DataTransferItem,
97
+ DataTransfer,
95
98
  TreeItem,
96
99
  TreeItemCollapsibleState,
97
100
  DocumentSymbol,
@@ -152,6 +155,8 @@ import {
152
155
  TextDocumentChangeReason,
153
156
  InputBoxValidationSeverity,
154
157
  TerminalLink,
158
+ TerminalLocation,
159
+ TerminalProfile,
155
160
  InlayHint,
156
161
  InlayHintKind,
157
162
  InlayHintLabelPart,
@@ -520,7 +525,7 @@ export function createAPIFactory(
520
525
  registerTreeDataProvider<T>(viewId: string, treeDataProvider: theia.TreeDataProvider<T>): Disposable {
521
526
  return treeViewsExt.registerTreeDataProvider(plugin, viewId, treeDataProvider);
522
527
  },
523
- createTreeView<T>(viewId: string, options: { treeDataProvider: theia.TreeDataProvider<T> }): theia.TreeView<T> {
528
+ createTreeView<T>(viewId: string, options: theia.TreeViewOptions<T>): theia.TreeView<T> {
524
529
  return treeViewsExt.createTreeView(plugin, viewId, options);
525
530
  },
526
531
  withScmProgress<R>(task: (progress: theia.Progress<number>) => Thenable<R>) {
@@ -546,6 +551,9 @@ export function createAPIFactory(
546
551
  registerTerminalLinkProvider(provider: theia.TerminalLinkProvider): theia.Disposable {
547
552
  return terminalExt.registerTerminalLinkProvider(provider);
548
553
  },
554
+ registerTerminalProfileProvider(id: string, provider: theia.TerminalProfileProvider): theia.Disposable {
555
+ return terminalExt.registerTerminalProfileProvider(id, provider);
556
+ },
549
557
  get activeColorTheme(): theia.ColorTheme {
550
558
  return themingExt.activeColorTheme;
551
559
  },
@@ -1088,7 +1096,7 @@ export function createAPIFactory(
1088
1096
  notebook: theia.NotebookDocument,
1089
1097
  controller: theia.NotebookController
1090
1098
  ): (void | Thenable<void>) { },
1091
- onDidChangeSelectedNotebooks: () => Disposable.create(() => {}),
1099
+ onDidChangeSelectedNotebooks: () => Disposable.create(() => { }),
1092
1100
  updateNotebookAffinity: (notebook: theia.NotebookDocument, affinity: theia.NotebookControllerAffinity) => undefined,
1093
1101
  dispose: () => undefined,
1094
1102
  };
@@ -1099,7 +1107,7 @@ export function createAPIFactory(
1099
1107
  ) {
1100
1108
  return {
1101
1109
  rendererId,
1102
- onDidReceiveMessage: () => Disposable.create(() => {} ),
1110
+ onDidReceiveMessage: () => Disposable.create(() => { }),
1103
1111
  postMessage: () => Promise.resolve({}),
1104
1112
  };
1105
1113
  },
@@ -1169,6 +1177,7 @@ export function createAPIFactory(
1169
1177
  Diagnostic,
1170
1178
  CompletionTriggerKind,
1171
1179
  TextEdit,
1180
+ SnippetTextEdit,
1172
1181
  ProgressLocation,
1173
1182
  ProgressOptions,
1174
1183
  Progress,
@@ -1192,6 +1201,8 @@ export function createAPIFactory(
1192
1201
  CodeActionTriggerKind,
1193
1202
  TextDocumentSaveReason,
1194
1203
  CodeAction,
1204
+ DataTransferItem,
1205
+ DataTransfer,
1195
1206
  TreeItem,
1196
1207
  TreeItemCollapsibleState,
1197
1208
  SymbolKind,
@@ -1249,6 +1260,7 @@ export function createAPIFactory(
1249
1260
  SourceControlInputBoxValidationType,
1250
1261
  FileDecoration,
1251
1262
  TerminalLink,
1263
+ TerminalProfile,
1252
1264
  CancellationError,
1253
1265
  ExtensionMode,
1254
1266
  LinkedEditingRanges,
@@ -1284,6 +1296,7 @@ export function createAPIFactory(
1284
1296
  TabInputNotebookDiff: NotebookDiffEditorTabInput,
1285
1297
  TabInputWebview: WebviewEditorTabInput,
1286
1298
  TabInputTerminal: TerminalEditorTabInput,
1299
+ TerminalLocation
1287
1300
  };
1288
1301
  };
1289
1302
  }
@@ -89,6 +89,7 @@ export class PluginManagerExtImpl implements PluginManagerExt, PluginManager {
89
89
  'workspaceContains',
90
90
  'onView',
91
91
  'onUri',
92
+ 'onTerminalProfile',
92
93
  'onWebviewPanel',
93
94
  'onFileSystem',
94
95
  'onCustomEditor',
@@ -170,7 +170,9 @@ export class PreferenceRegistryExtImpl implements PreferenceRegistryExt {
170
170
  },
171
171
  update: (key: string, value: any, targetScope?: ConfigurationTarget | boolean, withLanguageOverride?: boolean): PromiseLike<void> => {
172
172
  const resourceStr = overrides.resource?.toString();
173
- const fullPath = `${overrides.overrideIdentifier ? `[${overrides.overrideIdentifier}].` : ''}${rawSection}.${key}`;
173
+ const overrideSegment = overrides.overrideIdentifier ? `[${overrides.overrideIdentifier}].` : '';
174
+ const preferenceKey = rawSection ? `${rawSection}.${key}` : key;
175
+ const fullPath = overrideSegment + preferenceKey;
174
176
  if (typeof value !== 'undefined') {
175
177
  return this.proxy.$updateConfigurationOption(targetScope, fullPath, value, resourceStr, withLanguageOverride);
176
178
  } else {
@@ -178,7 +180,7 @@ export class PreferenceRegistryExtImpl implements PreferenceRegistryExt {
178
180
  }
179
181
  },
180
182
  inspect: <T>(key: string): ConfigurationInspect<T> | undefined => {
181
- const path = `${rawSection}.${key}`;
183
+ const path = rawSection ? `${rawSection}.${key}` : key;
182
184
  const result = this._preferences.inspect<T>(path, overrides, new TheiaWorkspace(this.workspace));
183
185
 
184
186
  if (!result) {
@@ -543,6 +543,7 @@ export class InputBoxExt extends QuickInputExt implements theia.InputBox {
543
543
 
544
544
  private _password: boolean;
545
545
  private _prompt: string | undefined;
546
+ private _valueSelection: readonly [number, number] | undefined;
546
547
  private _validationMessage: string | undefined;
547
548
 
548
549
  constructor(
@@ -576,6 +577,15 @@ export class InputBoxExt extends QuickInputExt implements theia.InputBox {
576
577
  this.update({ prompt });
577
578
  }
578
579
 
580
+ get valueSelection(): readonly [number, number] | undefined {
581
+ return this._valueSelection;
582
+ }
583
+
584
+ set valueSelection(valueSelection: readonly [number, number] | undefined) {
585
+ this._valueSelection = valueSelection;
586
+ this.update({ valueSelection });
587
+ }
588
+
579
589
  get validationMessage(): string | undefined {
580
590
  return this._validationMessage;
581
591
  }
package/src/plugin/scm.ts CHANGED
@@ -322,6 +322,17 @@ export class ScmInputBoxImpl implements theia.SourceControlInputBox {
322
322
  this._visible = visible;
323
323
  }
324
324
 
325
+ private _enabled: boolean;
326
+
327
+ get enabled(): boolean {
328
+ return this._enabled;
329
+ }
330
+
331
+ set enabled(enabled: boolean) {
332
+ this.proxy.$setInputBoxEnabled(this.sourceControlHandle, enabled);
333
+ this._enabled = enabled;
334
+ }
335
+
325
336
  private _validateInput: ValidateInput | undefined;
326
337
 
327
338
  get validateInput(): ValidateInput | undefined {
@@ -406,7 +406,7 @@ export class TabsExtImpl implements TabsExt {
406
406
  return this.proxy.$closeTab(extHostTabIds, preserveFocus);
407
407
  }
408
408
 
409
- private async _closeGroups(groups: theia.TabGroup[], preserverFoucs?: boolean): Promise<boolean> {
409
+ private async _closeGroups(groups: theia.TabGroup[], preserveFocus?: boolean): Promise<boolean> {
410
410
  const extHostGroupIds: number[] = [];
411
411
  for (const group of groups) {
412
412
  const extHostGroup = this._findExtHostTabGroupFromApi(group);
@@ -415,7 +415,7 @@ export class TabsExtImpl implements TabsExt {
415
415
  }
416
416
  extHostGroupIds.push(extHostGroup.groupId);
417
417
  }
418
- return this.proxy.$closeGroup(extHostGroupIds, preserverFoucs);
418
+ return this.proxy.$closeGroup(extHostGroupIds, preserveFocus);
419
419
  }
420
420
  }
421
421
 
@@ -20,9 +20,25 @@ import { RPCProtocol } from '../common/rpc-protocol';
20
20
  import { Event, Emitter } from '@theia/core/lib/common/event';
21
21
  import { Deferred } from '@theia/core/lib/common/promise-util';
22
22
  import * as theia from '@theia/plugin';
23
- import { Disposable, EnvironmentVariableMutatorType } from './types-impl';
23
+ import { Disposable, EnvironmentVariableMutatorType, ThemeIcon } from './types-impl';
24
24
  import { SerializableEnvironmentVariableCollection } from '@theia/terminal/lib/common/base-terminal-protocol';
25
25
  import { ProvidedTerminalLink } from '../common/plugin-api-rpc-model';
26
+ import { ThemeIcon as MonacoThemeIcon } from '@theia/monaco-editor-core/esm/vs/platform/theme/common/themeService';
27
+
28
+ export function getIconUris(iconPath: theia.TerminalOptions['iconPath']): { id: string } | undefined {
29
+ if (ThemeIcon.is(iconPath)) {
30
+ return { id: iconPath.id };
31
+ }
32
+ return undefined;
33
+ }
34
+
35
+ export function getIconClass(options: theia.TerminalOptions | theia.ExtensionTerminalOptions): string | undefined {
36
+ const iconClass = getIconUris(options.iconPath);
37
+ if (iconClass) {
38
+ return MonacoThemeIcon.asClassName(iconClass);
39
+ }
40
+ return undefined;
41
+ }
26
42
 
27
43
  /**
28
44
  * Provides high level terminal plugin api to use in the Theia plugins.
@@ -36,9 +52,9 @@ export class TerminalServiceExtImpl implements TerminalServiceExt {
36
52
 
37
53
  private readonly _pseudoTerminals = new Map<string, PseudoTerminal>();
38
54
 
39
- private static nextTerminalLinkProviderId = 0;
55
+ private static nextProviderId = 0;
40
56
  private readonly terminalLinkProviders = new Map<string, theia.TerminalLinkProvider>();
41
-
57
+ private readonly terminalProfileProviders = new Map<string, theia.TerminalProfileProvider>();
42
58
  private readonly onDidCloseTerminalEmitter = new Emitter<Terminal>();
43
59
  readonly onDidCloseTerminal: theia.Event<Terminal> = this.onDidCloseTerminalEmitter.event;
44
60
 
@@ -65,9 +81,9 @@ export class TerminalServiceExtImpl implements TerminalServiceExt {
65
81
  nameOrOptions: TerminalOptions | PseudoTerminalOptions | ExtensionTerminalOptions | (string | undefined),
66
82
  shellPath?: string, shellArgs?: string[] | string
67
83
  ): Terminal {
84
+ const id = `plugin-terminal-${UUID.uuid4()}`;
68
85
  let options: TerminalOptions;
69
86
  let pseudoTerminal: theia.Pseudoterminal | undefined = undefined;
70
- const id = `plugin-terminal-${UUID.uuid4()}`;
71
87
  if (typeof nameOrOptions === 'object') {
72
88
  if ('pty' in nameOrOptions) {
73
89
  pseudoTerminal = nameOrOptions.pty;
@@ -85,7 +101,22 @@ export class TerminalServiceExtImpl implements TerminalServiceExt {
85
101
  shellArgs: shellArgs
86
102
  };
87
103
  }
88
- this.proxy.$createTerminal(id, options, !!pseudoTerminal);
104
+
105
+ let parentId;
106
+
107
+ if (options.location && typeof options.location === 'object' && 'parentTerminal' in options.location) {
108
+ const parentTerminal = options.location.parentTerminal;
109
+ if (parentTerminal instanceof TerminalExtImpl) {
110
+ for (const [k, v] of this._terminals) {
111
+ if (v === parentTerminal) {
112
+ parentId = k;
113
+ break;
114
+ }
115
+ }
116
+ }
117
+ }
118
+
119
+ this.proxy.$createTerminal(id, options, parentId, !!pseudoTerminal);
89
120
 
90
121
  let creationOptions: theia.TerminalOptions | theia.ExtensionTerminalOptions = options;
91
122
  // make sure to pass ExtensionTerminalOptions as creation options
@@ -158,8 +189,7 @@ export class TerminalServiceExtImpl implements TerminalServiceExt {
158
189
  terminal.deferredProcessId = new Deferred<number>();
159
190
  terminal.deferredProcessId.resolve(processId);
160
191
  }
161
- // Pseudoterminal is keyed on ID
162
- const pseudoTerminal = this._pseudoTerminals.get(id);
192
+ const pseudoTerminal = this._pseudoTerminals.get(terminalId.toString());
163
193
  if (pseudoTerminal) {
164
194
  pseudoTerminal.emitOnOpen(cols, rows);
165
195
  }
@@ -189,7 +219,7 @@ export class TerminalServiceExtImpl implements TerminalServiceExt {
189
219
  }
190
220
 
191
221
  registerTerminalLinkProvider(provider: theia.TerminalLinkProvider): theia.Disposable {
192
- const providerId = (TerminalServiceExtImpl.nextTerminalLinkProviderId++).toString();
222
+ const providerId = (TerminalServiceExtImpl.nextProviderId++).toString();
193
223
  this.terminalLinkProviders.set(providerId, provider);
194
224
  this.proxy.$registerTerminalLinkProvider(providerId);
195
225
  return Disposable.create(() => {
@@ -198,6 +228,36 @@ export class TerminalServiceExtImpl implements TerminalServiceExt {
198
228
  });
199
229
  }
200
230
 
231
+ registerTerminalProfileProvider(id: string, provider: theia.TerminalProfileProvider): theia.Disposable {
232
+ this.terminalProfileProviders.set(id, provider);
233
+ return Disposable.create(() => {
234
+ this.terminalProfileProviders.delete(id);
235
+ });
236
+ }
237
+
238
+ protected isExtensionTerminalOptions(options: theia.TerminalOptions | theia.ExtensionTerminalOptions): options is theia.ExtensionTerminalOptions {
239
+ return 'pty' in options;
240
+ }
241
+
242
+ async $startProfile(profileId: string, cancellationToken: theia.CancellationToken): Promise<string> {
243
+ const provider = this.terminalProfileProviders.get(profileId);
244
+ if (!provider) {
245
+ throw new Error(`No terminal profile provider with id '${profileId}'`);
246
+ }
247
+ const profile = await provider.provideTerminalProfile(cancellationToken);
248
+ if (!profile) {
249
+ throw new Error(`Profile with id ${profileId} could not be created`);
250
+ }
251
+ const id = `plugin-terminal-${UUID.uuid4()}`;
252
+ const options = profile.options;
253
+ if (this.isExtensionTerminalOptions(options)) {
254
+ this._pseudoTerminals.set(id, new PseudoTerminal(id, this.proxy, options.pty));
255
+ return this.proxy.$createTerminal(id, { name: options.name }, undefined, true);
256
+ } else {
257
+ return this.proxy.$createTerminal(id, profile.options);
258
+ }
259
+ }
260
+
201
261
  async $provideTerminalLinks(line: string, terminalId: string, token: theia.CancellationToken): Promise<ProvidedTerminalLink[]> {
202
262
  const links: ProvidedTerminalLink[] = [];
203
263
  const terminal = this._terminals.get(terminalId);