Галоўная / Артыкулы / Розумеўчы кастамныя хукі React: павторна выкарыстоўванне логіки без спяльнага статаусу

Розумеўчы кастамныя хукі React: павторна выкарыстоўванне логіки без спяльнага статаусу

Дазвольце даклэ научыцца, што такое спецыяльныя хукі React, як яны выкарыстоўваюцься для выдзеявання та аднароўкі логіки, залежнай ад стану, між компонентамі, і якія распашчытныя памылкі трэба ухіляцца падчас ўтварэння такіх хукіў.

1281 слоў

Введэнне

Чы раней траплялася ситуацыя, калі вам давалося пісаць той самы пара useState і useEffect у трох прынцыпова разныя компаненты, зміняючы толькі назвы змэнных? Практычна кожны разработчык на React сталкиваецца з гэтым у які-небудзь момент. Код працюе нормальна, але гэта значыць, што ідэнтычная логіка копіюецца ў всій базе коду, і кожная копія з часам пачынае адхіляцься, калі ёй незалежна робяцца певныя змены.

Гэта самэўсёльва ситуацыя, якую было створана можлівасць спецыяльных хуков у React. документацыя React, якая распаведвае пра гэты тэму адзначае, што перанесенне поведзення компонентаў у спецыяльную, можна перадаць знову і знову функцыю дазволяе разным часткам прыложэння выкарыстоваць адно і тое ж поведзенне з станам, у замест на постаўленне той самай реалізацыі знову і знову. У гэтым часці статты показана, што такое спецыяльныя хукі на практыке, як яны працуюць у рэальнам кодзе, а таксама прычыны ўспэху і проблемы, якія трэба разумець перш чым ствараць своія.

Што такое спецыяльныя хукі React

У сваім сутнасці спецыяльны хук — гэта проста функцыя на JavaScript, якай павінен адпавядаць ад адной строгай правілу называння: яе назва павінна начынваліцца з use. Усередзіне яе можна вызваць іншыя хуки, такія як useState або useEffect, і яна вернэе тыя значэнні або функцыі, якія патрэбны компоненту, який яе вызваў. Сам React не надае гэтай функцыі жадных спецыяльных правіл працы пад час выконання — прэфікс use ўсё ж такі є простаю конвенцыяй, але яна неабходная, калі боўш тое дазволяе React правільна прыменяць правіла хукоў і дапамагае іншым разработчыкам адразу зрозумець, для чаго патрабуецца гэтая функцыя.

Спецыяльныя хуки проты звычайных функцый

Стандартная функцыя-інструмент можа выконваць множна корыстных задач, але яя не можа вызваць іншыя хукі, таму што знаходзится параду ўстановкі рэндарынгу React. А самастоятельны хук не мае такога обмежэння. Гэта якраз і ўсё його прыямоц: вы можете аб’еднаваць поведзенне, якое залежыць ад стану — напрыклад, стежэнне за флагам загрузкі, абэрэжанне за падзеямю браузера чы ўсё інша — у ўтварэнне, якое можна перысваіць і якае ўсё равно будзе правільна інтегрувацца ў жыцёвы цикл компонента React.

Як у практыцы працуюць самастоятельныя хукі React

Конкрэты прыклад раз’ясняе гэта набагато быстрей, чым будзь-якое абстрактнае поясненне.

Выдзелэнне логіки з компонента

Уявіце сабе тры нез’ўязаныя компоненты, кожны з якіх павінен выявляць, чы ў браузере зараз є сетевая з’ўязка. Без спяльнага хука кожны з іх павінен стварыць свой сабэй useState і useEffect, каб стежыць за гэтым:

