Хабрахабр

[Перевод] Сравнение React Native и Flutter с точки зрения их применения в реальных проектах

Чем React Native отличается от Flutter, за исключением того, что речь идёт о разных фреймворках, в основу которых положены разные технологии? На что ориентироваться тому, кто не знаком с этими инструментами для разработки кросс-платформенных приложений, но хочет выбрать один из них для своего очередного проекта?

Во всех этих сравнениях речь шла о таких вещах, которые, на самом деле, особого значения не имеют. Автор статьи, перевод которой мы публикуем, говорит, что в последнее время ему попадалось множество сравнений React Native и Flutter. Здесь будет сделано сравнение React Native и Flutter с точки зрения реального положения дел, с точки зрения того, что имеет значение для настоящих проектов. Например — о языках, используемых для разработки проектов, или об инструментах командной строки. Это сравнение призвано снабдить всех желающих сведениями, которые помогут им выбрать именно то, что им нужно.

Предварительные замечания

Мне сразу хотелось бы сказать о том, что здесь я не собираюсь заниматься критикой React Native или Flutter, не собираюсь их, так сказать, троллить. То, как именно вы распорядитесь тем, что узнали, зависит от вас — от того, что вы уже знаете и умеете, от нужд вашего проекта.

До этого я занимался разработкой проектов с использованием React.js и Node.js. Я начал использовать React Native (RN) три года назад. Но мне, кроме того, очень нравится Flutter. В итоге вполне закономерно то, что я выбрал именно RN. И RN и Flutter — это отличные инструменты, которые достойны того, чтобы на них обратил внимание тот, кто ищет базу для своего очередного приложения. Я наблюдал за ростом и развитием этого фреймворка, и я вполне уверен в том, что его ждёт светлое будущее.

Поэтому относитесь к моим выкладкам критически. Хочу отметить, что с RN я работаю ежедневно, а вот о Flutter я того же самого сказать не могу. А если обнаружите, что я в чём-то ошибаюсь — дайте мне знать об этом.

Языки

Есть много сравнений, посвящённых, например, языкам Dart и JavaScript, нативным компонентам, и компонентам, код которых генерируется автоматически. Я не буду тут приводить подобные сравнения — об этом написано уже много всего. Если вам это нужно — вы можете найти соответствующие материалы самостоятельно.

Он создавался компанией Google в качестве замены JavaScript (но Google не смогла склонить других производителей браузеров к тому, чтобы они включили бы в свои проекты поддержку виртуальной машины Dart; в итоге её поддерживает лишь Chrome). Мне хотелось бы сказать лишь о том, что в языке Dart, применяемом при разработке Flutter-приложений, используется статическая типизация. В JavaScript, на котором пишут код React Native-проектах, используется динамическая типизация, но тот, кого интересует статическая типизация, может создавать JS-приложения с использованием TypeScript.

Тут можно поговорить и об IDE, и об инструментах командной строки для автоматического генерирования кода, и много ещё о чём.

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

Их можно встретить буквально повсюду. Поэтому сейчас я предлагаю обсудить некоторые популярные аргументы, высказываемые в пользу того или иного фреймворка. Они далеко не всегда так однозначны, какими могут выглядеть. Мне доводилось читать о них, слышать их от коллег.

Ложные аргументы, используемые при сравнении Flutter и React Native

▍Dart — типизированный язык, а JavaScript — нет. Это значит, что писать на Dart безопаснее

Типобезопасность — это важнейший аргумент в пользу того или иного языка, используемого для разработки любого приложения. В особенности — мобильного проекта, которому, прежде чем попасть на устройства пользователей, нужно пройти непростой процесс проверки в некоем магазине приложений.

Это не даёт преимуществ в плане производительности, таких, какие есть у Dart, но в будущем ситуация может измениться. Но JavaScript-код можно типизировать с использованием TypeScript или Flow. В особенности — если учитывать то, что в 2020 году ожидается выход нового движка React Native.

