0

From example code below I'm trying to add a method inside an object where it generates new name based on object properties but "this" in this context is referring global object but not the parent one

It's ok using arrow function but the functions won't be hoisted and I need to express the function before using it. I prefer knowing what it does before seeing the code.

using arrow function expression it does work but is not hoisted using function declaration it doesn't work but is hoisted

Is there any best practice approach to this kind of problem?

const agent = {
  firsName: "John",
  lastName: "Depp",
  born: 12/04/1987,
  secretName: function() {

      return newFirstName() + newLastName()
    
    function newFirstName() {

      // complex codes here

      return "Agent " + this.firstName // for simplicity
      }
    
    function newLastName() {

      // complex codes here

      return "Agent " + this.LastName // for simplicity
    }
  },
};

console.log(agent.secretName()) // logs  "Agent undefinedAgent undefined"

3 Answers3

0

It's probably due to the lexical scope of your functions. You can read more about it here and here.

So if you move your helper functions one level up, it solves the problem:

const agent = {
  firstName: 'John',
  lastName: 'Depp',
  born: 12 / 04 / 1987,
  newFirstName: function () {
    // complex codes here

    return 'Agent ' + this.firstName; // for simplicity
  },
  newLastName: function () {
    // complex codes here

    return 'Agent ' + this.lastName; // for simplicity
  },
  secretName: function () {
    return this.newFirstName() + this.newLastName();
  },
};

console.log(agent.secretName()); // logs  "Agent undefinedAgent undefined"
StelKizi
  • 105
  • 7
0

you should use arrow function so they can target their parent scope.

const agent = {
  firstName: "John",
  lastName: "Depp",
  born: 12/04/1987,
  secretName: function() {
        const  newFirstName = () => {
      return "Agent " + this.firstName;
      }
    const newLastName = ()  => {
      return " Agent " + this.lastName;
      }
    
    return newFirstName() + newLastName();
  },
};
console.log(agent.secretName())
Saleh Majeed
  • 9
  • 1
  • 4
0

Ok I have found the answer from this thread How to access the correct `this` inside a callback?

In short: just define the outer scope let self = this

Example

const agent = {
  firstName: "John",
  lastName: "Depp",
  born: 12/04/1987,
  secretName: function() {
    const self = this;
    
      return newFirstName() + newLastName()
    
    function newFirstName() {
      return "Agent " + self.firstName 
      }
    function newLastName() {
      return "Agent " + self.lastName 
   }
  }
}

console.log(agent.secretName()) // logs JohnJohn it works!!