TypeError: Cannot read property 'push' of undefined

This is an error I keep getting and I can’t pinpoint the problem. The problem is javascript syntax 2, team stats project for the object module. My code is as follows:

const team = {
_players: [
  {firstName: 'Tom', lastName: 'Pedo', age: 19
}, {firstName: 'Sam', lastName: 'Jew', age: 20
}, {firstName: 'Bumble', lastName: 'Bee', age: 19,
}
],
_games: [
  {opponent: 'Kids', teamPoints: 19, opponentPoints: 27
  }, {opponent: 'Romans', teamPoints: 42, opponentPoints: 35
  }, {opponent: 'Ken', teamPoints: 25, opponentPoints: 99
  }
],
get players() {
  return this._player;
},
get games() {
  return this._games;
},
addPlayer(firstName, lastName, age){
  let player = {
    firstName: firstName,
    lastName: lastName,
    age: age
  };
  this.players.push(player)
},

addGame(opponent, teamPoints, opponentPoints){
  let game = {
  opponent: opponent,
  teamPoints: teamPoints,
  opponentPoints: opponentPoints
  };
  this.games.push(game)
}

}
team.addPlayer('Steph', 'Curry', 28);
team.addPlayer('Lisa', 'Leslie', 44);
team.addPlayer('Bugs', 'Bunny', 76);
console.log(team.players);

team.addGame('cheese', 54, 64);
team.addGame('chong', 32, 34);
team.addGame('duloe', 83, 84);
console.log(team.games);

Initially I thought the problem was cause by trying to push to the wrong array, but I am pushing to this.players.push(player) which is essentially pushing player to this._player[] after it goes through the getter method. Any ideas?

Hi there! It seems like you forget to put the underscore in front which is in the code on:
this._players.push(player); & this._games.push(game); & console.log(team._players); & console.log(team._games); .

I have helped you debugged it →

const team = {
  _players: [
    { firstName: "Tom", lastName: "Pedo", age: 19 },
    { firstName: "Sam", lastName: "Jew", age: 20 },
    { firstName: "Bumble", lastName: "Bee", age: 19 },
  ],

  _games: [
    { opponent: "Kids", teamPoints: 19, opponentPoints: 27 },
    { opponent: "Romans", teamPoints: 42, opponentPoints: 35 },
    { opponent: "Ken", teamPoints: 25, opponentPoints: 99 },
  ],

  get players() {
    return this._player;
  },

  get games() {
    return this._games;
  },

  addPlayer(firstName, lastName, age) {
    let player = {
      firstName: firstName,
      lastName: lastName,
      age: age,
    };
    this._players.push(player);
  },

  addGame(opponent, teamPoints, opponentPoints) {
    let game = {
      opponent: opponent,
      teamPoints: teamPoints,
      opponentPoints: opponentPoints,
    };
    this._games.push(game);
  },
};

team.addPlayer("Steph", "Curry", 28);
team.addPlayer("Lisa", "Leslie", 44);
team.addPlayer("Bugs", "Bunny", 76);
console.log(team._players);

team.addGame("cheese", 54, 64);
team.addGame("chong", 32, 34);
team.addGame("duloe", 83, 84);
console.log(team._games);

You should be able to get an output like this →

[
  { firstName: 'Tom', lastName: 'Pedo', age: 19 },
  { firstName: 'Sam', lastName: 'Jew', age: 20 },
  { firstName: 'Bumble', lastName: 'Bee', age: 19 },
  { firstName: 'Steph', lastName: 'Curry', age: 28 },
  { firstName: 'Lisa', lastName: 'Leslie', age: 44 },
  { firstName: 'Bugs', lastName: 'Bunny', age: 76 }
]
[
  { opponent: 'Kids', teamPoints: 19, opponentPoints: 27 },
  { opponent: 'Romans', teamPoints: 42, opponentPoints: 35 },
  { opponent: 'Ken', teamPoints: 25, opponentPoints: 99 },
  { opponent: 'cheese', teamPoints: 54, opponentPoints: 64 },
  { opponent: 'chong', teamPoints: 32, opponentPoints: 34 },
  { opponent: 'duloe', teamPoints: 83, opponentPoints: 84 }
]

Thank you, that seems to have fixed the problem. May I ask what is the point of the getter methods then? If I am going to refer to _players as _players and not players then why would I bother even putting a getter method there

Getters can get other properties and/or do other processes instead of simply returning a value. For instance, you can make a getter that gets the sum of all of the numbers in an object!

What is the purpose of the getter in this particular project though? With eugenegoh’s rendition I never use ‘player’ or ‘games’. Or was it simply there to make me practice it seeing as getters were one of the preceding lessons

Not sure about @eugenegoh his solution, from what I can see you a problem here:

get players() {
  return this._player;
},

this._player is an undefined property, should be: return this._players

then you can keep using your getter in addPlayer method

IDK, maybe.

Mainly I’d use getters for calculations, but it can also be used to fetch private data inside of a class.

Thank you that seems to be the more logical fix. I hate using variables with such similar names, in this project we hav ‘players’, ‘_players’ and ‘player’ and the same for games. Makes finding mistakes so much harder. Definitely going to try to avoid this when I start developing my own code!

Yeah I think I just need to use them in a project where I actually see a genuine benefit to using them, because so far it just seems to be adding extra means to achieve the same end

1 Like

My bad sorry, I agree there is something wrong with that. I overlooked it. @stetim94

More info on getter & setter @jacobkearns892582326 >

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/get

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/set

1 Like

singular and plural names is quite common. You will get used to it

One interesting example from the docs @eugenegoh provided:

const obj = {
  log: ['a', 'b', 'c'],
  get latest() {
    if (this.log.length === 0) {
      return undefined;
    }
    return this.log[this.log.length - 1];
  }
};

console.log(obj.latest);

where we use a getter to have a dynamic property. Which is very interesting.

but JavaScript is missing proper encapsulation, which reduces the usefulness of getters and setters. A getter can be useful to enforce certain behavior, so that other developers can understand

1 Like