diff --git a/Userland/Libraries/LibJS/Runtime/Object.cpp b/Userland/Libraries/LibJS/Runtime/Object.cpp index 3c989a7c7e..0e9bbaac85 100644 --- a/Userland/Libraries/LibJS/Runtime/Object.cpp +++ b/Userland/Libraries/LibJS/Runtime/Object.cpp @@ -751,19 +751,16 @@ Value Object::get_by_index(u32 property_index) const { const Object* object = this; while (object) { - if (is(*this)) { - auto& string = static_cast(this)->primitive_string().string(); + if (is(*object)) { + auto& string = static_cast(*object).primitive_string().string(); if (property_index < string.length()) return js_string(heap(), string.substring(property_index, 1)); - return js_undefined(); - } - if (static_cast(property_index) < object->m_indexed_properties.array_like_size()) { + } else if (static_cast(property_index) < object->m_indexed_properties.array_like_size()) { auto result = object->m_indexed_properties.get(const_cast(this), property_index); if (vm().exception()) return {}; if (result.has_value() && !result.value().value.is_empty()) return result.value().value; - return {}; } object = object->prototype(); if (vm().exception()) diff --git a/Userland/Libraries/LibJS/Tests/indexed-access-prototype-indirection.js b/Userland/Libraries/LibJS/Tests/indexed-access-prototype-indirection.js new file mode 100644 index 0000000000..47444a3c0b --- /dev/null +++ b/Userland/Libraries/LibJS/Tests/indexed-access-prototype-indirection.js @@ -0,0 +1,29 @@ +describe("normal behavior", () => { + test("regular object indexing", () => { + const o = {}; + const p = { 0: "foo" }; + Object.setPrototypeOf(o, p); + expect(o[0]).toBe("foo"); + }); + + test("array object indexing", () => { + const o = []; + const p = ["foo"]; + Object.setPrototypeOf(o, p); + expect(o[0]).toBe("foo"); + }); + + test("array object hole indexing", () => { + const o = [,]; + const p = ["foo"]; + Object.setPrototypeOf(o, p); + expect(o[0]).toBe("foo"); + }); + + test("string object indexing", () => { + const o = new String(""); + const p = new String("a"); + Object.setPrototypeOf(o, p); + expect(o[0]).toBe("a"); + }); +});