- Home
- /
- Tutorials
- /
- JavaScript Tutorial
- /
- JavaScript Reflect
JavaScript Performance
JavaScript Reflect
Reflectprovides the same operations as a Proxy trap, as plain functions you can call directly.
It mirrors the traps a Proxy handler can define.
Its main job is forwarding an operation from inside a trap to the real target.
Example
Example
javascript
const person = { name: "Ada" };
console.log(Reflect.get(person, "name"));
console.log(Reflect.has(person, "name"));Both do exactly what the equivalent plain syntax would do.
Reflect's Methods
Reflect.get and Reflect.set read and write a property.
Reflect.has is the same check as the in operator.
Reflect.ownKeys lists an object's own property names.
Syntax
Syntax
javascript
Reflect.get(target, key);
Reflect.set(target, key, value);Every Reflect method has a matching Proxy trap of the same name.
Forwarding Inside a Proxy
This is the pattern you will see constantly.
The trap does something extra, then forwards the real work to Reflect.
Example
Example
javascript
const target = { name: "Ada" };
const reads = [];
const proxy = new Proxy(target, {
get(obj, key) {
reads.push(key);
return Reflect.get(obj, key);
}
});
console.log(proxy.name);
console.log(reads.join(","));Reflect.get does exactly what obj[key] would, but as a function call.
Reflect.set Returns Success or Failure
Unlike a plain assignment, it tells you whether the write actually worked.
Example
Example
javascript
const frozen = Object.freeze({ name: "Ada" });
const succeeded = Reflect.set(frozen, "name", "Grace");
console.log(succeeded);
console.log(frozen.name);The output is false then Ada: the frozen object refused the write.
Listing Own Keys
This includes both string and symbol keys, unlike Object.keys.
Example
Example
javascript
const person = { name: "Ada", age: 36 };
console.log(Reflect.ownKeys(person).join(","));The output is name,age.
Deleting Through Reflect
Reflect.deleteProperty mirrors the delete operator, and returns success.
Example
Example
javascript
const person = { name: "Ada", age: 36 };
const removed = Reflect.deleteProperty(person, "age");
console.log(removed);
console.log(Reflect.has(person, "age"));The output is true then false.
Why Not Just Use Plain Syntax?
For everyday code, obj.prop and obj.prop = value are perfectly fine.
Reflect exists for exactly one job: mirroring Proxy traps as callable functions.
Example
Example
javascript
const target = { name: "Ada" };
const plain = target.name;
const viaReflect = Reflect.get(target, "name");
console.log(plain === viaReflect);Both give the same answer; Reflect is only needed inside a trap.
Complete Example
Complete Example
html
<!DOCTYPE html>
<html>
<head>
<title>JavaScript Reflect</title>
</head>
<body>
<h1>Reflect</h1>
<p id="out"></p>
<script>
const target = { name: "Ada", age: 36 };
const log = [];
const proxy = new Proxy(target, {
get(obj, key) {
log.push("read " + String(key));
return Reflect.get(obj, key);
},
set(obj, key, value) {
log.push("wrote " + String(key));
return Reflect.set(obj, key, value);
}
});
proxy.name;
proxy.age = 37;
document.getElementById("out").innerHTML =
log.join("<br>") + "<br>New age: " + target.age;
</script>
</body>
</html>Try It Yourself
Run the above example in the Try It Editor.
Try Reflect.has:
Add console.log(Reflect.has(target, "age")) and check the result.
Important Points
- Reflect provides the same operations as Proxy traps, as functions.
Reflect.getandsetread and write properties.Reflect.setreturns whether the write actually succeeded.Reflect.ownKeyslists every own property key.- Its main use is forwarding an operation from inside a Proxy trap.
Conclusion
Reflect and Proxy are designed as a pair.
Outside a Proxy trap you will rarely need it; plain syntax is simpler.
Together they are the mechanism behind reactive libraries and validation wrappers alike.
