Содержание
Любой современный веб-проект не обходится без использовании JavaScript-фреймворков, и одними из самых популярных являются Vue и React. Традиционно в Word Press запрашиваемый пользователем файл отправляется после длинной серии взаимодействия между базой данных, внутренним кодом, сервером, браузером и уровнями кэширования; а контент обновляется при помощи интерфейса CMS (Word Press или другой, например, Drupal). Разработчик знает, где «живет» весь сайт. Сегодня уже очевидна необходимость изучения нового подхода к созданию и работе сайтов, основанном на REST API WordPress с безголовой CMS или JAMstack, например, с генератором статичных сайтов Gatsby (или Hugo) на платформе Netlify. Скорость загрузки и обновления интерфейса сегодня становится приоритетным. Как показывает статистика кривой обучения, первые шаги и понимание принципов работы даются быстрее при изучении Vue, но React труднее даётся к пониманию на первых шагах, тогда как дальнейшее изучение проходит более быстрыми темпами.
Но это всё потом. Что вначале? Взять начинающего программиста, знакомого с базовыми понятиями JavaScript, HTML & CSS? Все когда-то начинали с позиции котенка, тыкающегося носом. Ведь в сети уйма руководств по изучению React и Vue, и в них утонуть — дело 2-х минут. Как всегда, нужно брать работающие примеры и разбирать, что у них под капотом.
Вот, пожалуй, самые показательные и простенькие примерчики, по которым можно сразу сложить впечатление об архитектуре и принципах работы React. Практика по этой статье — не больше 30 мин.
В двух словах о React
Начинать изучение с голой теории — не самое лучшее вхождение в тему. Особенно, если у вас уже сложились какие-то стереотипы. А при изучении React они будут ломаться оптом. Можно кое-что почитать, принять к сведению, и заняться практикой. Поначалу все равно в голове осядет процентов 10. Потому что многое придется переосмыслить. Как выяснилось, понимание теории происходит намного быстрее, если потратить некоторое время на простую игру с фреймворками, покрутив их и поработав прямо в консоли.
Вот, например, что говорит теория:
React является декларативным. Это означает именно то, что означает. Другими словами: React позволяет разработчикам декларативно описывать пользовательские интерфейсы и управлять действиями над их состоянием, вместо того, чтобы выполнять действия над каждым элементом DOM. Вместо того чтобы придумывать шаги для описания действий над интерфейсами, разработчики просто описывают интерфейсы в терминах «конечного» состояния (например, функции). Когда действия происходят с этим состоянием, React на основе этого позаботится об обновлении пользовательских интерфейсов в DOM.
API-интерфейс браузера, который известен как DOM API, работает по такому принципу: при каждом событии (набор текста, прокрутка, изменение размера экрана) браузер заново перерисовывает всю страницу. Поэтому всегда разработчику нужно было избегать частого обхода дерева DOM, так как любая операция в DOM выполняется в одном и том же потоке. А это, в свою очередь, сказывалось на замедлении работы приложения.
React сначала генерирует виртуальное представление DOM и сохраняет его в памяти для дальнейшего использования. Затем он продолжит выполнять операции DOM, отображая его в браузере. Когда мы сообщаем React обновить дерево ранее визуализированных элементов, оно генерирует новое виртуальное представление обновленного дерева. Теперь React имеет 2 версии дерева в памяти. Чтобы отобразить обновленное дерево в браузере, React сравнивает две виртуальные версии DOM, имеющиеся в памяти, вычисляет различия между ними, выясняет, какие элементы в основном дереве необходимо обновить, и обновляет в браузере только их. Этот принцип и называется алгоритмом согласования.
Звучит неплохо, но для новичка слишком абстрактно.
А теперь на практике. В сети есть хороший пример, который мы также рекомендуем для тестирования для понимания React.
Таймер с React
Для начала разберемся с подключением компонентов React. Есть 2 способа начать работу с React: просто подключить в Head необходимые компоненты:
<script crossorigin="" src="https://unpkg.com/react@16.13.0/umd/react.production.min.js"></script>
<script crossorigin="" src="https://unpkg.com/react-dom@16.13.0/umd/react-dom.production.min.js"></script>
<script crossorigin="" src="https://unpkg.com/@babel/standalone/babel.min.js"></script>
<!--Или Babel отсюда:
<script src="https://cdnjs.cloudflare.com/ajax/libs/babel-standalone/6.26.0/babel.min.js" integrity="sha256-FiZMk1zgTeujzf/+vomWZGZ9r00+xnGvOgXoj0Jo1jA=" crossorigin="anonymous"></script>
-->
или создать локальную среду разработки:
npx create-react-app my-app
Мы пока ничего не будем загружать, а просто покрутим React в консоли, используя первый способ.
Небольшое отступление. В React используется ES2015 (ES6), поэтому следует уделить внимание его изучению. Традиционного ванильного JS уже недостаточно. Например, вы будете использовать JSX, который в чистом виде браузер не понимает. Чтобы он работал, нужен транспайлер — программа, которая выполнит транспиляцию JSX в JS. В нашем случае таким транспайлером будет выступать Babel, который мы подключили в хедере файла. Можете на сайте посмотреть онлайн конвертер, как Babel превращает JSX в JS.
Чтобы иметь все последние версии подключаемых файлов, рекомендуем использовать форму поиска на сайте https://cdnjs.com/.
Кроме того, в React вы столкнётесь:
- Со стрелочными функциями, например:
// обычная запись var sum = function() { return [].reduce.call(arguments, function(m, n) { return m + n; }, 0); } // эквивалент стрелочной записи var sum = (...args) => args.reduce((m, n) => m + n, 0);
2. С интерполяцией строк — это замена заполнителей в строке значениями строковой переменной. В JS интерполяция поддерживается только при использовании обратных кавычек (клавиша `ё`
на клавиатуре):
var age = 25; // С обычными кавычками интерполяция не поддерживается console.log('I am ${age} years old'); // Вывод: I am ${age} years old console.log("I am ${age} years old"); //Вывод: I am ${age} years old // Поддерживается только с обратными console.log(`I am ${age} years old`); //Вывод: I am 25 years old
3. С блочными зонами видимости – const
, let
вместо var
.
4. С деструктуризацией объектов и массивов для извлечения данных из массивов и объектов:
//Раньше: var f = function() { return ['this', 'is', 'array']; }; var tmp = f(), first = tmp[0], second = tmp[1], third = tmp[2]; console.log(first, second, third); // this is array //В ES6: var f = function() { return ['this', 'is', 'array']; }; // ES6 destructuring для массивов var [ first, second, third ] = f(); console.log(first, second, third); // this is array
6. С новыми методы массивов: Array.from, find, fill, includes, Array.of .
5. При работе в локальной среде вы столкнетесь с модулями.
Все остальное вы «подтянете» по мере изучения React, сталкиваясь с новым синтаксисом или новыми конструкциями.
Теперь пример. Создадим два одинаковых таймера. Один — используя API Web DOM напрямую, второй — используя React API, и сравним их работу в консоли:
<!doctype html> <html> <head> <script crossorigin src="https://unpkg.com/react@16/umd/react.production.min.js"></script> <script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.production.min.js"></script> <script crossorigin src="https://cdnjs.cloudflare.com/ajax/libs/typescript/3.8.3/typescript.min.js"></script> <style> #mountNode, #mountNode2, #mountNode3, pre { margin-left:auto; margin-right:auto; margin-top:10px; padding:20px; border-radius:4px; box-shadow:0 0 3px rgba(0,0,0,0.4); } #mountNode, #mountNode2 {width:300px;} </style> </head> <body> <div id="mountNode"></div> <div id="mountNode2"></div> <script> //API Web DOM const render = () => { document.getElementById('mountNode').innerHTML = ` <div> Hello HTML <input /> <pre>${new Date().toLocaleTimeString()}</pre> </div> `; //React API ReactDOM.render( React.createElement( 'div', null, 'Hello React', React.createElement('input', null), React.createElement('pre', null, new Date().toLocaleTimeString()) ), document.getElementById('mountNode2') ); }; setInterval(render, 1000); </script> </body> </html>
Вот результат: