@lwc/errors
Version:
LWC Error Utilities
1,366 lines (1,357 loc) • 54.7 kB
JavaScript
/**
* Copyright (c) 2025 Salesforce, Inc.
*/
'use strict';
Object.defineProperty(exports, '__esModule', { value: true });
/*
* Copyright (c) 2024, Salesforce, Inc.
* All rights reserved.
* SPDX-License-Identifier: MIT
* For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
*/
const templateRegex = /\{([0-9]+)\}/g;
/**
* Replaces {0} in the given string with the value from the given array
* @param template Template string to fill
* @param args Values to fill with
* @returns Filled string
*/
function templateString(template, args) {
return template.replace(templateRegex, (_, index) => {
return args[index];
});
}
/*
* Copyright (c) 2018, salesforce.com, inc.
* All rights reserved.
* SPDX-License-Identifier: MIT
* For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
*/
exports.DiagnosticLevel = void 0;
(function (DiagnosticLevel) {
/** Unexpected error, parsing error, bundling error */
DiagnosticLevel[DiagnosticLevel["Fatal"] = 0] = "Fatal";
/** Linting error with error level, invalid external reference, invalid import, invalid transform */
DiagnosticLevel[DiagnosticLevel["Error"] = 1] = "Error";
/** Linting error with warning level, usage of an API to be deprecated */
DiagnosticLevel[DiagnosticLevel["Warning"] = 2] = "Warning";
/** Logging messages */
DiagnosticLevel[DiagnosticLevel["Log"] = 3] = "Log";
})(exports.DiagnosticLevel || (exports.DiagnosticLevel = {}));
/*
* Copyright (c) 2024, Salesforce, Inc.
* All rights reserved.
* SPDX-License-Identifier: MIT
* For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
*/
class CompilerError extends Error {
constructor(code, message, filename, location) {
super(message);
this.level = exports.DiagnosticLevel.Error;
this.code = code;
this.filename = filename;
this.location = location;
}
static from(diagnostic, origin) {
const { code, message } = diagnostic;
const filename = getFilename(origin, diagnostic);
const location = getLocation(origin, diagnostic);
const compilerError = new CompilerError(code, message, filename, location);
// The stack here is misleading and doesn't point to the cause of the original error message
// TODO [W-5712064]: Enhance diagnostics with useful stack trace and source code
compilerError.stack = undefined;
return compilerError;
}
toDiagnostic() {
return {
code: this.code,
message: this.message,
level: this.level,
filename: this.filename,
location: this.location,
};
}
}
/**
* Extracts an error code from the given error.
* @param error The error to check.
* @returns The error code, if found.
*/
function getCodeFromError(error) {
if (error.lwcCode && typeof error.lwcCode === 'number') {
return error.lwcCode;
}
else if (error.code && typeof error.code === 'number') {
return error.code;
}
return undefined;
}
/**
* Extracts the filename from the provided parameters, preferring to use the compiler diagnostic
* origin, if provided.
* @param origin Compiler diagnositic origin data
* @param obj Any object that might have a filename associated
* @returns The filename, if found.
*/
function getFilename(origin, obj) {
// Give priority to explicit origin
if (origin && origin.filename) {
return origin.filename;
}
else if (obj) {
return obj.filename || obj.fileName || obj.file;
}
return undefined;
}
/**
* Extracts the location from the provided parameters, preferring to use the compiler diagnostic
* origin, if provided.
* @param origin Compiler diagnositic origin data
* @param obj Any object that might have a location property
* @returns The location, if found.
*/
function getLocation(origin, obj) {
// Give priority to explicit origin
if (origin && origin.location) {
return origin.location;
}
return getLocationFromObject(obj);
}
function getLocationFromObject(obj) {
if (obj) {
if (obj.location) {
return obj.location;
}
else if (obj.loc) {
return obj.loc;
}
else if (Number.isInteger(obj.line) && Number.isInteger(obj.column)) {
return { line: obj.line, column: obj.column, start: obj.start, length: obj.length };
}
}
return undefined;
}
/*
* Copyright (c) 2024, Salesforce, Inc.
* All rights reserved.
* SPDX-License-Identifier: MIT
* For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
*/
/*
* For the next available error code, reference (and update!) the value in ./index.ts
*/
const GENERIC_COMPILER_ERROR = {
code: 1001,
message: 'Unexpected compilation error: {0}',
level: exports.DiagnosticLevel.Error,
url: '',
};
const CompilerValidationErrors = {
INVALID_COMPAT_PROPERTY: {
code: 1013,
message: 'Expected a boolean for outputConfig.compat, received "{0}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_ENV_ENTRY_VALUE: {
code: 1014,
message: 'Expected a string for outputConfig.env["{0}"], received "{1}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_ENV_PROPERTY: {
code: 1015,
message: 'Expected an object for outputConfig.env, received "{0}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_FILES_PROPERTY: {
code: 1016,
message: 'Expected an object with files to be compiled.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_NAME_PROPERTY: {
code: 1018,
message: 'Expected a string for name, received "{0}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_NAMESPACE_PROPERTY: {
code: 1019,
message: 'Expected a string for namespace, received "{0}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_SOURCEMAP_PROPERTY: {
code: 1021,
message: 'Expected a boolean value or \'inline\' for outputConfig.sourcemap, received "{0}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
MISSING_OPTIONS_OBJECT: {
code: 1023,
message: 'Expected options object, received "{0}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
UNEXPECTED_FILE_CONTENT: {
code: 1024,
message: 'Unexpected file content for "{0}". Expected a string, received "{1}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
UNKNOWN_ENV_ENTRY_KEY: {
code: 1025,
message: 'Unknown entry "{0}" in outputConfig.env.',
level: exports.DiagnosticLevel.Error,
url: '',
},
};
const ModuleResolutionErrors = {
MODULE_RESOLUTION_ERROR: {
code: 1002,
message: 'Error in module resolution: {0}',
level: exports.DiagnosticLevel.Warning,
url: '',
},
IMPORTEE_RESOLUTION_FAILED: {
code: 1010,
message: 'Failed to resolve entry for module "{0}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
IMPORTEE_RESOLUTION_FROM_IMPORTER_FAILED: {
code: 1011,
message: 'Failed to resolve import "{0}" from "{1}". Please add "{2}" file to the component folder.',
level: exports.DiagnosticLevel.Error,
url: '',
},
NONEXISTENT_FILE: {
code: 1004,
message: 'No such file {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
FOLDER_NAME_STARTS_WITH_CAPITAL_LETTER: {
code: 1116,
message: 'Illegal folder name "{0}". The folder name must start with a lowercase character: "{1}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
FOLDER_AND_FILE_NAME_CASE_MISMATCH: {
code: 1117,
message: 'Failed to resolve "{0}". The file name must case match the component folder name "{1}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
IMPORT_AND_FILE_NAME_CASE_MISMATCH: {
code: 1118,
message: 'Failed to resolve "{0}" from "{1}". Did you mean "{2}"?',
level: exports.DiagnosticLevel.Error,
url: '',
},
RELATIVE_DYNAMIC_IMPORT: {
code: 1120,
message: 'Illegal usage of the dynamic import syntax with a relative path.',
level: exports.DiagnosticLevel.Error,
url: '',
},
};
const TransformerErrors = {
CSS_TRANSFORMER_ERROR: {
code: 1009,
message: '{0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
CSS_IN_HTML_ERROR: {
code: 1026,
message: 'An error occurred parsing inline CSS. {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
HTML_TRANSFORMER_ERROR: {
code: 1008,
message: '{0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_ID: {
code: 1027,
message: 'Expect a string for id. Received {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_SOURCE: {
code: 1006,
message: 'Expect a string for source. Received {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
JS_TRANSFORMER_ERROR: {
code: 1007,
message: '{0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
NO_AVAILABLE_TRANSFORMER: {
code: 1005,
message: 'No available transformer for "{0}"',
level: exports.DiagnosticLevel.Error,
url: '',
},
JS_TRANSFORMER_DECORATOR_ERROR: {
code: 1198,
message: 'Decorators like @api, @track, and @wire are only supported in LightningElement classes. {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
};
/*
* Copyright (c) 2024, Salesforce, Inc.
* All rights reserved.
* SPDX-License-Identifier: MIT
* For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
*/
/*
* For the next available error code, reference (and update!) the value in ./index.ts
*/
const LWCClassErrors = {
INVALID_DYNAMIC_IMPORT_SOURCE_STRICT: {
code: 1121,
message: 'Invalid import. The argument "{0}" must be a stringLiteral for dynamic imports when strict mode is enabled.',
url: '',
level: exports.DiagnosticLevel.Error,
},
};
const DecoratorErrors = {
ADAPTER_SHOULD_BE_FIRST_PARAMETER: {
code: 1092,
message: '@wire expects an adapter as first parameter. @wire(adapter: WireAdapter, config?: any).',
level: exports.DiagnosticLevel.Error,
url: '',
},
API_AND_TRACK_DECORATOR_CONFLICT: {
code: 1093,
message: '@api method or property cannot be used with @track',
level: exports.DiagnosticLevel.Error,
url: '',
},
CONFIG_OBJECT_SHOULD_BE_SECOND_PARAMETER: {
code: 1094,
message: '@wire expects a configuration object expression as second parameter.',
level: exports.DiagnosticLevel.Error,
url: '',
},
CONFLICT_WITH_ANOTHER_DECORATOR: {
code: 1095,
message: '@wire method or property cannot be used with @{0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
DUPLICATE_API_PROPERTY: {
code: 1096,
message: 'Duplicate @api property "{0}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
FUNCTION_IDENTIFIER_SHOULD_BE_FIRST_PARAMETER: {
code: 1097,
message: '@wire expects a function identifier as first parameter.',
level: exports.DiagnosticLevel.Error,
url: '',
},
IMPORTED_FUNCTION_IDENTIFIER_SHOULD_BE_FIRST_PARAMETER: {
code: 1098,
message: '@wire expects a function identifier to be imported as first parameter.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_BOOLEAN_PUBLIC_PROPERTY: {
code: 1099,
message: 'Boolean public property must default to false.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_DECORATOR: {
code: 1100,
message: 'Invalid decorator usage. Supported decorators ({0}) should be imported from "{1}"',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_DECORATOR_TYPE: {
code: 1101,
message: 'Invalid property of field type',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_DECORATOR_WITH_NAME: {
code: 1102,
message: 'Invalid \'{0}\' decorator usage. Supported decorators ({1}) should be imported from "{2}"',
level: exports.DiagnosticLevel.Error,
url: '',
},
IS_NOT_CLASS_PROPERTY_OR_CLASS_METHOD: {
code: 1103,
message: '"@{0}" can only be applied on class properties',
level: exports.DiagnosticLevel.Error,
url: '',
},
IS_NOT_DECORATOR: {
code: 1104,
message: '"{0}" can only be used as a class decorator',
level: exports.DiagnosticLevel.Error,
url: '',
},
ONE_WIRE_DECORATOR_ALLOWED: {
code: 1105,
message: 'Method or property can only have 1 @wire decorator',
level: exports.DiagnosticLevel.Error,
url: '',
},
PROPERTY_CANNOT_BE_COMPUTED: {
code: 1106,
message: '@api cannot be applied to a computed property, getter, setter or method.',
level: exports.DiagnosticLevel.Error,
url: '',
},
PROPERTY_NAME_CANNOT_START_WITH_DATA: {
code: 1107,
message: 'Invalid property name "{0}". Properties starting with "data" are reserved attributes.',
level: exports.DiagnosticLevel.Error,
url: '',
},
PROPERTY_NAME_CANNOT_START_WITH_ON: {
code: 1108,
message: 'Invalid property name "{0}". Properties starting with "on" are reserved for event handlers.',
level: exports.DiagnosticLevel.Error,
url: '',
},
PROPERTY_NAME_IS_AMBIGUOUS: {
code: 1109,
message: 'Ambiguous attribute name "{0}". "{0}" will never be called from template because its corresponding property is camel cased. Consider renaming to "{1}".',
level: exports.DiagnosticLevel.Error,
url: '',
},
PROPERTY_NAME_IS_RESERVED: {
code: 1110,
message: 'Invalid property name "{0}". "{0}" is a reserved attribute.',
level: exports.DiagnosticLevel.Error,
url: '',
},
PROPERTY_NAME_PART_IS_RESERVED: {
code: 1111,
message: 'Invalid property name "{0}". "part" is a future reserved attribute for web components.',
level: exports.DiagnosticLevel.Error,
url: '',
},
SINGLE_DECORATOR_ON_SETTER_GETTER_PAIR: {
code: 1112,
message: '@api get {0} and @api set {0} detected in class declaration. Only one of the two needs to be decorated with @api.',
level: exports.DiagnosticLevel.Error,
url: '',
},
TRACK_ONLY_ALLOWED_ON_CLASS_PROPERTIES: {
code: 1113,
message: '@track decorator can only be applied to class properties.',
level: exports.DiagnosticLevel.Error,
url: '',
},
WIRE_ADAPTER_SHOULD_BE_IMPORTED: {
code: 1119,
message: 'Failed to resolve @wire adapter "{0}". Ensure it is imported.',
level: exports.DiagnosticLevel.Error,
url: '',
},
FUNCTION_IDENTIFIER_CANNOT_HAVE_COMPUTED_PROPS: {
code: 1131,
message: '@wire identifier cannot contain computed properties',
level: exports.DiagnosticLevel.Error,
url: '',
},
FUNCTION_IDENTIFIER_CANNOT_HAVE_NESTED_MEMBER_EXRESSIONS: {
code: 1132,
message: '@wire identifier cannot contain nested member expressions',
level: exports.DiagnosticLevel.Error,
url: '',
},
COMPUTED_PROPERTY_CANNOT_BE_TEMPLATE_LITERAL: {
code: 1199,
message: 'Cannot use a template literal as a computed property key. Instead, use a string or extract the value to a constant.',
level: exports.DiagnosticLevel.Error,
url: '',
},
COMPUTED_PROPERTY_MUST_BE_CONSTANT_OR_LITERAL: {
code: 1200,
message: 'Computed property in @wire config must be a constant or primitive literal.',
level: exports.DiagnosticLevel.Error,
url: '',
},
};
/*
* Copyright (c) 2024, Salesforce, Inc.
* All rights reserved.
* SPDX-License-Identifier: MIT
* For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
*/
/*
* For the next available error code, reference (and update!) the value in ./index.ts
*/
const TemplateErrors = {
INVALID_TEMPLATE: {
code: 1003,
message: 'Invalid template',
level: exports.DiagnosticLevel.Error,
url: '',
},
OPTIONS_MUST_BE_OBJECT: {
code: 1028,
message: 'Compiler options must be an object',
level: exports.DiagnosticLevel.Error,
url: '',
},
UNKNOWN_IF_MODIFIER: {
code: 1029,
message: 'Unknown if modifier {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
UNKNOWN_OPTION_PROPERTY: {
code: 1030,
message: 'Unknown option property {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
DUPLICATE_ELEMENT_ENTRY: {
code: 1150,
message: 'customRendererConfig contains duplicate entry for {0} element tag',
level: exports.DiagnosticLevel.Error,
url: '',
},
CUSTOM_ELEMENT_TAG_DISALLOWED: {
code: 1151,
message: 'customRendererConfig should not contain a custom element tag, but found {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
};
const ParserDiagnostics = {
AMBIGUOUS_ATTRIBUTE_VALUE: {
code: 1034,
message: 'Ambiguous attribute value {0}. ' +
'If you want to make it a valid identifier you should remove the surrounding quotes {1}. ' +
'If you want to make it a string you should escape it {2}.',
level: exports.DiagnosticLevel.Error,
url: '',
},
AMBIGUOUS_ATTRIBUTE_VALUE_STRING: {
code: 1035,
message: 'Ambiguous attribute value {0}. If you want to make it a string you should escape it {1}',
level: exports.DiagnosticLevel.Error,
url: '',
},
BOOLEAN_ATTRIBUTE_FALSE: {
code: 1036,
message: 'To not set a boolean attribute, try <{0}> instead of <{0} {1}="{2}">. ' +
'To represent a false value, the attribute has to be omitted altogether.',
level: exports.DiagnosticLevel.Error,
url: '',
},
BOOLEAN_ATTRIBUTE_TRUE: {
code: 1037,
message: 'To set a boolean attributes, try <{0} {1}> instead of <{0} {1}="{2}">. ' +
'If the attribute is present, its value must either be the empty string ' +
"or a value that is an ASCII case -insensitive match for the attribute's canonical name " +
'with no leading or trailing whitespace.',
level: exports.DiagnosticLevel.Error,
url: '',
},
COMPUTED_PROPERTY_ACCESS_NOT_ALLOWED: {
code: 1038,
message: "Template expression doesn't allow computed property access",
level: exports.DiagnosticLevel.Error,
url: '',
},
DIRECTIVE_SHOULD_BE_EXPRESSION: {
code: 1039,
message: '{0} directive is expected to be an expression',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_ID_ATTRIBUTE: {
code: 1040,
message: 'Invalid id value "{0}". Id values must not contain any whitespace.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_STATIC_ID_IN_ITERATION: {
code: 1041,
message: 'Static id values are not allowed in iterators. Id values must be unique within a template and must therefore be computed with an expression.',
level: exports.DiagnosticLevel.Warning,
url: '',
},
DUPLICATE_ID_FOUND: {
code: 1042,
message: 'Duplicate id value "{0}" detected. Id values must be unique within a template.',
level: exports.DiagnosticLevel.Error,
url: '',
},
EVENT_HANDLER_SHOULD_BE_EXPRESSION: {
code: 1043,
message: 'Event handler should be an expression',
level: exports.DiagnosticLevel.Error,
url: '',
},
FOR_EACH_AND_FOR_ITEM_DIRECTIVES_SHOULD_BE_TOGETHER: {
code: 1044,
message: 'for:each and for:item directives should be associated together.',
level: exports.DiagnosticLevel.Error,
url: '',
},
FOR_EACH_DIRECTIVE_SHOULD_BE_EXPRESSION: {
code: 1045,
message: 'for:each directive is expected to be a expression.',
level: exports.DiagnosticLevel.Error,
url: '',
},
FOR_INDEX_DIRECTIVE_SHOULD_BE_STRING: {
code: 1046,
message: 'for:index directive is expected to be a string.',
level: exports.DiagnosticLevel.Error,
url: '',
},
FOR_ITEM_DIRECTIVE_SHOULD_BE_STRING: {
code: 1047,
message: 'for:item directive is expected to be a string.',
level: exports.DiagnosticLevel.Error,
url: '',
},
FORBIDDEN_IFRAME_SRCDOC_ATTRIBUTE: {
code: 1048,
message: 'srcdoc attribute is disallowed on <iframe> for security reasons',
level: exports.DiagnosticLevel.Error,
url: '',
},
FORBIDDEN_SVG_NAMESPACE_IN_TEMPLATE: {
code: 1049,
message: "Forbidden svg namespace tag found in template: '<{0}>' tag is not allowed within <svg>",
level: exports.DiagnosticLevel.Error,
url: '',
},
FORBIDDEN_MATHML_NAMESPACE_IN_TEMPLATE: {
code: 1050,
message: "Forbidden MathML namespace tag found in template: '<{0}>' tag is not allowed within <math>",
level: exports.DiagnosticLevel.Error,
url: '',
},
FORBIDDEN_TAG_ON_TEMPLATE: {
code: 1051,
message: "Forbidden tag found in template: '<{0}>' tag is not allowed.",
level: exports.DiagnosticLevel.Error,
url: '',
},
GENERIC_PARSING_ERROR: {
code: 1052,
message: 'Error parsing attribute: {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
IDENTIFIER_PARSING_ERROR: {
code: 1053,
message: 'Error parsing identifier: {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
IF_DIRECTIVE_SHOULD_BE_EXPRESSION: {
code: 1054,
message: 'If directive should be an expression',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_ATTRIBUTE_CASE: {
code: 1055,
message: '{0} is not valid attribute for {1}. All attributes name should be all lowercase.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_EVENT_NAME: {
code: 1056,
message: 'Invalid event type "{0}". Event type must begin with a lower-case alphabetic character and contain only lower-case alphabetic characters, underscores, and numeric characters',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_HTML_ATTRIBUTE: {
code: 1057,
message: '{0} is not valid attribute for {1}. For more information refer to https://developer.mozilla.org/en-US/docs/Web/HTML/Element/{1}',
level: exports.DiagnosticLevel.Warning,
url: '',
},
INVALID_HTML_SYNTAX: {
code: 1058,
message: 'Invalid HTML syntax: {0}. For more information, ' +
'please visit https://html.spec.whatwg.org/multipage/parsing.html#parse-error-{0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_IDENTIFIER: {
code: 1059,
message: '{0} is not a valid identifier',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_NODE: {
code: 1060,
message: "Template expression doesn't allow {0}",
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_TABINDEX_ATTRIBUTE: {
code: 1061,
message: 'The attribute "tabindex" can only be set to "0" or "-1".',
level: exports.DiagnosticLevel.Error,
url: '',
},
DEPRECATED_IS_ATTRIBUTE_CANNOT_BE_EXPRESSION: {
code: 1062,
message: '"is" attribute value can\'t be an expression',
level: exports.DiagnosticLevel.Error,
url: '',
},
IS_ATTRIBUTE_NOT_SUPPORTED: {
code: 1063,
message: '"is" attribute is disallowed',
level: exports.DiagnosticLevel.Error,
url: '',
},
KEY_ATTRIBUTE_SHOULD_BE_EXPRESSION: {
code: 1064,
message: 'Key attribute value should be an expression',
level: exports.DiagnosticLevel.Error,
url: '',
},
KEY_SHOULDNT_REFERENCE_FOR_EACH_INDEX: {
code: 1065,
message: 'Invalid key value for element <{0}>. Key cannot reference for:each index {1}',
level: exports.DiagnosticLevel.Error,
url: '',
},
KEY_SHOULDNT_REFERENCE_ITERATOR_INDEX: {
code: 1066,
message: 'Invalid key value for element <{0}>. Key cannot reference iterator index',
level: exports.DiagnosticLevel.Error,
url: '',
},
MISSING_KEY_IN_ITERATOR: {
code: 1071,
message: 'Missing key for element <{0}> inside of iterator. Elements within iterators must have a unique, computed key value.',
level: exports.DiagnosticLevel.Error,
url: '',
},
MISSING_ROOT_TEMPLATE_TAG: {
code: 1072,
message: 'Missing root template tag',
level: exports.DiagnosticLevel.Error,
url: '',
},
MODIFYING_ITERATORS_NOT_ALLOWED: {
code: 1073,
message: "Template expression doesn't allow to modify iterators",
level: exports.DiagnosticLevel.Error,
url: '',
},
MULTIPLE_EXPRESSIONS: {
code: 1074,
message: 'Multiple expressions found',
level: exports.DiagnosticLevel.Error,
url: '',
},
MULTIPLE_ROOTS_FOUND: {
code: 1075,
message: 'Multiple roots found',
level: exports.DiagnosticLevel.Error,
url: '',
},
NAME_ON_SLOT_CANNOT_BE_EXPRESSION: {
code: 1076,
message: "Name attribute on slot tag can't be an expression.",
level: exports.DiagnosticLevel.Error,
url: '',
},
NO_DIRECTIVE_FOUND_ON_TEMPLATE: {
code: 1077,
message: 'Invalid template tag. A directive is expected to be associated with the template tag.',
level: exports.DiagnosticLevel.Error,
url: '',
},
NO_MATCHING_CLOSING_TAGS: {
code: 1078,
message: '<{0}> has no matching closing tag.',
level: exports.DiagnosticLevel.Error,
url: '',
},
ROOT_TAG_SHOULD_BE_TEMPLATE: {
code: 1079,
message: 'Expected root tag to be template, found {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
ROOT_TEMPLATE_HAS_UNKNOWN_ATTRIBUTES: {
code: 1080,
message: 'Root template has unknown or disallowed attributes: {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3100]: Update message to point to external documentation once available.
SLOT_TAG_CANNOT_HAVE_DIRECTIVES: {
code: 1082,
message: "<slot> tag can't be associated with {0} template directives.",
level: exports.DiagnosticLevel.Error,
url: '',
},
TEMPLATE_EXPRESSION_PARSING_ERROR: {
code: 1083,
message: 'Error parsing template expression: {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
UNEXPECTED_IF_MODIFIER: {
code: 1084,
message: 'Unexpected if modifier {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_DOM_INVALID_VALUE: {
code: 1085,
message: 'Invalid value for "lwc:dom". \'lwc:dom\' can only be set to {0}',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_DOM_INVALID_CONTENTS: {
code: 1086,
message: 'Invalid contents for element with "lwc:dom". Element must be empty',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_DOM_INVALID_CUSTOM_ELEMENT: {
code: 1087,
message: 'Invalid directive "lwc:dom" on element {0}. "lwc:dom" cannot be added to a custom element',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_DOM_INVALID_SLOT_ELEMENT: {
code: 1088,
message: 'Invalid directive "lwc:dom" on <slot>.. "lwc:dom" cannot be added to a <slot>',
level: exports.DiagnosticLevel.Error,
url: '',
},
STYLE_TAG_NOT_ALLOWED_IN_TEMPLATE: {
code: 1122,
message: "The <style> element is disallowed inside the template. Please add css rules into '.css' file of your component bundle.",
level: exports.DiagnosticLevel.Error,
url: '',
},
UNKNOWN_HTML_TAG_IN_TEMPLATE: {
code: 1123,
message: "Unknown html tag '<{0}>'. For more information refer to https://developer.mozilla.org/en-US/docs/Web/HTML/Element and https://developer.mozilla.org/en-US/docs/Web/SVG/Element",
level: exports.DiagnosticLevel.Warning,
url: '',
},
ATTRIBUTE_NAME_STARTS_WITH_INVALID_CHARACTER: {
code: 1124,
message: '{0} is not valid attribute for {1}. Attribute name must start with an underscore, dollar sign, or an optional hyphen character followed by an alphabetic character.',
level: exports.DiagnosticLevel.Error,
url: '',
},
ATTRIBUTE_NAME_MUST_END_WITH_ALPHA_NUMERIC_CHARACTER: {
code: 1125,
message: '{0} is not valid attribute for {1}. Attribute name must end with alpha-numeric character.',
level: exports.DiagnosticLevel.Error,
url: '',
},
UNKNOWN_LWC_DIRECTIVE: {
code: 1127,
message: 'Invalid directive "{0}" on element {1}.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_OPTS_LWC_DYNAMIC: {
code: 1128,
message: 'Invalid lwc:dynamic usage. The LWC dynamic directive must be enabled in order to use this feature.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_DYNAMIC_ON_NATIVE_ELEMENT: {
code: 1129,
message: 'Invalid lwc:dynamic usage on element "{0}". This directive can only be used in a custom element.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_DYNAMIC_LITERAL_PROP: {
code: 1130,
message: 'Invalid lwc:dynamic usage on element "{0}". The directive binding must be an expression.',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_RENDER_MODE_INVALID_VALUE: {
code: 1133,
message: 'Invalid value for "lwc:render-mode". \'lwc:render-mode\' can only be set to "shadow", or "light"',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_LIGHT_SLOT_INVALID_ATTRIBUTES: {
code: 1134,
message: "Invalid attribute(s) '{0}' on slot. Slots in Light DOM templates (which have 'lwc:render-mode' directive) can only have [{1}] attributes",
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_DOM_INVALID_IN_LIGHT_DOM: {
code: 1135,
message: "Invalid directive 'lwc:dom' on element {0}. 'lwc:dom' is not necessary in Light DOM components.",
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_FOR_EACH_WITH_ITERATOR: {
code: 1136,
message: "Invalid usage for 'for:each' and '{0}' directives on the same element.",
level: exports.DiagnosticLevel.Error,
url: '',
},
NO_DUPLICATE_SLOTS: {
code: 1137,
message: 'Invalid duplicate slot ({0}).',
level: exports.DiagnosticLevel.Warning,
url: '',
},
NO_SLOTS_IN_ITERATOR: {
code: 1138,
message: 'Invalid slot ({0}). A slot cannot appear inside of an iterator.',
level: exports.DiagnosticLevel.Warning,
url: '',
},
LWC_LIGHT_SLOT_INVALID_EVENT_LISTENER: {
code: 1139,
message: "Invalid event listener '{0}' on slot. Slots in Light DOM templates cannot have event listeners.",
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_INNER_HTML_INVALID_CUSTOM_ELEMENT: {
code: 1140,
message: 'Invalid lwc:inner-html usage on element "{0}". The directive can\'t be used on a custom element or special LWC managed elements denoted with lwc:*.',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_INNER_HTML_INVALID_ELEMENT: {
code: 1141,
message: 'Invalid lwc:inner-html usage on element "{0}". The directive can\'t be used on a slot or a template element.',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_INNER_HTML_INVALID_CONTENTS: {
code: 1142,
message: 'Invalid lwc:inner-html usage on element "{0}". The directive can\'t be used on an element with content.',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_INNER_HTML_INVALID_VALUE: {
code: 1143,
message: 'Invalid lwc:inner-html usage on element "{0}". The directive binding can only be an expression or a string.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_HTML_RECOVERY: {
code: 1144,
message: 'Invalid HTML detected, "<{0}>" was automatically inserted within "<{1}>"; the compiled template may not match the template source.',
level: exports.DiagnosticLevel.Warning,
url: '',
},
INVALID_TEMPLATE_ATTRIBUTE: {
code: 1145,
message: 'Invalid attributes detected on template. The following attributes are not supported on template tags in LWC: {0}. For more information, ' +
'please visit https://sfdc.co/template-directives',
level: exports.DiagnosticLevel.Warning,
url: '',
},
PRESERVE_COMMENTS_MUST_BE_BOOLEAN: {
code: 1146,
message: 'lwc:preserve-comments must be a boolean attribute.',
level: exports.DiagnosticLevel.Error,
url: '',
},
DUPLICATE_ATTR_PROP_TRANSFORM: {
code: 1147,
message: 'Found multiple HTML attributes mapping to the same JavaScript property. "{0}" and "{1}" both map to "{2}".',
level: exports.DiagnosticLevel.Warning,
url: '',
},
INVALID_HTML_SYNTAX_WARNING: {
code: 1148,
message: 'Invalid HTML syntax: {0}. This will not be supported in future versions of LWC. For more information, ' +
'please visit https://html.spec.whatwg.org/multipage/parsing.html#parse-error-{0}',
level: exports.DiagnosticLevel.Warning,
url: '',
},
KEY_SHOULD_BE_IN_ITERATION: {
code: 1149,
message: 'Invalid key attribute on element <{0}>. The key attribute should be applied to an element with for:each or iterator:*, or to a direct child of a <template> element with for:each or iterator:*. This key will be ignored, and may throw an error in future versions of LWC.',
level: exports.DiagnosticLevel.Warning,
url: '',
},
INVALID_TEMPLATE_WARNING: {
code: 1153,
message: 'Non-root template elements must contain valid LWC template directive attributes. Otherwise, the template and its children will be ignored. ' +
'For more information please visit https://sfdc.co/template-directives',
level: exports.DiagnosticLevel.Warning,
url: '',
},
INVALID_LWC_SPREAD_LITERAL_PROP: {
code: 1155,
message: 'Invalid lwc:spread usage on element "{0}". The directive binding must be an expression.',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_REF_INVALID_ELEMENT: {
code: 1156,
message: 'Invalid lwc:ref usage on element "{0}". The directive can\'t be used on a slot or a template element.',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_REF_INVALID_VALUE: {
code: 1157,
message: 'Invalid lwc:ref usage on element "{0}". The directive binding must be a non-empty string.',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_REF_INVALID_LOCATION_INSIDE_ITERATION: {
code: 1158,
message: 'Invalid lwc:ref usage on element "{0}". lwc:ref cannot be used inside for:each or an iterator.',
level: exports.DiagnosticLevel.Error,
url: '',
},
IF_BLOCK_DIRECTIVE_SHOULD_BE_EXPRESSION: {
code: 1159,
message: 'lwc:if directive value should be an expression',
level: exports.DiagnosticLevel.Error,
url: '',
},
ELSEIF_BLOCK_DIRECTIVE_SHOULD_BE_EXPRESSION: {
code: 1160,
message: 'lwc:elseif directive value should be an expression',
level: exports.DiagnosticLevel.Error,
url: '',
},
ELSE_BLOCK_DIRECTIVE_CANNOT_HAVE_VALUE: {
code: 1161,
message: 'lwc:else directive cannot have a value',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_IF_BLOCK_DIRECTIVE_WITH_CONDITIONAL: {
code: 1162,
message: "Invalid usage of 'lwc:if' and '{0}' directives on the same element.",
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_ELSEIF_BLOCK_DIRECTIVE_WITH_CONDITIONAL: {
code: 1163,
message: "Invalid usage of 'lwc:elseif' and '{0}' directives on the same element.",
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_ELSE_BLOCK_DIRECTIVE_WITH_CONDITIONAL: {
code: 1164,
message: "Invalid usage of 'lwc:else' and '{0}' directives on the same element.",
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_IF_SCOPE_NOT_FOUND: {
code: 1165,
message: "'{0}' directive must be used immediately after an element with 'lwc:if' or 'lwc:elseif'. No such element found.",
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_IF_CANNOT_BE_USED_WITH_IF_DIRECTIVE: {
code: 1166,
message: "'{0}' directive cannot be used with 'lwc:if', 'lwc:elseif', or 'lwc:else directives on the same element.",
level: exports.DiagnosticLevel.Error,
url: '',
},
SCOPED_SLOT_BIND_IN_LIGHT_DOM_ONLY: {
code: 1169,
message: 'Invalid lwc:slot-bind usage on <slot> element. Scoped slots usage is allowed in Light DOM templates only.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_SLOT_BIND_LITERAL_PROP: {
code: 1170,
message: 'Invalid lwc:slot-bind usage on element {0}. The directive binding must be an expression.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_SLOT_BIND_NON_SLOT_ELEMENT: {
code: 1171,
message: 'Invalid lwc:slot-bind usage on element {0}. The directive can be used on a <slot> element only.',
level: exports.DiagnosticLevel.Error,
url: '',
},
NO_DUPLICATE_SCOPED_SLOT: {
code: 1172,
message: 'Invalid duplicate scoped slots ({0})',
level: exports.DiagnosticLevel.Error,
url: '',
},
NO_MIXED_SLOT_TYPES: {
code: 1173,
message: 'Mixing slot types disallowed for same ({0}) slot.',
level: exports.DiagnosticLevel.Error,
url: '',
},
SLOT_DATA_VALUE_SHOULD_BE_STRING: {
code: 1174,
message: 'lwc:slot-data attribute value is expected to be a string.',
level: exports.DiagnosticLevel.Error,
url: '',
},
SCOPED_SLOT_DATA_ON_TEMPLATE_ONLY: {
code: 1176,
message: 'lwc:slot-data directive can be used on <template> elements only.',
level: exports.DiagnosticLevel.Error,
url: '',
},
NON_ELEMENT_SCOPED_SLOT_CONTENT: {
code: 1177,
message: '<template> tag with lwc:slot-data directive cannot contain a comment or text node as a direct child.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_PARENT_OF_LWC_SLOT_DATA: {
code: 1178,
message: '<template> tag with lwc:slot-data directive must be the direct child of a custom element.',
level: exports.DiagnosticLevel.Error,
url: '',
},
SCOPED_SLOTDATA_CANNOT_BE_COMBINED_WITH_OTHER_DIRECTIVE: {
code: 1179,
message: 'lwc:slot-data directive cannot be combined with other directives on the same <template> tag.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_EXTERNAL_ON_NON_CUSTOM_ELEMENT: {
code: 1180,
message: 'Invalid lwc:external directive usage: {0}. This directive can only be used on custom elements.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_EXTERNAL_VALUE: {
code: 1181,
message: 'Invalid lwc:external directive usage: {0}. This directive is a boolean attribute and should not have a value.',
level: exports.DiagnosticLevel.Error,
url: '',
},
SINGLE_IF_DIRECTIVE_ALLOWED: {
code: 1182,
message: `Multiple if: directives found on '{0}'. Only one if: directive is allowed; the rest are ignored.`,
level: exports.DiagnosticLevel.Warning,
url: '',
},
LWC_COMPONENT_TAG_WITHOUT_IS_DIRECTIVE: {
code: 1183,
message: `<lwc:component> must have an 'lwc:is' attribute.`,
level: exports.DiagnosticLevel.Error,
url: '',
},
UNSUPPORTED_LWC_TAG_NAME: {
code: 1184,
message: '{0} is not a special LWC tag name and will be treated as an HTML element.',
level: exports.DiagnosticLevel.Warning,
url: '',
},
INVALID_LWC_IS_DIRECTIVE_VALUE: {
code: 1185,
message: 'Invalid lwc:is usage for value {0}. The value assigned to lwc:is must be an expression.',
level: exports.DiagnosticLevel.Error,
url: '',
},
LWC_IS_INVALID_ELEMENT: {
code: 1186,
message: 'Invalid lwc:is usage for element {0}. The directive can only be used with <lwc:component>',
level: exports.DiagnosticLevel.Error,
url: '',
},
DEPRECATED_LWC_DYNAMIC_ATTRIBUTE: {
code: 1187,
message: `The lwc:dynamic directive is deprecated and will be removed in a future release. Please use lwc:is instead.`,
level: exports.DiagnosticLevel.Warning,
url: '',
},
INVALID_OPTS_LWC_ENABLE_DYNAMIC_COMPONENTS: {
code: 1188,
message: 'Invalid dynamic components usage, lwc:component and lwc:is can only be used when dynamic components have been enabled.',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_ARROW_FN_PARAM: {
code: 1189,
message: "Template expression doesn't allow {0} in arrow function params.",
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_STATEMENTS_PROHIBITED: {
code: 1190,
message: 'Statements are disallowed in template expressions.',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_MUTATION_OUTSIDE_ARROW: {
code: 1191,
message: 'Field mutations are only permitted within arrow functions.',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_DELETE_OP: {
code: 1192,
message: 'Use of the delete operator is prohibited within template expressions.',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_ARROW_FN_BODY: {
code: 1193,
message: 'The body of arrow functions in template expressions must be an expression.',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_ARROW_FN_KIND: {
code: 1194,
message: 'Arrow functions in template expressions cannot be {0}.',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_EARLY_STAGE_FEATURE: {
code: 1195,
message: 'Early-stage JS features are disallowed in template expressions.',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_PROHIBITED_NODE_TYPE: {
code: 1196,
message: 'Use of {0} is disallowed within template expressions.',
level: exports.DiagnosticLevel.Error,
url: '',
},
// TODO [#3370]: remove this error if template expressions is removed
INVALID_EXPR_COMMENTS_DISALLOWED: {
code: 1197,
message: 'Use of comments is disallowed within template expressions.',
level: exports.DiagnosticLevel.Error,
url: '',
},
IGNORED_SLOT_ATTRIBUTE_IN_CHILD: {
code: 1201,
message: 'The slot attribute in {0} will be ignored due to its ancestor {1}. It must be a direct child of the containing component.',
level: exports.DiagnosticLevel.Warning,
url: '',
},
INVALID_LWC_ON_ELEMENT: {
code: 1203,
message: 'Invalid lwc:on usage on element "{0}". The directive can\'t be used on a template element.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_ON_LITERAL_PROP: {
code: 1204,
message: 'Invalid lwc:on usage on element "{0}". The directive binding must be an expression.',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_ON_WITH_DECLARATIVE_LISTENERS: {
code: 1205,
message: 'Invalid lwc:on usage on element "{0}". It is not permitted to use declarative event listeners alongside lwc:on',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_LWC_ON_OPTS: {
code: 1206,
message: 'Invalid lwc:on usage. The `lwc:on` directive must be enabled in order to use this feature.',
level: exports.DiagnosticLevel.Error,
url: '',
},
COMPUTED_PROPERTY_ACCESS_NOT_ALLOWED_COMPLEX: {
code: 1207,
message: 'Template expression doesn\'t allow computed property access unless the expression is surrounded by quotes: "{0}"',
level: exports.DiagnosticLevel.Error,
url: '',
},
INVALID_NODE_COMPLEX: {
code: 1208,
message: 'Template expression doesn\'t allow {0} unless the expression is surrounded by quotes: "{1}"',
level: exports.DiagnosticLevel.Error,
url: '',
},
};
/*
* Copyright (c) 2025, Salesforce, Inc.
* All rights reserved.
* SPDX-License-Identifier: MIT
* For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
*/
/*
* For the next available error code, reference (and update!) the value in ./index.ts
*/
const SsrCompilerErrors = {
RESERVED_IDENTIFIER_PREFIX: {
code: 1202,
message: 'Identifier name cannot start with "__lwc".',
level: exports.DiagnosticLevel.Error,
url: '',
},
};
/*
* Copyright (c) 2024, Salesforce, Inc.
* All rights reserved.
* SPDX-License-Identifier: MIT
* For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/MIT
*/
/**
* Generates a friendly error message for the given error type, using the provided template values.
* @param errorInfo The object holding the error metadata.
* @param args Values used to fill the error message template.
* @returns The generated error message.
*/
function generateErrorMessage(errorInfo, args) {
const message = Array.isArray(args)
? templateString(errorInfo.message, args)
: errorInfo.message;
if (errorInfo.url && errorInfo.url !== '') ;
return `LWC${errorInfo.code}: ${message}`;
}
/**
* Generates a compiler diagnostic. This function is used to look up the specified errorInfo
* and generate a friendly and consistent diagnostic object. Diagnostic contains
* info about the error's code and its origin (filename, line, column) when applicable.
* @param errorInfo The object holding the error metadata.
* @param config A config object providing any message arguments and origin info needed to create the error.
* @returns The generated compiler diagnostic object.
*/
function generateCompilerDiagnostic(errorInfo, config) {
const message = generateErrorMessage(errorInfo, config && config.messageArgs);
const diagnostic = {
code: errorInfo.code,
message,
level: errorInfo.level,
};
if (config && config.origin) {
diagnostic.filename = getFilename(config.origin);
diagnostic.location = getLocation(config.origin);
}
return diagnostic;
}
/**
* Generates a