UNPKG

@codingame/monaco-vscode-extensions-service-override

Version:

VSCode public API plugged on the monaco editor - extensions service-override

376 lines (373 loc) 16.6 kB
import { __decorate, __param } from 'vscode/external/tslib/tslib.es6.js'; import { isNonEmptyArray } from 'vscode/vscode/vs/base/common/arrays'; import { CancellationToken } from 'vscode/vscode/vs/base/common/cancellation'; import { onUnexpectedError } from 'vscode/vscode/vs/base/common/errors'; import { Emitter } from 'vscode/vscode/vs/base/common/event'; import { DisposableMap, DisposableStore, toDisposable, combinedDisposable } from 'vscode/vscode/vs/base/common/lifecycle'; import { URI } from 'vscode/vscode/vs/base/common/uri'; import { ILanguageService } from 'vscode/vscode/vs/editor/common/languages/language'; import { NotebookDto } from './mainThreadNotebookDto.js'; import { extHostNamedCustomer } from '../../services/extensions/common/extHostCustomers.js'; import { INotebookEditorService } from 'vscode/vscode/vs/workbench/contrib/notebook/browser/services/notebookEditorService.service'; import { NotebookExecutionType } from 'vscode/vscode/vs/workbench/contrib/notebook/common/notebookExecutionStateService'; import { INotebookExecutionStateService } from 'vscode/vscode/vs/workbench/contrib/notebook/common/notebookExecutionStateService.service'; import { INotebookKernelService } from 'vscode/vscode/vs/workbench/contrib/notebook/common/notebookKernelService.service'; import { ExtHostContext, MainContext } from 'vscode/vscode/vs/workbench/api/common/extHost.protocol'; import { INotebookService } from 'vscode/vscode/vs/workbench/contrib/notebook/common/notebookService.service'; import { AsyncIterableSource } from 'vscode/vscode/vs/base/common/async'; class MainThreadKernel { get preloadUris() { return ( this.preloads.map(p => p.uri)); } get preloadProvides() { return this.preloads.flatMap(p => p.provides); } constructor(data, _languageService) { this._languageService = _languageService; this._onDidChange = ( new Emitter()); this.onDidChange = this._onDidChange.event; this.id = data.id; this.viewType = data.notebookType; this.extension = data.extensionId; this.implementsInterrupt = data.supportsInterrupt ?? false; this.label = data.label; this.description = data.description; this.detail = data.detail; this.supportedLanguages = isNonEmptyArray(data.supportedLanguages) ? data.supportedLanguages : _languageService.getRegisteredLanguageIds(); this.implementsExecutionOrder = data.supportsExecutionOrder ?? false; this.hasVariableProvider = data.hasVariableProvider ?? false; this.localResourceRoot = URI.revive(data.extensionLocation); this.preloads = data.preloads?.map(u => ({ uri: URI.revive(u.uri), provides: u.provides })) ?? []; } update(data) { const event = Object.create(null); if (data.label !== undefined) { this.label = data.label; event.label = true; } if (data.description !== undefined) { this.description = data.description; event.description = true; } if (data.detail !== undefined) { this.detail = data.detail; event.detail = true; } if (data.supportedLanguages !== undefined) { this.supportedLanguages = isNonEmptyArray(data.supportedLanguages) ? data.supportedLanguages : this._languageService.getRegisteredLanguageIds(); event.supportedLanguages = true; } if (data.supportsExecutionOrder !== undefined) { this.implementsExecutionOrder = data.supportsExecutionOrder; event.hasExecutionOrder = true; } if (data.supportsInterrupt !== undefined) { this.implementsInterrupt = data.supportsInterrupt; event.hasInterruptHandler = true; } if (data.hasVariableProvider !== undefined) { this.hasVariableProvider = data.hasVariableProvider; event.hasVariableProvider = true; } this._onDidChange.fire(event); } } class MainThreadKernelDetectionTask { constructor(notebookType) { this.notebookType = notebookType; } } let MainThreadNotebookKernels = class MainThreadNotebookKernels { constructor(extHostContext, _languageService, _notebookKernelService, _notebookExecutionStateService, _notebookService, notebookEditorService) { this._languageService = _languageService; this._notebookKernelService = _notebookKernelService; this._notebookExecutionStateService = _notebookExecutionStateService; this._notebookService = _notebookService; this._editors = ( new DisposableMap()); this._disposables = ( new DisposableStore()); this._kernels = ( new Map()); this._kernelDetectionTasks = ( new Map()); this._kernelSourceActionProviders = ( new Map()); this._kernelSourceActionProvidersEventRegistrations = ( new Map()); this._executions = ( new Map()); this._notebookExecutions = ( new Map()); this.variableRequestIndex = 0; this.variableRequestMap = ( new Map()); this._proxy = ( extHostContext.getProxy(ExtHostContext.ExtHostNotebookKernels)); notebookEditorService.listNotebookEditors().forEach(this._onEditorAdd, this); notebookEditorService.onDidAddNotebookEditor(this._onEditorAdd, this, this._disposables); notebookEditorService.onDidRemoveNotebookEditor(this._onEditorRemove, this, this._disposables); this._disposables.add(toDisposable(() => { this._executions.forEach(e => { e.complete({}); }); this._notebookExecutions.forEach(e => e.complete()); })); this._disposables.add(this._notebookExecutionStateService.onDidChangeExecution(e => { if (e.type === NotebookExecutionType.cell) { this._proxy.$cellExecutionChanged(e.notebook, e.cellHandle, e.changed?.state); } })); } dispose() { this._disposables.dispose(); for (const [, registration] of ( this._kernels.values())) { registration.dispose(); } for (const [, registration] of ( this._kernelDetectionTasks.values())) { registration.dispose(); } for (const [, registration] of ( this._kernelSourceActionProviders.values())) { registration.dispose(); } this._editors.dispose(); } _onEditorAdd(editor) { const ipcListener = editor.onDidReceiveMessage(e => { if (!editor.hasModel()) { return; } const { selected } = this._notebookKernelService.getMatchingKernel(editor.textModel); if (!selected) { return; } for (const [handle, candidate] of this._kernels) { if (candidate[0] === selected) { this._proxy.$acceptKernelMessageFromRenderer(handle, editor.getId(), e.message); break; } } }); this._editors.set(editor, ipcListener); } _onEditorRemove(editor) { this._editors.deleteAndDispose(editor); } async $postMessage(handle, editorId, message) { const tuple = this._kernels.get(handle); if (!tuple) { throw ( new Error('kernel already disposed')); } const [kernel] = tuple; let didSend = false; for (const [editor] of this._editors) { if (!editor.hasModel()) { continue; } if (this._notebookKernelService.getMatchingKernel(editor.textModel).selected !== kernel) { continue; } if (editorId === undefined) { editor.postMessage(message); didSend = true; } else if (editor.getId() === editorId) { editor.postMessage(message); didSend = true; break; } } return didSend; } $receiveVariable(requestId, variable) { const source = this.variableRequestMap.get(requestId); if (source) { source.emitOne(variable); } } async $addKernel(handle, data) { const that = this; const kernel = new (class extends MainThreadKernel { async executeNotebookCellsRequest(uri, handles) { await that._proxy.$executeCells(handle, uri, handles); } async cancelNotebookCellExecution(uri, handles) { await that._proxy.$cancelCells(handle, uri, handles); } provideVariables(notebookUri, parentId, kind, start, token) { const requestId = `${handle}variables${that.variableRequestIndex++}`; if (( that.variableRequestMap.has(requestId))) { return that.variableRequestMap.get(requestId).asyncIterable; } const source = ( new AsyncIterableSource()); that.variableRequestMap.set(requestId, source); that._proxy.$provideVariables(handle, requestId, notebookUri, parentId, kind, start, token).then(() => { source.resolve(); that.variableRequestMap.delete(requestId); }).catch((err) => { source.reject(err); that.variableRequestMap.delete(requestId); }); return source.asyncIterable; } })(data, this._languageService); const listener = this._notebookKernelService.onDidChangeSelectedNotebooks(e => { if (e.oldKernel === kernel.id) { this._proxy.$acceptNotebookAssociation(handle, e.notebook, false); } else if (e.newKernel === kernel.id) { this._proxy.$acceptNotebookAssociation(handle, e.notebook, true); } }); const registration = this._notebookKernelService.registerKernel(kernel); this._kernels.set(handle, [kernel, combinedDisposable(listener, registration)]); } $updateKernel(handle, data) { const tuple = this._kernels.get(handle); if (tuple) { tuple[0].update(data); } } $removeKernel(handle) { const tuple = this._kernels.get(handle); if (tuple) { tuple[1].dispose(); this._kernels.delete(handle); } } $updateNotebookPriority(handle, notebook, value) { const tuple = this._kernels.get(handle); if (tuple) { this._notebookKernelService.updateKernelNotebookAffinity(tuple[0], URI.revive(notebook), value); } } $createExecution(handle, controllerId, rawUri, cellHandle) { const uri = URI.revive(rawUri); const notebook = this._notebookService.getNotebookTextModel(uri); if (!notebook) { throw ( new Error(`Notebook not found: ${( uri.toString())}`)); } const kernel = this._notebookKernelService.getMatchingKernel(notebook); if (!kernel.selected || kernel.selected.id !== controllerId) { throw ( new Error(`Kernel is not selected: ${kernel.selected?.id} !== ${controllerId}`)); } const execution = this._notebookExecutionStateService.createCellExecution(uri, cellHandle); execution.confirm(); this._executions.set(handle, execution); } $updateExecution(handle, data) { const updates = data.value; try { const execution = this._executions.get(handle); execution?.update(( updates.map(NotebookDto.fromCellExecuteUpdateDto))); } catch (e) { onUnexpectedError(e); } } $completeExecution(handle, data) { try { const execution = this._executions.get(handle); execution?.complete(NotebookDto.fromCellExecuteCompleteDto(data.value)); } catch (e) { onUnexpectedError(e); } finally { this._executions.delete(handle); } } $createNotebookExecution(handle, controllerId, rawUri) { const uri = URI.revive(rawUri); const notebook = this._notebookService.getNotebookTextModel(uri); if (!notebook) { throw ( new Error(`Notebook not found: ${( uri.toString())}`)); } const kernel = this._notebookKernelService.getMatchingKernel(notebook); if (!kernel.selected || kernel.selected.id !== controllerId) { throw ( new Error(`Kernel is not selected: ${kernel.selected?.id} !== ${controllerId}`)); } const execution = this._notebookExecutionStateService.createExecution(uri); execution.confirm(); this._notebookExecutions.set(handle, execution); } $beginNotebookExecution(handle) { try { const execution = this._notebookExecutions.get(handle); execution?.begin(); } catch (e) { onUnexpectedError(e); } } $completeNotebookExecution(handle) { try { const execution = this._notebookExecutions.get(handle); execution?.complete(); } catch (e) { onUnexpectedError(e); } finally { this._notebookExecutions.delete(handle); } } async $addKernelDetectionTask(handle, notebookType) { const kernelDetectionTask = ( new MainThreadKernelDetectionTask(notebookType)); const registration = this._notebookKernelService.registerNotebookKernelDetectionTask(kernelDetectionTask); this._kernelDetectionTasks.set(handle, [kernelDetectionTask, registration]); } $removeKernelDetectionTask(handle) { const tuple = this._kernelDetectionTasks.get(handle); if (tuple) { tuple[1].dispose(); this._kernelDetectionTasks.delete(handle); } } async $addKernelSourceActionProvider(handle, eventHandle, notebookType) { const kernelSourceActionProvider = { viewType: notebookType, provideKernelSourceActions: async () => { const actions = await this._proxy.$provideKernelSourceActions(handle, CancellationToken.None); return ( actions.map(action => { let documentation = action.documentation; if (action.documentation && typeof action.documentation !== 'string') { documentation = URI.revive(action.documentation); } return { label: action.label, command: action.command, description: action.description, detail: action.detail, documentation, }; })); } }; if (typeof eventHandle === 'number') { const emitter = ( new Emitter()); this._kernelSourceActionProvidersEventRegistrations.set(eventHandle, emitter); kernelSourceActionProvider.onDidChangeSourceActions = emitter.event; } const registration = this._notebookKernelService.registerKernelSourceActionProvider(notebookType, kernelSourceActionProvider); this._kernelSourceActionProviders.set(handle, [kernelSourceActionProvider, registration]); } $removeKernelSourceActionProvider(handle, eventHandle) { const tuple = this._kernelSourceActionProviders.get(handle); if (tuple) { tuple[1].dispose(); this._kernelSourceActionProviders.delete(handle); } if (typeof eventHandle === 'number') { this._kernelSourceActionProvidersEventRegistrations.delete(eventHandle); } } $emitNotebookKernelSourceActionsChangeEvent(eventHandle) { const emitter = this._kernelSourceActionProvidersEventRegistrations.get(eventHandle); if (emitter instanceof Emitter) { emitter.fire(undefined); } } $variablesUpdated(notebookUri) { this._notebookKernelService.notifyVariablesChange(URI.revive(notebookUri)); } }; MainThreadNotebookKernels = __decorate([ extHostNamedCustomer(MainContext.MainThreadNotebookKernels), ( __param(1, ILanguageService)), ( __param(2, INotebookKernelService)), ( __param(3, INotebookExecutionStateService)), ( __param(4, INotebookService)), ( __param(5, INotebookEditorService)) ], MainThreadNotebookKernels); export { MainThreadNotebookKernels };