vscode-json-languageservice 5.3.2 → 5.3.4

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.
@@ -244,6 +244,11 @@ export interface ClientCapabilities {
244
244
  * The client supports commit characters on a completion item.
245
245
  */
246
246
  commitCharactersSupport?: boolean;
247
+ /**
248
+ * The client has support for completion item label
249
+ * details (see also `CompletionItemLabelDetails`).
250
+ */
251
+ labelDetailsSupport?: boolean;
247
252
  };
248
253
  };
249
254
  /**
@@ -47,7 +47,8 @@ export var ClientCapabilities;
47
47
  completion: {
48
48
  completionItem: {
49
49
  documentationFormat: [MarkupKind.Markdown, MarkupKind.PlainText],
50
- commitCharactersSupport: true
50
+ commitCharactersSupport: true,
51
+ labelDetailsSupport: true
51
52
  }
52
53
  }
53
54
  }
@@ -91,6 +91,9 @@ export class JSONCompletion {
91
91
  if (!existing.detail) {
92
92
  existing.detail = suggestion.detail;
93
93
  }
94
+ if (!existing.labelDetails) {
95
+ existing.labelDetails = suggestion.labelDetails;
96
+ }
94
97
  }
95
98
  },
96
99
  setAsIncomplete: () => {
@@ -404,14 +407,26 @@ export class JSONCompletion {
404
407
  for (const s of matchingSchemas) {
405
408
  if (s.node === node && !s.inverted && s.schema) {
406
409
  if (node.type === 'array' && s.schema.items) {
410
+ const arrayValues = Parser.getNodeValue(node);
411
+ const self = this;
412
+ const filteringCollector = {
413
+ ...collector,
414
+ add(suggestion) {
415
+ const value = self.getValueFromLabel(suggestion.label);
416
+ if (s.schema.uniqueItems === true && arrayValues.includes(value)) {
417
+ return;
418
+ }
419
+ collector.add(suggestion);
420
+ },
421
+ };
407
422
  if (Array.isArray(s.schema.items)) {
408
423
  const index = this.findItemAtOffset(node, document, offset);
409
424
  if (index < s.schema.items.length) {
410
- this.addSchemaValueCompletions(s.schema.items[index], separatorAfter, collector, types);
425
+ this.addSchemaValueCompletions(s.schema.items[index], separatorAfter, filteringCollector, types);
411
426
  }
412
427
  }
413
428
  else {
414
- this.addSchemaValueCompletions(s.schema.items, separatorAfter, collector, types);
429
+ this.addSchemaValueCompletions(s.schema.items, separatorAfter, filteringCollector, types);
415
430
  }
416
431
  }
417
432
  if (parentKey !== undefined) {
@@ -505,13 +520,19 @@ export class JSONCompletion {
505
520
  value = [value];
506
521
  type = 'array';
507
522
  }
508
- collector.add({
523
+ const completionItem = {
509
524
  kind: this.getSuggestionKind(type),
510
525
  label: this.getLabelForValue(value),
511
526
  insertText: this.getInsertTextForValue(value, separatorAfter),
512
- insertTextFormat: InsertTextFormat.Snippet,
513
- detail: l10n.t('Default value')
514
- });
527
+ insertTextFormat: InsertTextFormat.Snippet
528
+ };
529
+ if (this.doesSupportsLabelDetails()) {
530
+ completionItem.labelDetails = { description: l10n.t('Default value') };
531
+ }
532
+ else {
533
+ completionItem.detail = l10n.t('Default value');
534
+ }
535
+ collector.add(completionItem);
515
536
  hasProposals = true;
516
537
  }
517
538
  if (Array.isArray(schema.examples)) {
@@ -673,6 +694,9 @@ export class JSONCompletion {
673
694
  getLabelForValue(value) {
674
695
  return JSON.stringify(value);
675
696
  }
697
+ getValueFromLabel(value) {
698
+ return JSON.parse(value);
699
+ }
676
700
  getFilterTextForValue(value) {
677
701
  return JSON.stringify(value);
678
702
  }
@@ -684,7 +708,7 @@ export class JSONCompletion {
684
708
  return label.replace(/\$\{\d+:([^}]+)\}|\$\d+/g, '$1');
685
709
  }
686
710
  getInsertTextForPlainText(text) {
687
- return text.replace(/[\\\$\}]/g, '\\$&'); // escape $, \ and }
711
+ return text.replace(/[\\\$\}]/g, '\\$&'); // escape $, \ and }
688
712
  }
689
713
  getInsertTextForValue(value, separatorAfter) {
690
714
  const text = JSON.stringify(value, null, '\t');
@@ -905,16 +929,21 @@ export class JSONCompletion {
905
929
  }
906
930
  doesSupportMarkdown() {
907
931
  if (!isDefined(this.supportsMarkdown)) {
908
- const completion = this.clientCapabilities.textDocument && this.clientCapabilities.textDocument.completion;
909
- this.supportsMarkdown = completion && completion.completionItem && Array.isArray(completion.completionItem.documentationFormat) && completion.completionItem.documentationFormat.indexOf(MarkupKind.Markdown) !== -1;
932
+ const documentationFormat = this.clientCapabilities.textDocument?.completion?.completionItem?.documentationFormat;
933
+ this.supportsMarkdown = Array.isArray(documentationFormat) && documentationFormat.indexOf(MarkupKind.Markdown) !== -1;
910
934
  }
911
935
  return this.supportsMarkdown;
912
936
  }
913
937
  doesSupportsCommitCharacters() {
914
938
  if (!isDefined(this.supportsCommitCharacters)) {
915
- const completion = this.clientCapabilities.textDocument && this.clientCapabilities.textDocument.completion;
916
- this.supportsCommitCharacters = completion && completion.completionItem && !!completion.completionItem.commitCharactersSupport;
939
+ this.labelDetailsSupport = this.clientCapabilities.textDocument?.completion?.completionItem?.commitCharactersSupport;
917
940
  }
918
941
  return this.supportsCommitCharacters;
919
942
  }
943
+ doesSupportsLabelDetails() {
944
+ if (!isDefined(this.labelDetailsSupport)) {
945
+ this.labelDetailsSupport = this.clientCapabilities.textDocument?.completion?.completionItem?.labelDetailsSupport;
946
+ }
947
+ return this.labelDetailsSupport;
948
+ }
920
949
  }
@@ -244,6 +244,11 @@ export interface ClientCapabilities {
244
244
  * The client supports commit characters on a completion item.
245
245
  */