Иногда это помогает менять тип переменной без необходимости повторной сборки проекта. Правда, стоит помнить о том, что выбор динамически типизированного языка в некоторых случаях — это тоже очень даже хорошо. Очки возвращались в виде целых чисел 0, 15, 30, 40 из соответствующего перечисления. Я однажды встретился с чем-то подобным при работе над приложением, посвящённом теннису. Изначально мы эту строку к числам не добавляли. Затем к этим числам понадобилось добавлять строку AD, сообщающую о преимуществе. Нам в этом помогла динамическая типизация JavaScript. Однако мы смогли реализовать эту возможность, не выпуская новую сборку приложения. В Dart-приложении подобное привело бы к «падению» приложения или к возникновению ошибки. Мы смогли просто поменять схему GraphQL и возвращать значение в таком виде, в каком нам это было нужно.

▍Flutter и Dart — это разработки Google. Скоро выйдет Fuchsia — новая ОС от Google. RN, в результате, ждёт медленная смерть, так как Flutter будет гораздо лучше оптимизирован в расчёте на Fuchsia

Никто не может предсказать будущее, но кое-что можно утверждать с уверенностью: некоторые из крупнейших мировых компаний делают сейчас ставку на React Native.

Речь идёт, скажем, о CodePush и о проекте React Native for Windows, позволяющем разрабатывать нативные Windows-приложения с использованием React. Например — React Native серьёзно используется в Microsoft.

Компания, в частности, публикует много материалов о React Native. React Native пользуются и в компании Discord, которая занимается разработкой популярного мессенджера. В Discord, в RN-приложении, удалось добиться уровня производительности, близкого к уровню производительности нативных приложений.

RN, кроме того, используется в банковской сфере.

Однако я думаю, что бороться за первенство в ОС Fuchsia будут оба фреймворка. Flutter, безусловно, отлично подходит для многих проектов, сфера его использования продолжает расширяться.

Истинные аргументы, используемые при сравнении Flutter и React Native

▍Flutter отличается лучшей производительностью, чем React Native

Тут мне нечего сказать. Сейчас, благодаря тому, что Flutter-программы компилируются в нативный код, с этим утверждением можно лишь согласиться. Но и производительность RN-проектов, если их оптимизировать, оказывается на весьма приятном уровне, при этом каких-либо проблем с ними не наблюдается.

▍Flutter легче освоить тем, кто раньше занимался разработкой нативных приложений

Это, из-за типизации и логики реализации, тоже правда. Flutter ближе к внутренним механизмам Android и iOS, чем RN. Большая часть логики взята из Java, а основное отличие, например, в разработке под Android, заключается в большем уклоне в сторону декларативного подхода к разработке.

На Java, например, писали классы и вызывали функции, а применяя Flutter — пишут виджеты, используя нечто вроде свойств, которые описывают ожидаемые состояние и внешний вид приложения.

▍Инструменты разработчика Flutter очень хороши, а инструменты React Native отличаются низким качеством

Честно говоря, в этой сфере между Flutter и React Native сейчас имеется большая пропасть. Команда Flutter серьёзно поработала над интеграцией своих средств разработки с VS Code и с Android Studio. Создано множество инструментов для отладки и анализа проектов.

Компания Facebook, в стремлении изменить ситуацию, недавно выпустила отладчик для мобильных приложений Flipper. С другой стороны, если не учитывать пакет react-devtools и некоторые небольшие плагины, отладка RN-приложения полагается, в основном, на встроенные возможности соответствующих платформ. Но сейчас это — пока экспериментальный проект.

Теперь давайте рассмотрим основные различия Flutter и React Native. Несложно заметить, что в активе и того и другого фреймворков есть сильные аргументы.

Основные различия

▍Компиляция и «обновление по воздуху»

