How does the prototype chain work?

JavaScript

The short answer

The prototype chain is a series of links between objects. When you try to access a property on an object and it does not exist, JavaScript follows the chain — it looks at the object's prototype, then the prototype's prototype, and so on until it either finds the property or reaches the end of the chain (null).

How it works

Every object in JavaScript has a hidden internal property called [[Prototype]] (you can access it using __proto__ or Object.getPrototypeOf). This property points to another object — its prototype.

Let me show you step by step:

const grandparent = {
familyName: 'Smith',
};
const parent = Object.create(grandparent);
parent.job = 'Engineer';
const child = Object.create(parent);
child.name = 'John';

Now let's access different properties on child:

console.log(child.name); // "John" — found on child itself
console.log(child.job); // "Engineer" — found on parent (one step up)
console.log(child.familyName); // "Smith" — found on grandparent (two steps up)
console.log(child.age); // undefined — not found anywhere in the chain

Here is what JavaScript does when you access child.familyName:

  1. Does child have a familyName property? No.
  2. Does child.__proto__ (which is parent) have it? No.
  3. Does parent.__proto__ (which is grandparent) have it? Yes. Return "Smith".

If it had not found it on grandparent either, it would check grandparent.__proto__, which is Object.prototype. And Object.prototype.__proto__ is null — that is the end of the chain.

The default chain

Every regular object you create has this chain by default:

const obj = { a: 1 };
// obj → Object.prototype → null

That is why every object has methods like toString(), hasOwnProperty(), and valueOf() even though you never defined them. They come from Object.prototype.

const obj = { name: 'John' };
obj.hasOwnProperty('name'); // true
// obj does not have hasOwnProperty
// but Object.prototype does, so it works

The chain with constructor functions

When you use constructor functions with new, the chain is set up automatically:

function Animal(name) {
this.name = name;
}
Animal.prototype.speak = function () {
console.log(`${this.name} makes a sound`);
};
function Dog(name) {
Animal.call(this, name);
}
Dog.prototype = Object.create(Animal.prototype);
Dog.prototype.constructor = Dog;
Dog.prototype.bark = function () {
console.log('Woof!');
};
const rex = new Dog('Rex');

The chain looks like this:

rex → Dog.prototype → Animal.prototype → Object.prototype → null

So rex can access bark from Dog.prototype, speak from Animal.prototype, and toString from Object.prototype.

How property setting works

Here is something important — reading a property goes up the chain, but setting a property does not.

const parent = { color: 'red' };
const child = Object.create(parent);
console.log(child.color); // "red" — reads from parent
child.color = 'blue'; // creates a NEW property on child
console.log(child.color); // "blue" — found on child itself now
console.log(parent.color); // "red" — parent is not affected

When you set a property, it always gets created on the object itself. It does not go up the chain and modify the parent. This is called property shadowing — the child's color shadows (hides) the parent's color.

Checking where a property lives

You can use hasOwnProperty to check if a property belongs to the object itself or comes from the chain:

const parent = { inherited: true };
const child = Object.create(parent);
child.own = true;
child.hasOwnProperty('own'); // true
child.hasOwnProperty('inherited'); // false

Common Pitfalls

A common mistake is modifying Object.prototype directly, thinking it is a good way to add helper methods to all objects. Never do this. It affects every single object in your application and can break things in unpredictable ways. Libraries and frameworks depend on Object.prototype being clean.

Interview Tip

When explaining the prototype chain, draw the chain visually — show the arrows from one object to the next. Walk through a property lookup step by step, showing each hop in the chain. Interviewers want to see that you understand the lookup process, not just the concept. Also mention property shadowing — it shows you understand the difference between reading and writing in the chain.

Why interviewers ask this

The prototype chain is fundamental to how JavaScript works. Inheritance, method lookup, built-in methods like toString() and hasOwnProperty() — all of it depends on the prototype chain. When interviewers ask about it, they want to see if you can trace how JavaScript finds properties, if you understand the chain structure, and if you know the edge cases like property shadowing. This is a concept that separates candidates who know JavaScript deeply from those who just use it on the surface.