Hydux
A React-Compatible fork of Hyperapp, вдохновлённый Elmish, Elm, Redux и т. д. Работает с любой библиотекой vdom!
yarn add hydux # или npm i hydux
Предположим, у нас есть счётчик, вот так:
// Counter.js
export default {
init: () => ({ count: 1 }),
actions: {
down: () => state => ({ count: state.count - 1 }),
up: () => state => ({ count: state.count + 1 })
},
view: (state: State, actions: Actions) =>
<div>
<h1>{state.count}</h1>
<button onclick={actions.down}>–</button>
<button onclick={actions.up}>+</button>
</div>
}
Затем мы можем составить его в стиле Elm, вы можете легко повторно использовать свои компоненты.
import _app from 'hydux'
import withPersist from 'hydux/lib/enhancers/persist'
import withultradom, { h, React } from 'hydux/lib/enhancers/ultradom-render'
import Counter from './counter'
// let app = withPersist<State, Actions>({
// key: 'my-counter-app/v1'
// })(_app)
// используем встроенный ultradom размером 1kb для рендеринга представления.
let app = withultradom()(_app)
if (process.env.NODE_ENV === 'development') {
// встроенные инструменты разработчика, без боли.
const devTools = require('hydux/lib/enhancers/devtools').default
const logger = require('hydux/lib/enhancers/logger').default
const hmr = require('hydux/lib/enhancers/hmr').default
app = logger()(app)
app = devTools()(app)
app = hmr()(app)
}
const actions = {
counter1: Counter.actions,
counter2: Counter.actions,
}
const state = {
counter1: Counter.init(),
counter2: Counter.init(),
}
const view = (state: State, actions: Actions) =>
<main>
<h1>Counter1:</h1>
{Counter.view(state.counter1, actions.counter1)}
<h1>Counter2:</h1>
{Counter.view(state.counter2, actions.counter2)}
</main>
export default app({
init: () => state,
actions,
view,
})
В этой библиотеке также реализован менеджер побочных эффектов, похожий на Elm. Вы можете просто вернуть кортеж (массив из двух элементов) в своём действии и поместить Cmd в качестве второго элемента. Например:
import app, { Cmd } from 'hydux'
function upLater(n) {
return new Promise(resolve => setTimeout(() => resolve(n + 10), 1000))
}
app({
init: () => ({ count: 1}),
actions: {
down: () => state => ({ count: state.count - 1 }),
up: () => state => ({ count: state.count + 1 }),
upN: n => state => ({ count: state.count + n }),
upLater: n => state => actions/* действия того же уровня */ => [
state, // не изменять состояние, не будет запускать обновление представления
Cmd.ofPromise(
upLater /* функция с одним параметром и возвращающая обещание */,
n /* параметр функции */,
actions.upN /* обработчик успеха, опционально */,
console.error /* обработчик ошибок, опционально */)
]
},
view: () => {/*...*/} ,
})
В Elm мы можем перехватывать сообщения дочернего компонента в родительском компоненте, потому что функция обновления дочернего компонента вызывается в функции обновления родительского компонента. Но как мы можем сделать это в hydux? Перевод текста на русский язык:
from 'assert'
import app, { Cmd, wrapAction, noop } from '../index'
import Counter from './counter'
const initState = {
counter1: Counter.init(),
counter2: Counter.init()
}
const actions = {
counter2: counter.actions,
counter1: {
...counter.actions,
upN: (n: number) => wrapAction(counter.actions.upN, (action, parentState: State, parentActions: Actions) => {
const [state, cmd] = action(n + 1)
assert.equal(state.count, parentState.counter1.count + n + 1, 'call child action work')
return [state, Cmd.batch(cmd, Cmd.ofFn(() => parentActions.counter2.up()))]
})
}
}
type State = typeof initState
type Actions = typeof actions
let ctx = app<typeof initState, typeof actions>({
init: () => initState,
actions,
view: noop,
onRender: noop
})
``` ## Почему
После нескольких месяцев использования Fable + Elmish мне потребовалось написать небольшое веб-приложение для компании. По многим причинам я не мог выбрать что-то модное вроде Fable + Elmish, проще говоря, мне нужно было использовать основной стек JS, но я больше не хотел иметь дело с громоздким и сложным инструментарием Redux и т. д.
Немного покопавшись, я обнаружил, что hyperapp выглядит очень хорошо, но быстро понял, что он не работает с React, а многие библиотеки не работают с новейшим API. Поэтому я создал это для поддержки различных библиотек VDOM, таких как React (официальная поддержка), ultradom (встроенный), Preact, inferno или чего угодно, просто нужно написать простой энхансер!
Кроме того, чтобы избежать критических изменений, у нас есть встроенная поддержка HMR, логгера, персистентности, инструментов Redux Devtools, вы знаете, что хотите этого!
## Лицензия
MIT
Вы можете оставить комментарий после Вход в систему
Неприемлемый контент может быть отображен здесь и не будет показан на странице. Вы можете проверить и изменить его с помощью соответствующей функции редактирования.
Если вы подтверждаете, что содержание не содержит непристойной лексики/перенаправления на рекламу/насилия/вульгарной порнографии/нарушений/пиратства/ложного/незначительного или незаконного контента, связанного с национальными законами и предписаниями, вы можете нажать «Отправить» для подачи апелляции, и мы обработаем ее как можно скорее.
Опубликовать ( 0 )