Благодаря тому, что компиляция JavaScript-кода выполняется тогда, когда его нужно выполнить (JIT-компиляция), а не заранее (AOT-компиляция), при использовании React Native можно, так сказать, «обновлять приложения по воздуху». Это, на самом деле, предельно просто реализовать. Например — с использованием Microsoft CodePush или Expo.io.

Это — тот фактор, который кардинальным образом меняет расклад сил, особенно тогда, когда речь идёт о неких приложениях, привязанных к каким-то кратковременным событиям. Сейчас это — основная причина того, что я не осуществляю постепенный переход на Flutter (помимо того, что мне нравится парадигма React). Эти приложения за короткий отрезок времени набирают очень много пользователей. В таких условиях изменения в приложение нужно вносить очень и очень быстро.

Например — с помощью проекта snack.expo.io. Создать React Native-приложение можно, вообще не имея среды разработки и не думая о компиляции. Это очень удобно для создания простых проектов, демонстрирующих доказательство работоспособности некой концепции, или проектов, которые планируется показать команде разработчиков React Native, сообщая о какой-нибудь ошибке.

Можно, конечно, инициировать вызов интента установки, но это — далеко не то же самое, чего можно достичь средствами RN. Dart тоже поддерживает JIT-компиляцию, но сейчас невозможно отправлять обновления Dart-приложений «по воздуху», используя нечто вроде CodePush.

Возможно, в будущем команда разработчиков Flutter представит нам достойный ответ на вопрос об обновлениях приложений «по воздуху», но пока не существует чего-то вроде официально поддерживаемой библиотеки, это реализующей.

▍Инструменты разработки

Flutter-разработчики могут пользоваться отличными инструментами для отладки приложений. Это — сильный аргумент в пользу удобства разработки на Flutter. Это, к тому же, сильно облегчает оптимизацию приложений.

▍Описание пользовательских интерфейсов

В React Native для описания интерфейсов используется JSX, что значительно облегчает работу. А во Flutter используются интерфейсы, основанные на виджетах. Мне такой подход кажется слишком перегруженным деталями и не особенно дружественным к разработчикам.

Без использования IDE описание интерфейсов превращается в настоящий ад вложенных друг в друга конструкций, в котором тяжело ориентироваться. Разработка Flutter-интерфейсов подразумевает наличие больших объёмов шаблонного кода. Это может усложнить ревью пулл-запросов.

Речь идёт о чём-то наподобие библиотеки styled-components в RN, или о чём-то вроде вызова StyleSheet.create с передачей компоненту того, что получилось, через свойство style. Кроме того, здесь, насколько я знаю, нет нормальных средств для отделения чистого дизайна от самих виджетов.

Ситуацию ещё сильнее улучшают специализированные библиотеки, вроде styled-components. Использование JSX способствует созданию простых и читабельных описаний интерфейсов. Разработчик, который раньше занимался веб-проектами и перешёл на React Native, способен очень быстро войти в курс дела. Всё это даёт RN хорошее преимущество перед Flutter.

Этими возможностями приятно пользоваться. Оба фреймворка хорошо поддерживают возможности по «горячей» перезагрузке материалов. Это относится и к iOS, и к Android.

Сообщество и библиотеки

Экосистема JavaScript огромна, в ней имеется огромное количество разнообразных инструментов и библиотек. Но и сообщество Dart-разработчиков выглядит неплохо, хотя оно гораздо моложе и меньше JS-сообщества.

Однако большинство IT-стартапов в настоящее время не предоставляет тем, кто хочет с ними работать, SDK, рассчитанные на Dart. При разработке Dart-приложений можно пользоваться множеством пакетов. А вот средства разработки для Node.js весьма популярны в этой среде.

Dart поддерживает то, что это — проект Google, и то, что компания, вероятно, позаботится о создании множества полезных библиотек для этого языка.

Собственно говоря, в плане поддержки сообщества и наличия библиотек, React Native сейчас обходит Flutter.

Итоги

