JavaScript supports OOP by allowing you to create and work with objects. Objects are instances of classes (or prototypes) and can have properties (attributes) and methods (functions). Constructors and prototypes are used to create and extend classes.
Objects in JavaScript inherit properties and methods from their prototypes.
When you access a property or method on an object, if it's not found on the object itself, the JavaScript engine looks up the prototype chain until it finds the property or reaches the end of the chain.
For inheritance, JavaScript only has one construct: objects. Unlike classical inheritance in other programming languages, JavaScript uses a prototype chain to achieve inheritance where objects can inherit properties and methods from other objects.
All objects in JavaScript inherit from at least one other object. The object being inherited from is known as the prototype, and the inherited properties can be found in the prototype object of the constructor.
Each object has a private property [[Prototype]] which holds a link to another object called its prototype. This prototype object, in turn, may have its own [[Prototype]], and so on until an object is reached with null as its prototype forming a prototype chain.
By definition, null has no prototype, and acts as the final link in this prototype chain.
It is possible to mutate any member of the prototype chain or even swap out the prototype at runtime, so concepts like static dispatching do not exist in JavaScript.