mirror of
https://github.com/danbulant/monaco-yaml
synced 2026-06-10 01:51:48 +00:00
Merge yaml language services
This commit is contained in:
parent
6f8a8c5bbd
commit
8ba88be05d
9 changed files with 55 additions and 285 deletions
|
|
@ -5,9 +5,7 @@
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"compile": "gulp compile",
|
"compile": "gulp compile",
|
||||||
"watch": "gulp watch",
|
"watch": "gulp watch",
|
||||||
"prepublish": "gulp release",
|
"prepublish": "gulp release"
|
||||||
"install-service-next": "npm install vscode-json-languageservice@next -f -D && npm install vscode-languageserver-types@next -f -D",
|
|
||||||
"install-service-local": "npm install ../vscode-json-languageservice -f -D && npm install ../vscode-languageserver-node/types -f -D"
|
|
||||||
},
|
},
|
||||||
"author": "Microsoft Corporation",
|
"author": "Microsoft Corporation",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
|
|
@ -24,6 +22,7 @@
|
||||||
"gulp-requirejs": "^0.1.3",
|
"gulp-requirejs": "^0.1.3",
|
||||||
"gulp-tsb": "^2.0.0",
|
"gulp-tsb": "^2.0.0",
|
||||||
"gulp-uglify": "^1.5.3",
|
"gulp-uglify": "^1.5.3",
|
||||||
|
"js-yaml": "^3.10.0",
|
||||||
"jsonc-parser": "1.0.0",
|
"jsonc-parser": "1.0.0",
|
||||||
"merge-stream": "^1.0.0",
|
"merge-stream": "^1.0.0",
|
||||||
"monaco-editor-core": "^0.10.1",
|
"monaco-editor-core": "^0.10.1",
|
||||||
|
|
|
||||||
|
|
@ -1,62 +0,0 @@
|
||||||
"use strict"
|
|
||||||
|
|
||||||
export function insertionPointReturnValue(pt: number) {
|
|
||||||
return ((-pt) - 1)
|
|
||||||
}
|
|
||||||
|
|
||||||
export function binarySearch(array: number[], sought: number) {
|
|
||||||
|
|
||||||
let lower = 0
|
|
||||||
let upper = array.length - 1
|
|
||||||
|
|
||||||
while (lower <= upper) {
|
|
||||||
let idx = Math.floor((lower + upper) / 2)
|
|
||||||
const value = array[idx]
|
|
||||||
|
|
||||||
if (value === sought) {
|
|
||||||
return idx;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (lower === upper) {
|
|
||||||
const insertionPoint = (value < sought) ? idx + 1 : idx
|
|
||||||
return insertionPointReturnValue(insertionPoint)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (sought > value) {
|
|
||||||
lower = idx + 1;
|
|
||||||
} else if (sought < value) {
|
|
||||||
upper = idx - 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export function getLineStartPositions(text: string) {
|
|
||||||
const lineStartPositions = [0];
|
|
||||||
for (var i = 0; i < text.length; i++) {
|
|
||||||
const c = text[i];
|
|
||||||
|
|
||||||
if (c === '\r') {
|
|
||||||
// Check for Windows encoding, otherwise we are old Mac
|
|
||||||
if (i + 1 < text.length && text[i + 1] == '\n') {
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
|
|
||||||
lineStartPositions.push(i + 1);
|
|
||||||
} else if (c === '\n'){
|
|
||||||
lineStartPositions.push(i + 1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return lineStartPositions;
|
|
||||||
}
|
|
||||||
|
|
||||||
export function getPosition(pos: number, lineStartPositions: number[]){
|
|
||||||
let line = binarySearch(lineStartPositions, pos)
|
|
||||||
|
|
||||||
if (line < 0){
|
|
||||||
const insertionPoint = -1 * line - 1;
|
|
||||||
line = insertionPoint - 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
return {line, column: pos - lineStartPositions[line]}
|
|
||||||
}
|
|
||||||
|
|
@ -1,8 +0,0 @@
|
||||||
"use strict"
|
|
||||||
|
|
||||||
import { TextDocument } from "vscode-languageserver-types";
|
|
||||||
|
|
||||||
export function isInComment(document: TextDocument, start: number, offset: number) {
|
|
||||||
const text = document.getText().substr(start, offset);
|
|
||||||
return /(?:^|\s+)#/.test(text);
|
|
||||||
}
|
|
||||||
|
|
@ -1,19 +0,0 @@
|
||||||
{
|
|
||||||
"compilerOptions": {
|
|
||||||
"target": "es6",
|
|
||||||
"module": "umd",
|
|
||||||
"moduleResolution": "node",
|
|
||||||
"sourceMap": true,
|
|
||||||
"declaration": true,
|
|
||||||
"stripInternal": true,
|
|
||||||
"outDir": "../lib",
|
|
||||||
"lib": [
|
|
||||||
"es6"
|
|
||||||
],
|
|
||||||
"baseUrl": "../types",
|
|
||||||
"typeRoots": [
|
|
||||||
"../node_modules/@types",
|
|
||||||
"../types"
|
|
||||||
]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,187 +0,0 @@
|
||||||
/*---------------------------------------------------------------------------------------------
|
|
||||||
* Copyright (c) Adam Voss. All rights reserved.
|
|
||||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
|
||||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
|
||||||
*--------------------------------------------------------------------------------------------*/
|
|
||||||
'use strict';
|
|
||||||
|
|
||||||
import {TextDocument, Position, CompletionItem, CompletionList, Hover, Range, SymbolInformation, Diagnostic,
|
|
||||||
TextEdit, FormattingOptions, MarkedString} from 'vscode-languageserver-types';
|
|
||||||
|
|
||||||
import {JSONCompletion} from 'vscode-json-languageservice/lib/services/jsonCompletion';
|
|
||||||
import {JSONHover} from 'vscode-json-languageservice/lib/services/jsonHover';
|
|
||||||
import {JSONValidation} from 'vscode-json-languageservice/lib/services/jsonValidation';
|
|
||||||
import {JSONSchema} from 'vscode-json-languageservice/lib/jsonSchema';
|
|
||||||
import {JSONDocumentSymbols} from 'vscode-json-languageservice/lib/services/jsonDocumentSymbols';
|
|
||||||
import {parse as JSONDocumentConfig} from 'vscode-json-languageservice/lib/parser/jsonParser';
|
|
||||||
|
|
||||||
import {parse as parseYAML} from './parser/yamlParser';
|
|
||||||
import {isInComment} from './services/yamlCompletion'
|
|
||||||
import {format as formatYAML} from './services/yamlFormatter';
|
|
||||||
|
|
||||||
import {schemaContributions} from 'vscode-json-languageservice/lib/services/configuration';
|
|
||||||
import {JSONSchemaService} from 'vscode-json-languageservice/lib/services/jsonSchemaService';
|
|
||||||
import {JSONWorkerContribution, JSONPath, Segment, CompletionsCollector} from 'vscode-json-languageservice/lib/jsonContributions';
|
|
||||||
|
|
||||||
export type JSONDocument = {}
|
|
||||||
export type YAMLDocument = { documents: JSONDocument[]}
|
|
||||||
export {JSONSchema, JSONWorkerContribution, JSONPath, Segment, CompletionsCollector};
|
|
||||||
export {TextDocument, Position, CompletionItem, CompletionList, Hover, Range, SymbolInformation, Diagnostic,
|
|
||||||
TextEdit, FormattingOptions, MarkedString};
|
|
||||||
|
|
||||||
export interface LanguageService {
|
|
||||||
configure(settings: LanguageSettings): void;
|
|
||||||
doValidation(document: TextDocument, yamlDocument: YAMLDocument): Thenable<Diagnostic[]>;
|
|
||||||
parseYAMLDocument(document: TextDocument): YAMLDocument;
|
|
||||||
resetSchema(uri: string): boolean;
|
|
||||||
doResolve(item: CompletionItem): Thenable<CompletionItem>;
|
|
||||||
doComplete(document: TextDocument, position: Position, doc: YAMLDocument): Thenable<CompletionList>;
|
|
||||||
findDocumentSymbols(document: TextDocument, doc: YAMLDocument): SymbolInformation[];
|
|
||||||
doHover(document: TextDocument, position: Position, doc: YAMLDocument): Thenable<Hover>;
|
|
||||||
format(document: TextDocument, options: FormattingOptions): TextEdit[];
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface LanguageSettings {
|
|
||||||
/**
|
|
||||||
* If set, the validator will return syntax errors.
|
|
||||||
*/
|
|
||||||
validate?: boolean;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A list of known schemas and/or associations of schemas to file names.
|
|
||||||
*/
|
|
||||||
schemas?: SchemaConfiguration[];
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface SchemaConfiguration {
|
|
||||||
/**
|
|
||||||
* The URI of the schema, which is also the identifier of the schema.
|
|
||||||
*/
|
|
||||||
uri: string;
|
|
||||||
/**
|
|
||||||
* A list of file names that are associated to the schema. The '*' wildcard can be used. For example '*.schema.json', 'package.json'
|
|
||||||
*/
|
|
||||||
fileMatch?: string[];
|
|
||||||
/**
|
|
||||||
* The schema for the given URI.
|
|
||||||
* If no schema is provided, the schema will be fetched with the schema request service (if available).
|
|
||||||
*/
|
|
||||||
schema?: JSONSchema;
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface WorkspaceContextService {
|
|
||||||
resolveRelativePath(relativePath: string, resource: string): string;
|
|
||||||
}
|
|
||||||
/**
|
|
||||||
* The schema request service is used to fetch schemas. The result should the schema file comment, or,
|
|
||||||
* in case of an error, a displayable error string
|
|
||||||
*/
|
|
||||||
export interface SchemaRequestService {
|
|
||||||
(uri: string): Thenable<string>;
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface PromiseConstructor {
|
|
||||||
/**
|
|
||||||
* Creates a new Promise.
|
|
||||||
* @param executor A callback used to initialize the promise. This callback is passed two arguments:
|
|
||||||
* a resolve callback used resolve the promise with a value or the result of another promise,
|
|
||||||
* and a reject callback used to reject the promise with a provided reason or error.
|
|
||||||
*/
|
|
||||||
new <T>(executor: (resolve: (value?: T | Thenable<T>) => void, reject: (reason?: any) => void) => void): Thenable<T>;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a Promise that is resolved with an array of results when all of the provided Promises
|
|
||||||
* resolve, or rejected when any Promise is rejected.
|
|
||||||
* @param values An array of Promises.
|
|
||||||
* @returns A new Promise.
|
|
||||||
*/
|
|
||||||
all<T>(values: Array<T | Thenable<T>>): Thenable<T[]>;
|
|
||||||
/**
|
|
||||||
* Creates a new rejected promise for the provided reason.
|
|
||||||
* @param reason The reason the promise was rejected.
|
|
||||||
* @returns A new rejected Promise.
|
|
||||||
*/
|
|
||||||
reject<T>(reason: any): Thenable<T>;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Creates a new resolved promise for the provided value.
|
|
||||||
* @param value A promise.
|
|
||||||
* @returns A promise whose internal state matches the provided promise.
|
|
||||||
*/
|
|
||||||
resolve<T>(value: T | Thenable<T>): Thenable<T>;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface Thenable<R> {
|
|
||||||
/**
|
|
||||||
* Attaches callbacks for the resolution and/or rejection of the Promise.
|
|
||||||
* @param onfulfilled The callback to execute when the Promise is resolved.
|
|
||||||
* @param onrejected The callback to execute when the Promise is rejected.
|
|
||||||
* @returns A Promise for the completion of which ever callback is executed.
|
|
||||||
*/
|
|
||||||
then<TResult>(onfulfilled?: (value: R) => TResult | Thenable<TResult>, onrejected?: (reason: any) => TResult | Thenable<TResult>): Thenable<TResult>;
|
|
||||||
then<TResult>(onfulfilled?: (value: R) => TResult | Thenable<TResult>, onrejected?: (reason: any) => void): Thenable<TResult>;
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface LanguageServiceParams {
|
|
||||||
/**
|
|
||||||
* The schema request service is used to fetch schemas. The result should the schema file comment, or,
|
|
||||||
* in case of an error, a displayable error string
|
|
||||||
*/
|
|
||||||
schemaRequestService?: SchemaRequestService;
|
|
||||||
/**
|
|
||||||
* The workspace context is used to resolve relative paths for relative schema references.
|
|
||||||
*/
|
|
||||||
workspaceContext?: WorkspaceContextService;
|
|
||||||
/**
|
|
||||||
* An optional set of completion and hover participants.
|
|
||||||
*/
|
|
||||||
contributions?: JSONWorkerContribution[];
|
|
||||||
/**
|
|
||||||
* A promise constructor. If not set, the ES5 Promise will be used.
|
|
||||||
*/
|
|
||||||
promiseConstructor?: PromiseConstructor;
|
|
||||||
}
|
|
||||||
|
|
||||||
export function getLanguageService(params: LanguageServiceParams): LanguageService {
|
|
||||||
let promise = params.promiseConstructor || Promise;
|
|
||||||
|
|
||||||
let jsonSchemaService = new JSONSchemaService(params.schemaRequestService, params.workspaceContext, promise);
|
|
||||||
jsonSchemaService.setSchemaContributions(schemaContributions);
|
|
||||||
|
|
||||||
let jsonCompletion = new JSONCompletion(jsonSchemaService, params.contributions, promise);
|
|
||||||
jsonCompletion['isInComment'] = isInComment.bind(jsonCompletion);
|
|
||||||
|
|
||||||
let jsonHover = new JSONHover(jsonSchemaService, params.contributions, promise);
|
|
||||||
let jsonDocumentSymbols = new JSONDocumentSymbols(jsonSchemaService);
|
|
||||||
let jsonValidation = new JSONValidation(jsonSchemaService, promise);
|
|
||||||
|
|
||||||
|
|
||||||
function doValidation(textDocument: TextDocument, yamlDocument: YAMLDocument) {
|
|
||||||
var validate: (JSONDocument) => Thenable<Diagnostic[]> =
|
|
||||||
jsonValidation.doValidation.bind(jsonValidation, textDocument)
|
|
||||||
const validationResults = yamlDocument.documents.map(d => validate(d))
|
|
||||||
const resultsPromise = promise.all(validationResults);
|
|
||||||
return resultsPromise.then(res => (<Diagnostic[]>[]).concat(...res))
|
|
||||||
}
|
|
||||||
|
|
||||||
return {
|
|
||||||
configure: (settings: LanguageSettings) => {
|
|
||||||
jsonSchemaService.clearExternalSchemas();
|
|
||||||
if (settings.schemas) {
|
|
||||||
settings.schemas.forEach(settings => {
|
|
||||||
jsonSchemaService.registerExternalSchema(settings.uri, settings.fileMatch, settings.schema);
|
|
||||||
});
|
|
||||||
};
|
|
||||||
jsonValidation.configure(settings);
|
|
||||||
},
|
|
||||||
resetSchema: (uri: string) => jsonSchemaService.onResourceChange(uri),
|
|
||||||
doValidation: doValidation,
|
|
||||||
parseYAMLDocument : (document: TextDocument) => parseYAML(document.getText()),
|
|
||||||
doResolve: jsonCompletion.doResolve.bind(jsonCompletion),
|
|
||||||
doComplete: jsonCompletion.doComplete.bind(jsonCompletion),
|
|
||||||
findDocumentSymbols: jsonDocumentSymbols.findDocumentSymbols.bind(jsonDocumentSymbols),
|
|
||||||
doHover: jsonHover.doHover.bind(jsonHover),
|
|
||||||
format: formatYAML
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
@ -6,8 +6,7 @@
|
||||||
import { JSONSchemaService } from './jsonSchemaService';
|
import { JSONSchemaService } from './jsonSchemaService';
|
||||||
import { JSONDocument, ObjectASTNode, IProblem, ProblemSeverity } from '../parser/jsonParser';
|
import { JSONDocument, ObjectASTNode, IProblem, ProblemSeverity } from '../parser/jsonParser';
|
||||||
import { TextDocument, Diagnostic, DiagnosticSeverity } from 'vscode-languageserver-types';
|
import { TextDocument, Diagnostic, DiagnosticSeverity } from 'vscode-languageserver-types';
|
||||||
import { PromiseConstructor, Thenable } from '../yamlLanguageService';
|
import { LanguageSettings, PromiseConstructor, Thenable } from '../yamlLanguageService';
|
||||||
import { LanguageSettings } from '../../vscode-yaml-languageservice/yamlLanguageService';
|
|
||||||
|
|
||||||
export class YAMLValidation {
|
export class YAMLValidation {
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,4 @@
|
||||||
import { YAMLDocument } from "../../vscode-yaml-languageservice/yamlLanguageService";
|
import { YAMLDocument } from "../yamlLanguageService";
|
||||||
import { SingleYAMLDocument } from "../parser/yamlParser";
|
import { SingleYAMLDocument } from "../parser/yamlParser";
|
||||||
|
|
||||||
export function removeDuplicates(arr, prop) {
|
export function removeDuplicates(arr, prop) {
|
||||||
|
|
|
||||||
|
|
@ -1,13 +1,60 @@
|
||||||
|
|
||||||
|
import {
|
||||||
|
TextDocument, Position, CompletionItem, CompletionList, Hover, Range, SymbolInformation, Diagnostic,
|
||||||
|
TextEdit, FormattingOptions, MarkedString
|
||||||
|
} from 'vscode-languageserver-types';
|
||||||
|
|
||||||
import { JSONSchemaService } from './services/jsonSchemaService'
|
import { JSONSchemaService } from './services/jsonSchemaService'
|
||||||
import { TextDocument, Position, CompletionList } from 'vscode-languageserver-types';
|
|
||||||
import { JSONSchema } from './jsonSchema';
|
import { JSONSchema } from './jsonSchema';
|
||||||
import { parse as parseYAML } from "./parser/yamlParser";
|
import { parse as parseYAML } from "./parser/yamlParser";
|
||||||
import { YAMLDocumentSymbols } from './services/documentSymbols';
|
import { YAMLDocumentSymbols } from './services/documentSymbols';
|
||||||
import { YAMLCompletion } from "./services/yamlCompletion";
|
import { YAMLCompletion } from "./services/yamlCompletion";
|
||||||
import { YAMLHover } from "./services/yamlHover";
|
import { YAMLHover } from "./services/yamlHover";
|
||||||
import { YAMLValidation } from "./services/yamlValidation";
|
import { YAMLValidation } from "./services/yamlValidation";
|
||||||
import { LanguageSettings, YAMLDocument, Diagnostic } from '../vscode-yaml-languageservice/yamlLanguageService';
|
import { format as formatYAML } from './services/yamlFormatter';
|
||||||
|
|
||||||
|
export type JSONDocument = {}
|
||||||
|
export type YAMLDocument = { documents: JSONDocument[] }
|
||||||
|
|
||||||
|
export interface LanguageService {
|
||||||
|
configure(settings: LanguageSettings): void;
|
||||||
|
doValidation(document: TextDocument, yamlDocument: YAMLDocument): Thenable<Diagnostic[]>;
|
||||||
|
parseYAMLDocument(document: TextDocument): YAMLDocument;
|
||||||
|
resetSchema(uri: string): boolean;
|
||||||
|
doResolve(item: CompletionItem): Thenable<CompletionItem>;
|
||||||
|
doComplete(document: TextDocument, position: Position, doc: YAMLDocument): Thenable<CompletionList>;
|
||||||
|
findDocumentSymbols(document: TextDocument, doc: YAMLDocument): SymbolInformation[];
|
||||||
|
doHover(document: TextDocument, position: Position, doc: YAMLDocument): Thenable<Hover>;
|
||||||
|
format(document: TextDocument, options: FormattingOptions): TextEdit[];
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface LanguageSettings {
|
||||||
|
/**
|
||||||
|
* If set, the validator will return syntax errors.
|
||||||
|
*/
|
||||||
|
validate?: boolean;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A list of known schemas and/or associations of schemas to file names.
|
||||||
|
*/
|
||||||
|
schemas?: SchemaConfiguration[];
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface SchemaConfiguration {
|
||||||
|
/**
|
||||||
|
* The URI of the schema, which is also the identifier of the schema.
|
||||||
|
*/
|
||||||
|
uri: string;
|
||||||
|
/**
|
||||||
|
* A list of file names that are associated to the schema. The '*' wildcard can be used. For example '*.schema.json', 'package.json'
|
||||||
|
*/
|
||||||
|
fileMatch?: string[];
|
||||||
|
/**
|
||||||
|
* The schema for the given URI.
|
||||||
|
* If no schema is provided, the schema will be fetched with the schema request service (if available).
|
||||||
|
*/
|
||||||
|
schema?: JSONSchema;
|
||||||
|
}
|
||||||
export interface LanguageSettings {
|
export interface LanguageSettings {
|
||||||
validate?: boolean; //Setting for whether we want to validate the schema
|
validate?: boolean; //Setting for whether we want to validate the schema
|
||||||
schemas?: any[]; //List of schemas
|
schemas?: any[]; //List of schemas
|
||||||
|
|
@ -120,6 +167,7 @@ export function getLanguageService(schemaRequestService, workspaceContext, contr
|
||||||
doValidation: yamlValidation.doValidation.bind(yamlValidation),
|
doValidation: yamlValidation.doValidation.bind(yamlValidation),
|
||||||
doHover: hover.doHover.bind(hover),
|
doHover: hover.doHover.bind(hover),
|
||||||
findDocumentSymbols: yamlDocumentSymbols.findDocumentSymbols.bind(yamlDocumentSymbols),
|
findDocumentSymbols: yamlDocumentSymbols.findDocumentSymbols.bind(yamlDocumentSymbols),
|
||||||
resetSchema: (uri: string) => schemaService.onResourceChange(uri)
|
resetSchema: (uri: string) => schemaService.onResourceChange(uri),
|
||||||
|
format: formatYAML
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue