UNPKG

34 kBJavaScriptView Raw
1"use strict";
2var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
3 if (kind === "m") throw new TypeError("Private method is not writable");
4 if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
5 if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
6 return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
7};
8var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
9 if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
10 if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
11 return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
12};
13var _Code_defaultCategory, _Code_category, _Code_formatter, _JsiiDiagnostic_formatted;
14Object.defineProperty(exports, "__esModule", { value: true });
15exports.configureCategories = exports.JsiiDiagnostic = exports.Code = void 0;
16const spec = require("@jsii/spec");
17const case_1 = require("case");
18const ts = require("typescript");
19const deprecation_warnings_1 = require("./transforms/deprecation-warnings");
20const utils_1 = require("./utils");
21/**
22 * Descriptors for all valid jsii diagnostic codes.
23 *
24 * The `category` or non-error codes can be updated, for example to treat
25 * warnings as errors, or to suppress certain undesirable warnings.
26 */
27class Code {
28 /**
29 * @internal
30 */
31 static message({ code, name, formatter, }) {
32 return new Code(code, name, ts.DiagnosticCategory.Message, formatter);
33 }
34 /**
35 * @internal
36 */
37 static suggestion({ code, name, formatter, }) {
38 return new Code(code, name, ts.DiagnosticCategory.Suggestion, formatter);
39 }
40 /**
41 * @internal
42 */
43 static warning({ code, name, formatter, }) {
44 return new Code(code, name, ts.DiagnosticCategory.Warning, formatter);
45 }
46 /**
47 * @internal
48 */
49 static error({ code, name, formatter, }) {
50 return new Code(code, name, ts.DiagnosticCategory.Error, formatter);
51 }
52 /**
53 * Get a diagnostic code by code or name.
54 *
55 * @param codeOrName the looked up diagnostic code or name.
56 *
57 * @returns the JsiiDiagnosticCode instande, if one exists, or `undefined`
58 *
59 * @experimental this module is under active development and the error codes
60 * and names may change in the future.
61 */
62 static lookup(codeOrName) {
63 if (typeof codeOrName === 'number') {
64 return this.byCode[codeOrName];
65 }
66 return this.byName[codeOrName];
67 }
68 /**
69 * Registers a new diagnostic code.
70 *
71 * @param code the numeric code for the diagnostic
72 * @param name the symbolic name for the diagnostic
73 * @param defaultCategory the default category this diagnostic ranks in
74 * @param formatter a message formatter for easy creation of diagnostics
75 */
76 constructor(code, name, defaultCategory, formatter) {
77 this.code = code;
78 this.name = name;
79 // eslint-disable-next-line @typescript-eslint/explicit-member-accessibility
80 _Code_defaultCategory.set(this, void 0);
81 // eslint-disable-next-line @typescript-eslint/explicit-member-accessibility
82 _Code_category.set(this, void 0);
83 // eslint-disable-next-line @typescript-eslint/explicit-member-accessibility
84 _Code_formatter.set(this, void 0);
85 __classPrivateFieldSet(this, _Code_defaultCategory, defaultCategory, "f");
86 __classPrivateFieldSet(this, _Code_formatter, formatter, "f");
87 if (code in Code.byCode) {
88 throw new Error(`Attempted to create two instances of ${this.constructor.name} with code ${code}`);
89 }
90 if (name in Code.byName) {
91 throw new Error(`Attempted to create two instances of ${this.constructor.name} with name ${name}`);
92 }
93 Code.byCode[code] = Code.byName[name] = this;
94 }
95 /**
96 * Determines whether this diagnostic is a compilation error. Diagnostics
97 * where this is `true` cannot have their `category` overridden to a lower
98 * category.
99 */
100 get isError() {
101 return __classPrivateFieldGet(this, _Code_defaultCategory, "f") === ts.DiagnosticCategory.Error;
102 }
103 /**
104 * The diagnostic category this particular code is filed as.
105 */
106 get category() {
107 return __classPrivateFieldGet(this, _Code_category, "f") ?? __classPrivateFieldGet(this, _Code_defaultCategory, "f");
108 }
109 /**
110 * Update the diagnostic category for this particular code. If `isError` is
111 * `true`, attempting to set anything other than `ts.DiagnosticCategory.Error`
112 * will result in an error being throw.
113 *
114 * @param newValue the new diagnostic category to be used.
115 */
116 set category(newValue) {
117 if (this.isError && newValue !== ts.DiagnosticCategory.Error) {
118 throw new Error(`Illegal attempt to override category of error ${this.code} to ${ts.DiagnosticCategory[newValue]}`);
119 }
120 __classPrivateFieldSet(this, _Code_category, newValue, "f");
121 }
122 /**
123 * Creates a new `JsiiDiagnostic` message without any source code location
124 * data.
125 *
126 * @param args the arguments to the message formatter.
127 *
128 * @deprecated It is preferred to specify a source code location for problem
129 * markers. Prefer the use of `create` while providing a value
130 * for the `location` parameter whenever possible.
131 */
132 createDetached(...args) {
133 return new JsiiDiagnostic(this, __classPrivateFieldGet(this, _Code_formatter, "f").call(this, ...args));
134 }
135 /**
136 * Creates a new `JsiiDiagnostic` message with source code location denoted
137 * by the provided `location` node.
138 *
139 * @param location the source code location attachment of the message.
140 * @param args the arguments to the message formatter.
141 */
142 create(location, ...args) {
143 return new JsiiDiagnostic(this, __classPrivateFieldGet(this, _Code_formatter, "f").call(this, ...args), location);
144 }
145}
146exports.Code = Code;
147_Code_defaultCategory = new WeakMap(), _Code_category = new WeakMap(), _Code_formatter = new WeakMap();
148Code.byCode = {};
149Code.byName = {};
150/**
151 * A jsii-specific diagnostic entry.
152 */
153class JsiiDiagnostic {
154 //////////////////////////////////////////////////////////////////////////////
155 /**
156 * Determines whether a `Diagnostic` instance is a `JsiiDiagnostic` or not.
157 * @param diag
158 */
159 static isJsiiDiagnostic(diag) {
160 return diag.domain === JsiiDiagnostic.DOMAIN;
161 }
162 /**
163 * Creates a new `JsiiDiagnostic` with the provided properties.
164 *
165 * @internal
166 */
167 constructor(code, messageText, location) {
168 this.domain = JsiiDiagnostic.DOMAIN;
169 this.code = utils_1.JSII_DIAGNOSTICS_CODE;
170 this.relatedInformation = new Array();
171 // eslint-disable-next-line @typescript-eslint/explicit-member-accessibility
172 _JsiiDiagnostic_formatted.set(this, void 0);
173 this.category = code.category;
174 this.jsiiCode = code.code;
175 this.messageText = messageText;
176 if (location != null) {
177 this.file = location.getSourceFile();
178 this.start = location.getStart(this.file);
179 this.length = location.getEnd() - this.start;
180 }
181 }
182 addRelatedInformation(node, message) {
183 // Don't relate info into the TypeScript standard library
184 if (!/[\\/]typescript[\\/]lib[\\/]lib\..+\.d\.ts$/.test(node.getSourceFile().fileName)) {
185 this.relatedInformation.push(JsiiDiagnostic.JSII_9999_RELATED_INFO.create(node, message));
186 }
187 // Clearing out #formatted, as this would no longer be the correct string.
188 __classPrivateFieldSet(this, _JsiiDiagnostic_formatted, undefined, "f");
189 return this;
190 }
191 /**
192 * Links the provided `node` with the specified `message` as related to the
193 * current diagnostic, unless `node` is undefined.
194 *
195 * @param node the node where the message should be attached, if any.
196 * @param message the message to be attached to the diagnostic entry.
197 *
198 * @returns `this`
199 */
200 addRelatedInformationIf(node, message) {
201 if (node != null) {
202 return this.addRelatedInformation(node, message);
203 }
204 else {
205 return this;
206 }
207 }
208 /**
209 * Adds related information to this `JsiiDiagnostic` instance if the provided
210 * `node` is defined.
211 *
212 * @param node the node to bind as related information, or `undefined`.
213 * @param message the message to attach to the related information.
214 *
215 * @returns `this`
216 */
217 maybeAddRelatedInformation(node, message) {
218 if (node == null) {
219 return this;
220 }
221 this.relatedInformation.push(JsiiDiagnostic.JSII_9999_RELATED_INFO.create(node, message));
222 // Clearing out #formatted, as this would no longer be the correct string.
223 __classPrivateFieldSet(this, _JsiiDiagnostic_formatted, undefined, "f");
224 return this;
225 }
226 /**
227 * Formats this diagnostic with color and context if possible, and returns it.
228 * The formatted diagnostic is cached, so that it can be re-used. This is
229 * useful for diagnostic messages involving trivia -- as the trivia may have
230 * been obliterated from the `SourceFile` by the `TsCommentReplacer`, which
231 * makes the error messages really confusing.
232 */
233 format(projectRoot) {
234 if (__classPrivateFieldGet(this, _JsiiDiagnostic_formatted, "f") == null) {
235 __classPrivateFieldSet(this, _JsiiDiagnostic_formatted, (0, utils_1._formatDiagnostic)(this, projectRoot), "f");
236 }
237 return __classPrivateFieldGet(this, _JsiiDiagnostic_formatted, "f");
238 }
239}
240exports.JsiiDiagnostic = JsiiDiagnostic;
241_JsiiDiagnostic_formatted = new WeakMap();
242//////////////////////////////////////////////////////////////////////////////
243// 0001 => 0999 -- PACKAGE METADATA PROBLEMS
244JsiiDiagnostic.JSII_0001_PKG_MISSING_DESCRIPTION = Code.suggestion({
245 code: 1,
246 formatter: () => 'A "description" field should be specified in "package.json"',
247 name: 'metadata/package-json-missing-description',
248});
249JsiiDiagnostic.JSII_0002_PKG_MISSING_HOMEPAGE = Code.suggestion({
250 code: 2,
251 formatter: () => 'A "homepage" field should be specified in "package.json"',
252 name: 'metadata/package-json-missing-homepage',
253});
254JsiiDiagnostic.JSII_0003_MISSING_README = Code.warning({
255 code: 3,
256 formatter: () => 'There is no "README.md" file. It is required in order to generate valid PyPI (Python) packages.',
257 name: 'metadata/missing-readme',
258});
259JsiiDiagnostic.JSII_0004_COULD_NOT_FIND_ENTRYPOINT = Code.error({
260 code: 4,
261 formatter: (mainFile) => `Could not find "main" file: ${mainFile}`,
262 name: 'metadata/could-not-find-entrypoint',
263});
264JsiiDiagnostic.JSII_0005_MISSING_PEER_DEPENDENCY = Code.warning({
265 code: 5,
266 formatter: (assm, reference) => `The type "${reference}" is exposed in the public API of this module. ` +
267 `Therefore, the module "${assm}" must also be defined under "peerDependencies". ` +
268 'This will be auto-corrected unless --no-fix-peer-dependencies was specified.',
269 name: 'metadata/missing-peer-dependency',
270});
271// NOTE: currently not possible to change the severity of this code,
272// as it's being emitted before the overrides have been loaded
273JsiiDiagnostic.JSII_0006_MISSING_DEV_DEPENDENCY = Code.warning({
274 code: 6,
275 formatter: (dependencyName, peerRange, minVersion, actual) => `A "peerDependency" on "${dependencyName}" at "${peerRange}" means you ` +
276 `should take a "devDependency" on "${dependencyName}" at "${minVersion}" ` +
277 `(found ${JSON.stringify(actual)})`,
278 name: 'metadata/missing-dev-dependency',
279});
280JsiiDiagnostic.JSII_0007_MISSING_WARNINGS_EXPORT = Code.error({
281 code: 7,
282 formatter: () => 'If you are compiling with --add-deprecation-warnings and your package.json ' +
283 `declares subpath exports, you must include { "./${deprecation_warnings_1.WARNINGSCODE_FILE_NAME}": "./${deprecation_warnings_1.WARNINGSCODE_FILE_NAME}" } ` +
284 'in the set of exports.',
285 name: 'metadata/missing-warnings-export',
286});
287//////////////////////////////////////////////////////////////////////////////
288// 1000 => 1999 -- TYPESCRIPT LANGUAGE RESTRICTIONS
289JsiiDiagnostic.JSII_1000_NO_CONST_ENUM = Code.error({
290 code: 1000,
291 formatter: () => 'Exported "const enum" declarations are not allowed',
292 name: 'typescript-restrictions/no-const-enum',
293});
294JsiiDiagnostic.JSII_1001_TYPE_HAS_NO_SYMBOL = Code.error({
295 code: 1001,
296 formatter: () => 'Non-primitive types without a symbol cannot be processed.',
297 name: 'typescript-restrictions/type-has-no-symbol',
298});
299JsiiDiagnostic.JSII_1002_UNSPECIFIED_PROMISE = Code.error({
300 code: 1002,
301 formatter: () => 'Un-specified promise type. Specify it using "Promise<T>"',
302 name: 'typescript-restrictions/unspecified-promise',
303});
304JsiiDiagnostic.JSII_1003_UNSUPPORTED_TYPE = Code.error({
305 code: 1003,
306 formatter: (messageText) => messageText,
307 name: 'typescript-restrictions/unsupported-type',
308});
309JsiiDiagnostic.JSII_1004_DUPLICATE_ENUM_VALUE = Code.error({
310 code: 1004,
311 formatter: (enumValue, enumMemberNames) => `Value ${enumValue} is used for multiple enum values: ${enumMemberNames.join(', ')}`,
312 name: 'typescript-restrictions/duplicate-enum-value',
313});
314JsiiDiagnostic.JSII_1005_SEPARATE_WRITE_TYPE = Code.error({
315 code: 1005,
316 formatter: () => 'Visible property signatures cannot use a separate write type. Use the same type as the getter.',
317 name: 'typescript-restrictions/separate-write-type',
318});
319JsiiDiagnostic.JSII_1006_GENERIC_TYPE = Code.error({
320 code: 1006,
321 formatter: () => 'Generic types are not supported because semantics are not uniform in target languages.',
322 name: 'typescript-restriction/generic-type',
323});
324JsiiDiagnostic.JSII_1999_UNSUPPORTED = Code.error({
325 code: 1999,
326 formatter: ({ what, alternative, suggestInternal, }) => `${what} are not supported in jsii APIs.${alternative ? ` Consider using ${alternative} instead.` : ''}${suggestInternal
327 ? ` This declaration must${alternative ? ' otherwise' : ''} be marked "@internal" or "@jsii ignore".`
328 : ''}`,
329 name: 'typescript-restrictions/unsupported',
330});
331//////////////////////////////////////////////////////////////////////////////
332// 2000 => 2999 -- INCORRECT USE OF THE @jsii DIRECTIVE
333JsiiDiagnostic.JSII_2000_MISSING_DIRECTIVE_ARGUMENT = Code.warning({
334 code: 2000,
335 formatter: () => 'Missing argument to @jsii directive. Refer to the jsii compiler documentation for more information.',
336 name: 'jsii-directive/missing-argument',
337});
338JsiiDiagnostic.JSII_2100_STRUCT_ON_NON_INTERFACE = Code.warning({
339 code: 2100,
340 formatter: () => 'The "@jsii struct" directive is only applicable to interface declarations.',
341 name: 'jsii-directive/struct-on-non-interface',
342});
343JsiiDiagnostic.JSII_2999_UNKNOWN_DIRECTIVE = Code.warning({
344 code: 2999,
345 formatter: (text) => `Unknown @jsii directive: ${JSON.stringify(text)}. Refer to the jsii compiler documentation for more information.`,
346 name: 'jsii-directive/unknown',
347});
348//////////////////////////////////////////////////////////////////////////////
349// 3000 => 3999 -- TYPE MODEL COHERENCE
350JsiiDiagnostic.JSII_3000_EXPORTED_API_USES_HIDDEN_TYPE = Code.error({
351 code: 3000,
352 formatter: (badFqn) => `Exported APIs cannot use un-exported type "${badFqn}"`,
353 name: 'type-model/exported-api-cannot-use-unexported-type',
354});
355JsiiDiagnostic.JSII_3001_EXPOSED_INTERNAL_TYPE = Code.error({
356 code: 3001,
357 formatter: (symbol, isThisType, typeUse) => `Type ${isThisType ? `"this" (aka: "${symbol.name}")` : `"${symbol.name}"`} cannot be used as the ${typeUse} because it is private or @internal`,
358 name: 'type-model/use-of-internal-type',
359});
360JsiiDiagnostic.JSII_3002_USE_OF_UNEXPORTED_FOREIGN_TYPE = Code.error({
361 code: 3002,
362 formatter: (fqn, typeUse, pkg) => `Type "${fqn}" cannot be used as a ${typeUse} because it is not exported from ${pkg.name}`,
363 name: 'type-model/unexported-foreign-type',
364});
365JsiiDiagnostic.JSII_3003_SYMBOL_IS_EXPORTED_TWICE = Code.error({
366 code: 3003,
367 formatter: (ns1, ns2) => `Symbol is exported under two distinct submodules: ${ns1} and ${ns2}`,
368 name: 'type-model/symbol-is-exported-twice',
369});
370JsiiDiagnostic.JSII_3004_INVALID_SUPERTYPE = Code.error({
371 code: 3004,
372 formatter: (clause, badDeclaration) => {
373 return `Illegal ${clauseType(clause.token)} clause for an exported API: ${ts.SyntaxKind[badDeclaration.kind]}`;
374 function clauseType(token) {
375 switch (token) {
376 case ts.SyntaxKind.ExtendsKeyword:
377 return 'extends';
378 case ts.SyntaxKind.ImplementsKeyword:
379 return 'implements';
380 default:
381 return ts.SyntaxKind[token];
382 }
383 }
384 },
385 name: 'type-model/invalid-supertype',
386});
387JsiiDiagnostic.JSII_3005_TYPE_USED_AS_INTERFACE = Code.error({
388 code: 3005,
389 formatter: (badType) => `Type "${spec.describeTypeReference(badType)}" cannot be used as an interface`,
390 name: 'type-model/type-used-as-interface',
391});
392JsiiDiagnostic.JSII_3006_TYPE_USED_AS_CLASS = Code.error({
393 code: 3006,
394 formatter: (badType) => `Type "${spec.describeTypeReference(badType)}" cannot be used as a class`,
395 name: 'type-model/type-used-as-class',
396});
397JsiiDiagnostic.JSII_3007_ILLEGAL_STRUCT_EXTENSION = Code.error({
398 code: 3007,
399 formatter: (offender, struct) => `Attempt to extend or implement struct "${struct.fqn}" from "${offender.fqn}"`,
400 name: 'type-model/illegal-struct-extension',
401});
402JsiiDiagnostic.JSII_3008_STRUCT_PROPS_MUST_BE_READONLY = Code.error({
403 code: 3008,
404 formatter: (propName, struct) => `The "${propName}" property of struct "${struct.fqn}" must be "readonly". Rename "${struct.fqn}" to "I${struct.name}" if it is meant to be a behavioral interface.`,
405 name: 'type-model/struct-props-must-be-readonly',
406});
407JsiiDiagnostic.JSII_3009_OPTIONAL_PARAMETER_BEFORE_REQUIRED = Code.error({
408 code: 3009,
409 formatter: (param, nextParam) => `Parameter "${param.name}" cannot be optional, as it precedes required parameter "${nextParam.name}"`,
410 name: 'type-model/optional-parameter-before-required',
411});
412JsiiDiagnostic.JSII_3999_INCOHERENT_TYPE_MODEL = Code.error({
413 code: 3999,
414 formatter: (messageText) => messageText,
415 name: 'type-model/incoherent-type-model',
416});
417//////////////////////////////////////////////////////////////////////////////
418// 4000 => 4999 -- TYPESCRIPT & JSII CONFIG ERRORS
419JsiiDiagnostic.JSII_4000_FAILED_TSCONFIG_VALIDATION = Code.error({
420 code: 4000,
421 formatter: (config, ruleSet, violations) => {
422 return `Typescript compiler options in "${config}" are not passing validation against rule set "${ruleSet}", found the following rule violations:\n${violations
423 .map((v) => ` - ${v.field}: ${v.message}`)
424 .join('\n')}`;
425 },
426 name: 'typescript-config/invalid-tsconfig',
427});
428JsiiDiagnostic.JSII_4009_DISABLED_TSCONFIG_VALIDATION = Code.warning({
429 code: 4009,
430 formatter: (config) => `Validation of typescript config "${config}" is disabled. This is intended for experimental setups only. Compilation might fail or produce incompatible artifacts.`,
431 name: 'typescript-config/disabled-tsconfig-validation',
432});
433//////////////////////////////////////////////////////////////////////////////
434// 5000 => 5999 -- LANGUAGE COMPATIBILITY ERRORS
435JsiiDiagnostic.JSII_5000_JAVA_GETTERS = Code.error({
436 code: 5000,
437 formatter: (badName, typeName) => `Methods and properties cannot have names like "getXxx": those conflict with Java property getters. Rename "${typeName}.${badName}"`,
438 name: 'language-compatibility/potential-java-getter-conflict',
439});
440JsiiDiagnostic.JSII_5001_JAVA_SETTERS = Code.error({
441 code: 5001,
442 formatter: (badName, typeName) => `Methods and properties cannot have names like "setXxx": those conflict with Java property setters. Rename "${typeName}.${badName}"`,
443 name: 'language-compatibility/potential-java-setter-conflict',
444});
445JsiiDiagnostic.JSII_5002_OVERRIDE_CHANGES_VISIBILITY = Code.error({
446 code: 5002,
447 formatter: (newElement, action, newValue, oldValue) => `"${newElement}" changes visibility to ${newValue} when ${action}. Change it to ${oldValue}`,
448 name: 'language-compatibility/override-changes-visibility',
449});
450JsiiDiagnostic.JSII_5003_OVERRIDE_CHANGES_RETURN_TYPE = Code.error({
451 code: 5003,
452 formatter: (newElement, action, newValue, oldValue) => `"${newElement}" changes the return type to "${newValue}" when ${action}. Change it to "${oldValue}"`,
453 name: 'language-compatibility/override-changes-return-type',
454});
455JsiiDiagnostic.JSII_5004_OVERRIDE_CHANGES_PROP_TYPE = Code.error({
456 code: 5004,
457 formatter: (newElement, action, newType, oldType) => `"${newElement}" changes the property type to "${spec.describeTypeReference(newType)}" when ${action}. Change it to "${spec.describeTypeReference(oldType)}"`,
458 name: 'language-compatibility/override-changes-property-type',
459});
460JsiiDiagnostic.JSII_5005_OVERRIDE_CHANGES_PARAM_COUNT = Code.error({
461 code: 5005,
462 formatter: (newElement, action, newCount, oldCount) => `"${newElement}" has ${newCount} parameters when ${action}. It should accept ${oldCount} parameters`,
463 name: 'language-compatibility/override-changes-param-count',
464});
465JsiiDiagnostic.JSII_5006_OVERRIDE_CHANGES_PARAM_TYPE = Code.error({
466 code: 5006,
467 formatter: (newElement, action, newParam, oldParam) => `"${newElement}" changes the type of parameter "${newParam.name}" to ${spec.describeTypeReference(newParam.type)} when ${action}. Change it to ${spec.describeTypeReference(oldParam.type)}`,
468 name: 'language-compatibility/override-changes-param-type',
469});
470JsiiDiagnostic.JSII_5007_OVERRIDE_CHANGES_VARIADIC = Code.error({
471 code: 5007,
472 formatter: (newElement, action, newVariadic = false, oldVariadic = false) => `"${newElement}" turns ${newVariadic ? 'variadic' : 'non variadic'} when ${action}. Make it ${oldVariadic ? 'variadic' : 'non-variadic'}`,
473 name: 'language-compatibility/override-changes-variadic',
474});
475JsiiDiagnostic.JSII_5008_OVERRIDE_CHANGES_PARAM_OPTIONAL = Code.error({
476 code: 5008,
477 formatter: (newElement, action, newParam, oldParam) => `"${newElement}" turns parameter "${newParam.name}" ${newParam.optional ? 'optional' : 'required'} when ${action}. Make it ${oldParam.optional ? 'optional' : 'required'}`,
478 name: 'language-compatibility/override-changes-param-optional',
479});
480JsiiDiagnostic.JSII_5009_OVERRIDE_CHANGES_PROP_OPTIONAL = Code.error({
481 code: 5009,
482 formatter: (newElement, action, newOptional = false, oldOptional = false) => `"${newElement}" turns ${newOptional ? 'optional' : 'required'} when ${action}. Make it ${oldOptional ? 'optional' : 'required'}`,
483 name: 'language-compatibility/override-changes-prop-optional',
484});
485JsiiDiagnostic.JSII_5010_OVERRIDE_CHANGES_MUTABILITY = Code.error({
486 code: 5010,
487 formatter: (newElement, action, newReadonly = false, oldReadonly = false) => `"${newElement}" turns ${newReadonly ? 'readonly' : 'mutable'} when ${action}. Make it ${oldReadonly ? 'readonly' : 'mutable'}`,
488 name: 'language-compatibility/override-changes-mutability',
489});
490JsiiDiagnostic.JSII_5011_SUBMODULE_NAME_CONFLICT = Code.error({
491 code: 5011,
492 formatter: (submoduleName, typeName, reserved) => `Submodule "${submoduleName}" conflicts with "${typeName}, as different languages could represent it as: ${reserved
493 .map((x) => `"${x}"`)
494 .join(', ')}"`,
495 name: 'language-compatibility/submodule-name-conflicts',
496});
497JsiiDiagnostic.JSII_5012_NAMESPACE_IN_TYPE = Code.error({
498 code: 5012,
499 formatter: (typeName, namespaceName) => `All entities nested under a type (e.g: "${typeName}") must be concrete types, but "${namespaceName}" is a namespace. This structure cannot be supported in all languages (e.g: Java)`,
500 name: 'language-compatibility/namespace-in-type',
501});
502JsiiDiagnostic.JSII_5013_STATIC_INSTANCE_CONFLICT = Code.error({
503 code: 5013,
504 formatter: (member, type) => `Member "${member}" of class "${type.fqn}" has both a static and an instance delcaration`,
505 name: 'language-compatibility/static-instance-conflict',
506});
507JsiiDiagnostic.JSII_5014_INHERITED_STATIC_CONFLICT = Code.error({
508 code: 5014,
509 formatter: (member, type, baseMember, baseType) => `${member.static ? 'Static' : 'Instance'} member "${member.name}" of class "${type.fqn}" conflicts with ${baseMember.static ? 'static' : 'instance'} member in ancestor "${baseType.fqn}"`,
510 name: 'language-compatibility/inherited-static-conflict',
511});
512JsiiDiagnostic.JSII_5015_REDECLARED_INTERFACE_MEMBER = Code.error({
513 code: 5015,
514 formatter: (memberName, iface) => `Interface "${iface.fqn}" re-declares member "${memberName}". This is not supported as it results in invalid C#.`,
515 name: 'language-compatibility/redeclared-interface-member',
516});
517JsiiDiagnostic.JSII_5016_PROHIBITED_MEMBER_NAME = Code.error({
518 code: 5016,
519 formatter: (badName) => `Members cannot be named "${badName}" as it conflicts with synthetic declarations in some languages.`,
520 name: 'language-compatibility/prohibited-member-name',
521});
522JsiiDiagnostic.JSII_5017_POSITIONAL_KEYWORD_CONFLICT = Code.error({
523 code: 5017,
524 formatter: (badName) => `Parameter name "${badName}" is also the name of a property in a struct parameter. Rename the positional parameter.`,
525 name: 'language-compatibility/positional-keyword-conflict',
526});
527JsiiDiagnostic.JSII_5018_RESERVED_WORD = Code.warning({
528 code: 5018,
529 formatter: (badName, languages) => `"${badName}" is a reserved word in ${languages.join(', ')}. Using this name may cause problems when generating language bindings. Consider a different name.`,
530 name: 'language-compatibility/reserved-word',
531});
532JsiiDiagnostic.JSII_5019_MEMBER_TYPE_NAME_CONFLICT = Code.warning({
533 code: 5019,
534 formatter: (memberKind, memberSymbol, declaringType) => `The ${memberKind} name "${memberSymbol.name}" conflicts with the declaring ${declaringType.kind} "${declaringType.name}". This will result in renaming the ${declaringType.kind} to "_${declaringType.name}" in C#. Consider renaming "${memberSymbol.name}".`,
535 name: 'language-compatibility/member-name-conflicts-with-type-name',
536});
537JsiiDiagnostic.JSII_5020_STATIC_MEMBER_CONFLICTS_WITH_NESTED_TYPE = Code.error({
538 code: 5020,
539 formatter: (nestingType, staticMember, nestedType) => `The static member "${nestingType.name}.${staticMember.name}" has the same PascalCased representation as nested type "${nestingType.name}.${nestedType.name}". This would result in invalid code in Go.`,
540 name: 'language-compatibility/static-member-name-conflicts-with-nested-type',
541});
542//////////////////////////////////////////////////////////////////////////////
543// 6000 => 6999 -- RESERVED
544//////////////////////////////////////////////////////////////////////////////
545// 7000 => 7999 -- DOCUMENTATION ERRORS
546JsiiDiagnostic.JSII_7000_NON_EXISTENT_PARAMETER = Code.warning({
547 code: 7000,
548 formatter: (method, param) => `Documentation for method "${method.name}" refers to non-existent @param "${param}"`,
549 name: 'documentation/non-existent-parameter',
550});
551JsiiDiagnostic.JSII_7001_ILLEGAL_HINT = Code.error({
552 code: 7001,
553 formatter: (hint, ...valid) => `Illegal use of "@${hint}" hint. It is only valid on ${valid.join(', ')}.`,
554 name: 'documentation/illegal-hint',
555});
556JsiiDiagnostic.JSII_7999_DOCUMENTATION_ERROR = Code.error({
557 code: 7999,
558 formatter: (messageText) => messageText,
559 name: 'documentation/documentation-error',
560});
561//////////////////////////////////////////////////////////////////////////////
562// 8000 => 8999 -- JSII STYLE ENFORCEMENT
563JsiiDiagnostic.JSII_8000_PASCAL_CASED_TYPE_NAMES = Code.error({
564 code: 8000,
565 formatter: (badName, expectedName = (0, case_1.pascal)(badName)) => `Type names must be PascalCased. Rename "${badName}" to "${expectedName}"`,
566 name: 'code-style/type-names-must-use-pascal-case',
567});
568JsiiDiagnostic.JSII_8001_ALL_CAPS_ENUM_MEMBERS = Code.error({
569 code: 8001,
570 formatter: (badName, typeName) => `Enum members must be ALL_CAPS. Rename "${typeName}.${badName}" to "${(0, case_1.constant)(badName)}"`,
571 name: 'code-style/enum-members-must-use-all-caps',
572});
573JsiiDiagnostic.JSII_8002_CAMEL_CASED_MEMBERS = Code.error({
574 code: 8002,
575 formatter: (badName, typeName) => `Method and property (unless they are static readonly) names must use camelCase. Rename "${typeName}.${badName}" to "${(0, case_1.camel)(badName)}"`,
576 name: 'code-style/member-names-must-use-camel-case',
577});
578JsiiDiagnostic.JSII_8003_STATIC_CONST_CASING = Code.error({
579 code: 8003,
580 formatter: (badName, typeName) => `Static constant names must use ALL_CAPS, PascalCase, or camelCase. Rename "${typeName}.${badName}" to "${(0, case_1.constant)(badName)}"`,
581 name: 'code-style/static-readonly-property-casing',
582});
583JsiiDiagnostic.JSII_8004_SUBMOULE_NAME_CASING = Code.error({
584 code: 8004,
585 formatter: (badName) => `Submodule namespaces must be camelCased or snake_cased. Rename "${badName}" to ${(0, case_1.camel)(badName)}`,
586 name: 'code-style/submodule-name-casing',
587});
588JsiiDiagnostic.JSII_8005_INTERNAL_UNDERSCORE = Code.error({
589 code: 8005,
590 formatter: (badName) => `Members marked with @internal must have a name starting with "_". Rename "${badName}" to "_${badName}"`,
591 name: 'code-style/internal-members-underscore-prefix',
592});
593JsiiDiagnostic.JSII_8006_UNDERSCORE_INTERNAL = Code.error({
594 code: 8006,
595 formatter: (badName) => `Members with a name starting with "_" (e.g: "${badName}") must be marked @internal`,
596 name: 'code-style/underscored-members-must-be-internal',
597});
598JsiiDiagnostic.JSII_8007_BEHAVIORAL_INTERFACE_NAME = Code.error({
599 code: 8007,
600 formatter: (badName) => `Interface contains behavior. Rename "${badName}" to "I${badName}"`,
601 name: 'code-style/behavioral-interface-name',
602});
603//////////////////////////////////////////////////////////////////////////////
604// 9000 => 9999 -- SURPRISING ERRORS & INFORMATIONAL MESSAGES
605JsiiDiagnostic.JSII_9000_UNKNOWN_MODULE = Code.error({
606 code: 9000,
607 formatter: (moduleName) => `Encountered use of module that is not declared in "dependencies" or "peerDependencies": "${moduleName}"`,
608 name: 'miscellaneous/unknown-module',
609});
610JsiiDiagnostic.JSII_9001_TYPE_NOT_FOUND = Code.error({
611 code: 9001,
612 formatter: (typeRef) => `Type not found in the corresponding assembly: "${typeRef.fqn}"`,
613 name: 'miscellaneous/type-not-found',
614});
615JsiiDiagnostic.JSII_9002_UNRESOLVEABLE_TYPE = Code.error({
616 code: 9002,
617 formatter: (reference) => `Unable to resolve type "${reference}". It may be @internal or not exported from the module's entry point (as configured in "package.json" as "main").`,
618 name: 'miscellaneous/unresolveable-type',
619});
620JsiiDiagnostic.JSII_9003_UNRESOLVEABLE_MODULE = Code.error({
621 code: 9003,
622 formatter: (location) => `Unable to resolve module location "${location}"`,
623 name: 'miscellaneous/unresolveable-module',
624});
625JsiiDiagnostic.JSII_9004_UNABLE_TO_COMPUTE_SIGNATURE = Code.error({
626 code: 9004,
627 formatter: (methodName, type) => `Unable to compute signature for method "${methodName}" of "${type.fqn}"`,
628 name: 'miscellaneous/unable-to-compute-signature',
629});
630JsiiDiagnostic.JSII_9996_UNNECESSARY_TOKEN = Code.message({
631 code: 9996,
632 formatter: () => 'Unnecessary token, consider removing it',
633 name: 'miscellaneous/unnecessary-token',
634});
635JsiiDiagnostic.JSII_9997_UNKNOWN_ERROR = Code.error({
636 code: 9997,
637 formatter: (error) => `Unknown error: ${error.message} -- ${error.stack}`,
638 name: 'miscellaneous/unknown-error',
639});
640JsiiDiagnostic.JSII_9998_UNSUPPORTED_NODE = Code.message({
641 code: 9998,
642 formatter: (kindOrMessage) => typeof kindOrMessage === 'string'
643 ? kindOrMessage
644 : `Unsupported ${ts.SyntaxKind[kindOrMessage]} node. This declaration will not be accessible from other languages.`,
645 name: 'miscellaneous/unsupported-node',
646});
647//////////////////////////////////////////////////////////////////////////////
648JsiiDiagnostic.JSII_9999_RELATED_INFO = Code.suggestion({
649 code: 9999,
650 formatter: (messageText) => messageText,
651 name: 'miscellaneous/related-info',
652});
653//////////////////////////////////////////////////////////////////////////////
654/**
655 * This symbol unequivocally identifies the `JsiiDiagnostic` domain.
656 */
657JsiiDiagnostic.DOMAIN = Symbol('jsii');
658function configureCategories(records) {
659 for (const [code, category] of Object.entries(records)) {
660 const diagCode = Code.lookup(diagnosticCode(code));
661 if (!diagCode) {
662 throw new Error(`Unrecognized diagnostic code '${code}'`);
663 }
664 diagCode.category = category;
665 }
666}
667exports.configureCategories = configureCategories;
668function diagnosticCode(str) {
669 if (str.toLowerCase().startsWith('jsii')) {
670 const re = /^JSII(\d+)$/i.exec(str);
671 if (re) {
672 return parseInt(re[1], 10);
673 }
674 throw new Error(`Invalid diagnostic code ${str}. A number must follow code that starts with 'JSII'`);
675 }
676 return str;
677}
678//# sourceMappingURL=jsii-diagnostic.js.map
\No newline at end of file