Давайте подведём итоги и соберём всё, о чём мы говорили. Это поможет сделать правильный выбор тем, кто занимается выбором фреймворка для своего очередного мобильного проекта. Сразу хочется отметить, что на вопрос о том, какой фреймворк стоит выбрать, нет однозначно правильного или неправильного ответа. Всё зависит от особенностей проекта, а также от предпочтений и знаний команды разработчиков.

▍Flutter и Dart

Flutter и Dart — это отличный выбор для тех, кто делает ставку на будущее.

Единственный риск заключается в том, что, из-за того, что Flutter и Dart — технологии сравнительно молодые, тому, кто их выберет, придётся либо очень постараться в поисках необходимых ему библиотек, либо писать их самому. Полагаю, что тот, кто выберет этот технологический стек, ничем не рискует. В Dart-среде это не так. В JS-среде можно найти готовое, или почти готовое решение для множества задач.

Но Dart — хороший язык, который решает множество проблем, характерных для JavaScript.

В текущих условиях я порекомендовал бы выбирать Flutter тому, для кого справедливы хотя бы некоторые из следующих утверждений:

  • Вы идёте в мобильную разработку, не имея знаний в области JavaScript или React. В результате вы не сможете, выбрав не Flutter, а RN, строить новые знания на фундаменте старых.
  • Вы занимались раньше чем-то, что не связано с веб-разработкой, вы не знакомы с созданием макетов страниц средствами CSS и с чем-то наподобие styled-components.
  • У вас нет жёстких сроков сдачи проекта; проект, в плане возможностей, отличается определённым уровнем гибкости. Здесь дело в том, что, при создании Flutter-проекта, у программиста не будет доступа к такому же большому объёму наработок, доступ к которому есть у RN-разработчика. Во Flutter разработка специфических интерфейсов может оказаться сложнее, чем в RN.
  • В приложении используется простая схема навигации. Тут дело в том, что система маршрутизации Flutter сложнее, чем знаменитая система react-navigation.
  • Одно из важнейших требований к вашему приложению — высокая производительность.
  • Вы готовы к тому, что не сможете обновлять своё приложение «по воздуху», готовы полагаться на механизмы обновления, предлагаемые магазинами приложений для платформ iOS и Android. По крайней мере — вы готовы к тому, что такое положение дел будет существовать в ближайшие месяцы, или, возможно, в ближайший год.

▍React Native и TypeScript (или JavaScript)

React Native — это проект, который пользуется поддержкой Facebook и многих других компаний. Это — наиболее продвинутый фреймворк в своём классе.

Несмотря на то, что JavaScript не очень хорош в плане типизации, исправить это можно (и нужно), воспользовавшись, например, TypeScript.

Я порекомендовал бы выбрать React Native тому, для кого справедливо большинство следующих утверждений:

  • Вы уже являетесь React, Vue или Angular-разработчиком и знакомы с архитектурой приложений, основанных на компонентах.
  • Вы идёте в мобильную разработку из веб-разработки, вы знакомы с макетами, создаваемыми средствами CSS, у вас есть опыт работы с библиотеками наподобие styled-components.
  • Вы хотите полагаться на обширную экосистему вспомогательных средств, которыми можно пользоваться в собственных приложениях; вы собираетесь искать ответы на ваши вопросы на ресурсах наподобие StackOverflow.
  • Вы хотите воспользоваться возможностями обновлений программ «по воздуху» с помощью Microsoft CodePush и Expo.io, что позволит вам очень быстро исправлять ошибки в приложениях.
  • Вы хотите пользоваться популярными сервисами, которые, как правило, всегда предоставляют стандартную поддержку для Node.js.

Уважаемые читатели! Если бы сейчас вам нужно было бы выбирать фреймворк для мобильной разработки — на чём бы вы остановились? На Flutter, на React Native, или на нативных инструментах мобильных платформ?

Показать больше

Похожие публикации

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

Кнопка «Наверх»