246
246
  commitCharactersSupport?: boolean;
247
+ /**
248
+ * The client has support for completion item label
249
+ * details (see also `CompletionItemLabelDetails`).
250
+ */
251
+ labelDetailsSupport?: boolean;
247
252
  };
248
253
  };
249
254
  /**
@@ -94,7 +94,8 @@
94
94
  completion: {
95
95
  completionItem: {
96
96
  documentationFormat: [vscode_languageserver_types_1.MarkupKind.Markdown, vscode_languageserver_types_1.MarkupKind.PlainText],
97
- commitCharactersSupport: true
97
+ commitCharactersSupport: true,
98
+ labelDetailsSupport: true
98
99
  }
99
100
  }
100
101
  }
@@ -103,6 +103,9 @@
103
103
  if (!existing.detail) {
104
104
  existing.detail = suggestion.detail;
105
105
  }
106
+ if (!existing.labelDetails) {
107
+ existing.labelDetails = suggestion.labelDetails;
108
+ }
106
109
  }
107
110
  },
108
111
  setAsIncomplete: () => {
@@ -416,14 +419,26 @@
416
419
  for (const s of matchingSchemas) {
417
420
  if (s.node === node && !s.inverted && s.schema) {
418
421
  if (node.type === 'array' && s.schema.items) {
422
+ const arrayValues = Parser.getNodeValue(node);
423
+ const self = this;
424
+ const filteringCollector = {
425
+ ...collector,
426
+ add(suggestion) {
427
+ const value = self.getValueFromLabel(suggestion.label);
428
+ if (s.schema.uniqueItems === true && arrayValues.includes(value)) {
429
+ return;
430
+ }
431
+ collector.add(suggestion);
432
+ },
433
+ };
419
434
  if (Array.isArray(s.schema.items)) {
420
435
  const index = this.findItemAtOffset(node, document, offset);
421
436
  if (index < s.schema.items.length) {
422
- this.addSchemaValueCompletions(s.schema.items[index], separatorAfter, collector, types);
437
+ this.addSchemaValueCompletions(s.schema.items[index], separatorAfter, filteringCollector, types);
423
438
  }
424
439
  }
425
440
  else {
426
- this.addSchemaValueCompletions(s.schema.items, separatorAfter, collector, types);
441
+ this.addSchemaValueCompletions(s.schema.items, separatorAfter, filteringCollector, types);
427
442
  }
428
443
  }
429
444
  if (parentKey !== undefined) {
@@ -517,13 +532,19 @@
517
532
  value = [value];
518
533
  type = 'array';
519
534
  }
520
- collector.add({
535
+ const completionItem = {
521
536
  kind: this.getSuggestionKind(type),
522
537
  label: this.getLabelForValue(value),
523
538
  insertText: this.getInsertTextForValue(value, separatorAfter),
524
- insertTextFormat: jsonLanguageTypes_1.InsertTextFormat.Snippet,
525
- detail: l10n.t('Default value')
526
- });
539
+ insertTextFormat: jsonLanguageTypes_1.InsertTextFormat.Snippet
540
+ };
541
+ if (this.doesSupportsLabelDetails()) {
542
+ completionItem.labelDetails = { description: l10n.t('Default value') };
543
+ }
544
+ else {
545
+ completionItem.detail = l10n.t('Default value');
546
+ }
547
+ collector.add(completionItem);
527
548
  hasProposals = true;
528
549
  }
529
550
  if (Array.isArray(schema.examples)) {
@@ -685,6 +706,9 @@
685
706
  getLabelForValue(value) {
686
707
  return JSON.stringify(value);
687
708
  }
709
+ getValueFromLabel(value) {
710
+ return JSON.parse(value);
711
+ }
688
712
  getFilterTextForValue(value) {
689
713
  return JSON.stringify(value);
690
714
  }
@@ -696,7 +720,7 @@
696
720
  return label.replace(/\$\{\d+:([^}]+)\}|\$\d+/g, '$1');
697
721
  }
698
722
  getInsertTextForPlainText(text) {
699
- return text.replace(/[\\\$\}]/g, '\\$&'); // escape $, \ and }
723
+ return text.replace(/[\\\$\}]/g, '\\$&'); // escape $, \ and }
700
724
  }
701
725
  getInsertTextForValue(value, separatorAfter) {
702
726
  const text = JSON.stringify(value, null, '\t');
@@ -917,18 +941,23 @@
917
941
  }
918
942
  doesSupportMarkdown() {
919
943
  if (!(0, objects_1.isDefined)(this.supportsMarkdown)) {
920
- const completion = this.clientCapabilities.textDocument && this.clientCapabilities.textDocument.completion;
921
- this.supportsMarkdown = completion && completion.completionItem && Array.isArray(completion.completionItem.documentationFormat) && completion.completionItem.documentationFormat.indexOf(jsonLanguageTypes_1.MarkupKind.Markdown) !== -1;
944
+ const documentationFormat = this.clientCapabilities.textDocument?.completion?.completionItem?.documentationFormat;
945
+ this.supportsMarkdown = Array.isArray(documentationFormat) && documentationFormat.indexOf(jsonLanguageTypes_1.MarkupKind.Markdown) !== -1;
922
946
  }
923
947
  return this.supportsMarkdown;
924
948
  }
925
949
  doesSupportsCommitCharacters() {
926
950
  if (!(0, objects_1.isDefined)(this.supportsCommitCharacters)) {
927
- const completion = this.clientCapabilities.textDocument && this.clientCapabilities.textDocument.completion;
928
- this.supportsCommitCharacters = completion && completion.completionItem && !!completion.completionItem.commitCharactersSupport;
951
+ this.labelDetailsSupport = this.clientCapabilities.textDocument?.completion?.completionItem?.commitCharactersSupport;
929
952
  }
930
953
  return this.supportsCommitCharacters;
931
954
  }
955
+ doesSupportsLabelDetails() {
956
+ if (!(0, objects_1.isDefined)(this.labelDetailsSupport)) {
957
+ this.labelDetailsSupport = this.clientCapabilities.textDocument?.completion?.completionItem?.labelDetailsSupport;
958
+ }
959
+ return this.labelDetailsSupport;
960
+ }
932
961
  }
933
962
  exports.JSONCompletion = JSONCompletion;
934
963
  });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "vscode-json-languageservice",
3
- "version": "5.3.2",
3
+ "version": "5.3.4",
4
4
  "description": "Language service for JSON",
5
5
  "main": "./lib/umd/jsonLanguageService.js",
6
6
  "typings": "./lib/umd/jsonLanguageService",
@@ -17,20 +17,20 @@
17
17
  "devDependencies": {
18
18
  "@types/mocha": "^10.0.1",
19
19
  "@types/node": "16.x",
20
- "@typescript-eslint/eslint-plugin": "^5.52.0",
21
- "@typescript-eslint/parser": "^5.52.0",
22
- "eslint": "^8.34.0",
20
+ "@typescript-eslint/eslint-plugin": "^5.59.1",
21
+ "@typescript-eslint/parser": "^5.59.1",
22
+ "eslint": "^8.39.0",
23
23
  "json-schema-test-suite": "https://github.com/json-schema-org/JSON-Schema-Test-Suite.git#69acf52990b004240839ae19b4bec8fb01d50876",
24
24
  "mocha": "^10.2.0",
25
- "rimraf": "^4.1.2",
26
- "typescript": "^4.9.5"
25
+ "rimraf": "^5.0.0",
26
+ "typescript": "^5.0.4"
27
27
  },
28
28
  "dependencies": {
29
29
  "jsonc-parser": "^3.2.0",
30
30
  "vscode-languageserver-textdocument": "^1.0.8",
31
31
  "vscode-languageserver-types": "^3.17.3",
32
32
  "vscode-uri": "^3.0.7",
33
- "@vscode/l10n": "^0.0.11"
33
+ "@vscode/l10n": "^0.0.13"
34
34
  },
35
35
  "scripts": {
36
36
  "prepack": "npm run clean && npm run compile-esm && npm run test && npm run remove-sourcemap-refs",