From 4aa815f1ec13722f4f0fbc1a0dcbe707fa476294 Mon Sep 17 00:00:00 2001 From: Rich Harris Date: Thu, 1 Aug 2024 15:57:40 -0400 Subject: [PATCH] chore: dedupe list of reserved words (#12691) --- .../src/compiler/phases/1-parse/index.js | 4 +- .../svelte/src/compiler/phases/constants.js | 40 ------------- packages/svelte/src/compiler/phases/scope.js | 5 +- packages/svelte/src/constants.js | 51 ---------------- packages/svelte/src/utils.js | 59 +++++++++++++++++++ 5 files changed, 64 insertions(+), 95 deletions(-) diff --git a/packages/svelte/src/compiler/phases/1-parse/index.js b/packages/svelte/src/compiler/phases/1-parse/index.js index c5808f313a..1bf52cd932 100644 --- a/packages/svelte/src/compiler/phases/1-parse/index.js +++ b/packages/svelte/src/compiler/phases/1-parse/index.js @@ -3,11 +3,11 @@ import { isIdentifierStart, isIdentifierChar } from 'acorn'; import fragment from './state/fragment.js'; import { regex_whitespace } from '../patterns.js'; -import { reserved } from '../../../constants.js'; import full_char_code_at from './utils/full_char_code_at.js'; import * as e from '../../errors.js'; import { create_fragment } from './utils/create.js'; import read_options from './read/options.js'; +import { is_reserved } from '../../../utils.js'; const regex_position_indicator = / \(\d+:\d+\)$/; @@ -219,7 +219,7 @@ export class Parser { const identifier = this.template.slice(this.index, (this.index = i)); - if (!allow_reserved && reserved.includes(identifier)) { + if (!allow_reserved && is_reserved(identifier)) { e.unexpected_reserved_word(start, identifier); } diff --git a/packages/svelte/src/compiler/phases/constants.js b/packages/svelte/src/compiler/phases/constants.js index 4046f665ef..8696692e99 100644 --- a/packages/svelte/src/compiler/phases/constants.js +++ b/packages/svelte/src/compiler/phases/constants.js @@ -188,43 +188,3 @@ export const EventModifiers = [ 'self', 'trusted' ]; - -export const JsKeywords = [ - 'class', - 'break', - 'const', - 'let', - 'var', - 'continue', - 'if', - 'for', - 'while', - 'do', - 'new', - 'static', - 'true', - 'false', - 'void', - 'with', - 'yield', - 'await', - 'typeof', - 'throw', - 'throws', - 'null', - 'delete', - 'default', - 'catch', - 'debugger', - 'case', - 'arguments', - 'else', - 'extends', - 'export', - 'import', - 'extends', - 'switch', - 'instanceof', - 'return', - 'this' -]; diff --git a/packages/svelte/src/compiler/phases/scope.js b/packages/svelte/src/compiler/phases/scope.js index 6051dda570..49ccfed4ec 100644 --- a/packages/svelte/src/compiler/phases/scope.js +++ b/packages/svelte/src/compiler/phases/scope.js @@ -12,7 +12,8 @@ import { object, unwrap_pattern } from '../utils/ast.js'; -import { JsKeywords, Runes } from './constants.js'; +import { Runes } from './constants.js'; +import { is_reserved } from '../../utils.js'; export class Scope { /** @type {ScopeRoot} */ @@ -148,7 +149,7 @@ export class Scope { this.references.has(name) || this.declarations.has(name) || this.root.conflicts.has(name) || - JsKeywords.includes(name) + is_reserved(name) ) { name = `${preferred_name}_${n++}`; } diff --git a/packages/svelte/src/constants.js b/packages/svelte/src/constants.js index 42653d91c1..049a3821a9 100644 --- a/packages/svelte/src/constants.js +++ b/packages/svelte/src/constants.js @@ -129,57 +129,6 @@ export function is_capture_event(name, mode = 'exclude-on') { : name !== 'ongotpointercapture' && name !== 'onlostpointercapture'; } -export const reserved = [ - 'arguments', - 'await', - 'break', - 'case', - 'catch', - 'class', - 'const', - 'continue', - 'debugger', - 'default', - 'delete', - 'do', - 'else', - 'enum', - 'eval', - 'export', - 'extends', - 'false', - 'finally', - 'for', - 'function', - 'if', - 'implements', - 'import', - 'in', - 'instanceof', - 'interface', - 'let', - 'new', - 'null', - 'package', - 'private', - 'protected', - 'public', - 'return', - 'static', - 'super', - 'switch', - 'this', - 'throw', - 'true', - 'try', - 'typeof', - 'var', - 'void', - 'while', - 'with', - 'yield' -]; - // we use a list of ignorable runtime warnings because not every runtime warning // can be ignored and we want to keep the validation for svelte-ignore in place export const IGNORABLE_RUNTIME_WARNINGS = /** @type {const} */ ([ diff --git a/packages/svelte/src/utils.js b/packages/svelte/src/utils.js index 6e083d5d6d..1ba3dff435 100644 --- a/packages/svelte/src/utils.js +++ b/packages/svelte/src/utils.js @@ -39,3 +39,62 @@ const VOID_ELEMENT_NAMES = [ export function is_void(name) { return VOID_ELEMENT_NAMES.includes(name) || name.toLowerCase() === '!doctype'; } + +const RESERVED_WORDS = [ + 'arguments', + 'await', + 'break', + 'case', + 'catch', + 'class', + 'const', + 'continue', + 'debugger', + 'default', + 'delete', + 'do', + 'else', + 'enum', + 'eval', + 'export', + 'extends', + 'false', + 'finally', + 'for', + 'function', + 'if', + 'implements', + 'import', + 'in', + 'instanceof', + 'interface', + 'let', + 'new', + 'null', + 'package', + 'private', + 'protected', + 'public', + 'return', + 'static', + 'super', + 'switch', + 'this', + 'throw', + 'true', + 'try', + 'typeof', + 'var', + 'void', + 'while', + 'with', + 'yield' +]; + +/** + * Returns `true` if `word` is a reserved JavaScript keyword + * @param {string} word + */ +export function is_reserved(word) { + return RESERVED_WORDS.includes(word); +}