yaml-language-server 1.2.2 → 1.3.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.
- package/CHANGELOG.md +25 -0
- package/README.md +10 -1
- package/lib/esm/languageserver/handlers/settingsHandlers.js +4 -2
- package/lib/esm/languageserver/handlers/settingsHandlers.js.map +1 -1
- package/lib/esm/languageservice/parser/ast-converter.js +9 -1
- package/lib/esm/languageservice/parser/ast-converter.js.map +1 -1
- package/lib/esm/languageservice/parser/jsonParser07.d.ts +2 -2
- package/lib/esm/languageservice/parser/jsonParser07.js +74 -25
- package/lib/esm/languageservice/parser/jsonParser07.js.map +1 -1
- package/lib/esm/languageservice/parser/yaml-documents.d.ts +0 -1
- package/lib/esm/languageservice/parser/yaml-documents.js +11 -11
- package/lib/esm/languageservice/parser/yaml-documents.js.map +1 -1
- package/lib/esm/languageservice/services/documentSymbols.js +3 -2
- package/lib/esm/languageservice/services/documentSymbols.js.map +1 -1
- package/lib/esm/languageservice/services/yamlCodeActions.d.ts +1 -0
- package/lib/esm/languageservice/services/yamlCodeActions.js +14 -0
- package/lib/esm/languageservice/services/yamlCodeActions.js.map +1 -1
- package/lib/esm/languageservice/services/yamlCodeLens.js +2 -1
- package/lib/esm/languageservice/services/yamlCodeLens.js.map +1 -1
- package/lib/esm/languageservice/services/yamlCompletion.d.ts +2 -0
- package/lib/esm/languageservice/services/yamlCompletion.js +183 -40
- package/lib/esm/languageservice/services/yamlCompletion.js.map +1 -1
- package/lib/esm/languageservice/services/yamlDefinition.d.ts +6 -1
- package/lib/esm/languageservice/services/yamlDefinition.js +23 -17
- package/lib/esm/languageservice/services/yamlDefinition.js.map +1 -1
- package/lib/esm/languageservice/services/yamlHover.js +2 -1
- package/lib/esm/languageservice/services/yamlHover.js.map +1 -1
- package/lib/esm/languageservice/services/yamlLinks.js +2 -1
- package/lib/esm/languageservice/services/yamlLinks.js.map +1 -1
- package/lib/esm/languageservice/services/yamlSchemaService.js +12 -0
- package/lib/esm/languageservice/services/yamlSchemaService.js.map +1 -1
- package/lib/esm/languageservice/services/yamlValidation.js +2 -1
- package/lib/esm/languageservice/services/yamlValidation.js.map +1 -1
- package/lib/esm/languageservice/utils/objects.d.ts +5 -0
- package/lib/esm/languageservice/utils/objects.js +13 -0
- package/lib/esm/languageservice/utils/objects.js.map +1 -1
- package/lib/esm/languageservice/utils/schemaUrls.d.ts +1 -1
- package/lib/esm/languageservice/utils/schemaUrls.js +1 -1
- package/lib/esm/languageservice/yamlLanguageService.d.ts +4 -0
- package/lib/esm/languageservice/yamlLanguageService.js +3 -2
- package/lib/esm/languageservice/yamlLanguageService.js.map +1 -1
- package/lib/esm/server.js +5 -0
- package/lib/esm/server.js.map +1 -1
- package/lib/esm/yamlSettings.d.ts +2 -0
- package/lib/esm/yamlSettings.js +1 -0
- package/lib/esm/yamlSettings.js.map +1 -1
- package/lib/umd/languageserver/handlers/settingsHandlers.js +5 -3
- package/lib/umd/languageserver/handlers/settingsHandlers.js.map +1 -1
- package/lib/umd/languageservice/parser/ast-converter.js +9 -1
- package/lib/umd/languageservice/parser/ast-converter.js.map +1 -1
- package/lib/umd/languageservice/parser/jsonParser07.d.ts +2 -2
- package/lib/umd/languageservice/parser/jsonParser07.js +77 -28
- package/lib/umd/languageservice/parser/jsonParser07.js.map +1 -1
- package/lib/umd/languageservice/parser/yaml-documents.d.ts +0 -1
- package/lib/umd/languageservice/parser/yaml-documents.js +10 -10
- package/lib/umd/languageservice/parser/yaml-documents.js.map +1 -1
- package/lib/umd/languageservice/services/documentSymbols.js +4 -3
- package/lib/umd/languageservice/services/documentSymbols.js.map +1 -1
- package/lib/umd/languageservice/services/yamlCodeActions.d.ts +1 -0
- package/lib/umd/languageservice/services/yamlCodeActions.js +14 -0
- package/lib/umd/languageservice/services/yamlCodeActions.js.map +1 -1
- package/lib/umd/languageservice/services/yamlCodeLens.js +3 -2
- package/lib/umd/languageservice/services/yamlCodeLens.js.map +1 -1
- package/lib/umd/languageservice/services/yamlCompletion.d.ts +2 -0
- package/lib/umd/languageservice/services/yamlCompletion.js +182 -39
- package/lib/umd/languageservice/services/yamlCompletion.js.map +1 -1
- package/lib/umd/languageservice/services/yamlDefinition.d.ts +6 -1
- package/lib/umd/languageservice/services/yamlDefinition.js +26 -20
- package/lib/umd/languageservice/services/yamlDefinition.js.map +1 -1
- package/lib/umd/languageservice/services/yamlHover.js +3 -2
- package/lib/umd/languageservice/services/yamlHover.js.map +1 -1
- package/lib/umd/languageservice/services/yamlLinks.js +3 -2
- package/lib/umd/languageservice/services/yamlLinks.js.map +1 -1
- package/lib/umd/languageservice/services/yamlSchemaService.js +12 -0
- package/lib/umd/languageservice/services/yamlSchemaService.js.map +1 -1
- package/lib/umd/languageservice/services/yamlValidation.js +3 -2
- package/lib/umd/languageservice/services/yamlValidation.js.map +1 -1
- package/lib/umd/languageservice/utils/objects.d.ts +5 -0
- package/lib/umd/languageservice/utils/objects.js +15 -1
- package/lib/umd/languageservice/utils/objects.js.map +1 -1
- package/lib/umd/languageservice/utils/schemaUrls.d.ts +1 -1
- package/lib/umd/languageservice/utils/schemaUrls.js +1 -1
- package/lib/umd/languageservice/yamlLanguageService.d.ts +4 -0
- package/lib/umd/languageservice/yamlLanguageService.js +2 -1
- package/lib/umd/languageservice/yamlLanguageService.js.map +1 -1
- package/lib/umd/server.js +6 -1
- package/lib/umd/server.js.map +1 -1
- package/lib/umd/yamlSettings.d.ts +2 -0
- package/lib/umd/yamlSettings.js +1 -0
- package/lib/umd/yamlSettings.js.map +1 -1
- package/out/server/src/languageserver/handlers/settingsHandlers.js +4 -2
- package/out/server/src/languageserver/handlers/settingsHandlers.js.map +1 -1
- package/out/server/src/languageservice/parser/ast-converter.js +9 -1
- package/out/server/src/languageservice/parser/ast-converter.js.map +1 -1
- package/out/server/src/languageservice/parser/jsonParser07.d.ts +2 -2
- package/out/server/src/languageservice/parser/jsonParser07.js +76 -27
- package/out/server/src/languageservice/parser/jsonParser07.js.map +1 -1
- package/out/server/src/languageservice/parser/yaml-documents.d.ts +0 -1
- package/out/server/src/languageservice/parser/yaml-documents.js +10 -10
- package/out/server/src/languageservice/parser/yaml-documents.js.map +1 -1
- package/out/server/src/languageservice/services/documentSymbols.js +3 -2
- package/out/server/src/languageservice/services/documentSymbols.js.map +1 -1
- package/out/server/src/languageservice/services/yamlCodeActions.d.ts +1 -0
- package/out/server/src/languageservice/services/yamlCodeActions.js +14 -0
- package/out/server/src/languageservice/services/yamlCodeActions.js.map +1 -1
- package/out/server/src/languageservice/services/yamlCodeLens.js +2 -1
- package/out/server/src/languageservice/services/yamlCodeLens.js.map +1 -1
- package/out/server/src/languageservice/services/yamlCompletion.d.ts +2 -0
- package/out/server/src/languageservice/services/yamlCompletion.js +181 -38
- package/out/server/src/languageservice/services/yamlCompletion.js.map +1 -1
- package/out/server/src/languageservice/services/yamlDefinition.d.ts +6 -1
- package/out/server/src/languageservice/services/yamlDefinition.js +25 -19
- package/out/server/src/languageservice/services/yamlDefinition.js.map +1 -1
- package/out/server/src/languageservice/services/yamlHover.js +2 -1
- package/out/server/src/languageservice/services/yamlHover.js.map +1 -1
- package/out/server/src/languageservice/services/yamlLinks.js +2 -1
- package/out/server/src/languageservice/services/yamlLinks.js.map +1 -1
- package/out/server/src/languageservice/services/yamlSchemaService.js +12 -0
- package/out/server/src/languageservice/services/yamlSchemaService.js.map +1 -1
- package/out/server/src/languageservice/services/yamlValidation.js +2 -1
- package/out/server/src/languageservice/services/yamlValidation.js.map +1 -1
- package/out/server/src/languageservice/utils/objects.d.ts +5 -0
- package/out/server/src/languageservice/utils/objects.js +15 -1
- package/out/server/src/languageservice/utils/objects.js.map +1 -1
- package/out/server/src/languageservice/utils/schemaUrls.d.ts +1 -1
- package/out/server/src/languageservice/utils/schemaUrls.js +1 -1
- package/out/server/src/languageservice/yamlLanguageService.d.ts +4 -0
- package/out/server/src/languageservice/yamlLanguageService.js +2 -1
- package/out/server/src/languageservice/yamlLanguageService.js.map +1 -1
- package/out/server/src/server.js +5 -0
- package/out/server/src/server.js.map +1 -1
- package/out/server/src/yamlSettings.d.ts +2 -0
- package/out/server/src/yamlSettings.js +1 -0
- package/out/server/src/yamlSettings.js.map +1 -1
- package/out/server/test/autoCompletion.test.js +410 -74
- package/out/server/test/autoCompletion.test.js.map +1 -1
- package/out/server/test/autoCompletionFix.test.js +219 -3
- package/out/server/test/autoCompletionFix.test.js.map +1 -1
- package/out/server/test/code-action-schema.test.d.ts +1 -0
- package/out/server/test/code-action-schema.test.js +99 -0
- package/out/server/test/code-action-schema.test.js.map +1 -0
- package/out/server/test/defaultSnippets.test.js +3 -3
- package/out/server/test/defaultSnippets.test.js.map +1 -1
- package/out/server/test/hover.test.js +70 -0
- package/out/server/test/hover.test.js.map +1 -1
- package/out/server/test/integration.test.js +1 -1
- package/out/server/test/jsonParser.test.js +23 -13
- package/out/server/test/jsonParser.test.js.map +1 -1
- package/out/server/test/objects.test.js +16 -0
- package/out/server/test/objects.test.js.map +1 -1
- package/out/server/test/schema.test.js +18 -0
- package/out/server/test/schema.test.js.map +1 -1
- package/out/server/test/yamlDefinition.test.js +8 -2
- package/out/server/test/yamlDefinition.test.js.map +1 -1
- package/out/server/test/yamlParser.test.js +10 -0
- package/out/server/test/yamlParser.test.js.map +1 -1
- package/out/server/test/yamlSchemaService.test.js +21 -0
- package/out/server/test/yamlSchemaService.test.js.map +1 -1
- package/package.json +8 -6
|
@@ -11,20 +11,22 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
|
|
11
11
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
12
12
|
});
|
|
13
13
|
};
|
|
14
|
-
import { CompletionItem, CompletionItemKind, CompletionList, InsertTextFormat, InsertTextMode, MarkupKind, Range, TextEdit, } from 'vscode-languageserver/node';
|
|
14
|
+
import { CompletionItem as CompletionItemBase, CompletionItemKind, CompletionList, InsertTextFormat, InsertTextMode, MarkupKind, Range, TextEdit, } from 'vscode-languageserver/node';
|
|
15
15
|
import { isPair, isScalar, isMap, isSeq, isNode } from 'yaml';
|
|
16
16
|
import { filterInvalidCustomTags, matchOffsetToDocument } from '../utils/arrUtils';
|
|
17
17
|
import { guessIndentation } from '../utils/indentationGuesser';
|
|
18
18
|
import { TextBuffer } from '../utils/textBuffer';
|
|
19
19
|
import { stringifyObject } from '../utils/json';
|
|
20
|
-
import { isDefined, isString } from '../utils/objects';
|
|
20
|
+
import { convertErrorToTelemetryMsg, isDefined, isString } from '../utils/objects';
|
|
21
21
|
import * as nls from 'vscode-nls';
|
|
22
22
|
import { setKubernetesParserOption } from '../parser/isKubernetes';
|
|
23
23
|
import { isInComment, isMapContainsEmptyPair } from '../utils/astUtils';
|
|
24
24
|
import { indexOf } from '../utils/astUtils';
|
|
25
25
|
import { isModeline } from './modelineUtil';
|
|
26
|
+
import { getSchemaTypeName } from '../utils/schemaUtils';
|
|
26
27
|
const localize = nls.loadMessageBundle();
|
|
27
28
|
const doubleQuotesEscapeRegExp = /[\\]+"/g;
|
|
29
|
+
const parentCompletionKind = CompletionItemKind.Class;
|
|
28
30
|
export class YamlCompletion {
|
|
29
31
|
constructor(schemaService, clientCapabilities = {}, yamlDocument, telemetry) {
|
|
30
32
|
this.schemaService = schemaService;
|
|
@@ -40,6 +42,7 @@ export class YamlCompletion {
|
|
|
40
42
|
this.customTags = languageSettings.customTags;
|
|
41
43
|
this.yamlVersion = languageSettings.yamlVersion;
|
|
42
44
|
this.configuredIndentation = languageSettings.indentation;
|
|
45
|
+
this.disableDefaultProperties = languageSettings.disableDefaultProperties;
|
|
43
46
|
}
|
|
44
47
|
doComplete(document, position, isKubernetes = false) {
|
|
45
48
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -90,8 +93,34 @@ export class YamlCompletion {
|
|
|
90
93
|
overwriteRange = Range.create(document.positionAt(overwriteStart), position);
|
|
91
94
|
}
|
|
92
95
|
const proposed = {};
|
|
96
|
+
const existingProposeItem = '__';
|
|
93
97
|
const collector = {
|
|
94
98
|
add: (completionItem) => {
|
|
99
|
+
const addSuggestionForParent = function (completionItem) {
|
|
100
|
+
var _a;
|
|
101
|
+
const existsInYaml = ((_a = proposed[completionItem.label]) === null || _a === void 0 ? void 0 : _a.label) === existingProposeItem;
|
|
102
|
+
//don't put to parent suggestion if already in yaml
|
|
103
|
+
if (existsInYaml) {
|
|
104
|
+
return;
|
|
105
|
+
}
|
|
106
|
+
const schemaType = completionItem.parent.schemaType;
|
|
107
|
+
let parentCompletion = result.items.find((item) => item.label === schemaType && item.kind === parentCompletionKind);
|
|
108
|
+
if (parentCompletion && parentCompletion.parent.insertTexts.includes(completionItem.insertText)) {
|
|
109
|
+
// already exists in the parent
|
|
110
|
+
return;
|
|
111
|
+
}
|
|
112
|
+
else if (!parentCompletion) {
|
|
113
|
+
// create a new parent
|
|
114
|
+
parentCompletion = Object.assign(Object.assign({}, completionItem), { label: schemaType, sortText: '_' + schemaType, kind: parentCompletionKind });
|
|
115
|
+
parentCompletion.parent.insertTexts = [completionItem.insertText];
|
|
116
|
+
result.items.push(parentCompletion);
|
|
117
|
+
}
|
|
118
|
+
else {
|
|
119
|
+
// add to the existing parent
|
|
120
|
+
parentCompletion.parent.insertTexts.push(completionItem.insertText);
|
|
121
|
+
}
|
|
122
|
+
};
|
|
123
|
+
const isForParentCompletion = !!completionItem.parent;
|
|
95
124
|
let label = completionItem.label;
|
|
96
125
|
if (!label) {
|
|
97
126
|
// we receive not valid CompletionItem as `label` is mandatory field, so just ignore it
|
|
@@ -102,7 +131,7 @@ export class YamlCompletion {
|
|
|
102
131
|
label = String(label);
|
|
103
132
|
}
|
|
104
133
|
const existing = proposed[label];
|
|
105
|
-
if (!existing) {
|
|
134
|
+
if (!existing || isForParentCompletion) {
|
|
106
135
|
label = label.replace(/[\n]/g, '↵');
|
|
107
136
|
if (label.length > 60) {
|
|
108
137
|
const shortendedLabel = label.substr(0, 57).trim() + '...';
|
|
@@ -110,17 +139,28 @@ export class YamlCompletion {
|
|
|
110
139
|
label = shortendedLabel;
|
|
111
140
|
}
|
|
112
141
|
}
|
|
142
|
+
// trim $1 from end of completion
|
|
143
|
+
if (completionItem.insertText.endsWith('$1') && !isForParentCompletion) {
|
|
144
|
+
completionItem.insertText = completionItem.insertText.substr(0, completionItem.insertText.length - 2);
|
|
145
|
+
}
|
|
113
146
|
if (overwriteRange && overwriteRange.start.line === overwriteRange.end.line) {
|
|
114
147
|
completionItem.textEdit = TextEdit.replace(overwriteRange, completionItem.insertText);
|
|
115
148
|
}
|
|
116
149
|
completionItem.label = label;
|
|
117
|
-
|
|
118
|
-
|
|
150
|
+
if (isForParentCompletion) {
|
|
151
|
+
addSuggestionForParent(completionItem);
|
|
152
|
+
}
|
|
153
|
+
if (!existing) {
|
|
154
|
+
proposed[label] = completionItem;
|
|
155
|
+
result.items.push(completionItem);
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
else if (!existing.documentation && completionItem.documentation) {
|
|
159
|
+
existing.documentation = completionItem.documentation;
|
|
119
160
|
}
|
|
120
161
|
},
|
|
121
162
|
error: (message) => {
|
|
122
|
-
|
|
123
|
-
this.telemetry.sendError('yaml.completion.error', { error: message });
|
|
163
|
+
this.telemetry.sendError('yaml.completion.error', { error: convertErrorToTelemetryMsg(message) });
|
|
124
164
|
},
|
|
125
165
|
log: (message) => {
|
|
126
166
|
console.log(message);
|
|
@@ -185,6 +225,7 @@ export class YamlCompletion {
|
|
|
185
225
|
foundByClosest = true;
|
|
186
226
|
}
|
|
187
227
|
}
|
|
228
|
+
const originalNode = node;
|
|
188
229
|
if (node) {
|
|
189
230
|
if (lineContent.length === 0) {
|
|
190
231
|
node = currentDoc.internalDocument.contents;
|
|
@@ -329,11 +370,11 @@ export class YamlCompletion {
|
|
|
329
370
|
for (const p of properties) {
|
|
330
371
|
if (!currentProperty || currentProperty !== p) {
|
|
331
372
|
if (isScalar(p.key)) {
|
|
332
|
-
proposed[p.key.value.toString()] =
|
|
373
|
+
proposed[p.key.value.toString()] = CompletionItemBase.create(existingProposeItem);
|
|
333
374
|
}
|
|
334
375
|
}
|
|
335
376
|
}
|
|
336
|
-
this.addPropertyCompletions(schema, currentDoc, node, '', collector, textBuffer, overwriteRange);
|
|
377
|
+
this.addPropertyCompletions(schema, currentDoc, node, originalNode, '', collector, textBuffer, overwriteRange);
|
|
337
378
|
if (!schema && currentWord.length > 0 && document.getText().charAt(offset - currentWord.length - 1) !== '"') {
|
|
338
379
|
collector.add({
|
|
339
380
|
kind: CompletionItemKind.Property,
|
|
@@ -348,15 +389,54 @@ export class YamlCompletion {
|
|
|
348
389
|
this.getValueCompletions(schema, currentDoc, node, offset, document, collector, types);
|
|
349
390
|
}
|
|
350
391
|
catch (err) {
|
|
351
|
-
|
|
352
|
-
|
|
392
|
+
this.telemetry.sendError('yaml.completion.error', { error: convertErrorToTelemetryMsg(err) });
|
|
393
|
+
}
|
|
394
|
+
this.finalizeParentCompletion(result);
|
|
395
|
+
return result;
|
|
396
|
+
});
|
|
397
|
+
}
|
|
398
|
+
finalizeParentCompletion(result) {
|
|
399
|
+
const reindexText = (insertTexts) => {
|
|
400
|
+
//modify added props to have unique $x
|
|
401
|
+
let max$index = 0;
|
|
402
|
+
return insertTexts.map((text) => {
|
|
403
|
+
const match = text.match(/\$([0-9]+)|\${[0-9]+:/g);
|
|
404
|
+
if (!match) {
|
|
405
|
+
return text;
|
|
353
406
|
}
|
|
354
|
-
|
|
355
|
-
|
|
407
|
+
const max$indexLocal = match
|
|
408
|
+
.map((m) => +m.replace(/\${([0-9]+)[:|]/g, '$1').replace('$', '')) // get numbers form $1 or ${1:...}
|
|
409
|
+
.reduce((p, n) => (n > p ? n : p), 0); // find the max one
|
|
410
|
+
const reindexedStr = text
|
|
411
|
+
.replace(/\$([0-9]+)/g, (s, args) => '$' + (+args + max$index)) // increment each by max$index
|
|
412
|
+
.replace(/\${([0-9]+)[:|]/g, (s, args) => '${' + (+args + max$index) + ':'); // increment each by max$index
|
|
413
|
+
max$index += max$indexLocal;
|
|
414
|
+
return reindexedStr;
|
|
415
|
+
});
|
|
416
|
+
};
|
|
417
|
+
result.items.forEach((completionItem) => {
|
|
418
|
+
if (isParentCompletionItem(completionItem)) {
|
|
419
|
+
const indent = completionItem.parent.indent || '';
|
|
420
|
+
const reindexedTexts = reindexText(completionItem.parent.insertTexts);
|
|
421
|
+
// add indent to each object property and join completion item texts
|
|
422
|
+
let insertText = reindexedTexts.join(`\n${indent}`);
|
|
423
|
+
// trim $1 from end of completion
|
|
424
|
+
if (insertText.endsWith('$1')) {
|
|
425
|
+
insertText = insertText.substring(0, insertText.length - 2);
|
|
426
|
+
}
|
|
427
|
+
completionItem.insertText = insertText;
|
|
428
|
+
if (completionItem.textEdit) {
|
|
429
|
+
completionItem.textEdit.newText = insertText;
|
|
356
430
|
}
|
|
357
|
-
|
|
431
|
+
// remove $x or use {$x:value} in documentation
|
|
432
|
+
const mdText = insertText.replace(/\${[0-9]+[:|](.*)}/g, (s, arg) => arg).replace(/\$([0-9]+)/g, '');
|
|
433
|
+
const originalDocumentation = completionItem.documentation ? [completionItem.documentation, '', '----', ''] : [];
|
|
434
|
+
completionItem.documentation = {
|
|
435
|
+
kind: MarkupKind.Markdown,
|
|
436
|
+
value: [...originalDocumentation, '```yaml', indent + mdText, '```'].join('\n'),
|
|
437
|
+
};
|
|
438
|
+
delete completionItem.parent;
|
|
358
439
|
}
|
|
359
|
-
return result;
|
|
360
440
|
});
|
|
361
441
|
}
|
|
362
442
|
createTempObjNode(currentWord, node, currentDoc) {
|
|
@@ -368,13 +448,18 @@ export class YamlCompletion {
|
|
|
368
448
|
map.items[0].value.range = node.range;
|
|
369
449
|
return map;
|
|
370
450
|
}
|
|
371
|
-
addPropertyCompletions(schema, doc, node, separatorAfter, collector, textBuffer, overwriteRange) {
|
|
451
|
+
addPropertyCompletions(schema, doc, node, originalNode, separatorAfter, collector, textBuffer, overwriteRange) {
|
|
452
|
+
var _a;
|
|
372
453
|
const matchingSchemas = doc.getMatchingSchemas(schema.schema);
|
|
373
454
|
const existingKey = textBuffer.getText(overwriteRange);
|
|
374
|
-
const
|
|
455
|
+
const lineContent = textBuffer.getLineContent(overwriteRange.start.line);
|
|
456
|
+
const hasOnlyWhitespace = lineContent.trim().length === 0;
|
|
457
|
+
const hasColon = lineContent.indexOf(':') !== -1;
|
|
375
458
|
const nodeParent = doc.getParent(node);
|
|
459
|
+
const matchOriginal = matchingSchemas.find((it) => it.node.internalNode === originalNode && it.schema.properties);
|
|
376
460
|
for (const schema of matchingSchemas) {
|
|
377
|
-
if (schema.node.internalNode === node && !schema.
|
|
461
|
+
if (((schema.node.internalNode === node && !matchOriginal) || schema.node.internalNode === originalNode) &&
|
|
462
|
+
!schema.inverted) {
|
|
378
463
|
this.collectDefaultSnippets(schema.schema, separatorAfter, collector, {
|
|
379
464
|
newLineFirst: false,
|
|
380
465
|
indentFirstObject: false,
|
|
@@ -386,13 +471,13 @@ export class YamlCompletion {
|
|
|
386
471
|
if (maxProperties === undefined ||
|
|
387
472
|
node.items === undefined ||
|
|
388
473
|
node.items.length < maxProperties ||
|
|
389
|
-
|
|
474
|
+
(node.items.length === maxProperties && !hasOnlyWhitespace)) {
|
|
390
475
|
for (const key in schemaProperties) {
|
|
391
476
|
if (Object.prototype.hasOwnProperty.call(schemaProperties, key)) {
|
|
392
477
|
const propertySchema = schemaProperties[key];
|
|
393
478
|
if (typeof propertySchema === 'object' && !propertySchema.deprecationMessage && !propertySchema['doNotSuggest']) {
|
|
394
479
|
let identCompensation = '';
|
|
395
|
-
if (nodeParent && isSeq(nodeParent) && node.items.length <= 1) {
|
|
480
|
+
if (nodeParent && isSeq(nodeParent) && node.items.length <= 1 && !hasOnlyWhitespace) {
|
|
396
481
|
// because there is a slash '-' to prevent the properties generated to have the correct
|
|
397
482
|
// indent
|
|
398
483
|
const sourceText = textBuffer.getText();
|
|
@@ -417,17 +502,19 @@ export class YamlCompletion {
|
|
|
417
502
|
this.addSchemaValueCompletions(propertySchema.items[0], separatorAfter, collector, {});
|
|
418
503
|
}
|
|
419
504
|
else if (typeof propertySchema.items === 'object' && propertySchema.items.type === 'object') {
|
|
505
|
+
const insertText = `- ${this.getInsertTextForObject(propertySchema.items, separatorAfter, ' ').insertText.trimLeft()}`;
|
|
506
|
+
const documentation = this.getDocumentationWithMarkdownText(`Create an item of an array${propertySchema.description ? ' (' + propertySchema.description + ')' : ''}`, insertText);
|
|
420
507
|
collector.add({
|
|
421
508
|
kind: this.getSuggestionKind(propertySchema.items.type),
|
|
422
509
|
label: '- (array item)',
|
|
423
|
-
documentation
|
|
424
|
-
insertText
|
|
510
|
+
documentation,
|
|
511
|
+
insertText,
|
|
425
512
|
insertTextFormat: InsertTextFormat.Snippet,
|
|
426
513
|
});
|
|
427
514
|
}
|
|
428
515
|
}
|
|
429
516
|
let insertText = key;
|
|
430
|
-
if (!key.startsWith(existingKey) ||
|
|
517
|
+
if (!key.startsWith(existingKey) || !hasColon) {
|
|
431
518
|
insertText = this.getInsertTextForProperty(key, propertySchema, separatorAfter, identCompensation + this.indentation);
|
|
432
519
|
}
|
|
433
520
|
collector.add({
|
|
@@ -437,6 +524,20 @@ export class YamlCompletion {
|
|
|
437
524
|
insertTextFormat: InsertTextFormat.Snippet,
|
|
438
525
|
documentation: this.fromMarkup(propertySchema.markdownDescription) || propertySchema.description || '',
|
|
439
526
|
});
|
|
527
|
+
// if the prop is required add it also to parent suggestion
|
|
528
|
+
if ((_a = schema.schema.required) === null || _a === void 0 ? void 0 : _a.includes(key)) {
|
|
529
|
+
const schemaType = getSchemaTypeName(schema.schema);
|
|
530
|
+
collector.add({
|
|
531
|
+
label: key,
|
|
532
|
+
insertText: this.getInsertTextForProperty(key, propertySchema, separatorAfter, identCompensation + this.indentation),
|
|
533
|
+
insertTextFormat: InsertTextFormat.Snippet,
|
|
534
|
+
documentation: this.fromMarkup(propertySchema.markdownDescription) || propertySchema.description || '',
|
|
535
|
+
parent: {
|
|
536
|
+
schemaType,
|
|
537
|
+
indent: identCompensation,
|
|
538
|
+
},
|
|
539
|
+
});
|
|
540
|
+
}
|
|
440
541
|
}
|
|
441
542
|
}
|
|
442
543
|
}
|
|
@@ -507,11 +608,13 @@ export class YamlCompletion {
|
|
|
507
608
|
}
|
|
508
609
|
}
|
|
509
610
|
else if (typeof s.schema.items === 'object' && s.schema.items.type === 'object') {
|
|
611
|
+
const insertText = `- ${this.getInsertTextForObject(s.schema.items, separatorAfter, ' ').insertText.trimLeft()}`;
|
|
612
|
+
const documentation = this.getDocumentationWithMarkdownText(`Create an item of an array${s.schema.description ? ' (' + s.schema.description + ')' : ''}`, insertText);
|
|
510
613
|
collector.add({
|
|
511
614
|
kind: this.getSuggestionKind(s.schema.items.type),
|
|
512
615
|
label: '- (array item)',
|
|
513
|
-
documentation
|
|
514
|
-
insertText
|
|
616
|
+
documentation,
|
|
617
|
+
insertText,
|
|
515
618
|
insertTextFormat: InsertTextFormat.Snippet,
|
|
516
619
|
});
|
|
517
620
|
this.addSchemaValueCompletions(s.schema.items, separatorAfter, collector, types);
|
|
@@ -520,12 +623,15 @@ export class YamlCompletion {
|
|
|
520
623
|
s.schema.items.anyOf
|
|
521
624
|
.filter((i) => typeof i === 'object')
|
|
522
625
|
.forEach((i, index) => {
|
|
626
|
+
const schemaType = getSchemaTypeName(i);
|
|
523
627
|
const insertText = `- ${this.getInsertTextForObject(i, separatorAfter).insertText.trimLeft()}`;
|
|
524
628
|
//append insertText to documentation
|
|
525
|
-
const
|
|
629
|
+
const schemaTypeTitle = schemaType ? ' type `' + schemaType + '`' : '';
|
|
630
|
+
const schemaDescription = s.schema.description ? ' (' + s.schema.description + ')' : '';
|
|
631
|
+
const documentation = this.getDocumentationWithMarkdownText(`Create an item of an array${schemaTypeTitle}${schemaDescription}`, insertText);
|
|
526
632
|
collector.add({
|
|
527
633
|
kind: this.getSuggestionKind(i.type),
|
|
528
|
-
label: '- (array item) ' + (index + 1),
|
|
634
|
+
label: '- (array item) ' + (schemaType || index + 1),
|
|
529
635
|
documentation: documentation,
|
|
530
636
|
insertText: insertText,
|
|
531
637
|
insertTextFormat: InsertTextFormat.Snippet,
|
|
@@ -555,7 +661,7 @@ export class YamlCompletion {
|
|
|
555
661
|
}
|
|
556
662
|
}
|
|
557
663
|
}
|
|
558
|
-
getInsertTextForProperty(key, propertySchema, separatorAfter,
|
|
664
|
+
getInsertTextForProperty(key, propertySchema, separatorAfter, indent = this.indentation) {
|
|
559
665
|
const propertyText = this.getInsertTextForValue(key, '', 'string');
|
|
560
666
|
const resultText = propertyText + ':';
|
|
561
667
|
let value;
|
|
@@ -569,6 +675,9 @@ export class YamlCompletion {
|
|
|
569
675
|
else if (propertySchema.items) {
|
|
570
676
|
type = 'array';
|
|
571
677
|
}
|
|
678
|
+
else if (propertySchema.anyOf) {
|
|
679
|
+
type = 'anyOf';
|
|
680
|
+
}
|
|
572
681
|
}
|
|
573
682
|
if (Array.isArray(propertySchema.defaultSnippets)) {
|
|
574
683
|
if (propertySchema.defaultSnippets.length === 1) {
|
|
@@ -593,6 +702,14 @@ export class YamlCompletion {
|
|
|
593
702
|
}
|
|
594
703
|
nValueProposals += propertySchema.enum.length;
|
|
595
704
|
}
|
|
705
|
+
if (propertySchema.const) {
|
|
706
|
+
if (!value) {
|
|
707
|
+
value = this.getInsertTextForGuessedValue(propertySchema.const, '', type);
|
|
708
|
+
value = evaluateTab1Symbol(value); // prevent const being selected after snippet insert
|
|
709
|
+
value = ' ' + value;
|
|
710
|
+
}
|
|
711
|
+
nValueProposals++;
|
|
712
|
+
}
|
|
596
713
|
if (isDefined(propertySchema.default)) {
|
|
597
714
|
if (!value) {
|
|
598
715
|
value = ' ' + this.getInsertTextForGuessedValue(propertySchema.default, '', type);
|
|
@@ -606,10 +723,10 @@ export class YamlCompletion {
|
|
|
606
723
|
nValueProposals += propertySchema.examples.length;
|
|
607
724
|
}
|
|
608
725
|
if (propertySchema.properties) {
|
|
609
|
-
return `${resultText}\n${this.getInsertTextForObject(propertySchema, separatorAfter,
|
|
726
|
+
return `${resultText}\n${this.getInsertTextForObject(propertySchema, separatorAfter, indent).insertText}`;
|
|
610
727
|
}
|
|
611
728
|
else if (propertySchema.items) {
|
|
612
|
-
return `${resultText}\n${
|
|
729
|
+
return `${resultText}\n${indent}- ${this.getInsertTextForArray(propertySchema.items, separatorAfter, 1, indent).insertText}`;
|
|
613
730
|
}
|
|
614
731
|
if (nValueProposals === 0) {
|
|
615
732
|
switch (type) {
|
|
@@ -620,10 +737,10 @@ export class YamlCompletion {
|
|
|
620
737
|
value = ' $1';
|
|
621
738
|
break;
|
|
622
739
|
case 'object':
|
|
623
|
-
value = `\n${
|
|
740
|
+
value = `\n${indent}`;
|
|
624
741
|
break;
|
|
625
742
|
case 'array':
|
|
626
|
-
value = `\n${
|
|
743
|
+
value = `\n${indent}- `;
|
|
627
744
|
break;
|
|
628
745
|
case 'number':
|
|
629
746
|
case 'integer':
|
|
@@ -632,6 +749,9 @@ export class YamlCompletion {
|
|
|
632
749
|
case 'null':
|
|
633
750
|
value = ' ${1:null}';
|
|
634
751
|
break;
|
|
752
|
+
case 'anyOf':
|
|
753
|
+
value = ' $1';
|
|
754
|
+
break;
|
|
635
755
|
default:
|
|
636
756
|
return propertyText;
|
|
637
757
|
}
|
|
@@ -652,6 +772,9 @@ export class YamlCompletion {
|
|
|
652
772
|
const propertySchema = schema.properties[key];
|
|
653
773
|
let type = Array.isArray(propertySchema.type) ? propertySchema.type[0] : propertySchema.type;
|
|
654
774
|
if (!type) {
|
|
775
|
+
if (propertySchema.anyOf) {
|
|
776
|
+
type = 'anyOf';
|
|
777
|
+
}
|
|
655
778
|
if (propertySchema.properties) {
|
|
656
779
|
type = 'object';
|
|
657
780
|
}
|
|
@@ -665,11 +788,22 @@ export class YamlCompletion {
|
|
|
665
788
|
case 'string':
|
|
666
789
|
case 'number':
|
|
667
790
|
case 'integer':
|
|
668
|
-
|
|
791
|
+
case 'anyOf': {
|
|
792
|
+
let value = propertySchema.default || propertySchema.const;
|
|
793
|
+
if (value) {
|
|
794
|
+
if (type === 'string') {
|
|
795
|
+
value = convertToStringValue(value);
|
|
796
|
+
}
|
|
797
|
+
insertText += `${indent}${key}: \${${insertIndex++}:${value}}\n`;
|
|
798
|
+
}
|
|
799
|
+
else {
|
|
800
|
+
insertText += `${indent}${key}: $${insertIndex++}\n`;
|
|
801
|
+
}
|
|
669
802
|
break;
|
|
803
|
+
}
|
|
670
804
|
case 'array':
|
|
671
805
|
{
|
|
672
|
-
const arrayInsertResult = this.getInsertTextForArray(propertySchema.items, separatorAfter, insertIndex
|
|
806
|
+
const arrayInsertResult = this.getInsertTextForArray(propertySchema.items, separatorAfter, insertIndex++, indent);
|
|
673
807
|
const arrayInsertLines = arrayInsertResult.insertText.split('\n');
|
|
674
808
|
let arrayTemplate = arrayInsertResult.insertText;
|
|
675
809
|
if (arrayInsertLines.length > 1) {
|
|
@@ -692,7 +826,7 @@ export class YamlCompletion {
|
|
|
692
826
|
break;
|
|
693
827
|
}
|
|
694
828
|
}
|
|
695
|
-
else if (propertySchema.default !== undefined) {
|
|
829
|
+
else if (!this.disableDefaultProperties && propertySchema.default !== undefined) {
|
|
696
830
|
switch (type) {
|
|
697
831
|
case 'boolean':
|
|
698
832
|
case 'number':
|
|
@@ -716,7 +850,7 @@ export class YamlCompletion {
|
|
|
716
850
|
return { insertText, insertIndex };
|
|
717
851
|
}
|
|
718
852
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
719
|
-
getInsertTextForArray(schema, separatorAfter, insertIndex = 1) {
|
|
853
|
+
getInsertTextForArray(schema, separatorAfter, insertIndex = 1, indent = this.indentation) {
|
|
720
854
|
let insertText = '';
|
|
721
855
|
if (!schema) {
|
|
722
856
|
insertText = `$${insertIndex++}`;
|
|
@@ -744,7 +878,7 @@ export class YamlCompletion {
|
|
|
744
878
|
break;
|
|
745
879
|
case 'object':
|
|
746
880
|
{
|
|
747
|
-
const objectInsertResult = this.getInsertTextForObject(schema, separatorAfter, `${
|
|
881
|
+
const objectInsertResult = this.getInsertTextForObject(schema, separatorAfter, `${indent} `, insertIndex++);
|
|
748
882
|
insertText = objectInsertResult.insertText.trimLeft();
|
|
749
883
|
insertIndex = objectInsertResult.insertIndex;
|
|
750
884
|
}
|
|
@@ -915,7 +1049,7 @@ export class YamlCompletion {
|
|
|
915
1049
|
collector.add({
|
|
916
1050
|
kind: this.getSuggestionKind(schema.type),
|
|
917
1051
|
label: this.getLabelForValue(schema.const),
|
|
918
|
-
insertText: this.getInsertTextForValue(schema.const, separatorAfter,
|
|
1052
|
+
insertText: this.getInsertTextForValue(schema.const, separatorAfter, schema.type),
|
|
919
1053
|
insertTextFormat: InsertTextFormat.Snippet,
|
|
920
1054
|
documentation: this.fromMarkup(schema.markdownDescription) || schema.description,
|
|
921
1055
|
});
|
|
@@ -1140,8 +1274,7 @@ function convertToStringValue(value) {
|
|
|
1140
1274
|
if (value === 'true' || value === 'false' || value === 'null' || isNumberExp.test(value)) {
|
|
1141
1275
|
return `"${value}"`;
|
|
1142
1276
|
}
|
|
1143
|
-
|
|
1144
|
-
if (value.indexOf('\"') !== -1) {
|
|
1277
|
+
if (value.indexOf('"') !== -1) {
|
|
1145
1278
|
value = value.replace(doubleQuotesEscapeRegExp, '"');
|
|
1146
1279
|
}
|
|
1147
1280
|
let doQuote = value.charAt(0) === '@';
|
|
@@ -1169,4 +1302,14 @@ function convertToStringValue(value) {
|
|
|
1169
1302
|
}
|
|
1170
1303
|
return value;
|
|
1171
1304
|
}
|
|
1305
|
+
/**
|
|
1306
|
+
* simplify `{$1:value}` to `value`
|
|
1307
|
+
*/
|
|
1308
|
+
function evaluateTab1Symbol(value) {
|
|
1309
|
+
const result = value.replace(/\$\{1:(.*)\}/, '$1');
|
|
1310
|
+
return result;
|
|
1311
|
+
}
|
|
1312
|
+
function isParentCompletionItem(item) {
|
|
1313
|
+
return 'parent' in item;
|
|
1314
|
+
}
|
|
1172
1315
|
//# sourceMappingURL=yamlCompletion.js.map
|