Как стать автором
Обновить

Hyperapp + Parcel

Время на прочтение5 мин
Количество просмотров9K
Автор оригинала: Adam Boro
В данном посте, мы рассмотрим два новых инструмента из мира фронт-енд разработки. Они оба разработаны с мыслью о простоте и легкости использования. Первый инструмент это очень маленький фронт-енд фреймворк Hyperapp, а второй это бандлер Parcel. Вместе они могут быть лучшим выбором для написания легковесных приложений в начале 2018.

Обычно для разработки интерактивных веб-приложений я использую React & Webpack. Но зачастую бутсрапинг нового проекта с использованием этого стека занимает слишком много времени и выглядит громоздки. Использование React в случае когда мне нужен простой и не большой интерактивный виджет с поиском и отображением цен, выглядит как оверкилл.

Hyperapp


Главная особенность Hyperapp — это его размер, всего 1kb. Пользователи React & Redux, будут чувствовать себя как дома, они очень похожи с Hyperapp.

image
Hyperapp похож на крошечную версию React Рика
Hyperapp использует систему Virtual DOM, для вычислений обновлений DOM, а так же преследует схожу абстракцию компонентов и элементов поверх HTML, что позволяет использовать JSX. Ключевое отличие заключается в том компоненты не имеют state — есть только один глобальный state на все приложение и все компоненты представлены как stateless.

State менеджмент в Hyperapp вдохновлен подходом Elm, который в свое время вдохновил Redux.
Концепция имьютбл стейта и экшенов которые возвращают новый стейт очень похожа на ту, что используется в Redux. Однако в Hyperapp нету редюсеров, есть только экшены, которые принимают аргументы и возвращают новый стейт (асинхронные экшены возвращающие промисы, так же присутствуют).

Parcel


Parcel это новый вид фронт-енд бандлера, своего рода более быстрый и пре-сконфигурированный webpack. Я фанат webpack'a, но как и любой другой, могу заметить, что конфигурация webpack'a довольно громоздкая.

Parcel из коробки предоставляет HOC (hot module replacement) и code-splitting. К моему удивлению, заимпортив .sass файл, после запуска дев сервера parcel, он автоматически установил node-sass в зависимости и собрал мне CSS файл! Также стоит отметить, что parcel нереально быстрый.

И так, как же я использую эти два инструмента?


Мы напишем приложение с использованием Hyperapp & Parcel — очень простое, оно будет просто отображать базовую информацию о пользователе используя Github API.

Линк на готовое решение

Давайте начнем с создания новой директории и установки необходимых зависимостей:

mkdir hyperparcel && cd $_ && npm init -y && npm i hyperapp parcel-bundler babel-plugin-transform-react-jsx babel-preset-env

Наряду с главными инструментами, что нас интересует, мы установили babel пресеты для траспилинга кода под старые окружения.
$_ означает «аргумент последней команды»

Теперь давайте добавим index.html и index.js файлы:
index.html

<html>
  <body>
    <script src="./index.js"></script>
  </body>
</html>

index.js

console.log('hello parcel')

Так же давайте добавим скрипты запуска дев сервера и билда в package.json:

...
"start": "parcel index.html",
"build": "parcel build index.html --public-url ./"
...

Запустите дев сервер $ npm start по адресу localhost:1234 в браузере будет доступна наша страница и в консоле можно увидеть результат console.log из index.js.

Окей, теперь Hyperapp приложение. Для упрощения, мы будем использовать ES6 и JSX — используя babel компилятор. К счастью он есть в Parcel по умолчанию и все, что нам необходимо это указать env пресет и компиляцию JSX под Hyperapp. (Вместо React.createElement, должна вызываться функция h).

Создайте файл .babelrc в корне проекта:

{
  "presets": ["env"],
  "plugins": [
    [
      "transform-react-jsx",
      {
        "pragma": "h"
      }
    ]
  ]
}

К этому моменту мы закончили настройку нашего окружения и можем приступить к написанию приложения. Давайте начнем с простого Hyperapp представления:

import { h, app } from 'hyperapp'
const view = () =>
  <div>
    hello hyperapp
  </div>
app({}, {}, view, document.body)

Поскольку Parсel использует hot релоады, вы сразу же увидите результат.
Код очень простой и не требует каких либо глубоких познаний Hyperapp.

Мы импортируем необходимое из Hyperapp, создаем view функцию которая отвечает за отображение контента и рендерит все это в body страницы используя app функцию.

Теперь займемся вытяжкой Github информации о пользователе. В первую очередь нам нужно некое состояние для того, чтобы хранить пользовательский ввод и данные полученные с API. (Как было сказано в начале, компонент в Hyperapp не имеет своего сайта).

const state = {
  username: '',
  userData: null,
}

Также нам необходим способ изменить этот стейт. Изменения стейта в Hyperapp похожи на то как это делается в Elm и Redux и представлены в виде функций которые принимают стейт с экшеном и возвращают новый стейт:

const nameChangeAction = (name) => (state, actions) => ({...state, name})

В нашем случае, экшены будут выглядить так:

const actions = {
  updateUsername: (username) => (state, actions) => {
    getUserData(username).then(actions.setUserData)
    return { username }
  },
  setUserData: userData => state => ({ userData })
}

Как вы можете видеть updateUsername асинхронный и использует другой экшен для изменения стейта.

Разумеется нам понадобится функция getUserData. Мы будем использовать Github API для получения информации Github аккаунте ник которого ввел пользователь.

Для того, что бы не дергать API на каждый символ, мы будем использовать debounce.

npm i debounce-promise babel-preset-es2015

const getUserDataFn = username => {
  return fetch(`https://api.github.com/users/${username}`)
    .then(res => res.json())
}
const getUserData = debounce(getUserDataFn, 700)

Создайте файл стилей (можно взять туть) .sass и испортируете его в index.js

А так же обновите view:

const view = (state, actions) =>
  <main>
    <div>Search github users:</div>
    <input
      type='text'
      className='searchInput'
      value={state.username}
      oninput={e => actions.updateUsername(e.target.value)}
    />
    <br/>
    <div className='userCard'>
      {state.userData ? (
        <div>
          <img class='userCard__img' src={state.userData.avatar_url} />
          <div class='userCard__name'>{state.userData.name}</div>
          <div class='userCard__location'>{state.userData.location}</div>
        </div>
      ) : (
        <div> search 'em</div>
      )}
    </div>
  </main>
app(state, actions, view, document.body)

Вот и все! Наше маленькое приложение готово.

В заключение


Hyperapp и Parcel отличный пример того как инструментарий разработчика эволюционирует. Существует множество идей и подходов создания фронт-енд приложений с богатым интерактивным интерфейсом. Некоторые из них быстро адаптируются под новые реалии и нужды, а некоторые из них будут оставлены позади в этом дивном мире Javascript разработки. React & Redux является очень популярным выбором среди разработчиков и их ключевые особенности используются в Hyperapp. Webpack в свою очередь повлиял на мир бандлеров и установил новые стандарты которые Parcel удовлетворяет с лихвой и кто знает, возможно в будущем он займет лидирующую позицию. Эволюция так же является причиной по которой мы не должны пытаться использовать один и тот же набор инструментов для решения каждой новой проблемы.
Теги:
Хабы:
Всего голосов 32: ↑29 и ↓3+26
Комментарии11

Публикации

Истории

Ближайшие события

7 – 8 ноября
Конференция byteoilgas_conf 2024
МоскваОнлайн
7 – 8 ноября
Конференция «Матемаркетинг»
МоскваОнлайн
15 – 16 ноября
IT-конференция Merge Skolkovo
Москва
22 – 24 ноября
Хакатон «AgroCode Hack Genetics'24»
Онлайн
28 ноября
Конференция «TechRec: ITHR CAMPUS»
МоскваОнлайн
25 – 26 апреля
IT-конференция Merge Tatarstan 2025
Казань