LibJS: Only "var" declarations go in the global object at program level

"let" and "const" go in the lexical environment.

This fixes one part of #4001 (Lexically declared variables are mixed up
with global object properties)
This commit is contained in:
Andreas Kling 2021-06-09 23:21:42 +02:00
parent d5fa0ea60f
commit 4bc98fd39f
Notes: sideshowbarker 2024-07-18 12:30:37 +09:00
2 changed files with 24 additions and 1 deletions

View file

@ -94,9 +94,11 @@ void Interpreter::enter_scope(const ScopeNode& scope_node, ScopeType scope_type,
HashMap<FlyString, Variable> scope_variables_with_declaration_kind; HashMap<FlyString, Variable> scope_variables_with_declaration_kind;
scope_variables_with_declaration_kind.ensure_capacity(16); scope_variables_with_declaration_kind.ensure_capacity(16);
bool is_program_node = is<Program>(scope_node);
for (auto& declaration : scope_node.variables()) { for (auto& declaration : scope_node.variables()) {
for (auto& declarator : declaration.declarations()) { for (auto& declarator : declaration.declarations()) {
if (is<Program>(scope_node)) { if (is_program_node && declaration.declaration_kind() == DeclarationKind::Var) {
declarator.target().visit( declarator.target().visit(
[&](const NonnullRefPtr<Identifier>& id) { [&](const NonnullRefPtr<Identifier>& id) {
global_object.put(id->string(), js_undefined()); global_object.put(id->string(), js_undefined());

View file

@ -0,0 +1,21 @@
var foo = 1;
let bar = 2;
const baz = 3;
test("behavior of program-level var/let/const", () => {
expect(foo).toBe(1);
expect(bar).toBe(2);
expect(baz).toBe(3);
expect(globalThis.foo).toBe(1);
expect(globalThis.bar).toBeUndefined();
expect(globalThis.baz).toBeUndefined();
globalThis.foo = 4;
globalThis.bar = 5;
globalThis.baz = 6;
expect(foo).toBe(4);
expect(bar).toBe(2);
expect(baz).toBe(3);
expect(globalThis.foo).toBe(4);
expect(globalThis.bar).toBe(5);
expect(globalThis.baz).toBe(6);
});