Property Descriptors

  • There are four descriptors for a property of an object:
    • value
    • writable: boolean
    • enumerable: boolean
    • configurable: boolean
  • When object is created, by default all the flags are true

Get the descriptors of property of object

const obj = {
    "a": 1
};
 
console.log(Object.getOwnPropertyDescriptor(obj, 'a'));
{ value: 1, writable: true, enumerable: true, configurable: true }

writable

  • If value can be changed or not
  • If false then it is readonly. In non-strict mode no error occurs when writing to to readonly property but still it will not succeed

enumerable

  • if property will be listed in loops like for...in

configurable

  • If modification is possible
  • If false then it cannot be deleted via delete or any property flag cannot modified
  • Making a property non-configurable i.e false is a one-way road. We cannot change it back to true
  • Exception: flags of non-configurable property cannot be updated except the following:
    • writable: true writable: false (only one way change is possible)

Changing the property descriptor flags

  • It can be done using Object.defineProperty
let user = {
  name: "John",
};
 
// Changing the descriptor
Object.defineProperty(user, "name", {
  writable: false,
});
 
// trying to assign to readonly property
// if non-strict mode:
//     * no error but operation will be unsuccessful
// If strict mode:
//     * error: TypeError: Cannot assign to read only property 'name' of object
user.name = "Pete";
 
// Will output John not Pete
console.log(user.name);
  • Behavior of configurable:
let user = {
  name: "John",
};
 
Object.defineProperty(user, "name", {
  configurable: false,
});
 
// Once configurable is set false, we cannot make it true or change other flags
// error: TypeError: Cannot redefine property: name
// Object.defineProperty(user, "name", {
//   configurable: true,
// });
 
// updation of value is possible
user.name = 'Pete'
 
// non-strict mode: no error but operation will be unsuccessful
// strict mode: TypeError: Cannot delete property 'name'
delete user.name;
 
// Pete
console.log(user.name);

Property Descriptor functions

  • Object.preventExtensions(obj)
    • Can be done one way only
    • Prevents adding new properties to the object while existing ones can be updated/deleted
    • Testing function:
      • Object.isExtensible()
  • Object.seal(obj)
    • Forbids adding/removing of properties
    • Sets configurable: false for all existing properties
    • Testing function:
      • Object.isSealed()
  • Object.freeze(obj)
    • Forbids adding/removing/changing of properties
    • Sets configurable: false, writable: false for all existing properties.
    • Testing function:
      • Object.isFrozen()