Files
vscode-debug-visualizer/extension/src/webviewContract.ts
2020-08-14 16:10:45 +02:00

172 lines
3.6 KiB
TypeScript

import {
contract,
notificationContract,
types,
requestContract,
} from "@hediet/typed-json-rpc";
import {
DataExtractionResult,
DataExtractorId,
} from "@hediet/debug-visualizer-data-extraction";
interface WebviewConfig {
serverSecret: string;
serverPort: number;
publicPath: string;
expression?: string;
theme: "light" | "dark";
}
export interface WebviewUrlParams {
serverPort: string;
serverSecret: string;
mode: "standalone" | "webviewIFrame";
expression: string;
theme: "light" | "dark";
}
export interface WindowWithWebviewData {
webviewData?: WebviewConfig;
}
export const webviewContract = contract({
client: {
updateState: notificationContract({
params: types.type({
newState: unchecked<DataExtractionState>(),
}),
}),
updateLanguageId: notificationContract({
params: types.type({
languageId: types.union([types.null, types.string]),
}),
}),
setExpression: requestContract({
params: types.type({
expression: types.string,
}),
}),
setTheme: notificationContract({
params: types.type({
theme: types.union([
types.literal("light"),
types.literal("dark"),
]),
}),
}),
},
server: {
authenticate: requestContract({
params: types.type({
secret: types.string,
}),
}),
setPreferredDataExtractor: notificationContract({
params: types.type({
dataExtractorId: unchecked<DataExtractorId>(),
}),
}),
setExpression: notificationContract({
params: types.type({
newExpression: types.string,
}),
}),
refresh: notificationContract({}),
openInBrowser: notificationContract({}),
getCompletions: requestContract({
params: types.type({
text: types.string,
column: types.number,
}),
result: types.type({
completions: types.array(unchecked<CompletionItem>()),
}),
}),
},
});
function unchecked<T>(): types.Type<T, any, unknown> {
return new types.Type<T, T, unknown>(
"unchecked",
(u): u is T => true,
value => types.success(value as T),
value => value
);
}
export type FormattedMessage =
| string
| {
kind: "list";
items: FormattedMessage[];
}
| {
kind: "inlineList";
items: FormattedMessage[];
}
| {
kind: "code";
content: string;
};
export type DataExtractionState =
| { kind: "loading" }
| { kind: "error"; message: FormattedMessage }
| { kind: "noDebugSession" }
| {
kind: "data";
result: DataExtractionResult;
};
// https://microsoft.github.io/debug-adapter-protocol/specification#CompletionItem
type CompletionItemType =
| "method"
| "function"
| "constructor"
| "field"
| "variable"
| "class"
| "interface"
| "module"
| "property"
| "unit"
| "value"
| "enum"
| "keyword"
| "snippet"
| "text"
| "color"
| "file"
| "reference"
| "customcolor";
export interface CompletionItem {
/**
* The label of this completion item. By default this is also the text that is inserted when selecting this completion.
*/
label: string;
/**
* If text is not falsy then it is inserted instead of the label.
*/
text?: string;
/**
* The item's type. Typically the client uses this information to render the item in the UI with an icon.
*/
type?: CompletionItemType;
/**
* This value determines the location (in the CompletionsRequest's 'text' attribute) where the completion text is added.
* If missing the text is added at the location specified by the CompletionsRequest's 'column' attribute.
*/
start?: number;
/**
* This value determines how many characters are overwritten by the completion text.
* If missing the value 0 is assumed which results in the completion text being inserted.
*/
length?: number;
}