Skip to content

Commit 7140d70

Browse files
authored
prepare 5.7.1, add DiagnosticRelatedInformation (#303)
1 parent b37efb6 commit 7140d70

File tree

5 files changed

+36
-22
lines changed

5 files changed

+36
-22
lines changed

package-lock.json

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "vscode-json-languageservice",
3-
"version": "5.7.0",
3+
"version": "5.7.1",
44
"description": "Language service for JSON",
55
"main": "./lib/umd/jsonLanguageService.js",
66
"typings": "./lib/umd/jsonLanguageService",

src/services/jsonSchemaService.ts

Lines changed: 18 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import { SchemaRequestService, WorkspaceContextService, PromiseConstructor, Matc
1313
import * as l10n from '@vscode/l10n';
1414
import { createRegex } from '../utils/glob';
1515
import { isObject, isString } from '../utils/objects';
16+
import { DiagnosticRelatedInformation, Range } from 'vscode-languageserver-types';
1617

1718
export interface IJSONSchemaService {
1819

@@ -180,19 +181,23 @@ class SchemaHandle implements ISchemaHandle {
180181

181182

182183
export class UnresolvedSchema {
183-
public schema: JSONSchema;
184-
public errors: SchemaDiagnostic[];
184+
public readonly schema: JSONSchema;
185+
public readonly errors: SchemaDiagnostic[];
185186

186187
constructor(schema: JSONSchema, errors: SchemaDiagnostic[] = []) {
187188
this.schema = schema;
188189
this.errors = errors;
189190
}
190191
}
191192

192-
export type SchemaDiagnostic = { message: string; code: ErrorCode }
193+
export type SchemaDiagnostic = { readonly message: string; readonly code: ErrorCode; relatedInformation?: DiagnosticRelatedInformation[] }
193194

194-
function toDiagnostic(message: string, code: ErrorCode): SchemaDiagnostic {
195-
return { message, code };
195+
function toDiagnostic(message: string, code: ErrorCode, relatedURL?: string): SchemaDiagnostic {
196+
const relatedInformation: DiagnosticRelatedInformation[] | undefined = relatedURL ? [{
197+
location: { uri: relatedURL, range: Range.create(0, 0, 0, 0) },
198+
message
199+
}] : undefined;
200+
return { message, code, relatedInformation };
196201
}
197202

198203
export class ResolvedSchema {
@@ -394,25 +399,25 @@ export class JSONSchemaService implements IJSONSchemaService {
394399
public loadSchema(url: string): PromiseLike<UnresolvedSchema> {
395400
if (!this.requestService) {
396401
const errorMessage = l10n.t('Unable to load schema from \'{0}\'. No schema request service available', toDisplayString(url));
397-
return this.promise.resolve(new UnresolvedSchema(<JSONSchema>{}, [toDiagnostic(errorMessage, ErrorCode.SchemaResolveError)]));
402+
return this.promise.resolve(new UnresolvedSchema(<JSONSchema>{}, [toDiagnostic(errorMessage, ErrorCode.SchemaResolveError, url)]));
398403
}
399404
return this.requestService(url).then(
400405
content => {
401406
if (!content) {
402407
const errorMessage = l10n.t('Unable to load schema from \'{0}\': No content.', toDisplayString(url));
403-
return new UnresolvedSchema(<JSONSchema>{}, [toDiagnostic(errorMessage, ErrorCode.SchemaResolveError)]);
408+
return new UnresolvedSchema(<JSONSchema>{}, [toDiagnostic(errorMessage, ErrorCode.SchemaResolveError, url)]);
404409
}
405410
const errors = [];
406411
if (content.charCodeAt(0) === 65279) {
407-
errors.push(toDiagnostic(l10n.t('Problem reading content from \'{0}\': UTF-8 with BOM detected, only UTF 8 is allowed.', toDisplayString(url)), ErrorCode.SchemaResolveError));
412+
errors.push(toDiagnostic(l10n.t('Problem reading content from \'{0}\': UTF-8 with BOM detected, only UTF 8 is allowed.', toDisplayString(url)), ErrorCode.SchemaResolveError, url));
408413
content = content.trimStart();
409414
}
410415

411416
let schemaContent: JSONSchema = {};
412417
const jsonErrors: Json.ParseError[] = [];
413418
schemaContent = Json.parse(content, jsonErrors);
414419
if (jsonErrors.length) {
415-
errors.push(toDiagnostic(l10n.t('Unable to parse content from \'{0}\': Parse error at offset {1}.', toDisplayString(url), jsonErrors[0].offset), ErrorCode.SchemaResolveError));
420+
errors.push(toDiagnostic(l10n.t('Unable to parse content from \'{0}\': Parse error at offset {1}.', toDisplayString(url), jsonErrors[0].offset), ErrorCode.SchemaResolveError, url));
416421
}
417422
return new UnresolvedSchema(schemaContent, errors);
418423
},
@@ -435,7 +440,7 @@ export class JSONSchemaService implements IJSONSchemaService {
435440
errorCode += code;
436441
}
437442
const errorMessage = l10n.t('Unable to load schema from \'{0}\': {1}.', toDisplayString(url), message);
438-
return new UnresolvedSchema(<JSONSchema>{}, [toDiagnostic(errorMessage, errorCode)]);
443+
return new UnresolvedSchema(<JSONSchema>{}, [toDiagnostic(errorMessage, errorCode, url)]);
439444
}
440445
);
441446
}
@@ -511,9 +516,10 @@ export class JSONSchemaService implements IJSONSchemaService {
511516
return referencedHandle.getUnresolvedSchema().then(unresolvedSchema => {
512517
parentHandle.dependencies.add(uri);
513518
if (unresolvedSchema.errors.length) {
519+
const error = unresolvedSchema.errors[0];
514520
const loc = refSegment ? uri + '#' + refSegment : uri;
515-
const errorMessage = l10n.t('Problems loading reference \'{0}\': {1}', loc, unresolvedSchema.errors[0].message);
516-
resolveErrors.push(toDiagnostic(errorMessage, unresolvedSchema.errors[0].code));
521+
const errorMessage = refSegment? l10n.t('Problems loading reference \'{0}\': {1}', refSegment, error.message) : error.message;
522+
resolveErrors.push(toDiagnostic(errorMessage, error.code, uri));
517523
}
518524
mergeRef(node, unresolvedSchema.schema, referencedHandle, refSegment);
519525
return resolveRefs(node, unresolvedSchema.schema, referencedHandle);

src/services/jsonValidation.ts

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import { TextDocument, ErrorCode, PromiseConstructor, LanguageSettings, Document
1010
import * as l10n from '@vscode/l10n';
1111
import { JSONSchemaRef, JSONSchema } from '../jsonSchema';
1212
import { isBoolean } from '../utils/objects';
13+
import { DiagnosticRelatedInformation } from 'vscode-languageserver-types';
1314

1415
export class JSONValidation {
1516

@@ -53,25 +54,26 @@ export class JSONValidation {
5354
let schemaRequest = documentSettings?.schemaRequest ? toDiagnosticSeverity(documentSettings.schemaRequest) : DiagnosticSeverity.Warning;
5455

5556
if (schema) {
56-
const addSchemaProblem = (errorMessage: string, errorCode: ErrorCode) => {
57+
const addSchemaProblem = (errorMessage: string, errorCode: ErrorCode, relatedInformation?: DiagnosticRelatedInformation[]) => {
5758
if (jsonDocument.root && schemaRequest) {
5859
const astRoot = jsonDocument.root;
5960
const property = astRoot.type === 'object' ? astRoot.properties[0] : undefined;
6061
if (property && property.keyNode.value === '$schema') {
6162
const node = property.valueNode || property;
6263
const range = Range.create(textDocument.positionAt(node.offset), textDocument.positionAt(node.offset + node.length));
63-
addProblem(Diagnostic.create(range, errorMessage, schemaRequest, errorCode));
64+
addProblem(Diagnostic.create(range, errorMessage, schemaRequest, errorCode, 'json', relatedInformation));
6465
} else {
6566
const range = Range.create(textDocument.positionAt(astRoot.offset), textDocument.positionAt(astRoot.offset + 1));
66-
addProblem(Diagnostic.create(range, errorMessage, schemaRequest, errorCode));
67+
addProblem(Diagnostic.create(range, errorMessage, schemaRequest, errorCode, 'json', relatedInformation));
6768
}
6869
}
6970
};
7071
if (schema.errors.length) {
71-
addSchemaProblem(schema.errors[0].message, schema.errors[0].code);
72+
const error = schema.errors[0];
73+
addSchemaProblem(error.message, error.code, error.relatedInformation);
7274
} else if (schemaValidation) {
7375
for (const warning of schema.warnings) {
74-
addSchemaProblem(warning.message, warning.code);
76+
addSchemaProblem(warning.message, warning.code, warning.relatedInformation);
7577
}
7678
const semanticErrors = jsonDocument.validate(textDocument, schema.schema, schemaValidation, documentSettings?.schemaDraft);
7779
if (semanticErrors) {

src/test/schema.test.ts

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ import { promises as fs } from 'fs';
1010
import * as url from 'url';
1111
import * as path from 'path';
1212
import { getLanguageService, JSONSchema, SchemaRequestService, TextDocument, MatchingSchema, LanguageService } from '../jsonLanguageService';
13-
import { DiagnosticSeverity, ErrorCode, SchemaConfiguration } from '../jsonLanguageTypes';
13+
import { DiagnosticSeverity, ErrorCode, Range, SchemaConfiguration } from '../jsonLanguageTypes';
1414

1515
function toDocument(text: string, config?: Parser.JSONDocumentConfig, uri = 'foo://bar/file.json'): { textDoc: TextDocument, jsonDoc: Parser.JSONDocument } {
1616

@@ -1079,7 +1079,13 @@ suite('JSON Schema', () => {
10791079
service.clearExternalSchemas();
10801080

10811081
resolvedSchema = await service.getSchemaForResource('main.bar');
1082-
assert.deepStrictEqual(resolvedSchema?.errors, [{ message: "Problems loading reference 'http://myschemastore/myschemafoo': Unable to load schema from 'http://myschemastore/myschemafoo': Resource not found.", code: ErrorCode.SchemaResolveError }]);
1082+
const message = "Unable to load schema from 'http://myschemastore/myschemafoo': Resource not found.";
1083+
assert.deepStrictEqual(resolvedSchema?.errors, [
1084+
{
1085+
message: message,
1086+
code: ErrorCode.SchemaResolveError,
1087+
relatedInformation: [{ location: { uri: 'http://myschemastore/myschemafoo', range: Range.create(0, 0, 0, 0) }, message: message }]
1088+
}]);
10831089

10841090
service.clearExternalSchemas();
10851091
service.registerExternalSchema({ uri: id2, schema: schema2 });

0 commit comments

Comments
 (0)