Since 2015, JavaScript has improved immensely.
It’s much more pleasant to use it now than ever.
In this article, we’ll look at new OOP features in JavaScript.
The proto Property
We can use the __proto__
property to get and set the prototype of an object easily.
For example, we can write:
Object.getPrototypeOf({ __proto__: null })
Then it’ll return null
since we set the __proto__
property to null
.
This doesn’t work with the string version of the key as it creates its own property:
Object.getPrototypeOf({ ['__proto__']: null })
It’ll return Object.prototype
.
And Object.keys({ [‘__proto__’]: null })
returns the array[ ‘__proto__’ ]
.
Also, if we define our own property named __proto__
, it also won’t work.
For instance, we can write:
const obj = {};
Object.defineProperty(obj, '__proto__', { value: 'bar' })
Objects that don’t have Object.prototype as a Prototype
We can use the Object.create
method with the argument null
to create an object with no prototype.
For example, we can write:
const obj = Object.create(null);
Then obj
has no __proto__
property.
This method makes it easy to create dictionary objects where we don’t want any inherited properties from it.
proto and JSON
__proto__
may be stringified with JSON.stringify
.
For example, we can write:
JSON.stringify({['__proto__']: 'foo' })
And then that returns:
"{"__proto__":"foo"}"
Detecting support for ES6-style proto
There are several ways to detect the ES6 style __proto__
property.
We can check it with the Object.prototype.__proto__
property and the __proto__
in the object literals.
For example, we can write:
const supported = ({}).hasOwnProperty.call(Object.prototype, '__proto__');
We check if the Object.prototype.__proto__
property exists.
We can also check that getter and setter of __proto__
are functions to make sure that we can get and set the value of this property.
For example, we can write:
const desc = Object.getOwnPropertyDescriptor(Object.prototype, '__proto__');
const supported = (
typeof desc.get === 'function' && typeof desc.set === 'function'
);
And we can also use the Object.getPrototypeOf
method to do the check by passing in an object with the __proto__
property set to null
.
Then we can use that to check if the prototype returned is null
.
For example, we can write:
const supported = Object.getPrototypeOf({__proto__: null}) === null;
Enumerability in ES6
In JavaScript, each object can have zero or more p[roperties.
Each property has a key and 3 or more descriptors.
All properties have the enumerable
and configurable
attributes
enumerable
means that whether we show the property everywhere.
configurable
set to false
disables property value changes and prevents deletion.
Properties have the value
and writable
attributes.
value
has the value of the property.
And writable
controls whether we can change the value of the property.
Properties also have the getter get
accessor and setter set
accessor.
We can use the Object.getOwnPropertyDescriptor
method to get the property descriptors.
For example, we can write:
const obj = { foo: 'bar' };
consr desc = Object.getOwnPropertyDescriptor(obj, 'foo')
Then desc
is:
{
value: "bar",
writable: true,
enumerable: true,
configurable: true
}
Conclusion
Object properties have property descriptors.
Also, the __proto__
property acts differently in different contexts.
We can check if the property is available in different ways.