Angularшлях до Strong Junior
🔥 0

Фундамент Ф1 · урок 4 з 12

Обʼєкти

Обʼєкт описує одну річ через набір властивостей: у задачі є назва, статус, виконавець; у користувача — імʼя й налаштування. Дані, що приходять із сервера, — це обʼєкти. Моделі в Angular, інтерфейси в TypeScript, стан у сервісах — теж обʼєкти. А ще тут живе найчастіша помилка JavaScript — Cannot read properties of undefined. Після уроку ти знатимеш, як її уникати.

Створення й доступ

const task = {
  id: 7,
  title: 'Підготувати звіт',
  done: false,
  owner: { name: 'Оля', role: 'analyst' },   // обʼєкт усередині обʼєкта
};

task.title;              // 'Підготувати звіт' — через крапку
task['title'];           // те саме через квадратні дужки
task.owner.name;         // 'Оля' — крапки можна ланцюжком

task.done = true;        // змінити властивість
task.priority = 'high';  // додати нову — просто присвоїти

Обʼєкт — це пари «ключ: значення» у фігурних дужках, через кому. Квадратні дужки при читанні потрібні, коли ключ лежить у змінній (task[field]) або містить символи, недопустимі в імені (headers['Content-Type']). В інших випадках пиши через крапку.

Помітив const task і при цьому task.done = true? Це працює: const закріплює ярлик за обʼєктом, але не забороняє змінювати сам обʼєкт. Чому це важливо й чим небезпечно — урок 6.

Чого може не бути: ?. і ??

Дані з сервера часто неповні: у задачі ще немає виконавця, у користувача — налаштувань. Звернення task.assignee.name, коли assignee — undefined, дає найчастішу помилку JavaScript: Cannot read properties of undefined.

task.assignee.name;      // ✗ TypeError — assignee немає
task.assignee?.name;     // undefined — «якщо є, візьми name»

?. (optional chaining) зупиняє ланцюжок і повертає undefined, щойно ліворуч від нього null або undefined. А ?? (nullish coalescing) дає значення за замовчуванням лише для null і undefined — на відміну від || з минулого уроку, який спрацьовує на будь-якому falsy:

const settings = { pageSize: 0, theme: null };

settings.pageSize || 20;    // 20 — нуль falsy, і його «загубили»
settings.pageSize ?? 20;    // 0 — нуль — це значення, його лишили
settings.theme ?? 'light';  // 'light' — значення немає

Разом вони дають безпечне читання з запасним значенням: user.settings?.theme ?? 'light'. У шаблонах Angular ?. працює так само.

Код зараз виводить не те і падає з помилкою. Виправ три рядки з console.log так, щоб вивід був: light, потім 0 (розмір сторінки нуль — це законне значення, не підміняй його), потім undefined замість помилки.

Для другого рядка — ?? замість ||. Для третього — ?. після profile.

Скорочення, які трапляються скрізь

Короткі властивості. Якщо змінна називається так само, як ключ, ключ можна не повторювати:

const title = 'Звіт';
const done = false;
const task = { title, done };     // те саме, що { title: title, done: done }

Методи. Функція всередині обʼєкта називається методом:

const cart = {
  items: 3,
  describe() {                    // коротка форма для describe: function () {}
    return `Товарів: ${this.items}`;
  },
};

Слово this тут означає «цей обʼєкт». Про нього — окремий урок, восьмий.

Деструктуризація. Дістати кілька властивостей у змінні одним рядком:

const { title, done } = task;           // дві змінні з task
const { title: name } = task;           // перейменувати: буде змінна name
const { priority = 'normal' } = task;   // значення за замовчуванням

// найчастіше — прямо в параметрах функції
function describe({ title, done }) {
  return `${title}: ${done ? 'готово' : 'в роботі'}`;
}

describe(task);

Останній запис ти зустрінеш у коді Angular і TypeScript на кожному кроці. Тепер ти знаєш, що він означає: «функція отримує обʼєкт і одразу бере з нього title і done».

Перебір властивостей

Object.keys(task);      // ['title', 'done', 'hours'] — ключі
Object.values(task);    // ['Реліз', false, 8] — значення
Object.entries(task);   // [['title', 'Реліз'], ['done', false], …] — пари

for (const key of Object.keys(task)) {
  console.log(key, '=', task[key]);
}

Ці три функції повертають масиви — про них наступний урок.

JSON: обʼєкт у вигляді тексту

Сервер не може передати «обʼєкт» — лише текст. JSON — це текстовий запис обʼєктів, майже як у JavaScript, тільки ключі й рядки завжди в подвійних лапках. Перетворення в обидва боки:

const text = JSON.stringify(task);   // обʼєкт → текст: '{"title":"Реліз","done":false,"hours":8}'
const copy = JSON.parse(text);       // текст → новий обʼєкт

Звідси й правило з першого уроку: у localStorage лежать лише рядки, тому обʼєкти туди кладуть через JSON.stringify, а дістають через JSON.parse. Angular HttpClient робить JSON.parse за тебе — відповідь сервера одразу приходить обʼєктом.

Типові помилки
  • a.b.c, коли b може не бути, — TypeError. Пиши a.b?.c.
  • || там, де нуль чи порожній рядок — нормальні значення. Пиши ??.
  • `${task}` дає '[object Object]': у рядок вставляй конкретні властивості або JSON.stringify(task).
  • Порівняння двох обʼєктів через === — майже завжди false. Чому — наступний урок, шостий.

Підсумок

  • Обʼєкт — пари «ключ: значення». Читай через крапку, а коли ключ у змінній — через [].
  • ?. — безпечне читання того, чого може не бути. ?? — запасне значення лише для null і undefined.
  • Деструктуризація const { a, b } = obj і в параметрах function f({ a, b }) — скрізь у коді Angular.
  • JSON — обʼєкти у вигляді тексту: JSON.stringify і JSON.parse.