function StatusBadge() {
  const [isOnline, setIsOnline] = useState(navigator.onLine);

  useEffect(() => {
    const goOnline = () => setIsOnline(true);
    const goOffline = () => setIsOnline(false);

    window.addEventListener('online', goOnline);
    window.addEventListener('offline', goOffline);

    return () => {
      window.removeEventListener('online', goOnline);
      window.removeEventListener('offline', goOffline);
    };
  }, []);

  return <span>{isOnline ? 'Online' : 'Offline'}</span>;
}

У замену вы можете пераносіць гэтую логіку ў адны спецыяльны хук, і з таго часу кожны компонент, які патрэбуе статус, проста вызывае яго:

function useOnlineStatus() {
  const [isOnline, setIsOnline] = useState(navigator.onLine);

  useEffect(() => {
    const goOnline = () => setIsOnline(true);
    const goOffline = () => setIsOnline(false);

    window.addEventListener('online', goOnline);
    window.addEventListener('offline', goOffline);

    return () => {
      window.removeEventListener('online', goOnline);
      window.removeEventListener('offline', goOffline);
    };
  }, []);

  return isOnline;
}

// Usage in any component:
function StatusBadge() {
  const isOnline = useOnlineStatus();
  return <span>{isOnline ? 'Online' : 'Offline'}</span>;
}

Ніякі з компонентаў больш не павінен сам ствараць абэранты за змянамі — кожны проста запытае useOnlineStatus аб текущай значэнні.

Аднароджанне логіки статусу без аднароджання самага статусу

Гэты детал часта застае новачкаў без адпаведнага падходу: спецыяльны хук аднароджвае паведанне, а не сам статус. Якщо два разлучныя компоненты кожны вызываюць useOnlineStatus, кожны з іх атрымлея свой сабэйскі копію таго статусу. Яны выконваюць ідэнтычную логіку, але фактычныя значэнні, якія знаходзяцца ў кожным компоненте, ўсё ж абсалютна незалежныя — між імі немае ніякога аднароджанага чы сувязанага статусу.

