Skip to content

Instantly share code, notes, and snippets.

@euri16
Created May 28, 2025 10:06
Show Gist options
  • Save euri16/f32f8154072c1e6f22f9cb55caed70e5 to your computer and use it in GitHub Desktop.
Save euri16/f32f8154072c1e6f22f9cb55caed70e5 to your computer and use it in GitHub Desktop.
import xs from 'xstream';
import { run } from '@cycle/run';
import { div, button, p, makeDOMDriver } from '@cycle/dom';
// Intent: capture user actions as streams
function intent(DOMSource) {
const increment$ = DOMSource.select('.increment').events('click')
.mapTo({ type: 'INCREMENT' });
const decrement$ = DOMSource.select('.decrement').events('click')
.mapTo({ type: 'DECREMENT' });
return xs.merge(increment$, decrement$);
}
// Model: update the state based on actions
function model(action$) {
const initialState = 0;
return action$.fold((state, action) => {
switch (action.type) {
case 'INCREMENT':
return state + 1;
case 'DECREMENT':
return state - 1;
default:
return state;
}
}, initialState);
}
// View: render the UI from the current state
function view(state$) {
return state$.map(count =>
div([
button('.decrement', 'Decrement'),
button('.increment', 'Increment'),
p(`Count: ${count}`)
])
);
}
// Main: glue everything together
function main(sources) {
const action$ = intent(sources.DOM);
const state$ = model(action$);
const vdom$ = view(state$);
return {
DOM: vdom$
};
}
run(main, {
DOM: makeDOMDriver('#app')
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment