Почему возникает ошибка: Uncaught TypeError: *** is not a function
Периодически, при разработке на JavaScript возникает ошибка: Uncaught TypeError: *** is not a function
Например в этом коде:
const result = this.response;
result.forEach((e) => console.log(e));
Uncaught TypeError: result.forEach is not a function
Или в этом:
const errors = response.errors.map(item => item.toString());
Uncaught TypeError: response.errors.map is not a function
Как понять, что это за ошибка, что оно означает, почему появляется и как её исправить?
Ответы (1 шт):
Рассматривать будем на примере данного объекта
const data = {
name: 'TypeError',
message: '',
errors: null,
sayHi: function() {
console.log(this.name)
}
}
Uncaught TypeError: *** is not a function
Данная ошибка возникает в том случае, когда у объекта мы пытаемся вызвать метод(функцию), но она таковой не является.
data.getName(); // <- Uncaught TypeError: data.getName is not a function
data.errors(); // <- Uncaught TypeError: data.errors is not a function
В первом случае getName() нет в объекте, во втором, errors не является функцией.
Несоответствие типов
Возможно, мы ожидаем, что к нам придет массив и мы пытаемся выполнить:
data.name.forEach(item => console.log(item));
Получим ошибку, так как у строк нет метода forEach
Как избежать подобных ошибок?
Проверять, что приходит в объекте и существуют ли в объекте нужные нам данные. Один из вариантов проверки, воспользоваться console.log().
Можно начать с последнего ключа, однако лучше весь пусть вывести, что бы понимать структуру, с которой работаем:
console.log(data) // { name: 'TypeError', message: '', errors: null, sayHi: [Function] }
console.log(data.errors) // null
console.log(data.sayHi) // [Function: sayHi]
Перед вызовом функции, желательно проверить ключ на тип. И если наш ключ является функцией, то вызывать.
// data существует, есть ключ sayHi и sayHi функция
if (data && data.sayHi && typeof data.sayHi === 'function') {
data.sayHi();
}
При проверке в if лучше указывать полную цепочку ключей для проверки, так как, например, следующая конструкция вызовет исключение, т.к. data.values не существует:
if (data.values.showValue && typeof data.values.showValue === 'function') {
console.log(data.values.showValue());
}
Сократить код можно, воспользовавшись оператором необязательной цепочки вызовов '?.':
// data существует?, есть ключ sayHi и sayHi функция
if (data?.sayHi && typeof data.sayHi === 'function') {
data.sayHi();
}
Оператор необязательной цепочки вызовов будет проверять значение слева. Если значение null или undefined, цепочка прерывается и возвращается значение undefined.
Порой, такие ошибки, даже когда мы уверены в правильности данных, могут быть вызваны банальной опечаткой. Проверяйте себя и свой код!
if (data && data.sayHi && typeof data.sayHi === 'function') {
data.sayHI(); // sayHI нет, но есть sayHi
}