6

I made a mistake with the age property on these objects and when I try to reassign different values later, it won't change it at all.

I want this to work with the Object.create Method. What should I do to fix this?

var personProto = {
  calculateAge: function() {
    console.log(2019 - this.yearOfBirth)
  },
  fullName: function() {
    console.log(this.name + ' ' + this.lastName)
  }
}

var sam = Object.create(personProto, {
  name: { value: "samuel" },
  yearOfBirth: { value: 1092 },
  lastName: { value: "max" },
  job: { value: "developer" }
});

sam.yearOfBirth = 1992;

sam.calculateAge(); // 927

console.log(sam.calculateAge()); is giving me 927 assuming yearsOfBirth is still 1092 even if I changed it to 1992 and the output was supposed to be 27.

2
  • 3
    Because the property descriptors that you use default to writable: false. Commented Nov 2, 2019 at 19:18
  • See Object.defineProperties() Commented Nov 2, 2019 at 19:18

2 Answers 2

8

By default, properties assigned using Object.create are not writable. Attempting to write to a non-writable property is a silent error in JavaScript - one of many reasons to use Strict Mode.

Here is your code again, but in Strict Mode:

'use strict';

var personProto = {

        calculateAge:function(){
            console.log(2019 -this.yearOfBirth)
        },
        fullName:function(){
            console.log(this.name + ' ' + this.lastName)
        }
    }

    var sam = Object.create(personProto, {
        name:{value:'samuel'}, 
        yearOfBirth:{value:1092}, 
        lastName:{value:'max'},
        job:{value:'developer'}
    });

    sam.yearOfBirth = 1992;

    console.log(sam.calculateAge());
    927

Notice that it now fires an error and tells you exactly what's wrong.

To fix this, just make the properties writable.

'use strict';

var personProto = {

        calculateAge:function(){
            console.log(2019 -this.yearOfBirth)
        },
        fullName:function(){
            console.log(this.name + ' ' + this.lastName)
        }
    }

    var sam = Object.create(personProto, {
        name:{value:'samuel',writable:true}, 
        yearOfBirth:{value:1092,writable:true}, 
        lastName:{value:'max',writable:true},
        job:{value:'developer',writable:true}
    });

    sam.yearOfBirth = 1992;

    console.log(sam.calculateAge());
    927

Sign up to request clarification or add additional context in comments.

1 Comment

"silent error". Yet another great JS design. Slow clap.
2

The second argument to Object.create uses property descriptors, and the writable attribute defaults to false when you don't specify it.

I would recommend to drop the second argument entirely, and instead use Object.assign to create the properties on the new object:

var sam = Object.assign(Object.create(personProto), {
    name: 'samuel',
    yearOfBirth: 1092,
    lastName: 'max',
    job: 'developer',
});

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.