Ключовыя прынтэсы вікорыстання спецыяльных хукав у React

  • Магчымасць паўтаральнага выкарыстання ў розных компанентах: Калі логіка знаходзится ўнутры хука, жадны з компанентаў у прыёмніце не патрабуе дублювання нават адной лініі коду, каб яе выкарыстаць, і гарантуецца, што ўсюды, дзе яна выкарыстоўваецца, ўсё будзе дзейсніцца адночына.
  • Чыстэйшыя, лепш чытаемыя компаненты: Вынесенне логіки, якая керуе станам, за межы компаненты значыць, што рэштка коду компаненты практычна не мае проблем з керуванням станам, таму новак можа быстрэй ёё зрозумець простым паглядам.
  • Лёгкасць тэставання адсалідна: Вынесеную логіку можна тэставаць абсалютна незалежна ад будзь-якага компаненту, який яе выкарыстоўвае, тое значыць, ёё трэба пераканацца толькі адназначна, а не паўтараць тэстыванне кожны раз, калі змінюецца компанент-выкарыстоўчык.
  • Доступ да адпрыгліванаму таленту: Стварэнне хуків, якія можна справжняя адпрыгліваць — а не проста логіка з перэназначанням імёна, скопіяванае і вставленаяе з прымакам use — выклікае практычныя знанні пра асновныя патэрны React. Команды, якія хочуць, каб гэта было правільна адмаўлявана з самага пачатку, іноды шукаюць спадкаванне за межамі своей калекты і прыглашаюць спецыялістаў, якія працуюць з ReactJS; їхній дазнаўанне памагае заставляць дизайн хуків застойвацца стабільным, нават калі проект расте.
  • Пашытковыя памылкі, якіх трэба ужывацца

    Нават хукі, напісаныя з добрымі намерамі, могу пацяпіцца калькама прызначальных способаў.

    • Адзінакавасць з правіламі хуков: Выкліканне хука ў умовнай структуре, у цікле або з звычайнай функцыі, а не з компонента чыста іншага хука, паслабляе можлівасць React падтрымляць адносовую стабільнасць стану праз кожны рэндар. У результате часта з’яўляецца незвычайны, періодычны баг, які важка адстаўляць да його прычыны.
    • Занадта больша колькасць функцыяй у аднам хуку: Адкладанне прабавакі формы, запытоў да сеті і керування станам UI ў адны спецыяльны хук ускладнюе яго тэставанне, паўтарнае выкарыстанне і розумеенне, у працоўным порядку, чым у случае, калі тыя ж абавязкі разделяюцца межа двума чы трывом меншымі, болей спецыялізаванымі хукамі.
  • Выявленне логікі, яку не трэба было выяўляць: Не кожны вызов useState заслуговае на тое, каб стаць самастоятельным хукам. Якщо якая-небудзь частка логіки викорыстоўваецца толькі ў аднам месцы, яе выяўленне проста дадае дапэўнай шар звычайнага выканання без жадных рэальных пераваг.
  • Забыванне пра мемазаванне, калі гэта важна: Калі спецыяльны хук вяртае функцыі або об’екты без правильнага ўтримвання іх у памяці, компоненты, якія ўжоўнае гэты хук, можу працаваць занова без неабходнасці. Такія втраты ў продуктывасці є тонкімі і лёгкаямі праўачыць пад час звычайных тэставанняў.
  • Вывык

    Спецыяльныя хукі ў React не толькі дапамагаюць утримваць код ад павторэння, але і выступаюць справжнім механізамам для падтрымкі цялесупрацоўнасці та адноснай стабільнасці зростаючага кодавой базы. Калі каманда вырабоўвае навык відлічвання логіки, яку варта вынесць у окремы хук, складнасць компонентаў зазвычай зменшуецца, багі становяцца лёгкімі да выявлення, а ўсе функцыі праекту застаюцца аднаковымі, утрамбоўваючыся ад разлікав між компонентамі, якія должны працаваць аднойчы. Калі дапрацоўкі на базе React продовжаюць растаць за масштабам і складнасцю, розумеў, калі і як стварыць надзейны спецыяльны хук, стае базовай навыком, а не чымсь, што належыць толькі досвідчытым разработчыкам.

    Якщо ваша команда працуе з кодавой базай, наполненай дублюючыміся логікамі, і хочаць надаць ёй рэальнай структуры, можа быць корыстна кансалтация з компаніей па развіццю React js, яка вже адмахнулася падобных процэсаў рефакторавання на іншых вялкамасштабных проектах.

    Супакойлена літэратура

    • Typing React Hooks: useState, useEffect, useReducer, і Custom Hooks — Дазнаецеся, як правільная працэўнае з useState, useEffect, useReducer і спецыяльнымі хукамі ў TypeScript, а таксама калі выбор TypeScript замест звычайнага JavaScript дэйсна ўзрабатваецца.
  • React Query і Redux: Наватаранне падчынства серверскага стата ў вялікіх прыладах — Дазвольце вам дазнацца, чырваў прылад для чату ў працэсе вырабоцтва выкорыстоўваў TanStack Query заместа Redux для керавання дадзеннямі сервера, і дзе Redux яшчэ мае сваё месца ў савечнай архітэктуре React.
  • Как аэватацыяі багоў стата, якія не пазначаюцца, з-за мутацый у кансэкты JavaScript — Дазвольце вам дазнацца, чырваў мутацыі об’ектаў і масоў праз кансэкты нарабляюць проблемы з перырэндароўкай у React, чырваў распраджэнне копіюе толькі паверхневыя элементы, і як безпечна ствараць глыбокую копію стата.
  • Стварэнне ментальнага модэлю для React: супрацоўка, стан і хукі — Дазвольце вам пазнакоміцца з прычынамі, якія стояць за асновнымі концэптамі React — супрацоўкай, компонентамі, пропамі, станом і хукамі — каб развіць інтуўіцыю замест таго, каб запамятаваць API.