From dcc66f13a8e8b2c856910f09b8b08b6eaf895305 Mon Sep 17 00:00:00 2001 From: "Brett V. Forsgren" Date: Wed, 26 May 2021 09:23:41 -0600 Subject: [PATCH] update cell output api from `value` to `data` --- NotebookTestScript.dib | 12 ++ .../common/interactiveClient.ts | 7 +- .../common/interfaces/utilities.ts | 28 +++-- .../common/interfaces/vscode-like.ts | 2 +- .../common/tests/unit/client.test.ts | 35 +++--- .../common/tests/unit/misc.test.ts | 27 ++--- .../common/tests/unit/notebook.test.ts | 28 +++-- .../common/tests/unit/utilities.ts | 21 +++- .../common/vscode/vscodeUtilities.ts | 4 +- .../insiders/src/notebookControllers.ts | 8 +- .../insiders/src/notebookSerializers.ts | 12 +- .../insiders/src/vscode.d.ts | 114 +++++++++--------- .../insiders/src/vscode.proposed.d.ts | 46 +++---- 13 files changed, 183 insertions(+), 161 deletions(-) diff --git a/NotebookTestScript.dib b/NotebookTestScript.dib index 6ddc353dc5..2c8f35e4df 100644 --- a/NotebookTestScript.dib +++ b/NotebookTestScript.dib @@ -49,6 +49,18 @@ document.getElementById("output").innerText = `The value is ${x}.`; #!markdown +# Execute the next cell, the output should be displayed as JSON like so: + +``` json +{"Name":"Developer","Salary":42} +``` + +#!csharp + +display(new { Name = "Developer", Salary = 42 }, "application/json"); + +#!markdown + # Execute the next cell and verify the following error appears: ``` diff --git a/src/dotnet-interactive-vscode/common/interactiveClient.ts b/src/dotnet-interactive-vscode/common/interactiveClient.ts index 07da86e15b..c9248eaa7e 100644 --- a/src/dotnet-interactive-vscode/common/interactiveClient.ts +++ b/src/dotnet-interactive-vscode/common/interactiveClient.ts @@ -381,15 +381,14 @@ export class InteractiveClient { } private displayEventToCellOutput(disp: DisplayEvent): vscodeLike.NotebookCellOutput { + const encoder = new TextEncoder(); let outputItems: Array = []; if (disp.formattedValues && disp.formattedValues.length > 0) { for (let formatted of disp.formattedValues) { - let value: any = formatted.mimeType === 'application/json' - ? JSON.parse(formatted.value) - : formatted.value; + let data = encoder.encode(formatted.value); outputItems.push({ mime: formatted.mimeType, - value, + data, }); } } diff --git a/src/dotnet-interactive-vscode/common/interfaces/utilities.ts b/src/dotnet-interactive-vscode/common/interfaces/utilities.ts index 35d7d5e183..c2bf46134e 100644 --- a/src/dotnet-interactive-vscode/common/interfaces/utilities.ts +++ b/src/dotnet-interactive-vscode/common/interfaces/utilities.ts @@ -6,7 +6,7 @@ import { NotebookCellErrorOutput, NotebookCellTextOutput, } from './contracts'; -import * as notebook from './vscode-like'; +import * as vscodeLike from './vscode-like'; export function isErrorOutput(arg: any): arg is NotebookCellErrorOutput { return arg @@ -25,17 +25,19 @@ export function isTextOutput(arg: any): arg is NotebookCellTextOutput { && typeof arg.text === 'string'; } -export function reshapeOutputValueForVsCode(mimeType: string, value: unknown): unknown { - if (mimeType === notebook.ErrorOutputMimeType && - typeof value === 'string') { - // this looks suspiciously like an error message; make sure it's the shape that vs code expects - return { - ename: 'Error', - evalue: value, - traceback: [], - }; +export function reshapeOutputValueForVsCode(value: Uint8Array | string, mime: string): Uint8Array { + if (typeof value === 'string') { + const encoder = new TextEncoder(); + const dataString = mime === vscodeLike.ErrorOutputMimeType + ? JSON.stringify({ + ename: 'Error', + evalue: value, + traceback: [], + }) + : value; + const data = encoder.encode(dataString); + return data; + } else { + return value; } - - // no change - return value; } diff --git a/src/dotnet-interactive-vscode/common/interfaces/vscode-like.ts b/src/dotnet-interactive-vscode/common/interfaces/vscode-like.ts index 5cb7a70755..cc2d161aba 100644 --- a/src/dotnet-interactive-vscode/common/interfaces/vscode-like.ts +++ b/src/dotnet-interactive-vscode/common/interfaces/vscode-like.ts @@ -12,7 +12,7 @@ export const ErrorOutputMimeType = 'application/vnd.code.notebook.error'; export interface NotebookCellOutputItem { readonly mime: string; - readonly value: Uint8Array | unknown; + readonly data: Uint8Array; readonly metadata?: { [key: string]: any }; } diff --git a/src/dotnet-interactive-vscode/common/tests/unit/client.test.ts b/src/dotnet-interactive-vscode/common/tests/unit/client.test.ts index 759ab95cf4..a1ff204591 100644 --- a/src/dotnet-interactive-vscode/common/tests/unit/client.test.ts +++ b/src/dotnet-interactive-vscode/common/tests/unit/client.test.ts @@ -75,13 +75,14 @@ describe('InteractiveClient tests', () => { const client = await clientMapper.getOrAddClient(createUri('test/path')); let result: Array = []; await client.execute(code, 'csharp', outputs => result = outputs, _ => { }, { token }); - expect(result).to.deep.equal([ + const decodedResults = decodeNotebookCellOutputs(result); + expect(decodedResults).to.deep.equal([ { id: '1', outputs: [ { mime: 'text/plain', - value: 'deferred output', + decodedData: 'deferred output', } ] }, @@ -90,7 +91,7 @@ describe('InteractiveClient tests', () => { outputs: [ { mime: 'text/html', - value: '2', + decodedData: '2', } ] } @@ -156,13 +157,14 @@ describe('InteractiveClient tests', () => { const client = await clientMapper.getOrAddClient(createUri('test/path')); let result: Array = []; await client.execute(code, 'csharp', outputs => result = outputs, _ => { }, { token }); - expect(result).to.deep.equal([ + const decodedResults = decodeNotebookCellOutputs(result); + expect(decodedResults).to.deep.equal([ { id: '1', outputs: [ { mime: 'text/plain', - value: 'deferred output', + decodedData: 'deferred output', } ] }, @@ -171,7 +173,7 @@ describe('InteractiveClient tests', () => { outputs: [ { mime: 'text/html', - value: '2', + decodedData: '2', } ] } @@ -252,13 +254,14 @@ describe('InteractiveClient tests', () => { const client = await clientMapper.getOrAddClient(createUri('test/path')); let result: Array = []; await client.execute(code, 'csharp', outputs => result = outputs, _ => { }, { token }); - expect(result).to.deep.equal([ + const decodedResults = decodeNotebookCellOutputs(result); + expect(decodedResults).to.deep.equal([ { id: '1', outputs: [ { mime: 'text/plain', - value: 'deferred output 1', + decodedData: 'deferred output 1', } ] }, @@ -267,7 +270,7 @@ describe('InteractiveClient tests', () => { outputs: [ { mime: 'text/html', - value: '2', + decodedData: '2', } ] }, @@ -276,7 +279,7 @@ describe('InteractiveClient tests', () => { outputs: [ { mime: 'text/plain', - value: 'deferred output 2', + decodedData: 'deferred output 2', } ] } @@ -335,13 +338,14 @@ describe('InteractiveClient tests', () => { // execute first command let result1: Array = []; await client.execute(code, 'csharp', outputs => result1 = outputs, _ => { }, { token: 'token 1' }); - expect(result1).to.deep.equal([ + let decodedResults1 = decodeNotebookCellOutputs(result1); + expect(decodedResults1).to.deep.equal([ { id: '1', outputs: [ { mime: 'text/html', - value: '1', + decodedData: '1', } ] } @@ -353,13 +357,14 @@ describe('InteractiveClient tests', () => { expect(result2).to.deep.equal([]); // ensure first result array was updated - expect(result1).to.deep.equal([ + decodedResults1 = decodeNotebookCellOutputs(result1); + expect(decodedResults1).to.deep.equal([ { id: '2', outputs: [ { mime: 'text/html', - value: '2', + decodedData: '2', } ] } @@ -478,7 +483,7 @@ describe('InteractiveClient tests', () => { id: '1', outputs: [{ mime: vscodeLike.ErrorOutputMimeType, - decodedValue: { + decodedData: { name: 'Error', message: 'Error: expected exception during submit', }, diff --git a/src/dotnet-interactive-vscode/common/tests/unit/misc.test.ts b/src/dotnet-interactive-vscode/common/tests/unit/misc.test.ts index 288c3d2817..a64c4f594c 100644 --- a/src/dotnet-interactive-vscode/common/tests/unit/misc.test.ts +++ b/src/dotnet-interactive-vscode/common/tests/unit/misc.test.ts @@ -6,6 +6,7 @@ import { NotebookCellDisplayOutput, NotebookCellErrorOutput, NotebookCellTextOut import { isDisplayOutput, isErrorOutput, isTextOutput, reshapeOutputValueForVsCode } from '../../interfaces/utilities'; import { isDotNetNotebookMetadata, isIpynbFile } from '../../ipynbUtilities'; import { createUri, debounce, executeSafe, getWorkingDirectoryForNotebook, isDotNetUpToDate, parse, processArguments, stringify } from '../../utilities'; +import { decodeNotebookCellOutputs, decodeToString } from './utilities'; import * as vscodeLike from '../../interfaces/vscode-like'; @@ -207,33 +208,19 @@ describe('Miscellaneous tests', () => { describe('vs code output value reshaping', () => { it('error string is reshaped', () => { - const reshaped = reshapeOutputValueForVsCode(vscodeLike.ErrorOutputMimeType, 'some error message'); - expect(reshaped).to.deep.equal({ + const reshaped = reshapeOutputValueForVsCode('some error message', vscodeLike.ErrorOutputMimeType); + const decoded = JSON.parse(decodeToString(reshaped)); + expect(decoded).to.deep.equal({ ename: 'Error', evalue: 'some error message', traceback: [], }); }); - it(`properly shaped output isn't reshaped`, () => { - const reshaped = reshapeOutputValueForVsCode(vscodeLike.ErrorOutputMimeType, { ename: 'Error2', evalue: 'some error message', traceback: [] }); - expect(reshaped).to.deep.equal({ - ename: 'Error2', - evalue: 'some error message', - traceback: [], - }); - }); - - it('non-string error message is not reshaped', () => { - const reshaped = reshapeOutputValueForVsCode(vscodeLike.ErrorOutputMimeType, { some_deep_value: 'some error message' }); - expect(reshaped).to.deep.equal({ - some_deep_value: 'some error message', - }); - }); - it(`non-error mime type doesn't reshape output`, () => { - const reshaped = reshapeOutputValueForVsCode('text/plain', 'some error message'); - expect(reshaped).to.equal('some error message'); + const reshaped = reshapeOutputValueForVsCode('some error message', 'text/plain'); + const decoded = decodeToString(reshaped); + expect(decoded).to.equal('some error message'); }); }); diff --git a/src/dotnet-interactive-vscode/common/tests/unit/notebook.test.ts b/src/dotnet-interactive-vscode/common/tests/unit/notebook.test.ts index bd89bb6ae4..9cd8e88562 100644 --- a/src/dotnet-interactive-vscode/common/tests/unit/notebook.test.ts +++ b/src/dotnet-interactive-vscode/common/tests/unit/notebook.test.ts @@ -22,7 +22,7 @@ import { ReturnValueProducedType, StandardOutputValueProducedType, } from '../../interfaces/contracts'; -import { createKernelTransportConfig, withFakeGlobalStorageLocation } from './utilities'; +import { createKernelTransportConfig, decodeNotebookCellOutputs, withFakeGlobalStorageLocation } from './utilities'; import { createUri } from '../../utilities'; import { backupNotebook, languageToCellKind } from '../../interactiveNotebook'; import * as vscodeLike from '../../interfaces/vscode-like'; @@ -72,13 +72,14 @@ describe('Notebook tests', () => { const client = await clientMapper.getOrAddClient(createUri('test/path')); let result: Array = []; await client.execute(code, language, outputs => result = outputs, _ => { }, { token }); - expect(result).to.deep.equal([ + const decodedResults = decodeNotebookCellOutputs(result); + expect(decodedResults).to.deep.equal([ { id: '1', outputs: [ { mime: 'text/html', - value: '2', + decodedData: '2', } ] } @@ -159,13 +160,14 @@ Console.WriteLine(1); const client = await clientMapper.getOrAddClient(createUri('test/path')); let result: Array = []; await client.execute(code, 'csharp', outputs => result = outputs, _ => { }, { token }); - expect(result).to.deep.equal([ + const decodedResults = decodeNotebookCellOutputs(result); + expect(decodedResults).to.deep.equal([ { id: '1', outputs: [ { mime: 'text/plain', - value: '1\r\n', + decodedData: '1\r\n', } ], }, @@ -174,7 +176,7 @@ Console.WriteLine(1); outputs: [ { mime: 'text/plain', - value: '2\r\n', + decodedData: '2\r\n', } ] }, @@ -183,7 +185,7 @@ Console.WriteLine(1); outputs: [ { mime: 'text/plain', - value: '3\r\n', + decodedData: '3\r\n', } ] } @@ -254,13 +256,14 @@ Console.WriteLine(1); const client = await clientMapper.getOrAddClient(createUri('test/path')); let result: Array = []; await client.execute(code, 'csharp', outputs => result = outputs, _ => { }, { token }); - expect(result).to.deep.equal([ + const decodedResults = decodeNotebookCellOutputs(result); + expect(decodedResults).to.deep.equal([ { id: '2', outputs: [ { mime: 'text/plain', - value: 'Installed package Newtonsoft.Json version 1.2.3.4', + decodedData: 'Installed package Newtonsoft.Json version 1.2.3.4', } ] }, @@ -269,7 +272,7 @@ Console.WriteLine(1); outputs: [ { mime: 'text/plain', - value: 'sentinel', + decodedData: 'sentinel', } ] }, @@ -319,13 +322,14 @@ Console.WriteLine(1); const client = await clientMapper.getOrAddClient(createUri('test/path')); let result: Array = []; await client.execute(code, 'csharp', outputs => result = outputs, _ => { }, { token }); - expect(result).to.deep.equal([ + const decodedResults = decodeNotebookCellOutputs(result); + expect(decodedResults).to.deep.equal([ { id: '1', outputs: [ { mime: 'application/json', - value: { + decodedData: { a: 1, b: false, } diff --git a/src/dotnet-interactive-vscode/common/tests/unit/utilities.ts b/src/dotnet-interactive-vscode/common/tests/unit/utilities.ts index a09278e8e7..daab008f5c 100644 --- a/src/dotnet-interactive-vscode/common/tests/unit/utilities.ts +++ b/src/dotnet-interactive-vscode/common/tests/unit/utilities.ts @@ -39,9 +39,9 @@ export function createKernelTransportConfig(kernelTransportCreator: (notebookUri const defaultClientMapperConfig = { kernelTransportCreator: defaultKernelTransportCreator, createErrorOutput: (message: string, outputId?: string) => { - const errorItem = { + const errorItem: vscodeLike.NotebookCellOutputItem = { mime: 'application/vnd.code.notebook.error', - value: encoder.encode(JSON.stringify({ + data: encoder.encode(JSON.stringify({ name: 'Error', message, })), @@ -58,15 +58,24 @@ export function createKernelTransportConfig(kernelTransportCreator: (notebookUri }; } -export function decodeNotebookCellOutputs(outputs: vscodeLike.NotebookCellOutput[]): any[] { +export function decodeToString(data: Uint8Array): string { const decoder = new TextDecoder('utf-8'); + const decoded = decoder.decode(data); + return decoded; +} + +export function decodeNotebookCellOutputs(outputs: vscodeLike.NotebookCellOutput[]): any[] { + const jsonLikeMimes = new Set(); + jsonLikeMimes.add('application/json'); + jsonLikeMimes.add(vscodeLike.ErrorOutputMimeType); return outputs.map(o => ({ ...o, outputs: o.outputs.map(oi => { - let result = { + const decoded = decodeToString(oi.data); + let result = { ...oi, - decodedValue: JSON.parse(decoder.decode(oi.value)) + decodedData: jsonLikeMimes.has(oi.mime) ? JSON.parse(decoded) : decoded, }; - delete result.value; + delete result.data; return result; }) })); diff --git a/src/dotnet-interactive-vscode/common/vscode/vscodeUtilities.ts b/src/dotnet-interactive-vscode/common/vscode/vscodeUtilities.ts index 1791737c6e..39a9707889 100644 --- a/src/dotnet-interactive-vscode/common/vscode/vscodeUtilities.ts +++ b/src/dotnet-interactive-vscode/common/vscode/vscodeUtilities.ts @@ -94,7 +94,7 @@ export function vsCodeCellOutputToContractCellOutput(output: vscode.NotebookCell const errorOutputItem = errorOutputItems[0]; const error: NotebookCellErrorOutput = { errorName: 'Error', - errorValue: '' + errorOutputItem.value, + errorValue: '' + errorOutputItem.data, stackTrace: [], }; return error; @@ -102,7 +102,7 @@ export function vsCodeCellOutputToContractCellOutput(output: vscode.NotebookCell //otherwise build the mime=>value dictionary const data: { [key: string]: any } = {}; for (const outputItem of output.outputs) { - data[outputItem.mime] = outputItem.value; + data[outputItem.mime] = outputItem.data; } const cellOutput: NotebookCellDisplayOutput = { diff --git a/src/dotnet-interactive-vscode/insiders/src/notebookControllers.ts b/src/dotnet-interactive-vscode/insiders/src/notebookControllers.ts index 56ed41a523..2097ea1882 100644 --- a/src/dotnet-interactive-vscode/insiders/src/notebookControllers.ts +++ b/src/dotnet-interactive-vscode/insiders/src/notebookControllers.ts @@ -194,7 +194,7 @@ export async function updateCellLanguages(document: vscode.NotebookDocument): Pr } async function updateCellOutputs(executionTask: vscode.NotebookCellExecutionTask, cell: vscode.NotebookCell, outputs: Array): Promise { - const reshapedOutputs = outputs.map(o => new vscode.NotebookCellOutput(o.outputs.map(oi => generateVsCodeNotebookCellOutputItem(oi.mime, oi.value)))); + const reshapedOutputs = outputs.map(o => new vscode.NotebookCellOutput(o.outputs.map(oi => generateVsCodeNotebookCellOutputItem(oi.data, oi.mime)))); await executionTask.replaceOutput(reshapedOutputs, cell.index); } @@ -211,9 +211,9 @@ export function endExecution(cell: vscode.NotebookCell, success: boolean) { } } -function generateVsCodeNotebookCellOutputItem(mimeType: string, value: unknown): vscode.NotebookCellOutputItem { - const displayValue = reshapeOutputValueForVsCode(mimeType, value); - return new vscode.NotebookCellOutputItem(mimeType, displayValue); +function generateVsCodeNotebookCellOutputItem(data: Uint8Array, mime: string): vscode.NotebookCellOutputItem { + const displayData = reshapeOutputValueForVsCode(data, mime); + return new vscode.NotebookCellOutputItem(displayData, mime); } async function updateDocumentKernelspecMetadata(document: vscode.NotebookDocument): Promise { diff --git a/src/dotnet-interactive-vscode/insiders/src/notebookSerializers.ts b/src/dotnet-interactive-vscode/insiders/src/notebookSerializers.ts index 0a104defe9..522184bfba 100644 --- a/src/dotnet-interactive-vscode/insiders/src/notebookSerializers.ts +++ b/src/dotnet-interactive-vscode/insiders/src/notebookSerializers.ts @@ -122,18 +122,18 @@ function contractCellOutputToVsCodeCellOutput(output: contracts.NotebookCellOutp const outputItems: Array = []; if (utilities.isDisplayOutput(output)) { for (const mimeKey in output.data) { - outputItems.push(generateVsCodeNotebookCellOutputItem(mimeKey, output.data[mimeKey])); + outputItems.push(generateVsCodeNotebookCellOutputItem(output.data[mimeKey], mimeKey)); } } else if (utilities.isErrorOutput(output)) { - outputItems.push(generateVsCodeNotebookCellOutputItem(vscodeLike.ErrorOutputMimeType, output.errorValue)); + outputItems.push(generateVsCodeNotebookCellOutputItem(output.errorValue, vscodeLike.ErrorOutputMimeType)); } else if (utilities.isTextOutput(output)) { - outputItems.push(generateVsCodeNotebookCellOutputItem('text/plain', output.text)); + outputItems.push(generateVsCodeNotebookCellOutputItem(output.text, 'text/plain')); } return new vscode.NotebookCellOutput(outputItems); } -function generateVsCodeNotebookCellOutputItem(mimeType: string, value: unknown): vscode.NotebookCellOutputItem { - const displayValue = utilities.reshapeOutputValueForVsCode(mimeType, value); - return new vscode.NotebookCellOutputItem(mimeType, displayValue); +function generateVsCodeNotebookCellOutputItem(value: Uint8Array | string, mime: string): vscode.NotebookCellOutputItem { + const displayValue = utilities.reshapeOutputValueForVsCode(value, mime); + return new vscode.NotebookCellOutputItem(displayValue, mime); } diff --git a/src/dotnet-interactive-vscode/insiders/src/vscode.d.ts b/src/dotnet-interactive-vscode/insiders/src/vscode.d.ts index 6ba49ea6a2..a339d5c864 100644 --- a/src/dotnet-interactive-vscode/insiders/src/vscode.d.ts +++ b/src/dotnet-interactive-vscode/insiders/src/vscode.d.ts @@ -536,7 +536,7 @@ declare module 'vscode' { /** * The new value for the {@link TextEditor.selections text editor's selections}. */ - readonly selections: ReadonlyArray; + readonly selections: readonly Selection[]; /** * The {@link TextEditorSelectionChangeKind change kind} which has triggered this * event. Can be `undefined`. @@ -555,7 +555,7 @@ declare module 'vscode' { /** * The new value for the {@link TextEditor.visibleRanges text editor's visible ranges}. */ - readonly visibleRanges: ReadonlyArray; + readonly visibleRanges: readonly Range[]; } /** @@ -1150,7 +1150,7 @@ declare module 'vscode' { * @return A promise that resolves with a value indicating if the snippet could be inserted. Note that the promise does not signal * that the snippet is completely filled-in or accepted. */ - insertSnippet(snippet: SnippetString, location?: Position | Range | ReadonlyArray | ReadonlyArray, options?: { undoStopBefore: boolean; undoStopAfter: boolean; }): Thenable; + insertSnippet(snippet: SnippetString, location?: Position | Range | readonly Position[] | readonly Range[], options?: { undoStopBefore: boolean; undoStopAfter: boolean; }): Thenable; /** * Adds a set of decorations to the text editor. If a set of decorations already exists with @@ -1163,7 +1163,7 @@ declare module 'vscode' { * @param decorationType A decoration type. * @param rangesOrOptions Either {@link Range ranges} or more detailed {@link DecorationOptions options}. */ - setDecorations(decorationType: TextEditorDecorationType, rangesOrOptions: Range[] | DecorationOptions[]): void; + setDecorations(decorationType: TextEditorDecorationType, rangesOrOptions: readonly Range[] | readonly DecorationOptions[]): void; /** * Scroll as indicated by `revealType` in order to reveal the given range. @@ -2211,7 +2211,7 @@ declare module 'vscode' { /** * An array of diagnostics. */ - readonly diagnostics: ReadonlyArray; + readonly diagnostics: readonly Diagnostic[]; /** * Requested kind of actions to return. @@ -2975,7 +2975,7 @@ declare module 'vscode' { /** * Tags for this symbol. */ - tags?: ReadonlyArray; + tags?: readonly SymbolTag[]; /** * The location of this symbol. @@ -3031,7 +3031,7 @@ declare module 'vscode' { /** * Tags for this symbol. */ - tags?: ReadonlyArray; + tags?: readonly SymbolTag[]; /** * The range enclosing this symbol not including leading/trailing whitespace but everything else, e.g. comments and code. @@ -3955,7 +3955,7 @@ declare module 'vscode' { /** * List of characters that trigger signature help. */ - readonly triggerCharacters: ReadonlyArray; + readonly triggerCharacters: readonly string[]; /** * List of characters that re-trigger signature help. @@ -3963,7 +3963,7 @@ declare module 'vscode' { * These trigger characters are only active when signature help is already showing. All trigger characters * are also counted as re-trigger characters. */ - readonly retriggerCharacters: ReadonlyArray; + readonly retriggerCharacters: readonly string[]; } /** @@ -4043,7 +4043,7 @@ declare module 'vscode' { /** * Tags for this completion item. */ - tags?: ReadonlyArray; + tags?: readonly CompletionItemTag[]; /** * A human-readable string with additional information @@ -4608,7 +4608,7 @@ declare module 'vscode' { /** * Tags for this item. */ - tags?: ReadonlyArray; + tags?: readonly SymbolTag[]; /** * More detail for this item, e.g. the signature of a function. @@ -5197,7 +5197,7 @@ declare module 'vscode' { /** * An array of resources for which diagnostics have changed. */ - readonly uris: ReadonlyArray; + readonly uris: readonly Uri[]; } /** @@ -5366,7 +5366,7 @@ declare module 'vscode' { * @param uri A resource identifier. * @param diagnostics Array of diagnostics or `undefined` */ - set(uri: Uri, diagnostics: ReadonlyArray | undefined): void; + set(uri: Uri, diagnostics: readonly Diagnostic[] | undefined): void; /** * Replace diagnostics for multiple resources in this collection. @@ -5378,7 +5378,7 @@ declare module 'vscode' { * * @param entries An array of tuples, like `[[file1, [d1, d2]], [file2, [d3, d4, d5]]]`, or `undefined`. */ - set(entries: ReadonlyArray<[Uri, ReadonlyArray | undefined]>): void; + set(entries: ReadonlyArray<[Uri, readonly Diagnostic[] | undefined]>): void; /** * Remove all diagnostics from this collection that belong @@ -5400,7 +5400,7 @@ declare module 'vscode' { * @param callback Function to execute for each entry. * @param thisArg The `this` context used when invoking the handler function. */ - forEach(callback: (uri: Uri, diagnostics: ReadonlyArray, collection: DiagnosticCollection) => any, thisArg?: any): void; + forEach(callback: (uri: Uri, diagnostics: readonly Diagnostic[], collection: DiagnosticCollection) => any, thisArg?: any): void; /** * Get the diagnostics for a given resource. *Note* that you cannot @@ -5409,7 +5409,7 @@ declare module 'vscode' { * @param uri A resource identifier. * @returns An immutable array of {@link Diagnostic diagnostics} or `undefined`. */ - get(uri: Uri): ReadonlyArray | undefined; + get(uri: Uri): readonly Diagnostic[] | undefined; /** * Check if this collection contains diagnostics for a @@ -6015,7 +6015,7 @@ declare module 'vscode' { * * @param keys The set of keys whose values are synced. */ - setKeysForSync(keys: string[]): void; + setKeysForSync(keys: readonly string[]): void; }; /** @@ -6879,7 +6879,7 @@ declare module 'vscode' { /** * The currently active task executions or an empty array. */ - export const taskExecutions: ReadonlyArray; + export const taskExecutions: readonly TaskExecution[]; /** * Fires when a task starts. @@ -7327,7 +7327,7 @@ declare module 'vscode' { * * Pass in an empty array to disallow access to any local resources. */ - readonly localResourceRoots?: ReadonlyArray; + readonly localResourceRoots?: readonly Uri[]; /** * Mappings of localhost ports used inside the webview. @@ -7342,7 +7342,7 @@ declare module 'vscode' { * *Note* that port mappings only work for `http` or `https` urls. Websocket urls (e.g. `ws://localhost:3000`) * cannot be mapped to another port. */ - readonly portMapping?: ReadonlyArray; + readonly portMapping?: readonly WebviewPortMapping[]; } /** @@ -8408,7 +8408,7 @@ declare module 'vscode' { /** * The currently opened terminals or an empty array. */ - export const terminals: ReadonlyArray; + export const terminals: readonly Terminal[]; /** * The currently active terminal or `undefined`. The active terminal is the one that @@ -8631,7 +8631,7 @@ declare module 'vscode' { * @param token A token that can be used to signal cancellation. * @return A promise that resolves to the selected items or `undefined`. */ - export function showQuickPick(items: string[] | Thenable, options: QuickPickOptions & { canPickMany: true; }, token?: CancellationToken): Thenable; + export function showQuickPick(items: readonly string[] | Thenable, options: QuickPickOptions & { canPickMany: true; }, token?: CancellationToken): Thenable; /** * Shows a selection list. @@ -8641,7 +8641,7 @@ declare module 'vscode' { * @param token A token that can be used to signal cancellation. * @return A promise that resolves to the selection or `undefined`. */ - export function showQuickPick(items: string[] | Thenable, options?: QuickPickOptions, token?: CancellationToken): Thenable; + export function showQuickPick(items: readonly string[] | Thenable, options?: QuickPickOptions, token?: CancellationToken): Thenable; /** * Shows a selection list allowing multiple selections. @@ -8651,7 +8651,7 @@ declare module 'vscode' { * @param token A token that can be used to signal cancellation. * @return A promise that resolves to the selected items or `undefined`. */ - export function showQuickPick(items: T[] | Thenable, options: QuickPickOptions & { canPickMany: true; }, token?: CancellationToken): Thenable; + export function showQuickPick(items: readonly T[] | Thenable, options: QuickPickOptions & { canPickMany: true; }, token?: CancellationToken): Thenable; /** * Shows a selection list. @@ -8661,7 +8661,7 @@ declare module 'vscode' { * @param token A token that can be used to signal cancellation. * @return A promise that resolves to the selected item or `undefined`. */ - export function showQuickPick(items: T[] | Thenable, options?: QuickPickOptions, token?: CancellationToken): Thenable; + export function showQuickPick(items: readonly T[] | Thenable, options?: QuickPickOptions, token?: CancellationToken): Thenable; /** * Shows a selection list of {@link workspace.workspaceFolders workspace folders} to pick from. @@ -9849,7 +9849,7 @@ declare module 'vscode' { /** * Buttons for actions in the UI. */ - buttons: ReadonlyArray; + buttons: readonly QuickInputButton[]; /** * An event signaling when a button was triggered. @@ -9859,7 +9859,7 @@ declare module 'vscode' { /** * Items to pick from. */ - items: ReadonlyArray; + items: readonly T[]; /** * If multiple items can be selected at the same time. Defaults to false. @@ -9879,7 +9879,7 @@ declare module 'vscode' { /** * Active items. This can be read and updated by the extension. */ - activeItems: ReadonlyArray; + activeItems: readonly T[]; /** * An event signaling when the active items have changed. @@ -9889,7 +9889,7 @@ declare module 'vscode' { /** * Selected items. This can be read and updated by the extension. */ - selectedItems: ReadonlyArray; + selectedItems: readonly T[]; /** * An event signaling when the selected items have changed. @@ -9934,7 +9934,7 @@ declare module 'vscode' { /** * Buttons for actions in the UI. */ - buttons: ReadonlyArray; + buttons: readonly QuickInputButton[]; /** * An event signaling when a button was triggered. @@ -10022,7 +10022,7 @@ declare module 'vscode' { /** * An array of content changes. */ - readonly contentChanges: ReadonlyArray; + readonly contentChanges: readonly TextDocumentContentChangeEvent[]; } /** @@ -10110,7 +10110,7 @@ declare module 'vscode' { /** * The files that are going to be created. */ - readonly files: ReadonlyArray; + readonly files: readonly Uri[]; /** * Allows to pause the event and to apply a {@link WorkspaceEdit workspace edit}. @@ -10150,7 +10150,7 @@ declare module 'vscode' { /** * The files that got created. */ - readonly files: ReadonlyArray; + readonly files: readonly Uri[]; } /** @@ -10165,7 +10165,7 @@ declare module 'vscode' { /** * The files that are going to be deleted. */ - readonly files: ReadonlyArray; + readonly files: readonly Uri[]; /** * Allows to pause the event and to apply a {@link WorkspaceEdit workspace edit}. @@ -10205,7 +10205,7 @@ declare module 'vscode' { /** * The files that got deleted. */ - readonly files: ReadonlyArray; + readonly files: readonly Uri[]; } /** @@ -10220,7 +10220,7 @@ declare module 'vscode' { /** * The files that are going to be renamed. */ - readonly files: ReadonlyArray<{ oldUri: Uri, newUri: Uri }>; + readonly files: ReadonlyArray<{ readonly oldUri: Uri, readonly newUri: Uri }>; /** * Allows to pause the event and to apply a {@link WorkspaceEdit workspace edit}. @@ -10260,7 +10260,7 @@ declare module 'vscode' { /** * The files that got renamed. */ - readonly files: ReadonlyArray<{ oldUri: Uri, newUri: Uri }>; + readonly files: ReadonlyArray<{ readonly oldUri: Uri, readonly newUri: Uri }>; } /** @@ -10270,12 +10270,12 @@ declare module 'vscode' { /** * Added workspace folders. */ - readonly added: ReadonlyArray; + readonly added: readonly WorkspaceFolder[]; /** * Removed workspace folders. */ - readonly removed: ReadonlyArray; + readonly removed: readonly WorkspaceFolder[]; } /** @@ -10350,7 +10350,7 @@ declare module 'vscode' { * * *Note* that the first entry corresponds to the value of `rootPath`. */ - export const workspaceFolders: ReadonlyArray | undefined; + export const workspaceFolders: readonly WorkspaceFolder[] | undefined; /** * The name of the workspace. `undefined` when no workspace @@ -10534,7 +10534,7 @@ declare module 'vscode' { /** * All text documents currently known to the editor. */ - export const textDocuments: ReadonlyArray; + export const textDocuments: readonly TextDocument[]; /** * Opens a document. Will return early if this document is already open. Otherwise @@ -11922,17 +11922,17 @@ declare module 'vscode' { /** * Added breakpoints. */ - readonly added: ReadonlyArray; + readonly added: readonly Breakpoint[]; /** * Removed breakpoints. */ - readonly removed: ReadonlyArray; + readonly removed: readonly Breakpoint[]; /** * Changed breakpoints. */ - readonly changed: ReadonlyArray; + readonly changed: readonly Breakpoint[]; } /** @@ -12167,13 +12167,13 @@ declare module 'vscode' { * Add breakpoints. * @param breakpoints The breakpoints to add. */ - export function addBreakpoints(breakpoints: Breakpoint[]): void; + export function addBreakpoints(breakpoints: readonly Breakpoint[]): void; /** * Remove breakpoints. * @param breakpoints The breakpoints to remove. */ - export function removeBreakpoints(breakpoints: Breakpoint[]): void; + export function removeBreakpoints(breakpoints: readonly Breakpoint[]): void; /** * Converts a "Source" descriptor object received via the Debug Adapter Protocol into a Uri that can be used to load its contents. @@ -12242,7 +12242,7 @@ declare module 'vscode' { /** * All extensions currently known to the system. */ - export const all: ReadonlyArray>; + export const all: readonly Extension[]; /** * An event which fires when `extensions.all` changes. This can happen when extensions are @@ -12299,7 +12299,7 @@ declare module 'vscode' { /** * The ordered comments of the thread. */ - comments: ReadonlyArray; + comments: readonly Comment[]; /** * Whether the thread should be collapsed or expanded when opening the document. @@ -12512,7 +12512,7 @@ declare module 'vscode' { * @param range The range the comment thread is located within the document. * @param comments The ordered comments of the thread. */ - createCommentThread(uri: Uri, range: Range, comments: Comment[]): CommentThread; + createCommentThread(uri: Uri, range: Range, comments: readonly Comment[]): CommentThread; /** * Optional reaction handler for creating and deleting reactions on a {@link Comment}. @@ -12564,7 +12564,7 @@ declare module 'vscode' { * The permissions granted by the session's access token. Available scopes * are defined by the {@link AuthenticationProvider}. */ - readonly scopes: ReadonlyArray; + readonly scopes: readonly string[]; } /** @@ -12656,19 +12656,19 @@ declare module 'vscode' { /** * The {@link AuthenticationSession}s of the {@link AuthentiationProvider AuthenticationProvider} that have been added. */ - readonly added?: ReadonlyArray; + readonly added?: readonly AuthenticationSession[]; /** * The {@link AuthenticationSession}s of the {@link AuthentiationProvider AuthenticationProvider} that have been removed. */ - readonly removed?: ReadonlyArray; + readonly removed?: readonly AuthenticationSession[]; /** * The {@link AuthenticationSession}s of the {@link AuthentiationProvider AuthenticationProvider} that have been changed. * A session changes when its data excluding the id are updated. An example of this is a session refresh that results in a new * access token being set for the session. */ - readonly changed?: ReadonlyArray; + readonly changed?: readonly AuthenticationSession[]; } /** @@ -12687,7 +12687,7 @@ declare module 'vscode' { * these permissions, otherwise all sessions should be returned. * @returns A promise that resolves to an array of authentication sessions. */ - getSessions(scopes?: string[]): Thenable>; + getSessions(scopes?: readonly string[]): Thenable; /** * Prompts a user to login. @@ -12702,7 +12702,7 @@ declare module 'vscode' { * @param scopes A list of scopes, permissions, that the new session should be created with. * @returns A promise that resolves to an authentication session. */ - createSession(scopes: string[]): Thenable; + createSession(scopes: readonly string[]): Thenable; /** * Removes the session corresponding to session id. @@ -12733,7 +12733,7 @@ declare module 'vscode' { * @param options The {@link GetSessionOptions} to use * @returns A thenable that resolves to an authentication session */ - export function getSession(providerId: string, scopes: string[], options: AuthenticationGetSessionOptions & { createIfNone: true }): Thenable; + export function getSession(providerId: string, scopes: readonly string[], options: AuthenticationGetSessionOptions & { createIfNone: true }): Thenable; /** * Get an authentication session matching the desired scopes. Rejects if a provider with providerId is not @@ -12748,7 +12748,7 @@ declare module 'vscode' { * @param options The {@link GetSessionOptions} to use * @returns A thenable that resolves to an authentication session if available, or undefined if there are no sessions */ - export function getSession(providerId: string, scopes: string[], options?: AuthenticationGetSessionOptions): Thenable; + export function getSession(providerId: string, scopes: readonly string[], options?: AuthenticationGetSessionOptions): Thenable; /** * An {@link Event} which fires when the authentication sessions of an authentication provider have diff --git a/src/dotnet-interactive-vscode/insiders/src/vscode.proposed.d.ts b/src/dotnet-interactive-vscode/insiders/src/vscode.proposed.d.ts index 94096b84ec..10df4b473f 100644 --- a/src/dotnet-interactive-vscode/insiders/src/vscode.proposed.d.ts +++ b/src/dotnet-interactive-vscode/insiders/src/vscode.proposed.d.ts @@ -1247,11 +1247,12 @@ declare module 'vscode' { * * *Note* that an UTF-8 encoder is used to create bytes for the string. * - * @param value A string/ + * @param value A string. * @param mime Optional MIME type, defaults to `text/plain`. + * @param metadata Optional metadata. * @returns A new output item object. */ - static text(value: string, mime?: string): NotebookCellOutputItem; + static text(value: string, mime?: string, metadata?: { [key: string]: any }): NotebookCellOutputItem; /** * Factory function to create a `NotebookCellOutputItem` from @@ -1263,46 +1264,40 @@ declare module 'vscode' { * * @param value A JSON-stringifyable value. * @param mime Optional MIME type, defaults to `application/json` + * @param metadata Optional metadata. * @returns A new output item object. */ - static json(value: any, mime?: string): NotebookCellOutputItem; - - /** - * Factory function to create a `NotebookCellOutputItem` from bytes. - * - * @param value An array of unsigned 8-bit integers. - * @param mime Optional MIME type, defaults to `application/octet-stream`. - * @returns A new output item object. - */ - //todo@API better names: bytes, raw, buffer? - static bytes(value: Uint8Array, mime?: string): NotebookCellOutputItem; + static json(value: any, mime?: string, metadata?: { [key: string]: any }): NotebookCellOutputItem; /** * Factory function to create a `NotebookCellOutputItem` that uses * uses the `application/vnd.code.notebook.stdout` mime type. * * @param value A string. + * @param metadata Optional metadata. * @returns A new output item object. */ - static stdout(value: string): NotebookCellOutputItem; + static stdout(value: string, metadata?: { [key: string]: any }): NotebookCellOutputItem; /** * Factory function to create a `NotebookCellOutputItem` that uses * uses the `application/vnd.code.notebook.stderr` mime type. * * @param value A string. + * @param metadata Optional metadata. * @returns A new output item object. */ - static stderr(value: string): NotebookCellOutputItem; + static stderr(value: string, metadata?: { [key: string]: any }): NotebookCellOutputItem; /** * Factory function to create a `NotebookCellOutputItem` that uses * uses the `application/vnd.code.notebook.error` mime type. * * @param value An error object. + * @param metadata Optional metadata. * @returns A new output item object. */ - static error(value: Error): NotebookCellOutputItem; + static error(value: Error, metadata?: { [key: string]: any }): NotebookCellOutputItem; /** * The mime type which determines how the {@link NotebookCellOutputItem.value `value`}-property @@ -1314,21 +1309,26 @@ declare module 'vscode' { mime: string; /** - * The value of this output item. Must always be an array of unsigned 8-bit integers. + * The data of this output item. Must always be an array of unsigned 8-bit integers. */ - //todo@API only Unit8Array - value: Uint8Array | unknown; + data: Uint8Array; + /** + * @deprecated + */ + value: unknown; + + //todo@API metadata?: { [key: string]: any }; /** * Create a new notbook cell output item. * + * @param data The value of the output item. * @param mime The mime type of the output item. - * @param value The value of the output item. * @param metadata Optional metadata for this output item. */ - constructor(mime: string, value: Uint8Array | unknown, metadata?: { [key: string]: any }); + constructor(data: Uint8Array, mime: string, metadata?: { [key: string]: any }); } // @jrieken transient @@ -1563,6 +1563,9 @@ declare module 'vscode' { /** * The identifier of this notebook controller. + * + * _Note_ that controllers are remembered by their identifier and that extensions should use + * stable identifiers across sessions. */ readonly id: string; @@ -1654,6 +1657,7 @@ declare module 'vscode' { * @param cell The notebook cell for which to create the execution. * @returns A notebook cell execution. */ + // todo@API rename to NotebookCellExecution createNotebookCellExecutionTask(cell: NotebookCell): NotebookCellExecutionTask; // todo@API find a better name than "preloads"