Почему возникает ошибка: Uncaught TypeError: Cannot read property of undefined or null (reading ***)
Периодически, при разработке на JavaScript возникает ошибка: Cannot read property *** of undefined или Cannot read property *** of null
Например в этом коде:
const count = result.data.length;
Cannot read property of undefined (reading 'length')
Или в этом:
const dataMap = response.lines.map(item => item * 2);
Uncaught TypeError: Cannot read properties of undefined (reading 'map')
Как понять причину ошибки, что оно означает, почему появляются и как ее исправить?
Ответы (1 шт):
Рассматривать будем на примере данного объекта
const data = {
name: 'TypeError',
message: '',
errors: null,
sayHi: function() {
console.log(this.name)
}
}
Cannot read property of undefined or null
Ошибка возникнет, если мы попытаемся выполнить следующий код:
data.errors.forEach(item => console.log(item)); // null.forEach()
Uncaught TypeError: Cannot read properties of null (reading 'forEach')
data.values.map(item => console.log(item)); // undefined.map()
Uncaught TypeError: Cannot read properties of undefined (reading 'map')
Данные ошибки говорят нам о том, что мы пытаемся вызвать методы у ничего(null или undefined).
data.errors это null. У null нет методов. А data.values вообще не существует. Нельзя вызвать метод у того, что не существует.
Так же, если объявить переменную и попытаться вызвать у нее какой либо метод без инициализации, то получим ошибку(в данном случае Cannot read properties of undefined (reading 'push')):
const arr;
arr.push(1); // undefined.push();
Cannot read property
of undefined - ключ не определен, т.е. отсутствует в объекте.
of null - ключ в объекте есть, но имеет значение null. Уnullнет методов.
Как этого избежать?
Проверять, что приходит в объекте и существуют ли в объекте нужные нам значения. Один из вариантов проверки, воспользоваться console.log().
Можно начать с последнего ключа, однако лучше весь пусть вывести, что бы понимать структуру, с которой работаем:
console.log(data) // { name: 'TypeError', message: '', errors: null, sayHi: [Function] }
console.log(data.errors) // null
Так же можно воспользоваться оператором необязательной цепочки вызовов '?.'
const a = data?.errors?.forEach(item => console.log(item)); // null.forEach()
const b = data?.values?.map(item => console.log(item)); // undefined.map()
Оператор необязательной цепочки вызовов будет проверять значение слева. Если значение null или undefined, цепочка прерывается и возвращается значение undefined.
Для объявленных переменных указывать тип данных
const arr = []; // Указываем, что меременная это массив
arr.push(1); // Можем воспользоваться любым методом массива;