Skip to content
This repository has been archived by the owner on Sep 3, 2022. It is now read-only.

Commit

Permalink
Updated how the run function handles state.
Browse files Browse the repository at this point in the history
1. Previously a program's init was just an array assignment. Now its a function that returns a tuple of state and effect: init() { return [state, effect]}
2. Updated README to reflect changes.
3. Updated test for changes.
  • Loading branch information
Wobbabits committed Nov 3, 2018
1 parent 77e159a commit 86669c1
Show file tree
Hide file tree
Showing 8 changed files with 54 additions and 32 deletions.
2 changes: 1 addition & 1 deletion .eslintrc.json
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@
"no-empty": 0,
"no-ex-assign": 2,
"no-extra-boolean-cast": 2,
"no-extra-semi": 2,
"no-extra-semi": 0,
"no-fallthrough": 2,
"no-func-assign": 2,
"no-global-assign": 2,
Expand Down
20 changes: 13 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -426,13 +426,13 @@ let list = render(<List data={fruits} />, 'section', serverList)
import { h, render, run } from '@composi/core'
```

Run takes one argument, the program to run. This is where it gets interesting. A program has at least three properties:
Run takes one argument, the program to run. This is where it gets interesting. A program has at least three methods:

1. init
2. update
3. view

Init holds the program's state and optionally an effect to run at startup. That's why its called init.
Init is a function that returns the program's state and optionally an effect to run at startup. That's why its called init.

Update is like a Redux reducer. It executes various actions conditionally. The can modify and return the programs state. When it returns the state, it gets passed to the view.

Expand All @@ -451,7 +451,7 @@ run(program)

Each property expects certain arguments.

Init must be an array. Its first value is the state for the program. The second, which is optional, is an effect to run at startup. This might be a setInterval timer, or a code to fetch data.
Init is a function that returns an array. The first entry in that array is the state for the program. The second entry, which is optional, is an effect to run at startup. This might be a setInterval timer, or a code to fetch data.

Update get two arguments: message and state. Message is any message sent to it by the view. Message get sent when events are triggered in the UI, possibly by the user.

Expand All @@ -474,8 +474,10 @@ function Counter({state, send}) {

// Assemble programe together:
const program = {
// Initial state:
init: [0],
// Set initial state:
init() {
return [0]
},
update(msg, state) {
return [state + 1]
},
Expand Down Expand Up @@ -569,7 +571,9 @@ function List({state, send}) {

// Assemble programe together:
const program = {
init: [state],
init() {
return [state]
},
update(msg, state) {
return actions(msg, state)
},
Expand Down Expand Up @@ -691,7 +695,9 @@ function List({state, send}) {

// Assemble program to run:
const program = {
init: [state],
init() {
return [state]
},
update(msg, state) {
return actions(msg, state)
},
Expand Down
2 changes: 1 addition & 1 deletion dist/composi-core.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion dist/composi-core.js.map

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@composi/core",
"version": "0.8.6",
"version": "0.9.0",
"description": "A JavaScript library for creating websites, PWAs and hybrid apps.",
"main": "src/index.js",
"scripts": {
Expand Down
28 changes: 15 additions & 13 deletions src/runtime.js
Original file line number Diff line number Diff line change
@@ -1,25 +1,25 @@
/**
* The @composi/runtime.
* @typedef {any[]} State
* @typedef {any} State
* @typedef {Function} Effect
* @typedef {Object<string, any>} Program
* @prop {Array<State, Effect>} Program.init
* @prop {function} Program.update
* @prop {function} Program.view
* @prop {function} [Program.done]
* @prop {Function} Program.init
* @prop {Function} Program.update
* @prop {Function} Program.view
* @prop {Function} [Program.done]
* @param {Program} program
* @return {() => void} Function to terminate runtime.
*/
export function run(program) {
const update = program.update
const view = program.view
const done = program.done
let state
let state, effect
let isRunning = true

/**
* Send a message.
* @param {*} message A message of any type.
* @param {any} message A message of any type.
* @return {void} undefined
*/
function send(message) {
Expand All @@ -30,20 +30,22 @@ export function run(program) {

/**
* Handle changes to state and executing effects.
* @param {any[]} change
* @param {any[]} update
* @return {void} undefined
*/
function change(change) {
state = change[0]
let effect = change[1]
function change(update) {
if (update) {
;[state, effect] = update
} else {
;[state, effect] = program.init()
}
if (effect) {
effect(send)
}
program.init[0] = state
view(state, send)
}

change(program.init)
change(state)

/**
* Function to end runtime.
Expand Down
28 changes: 21 additions & 7 deletions test/runtime.html
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,9 @@ <h1>Mocha Tests - Composi Runtime &amp; Union</h1>
return h('h1', { id: 'title' }, `Hello, ${greeting}!`)
}
const program = {
init: ['World'],
init() {
return ['World']
},
update(msg, state) {

},
Expand Down Expand Up @@ -96,7 +98,9 @@ <h1>Mocha Tests - Composi Runtime &amp; Union</h1>
}

const program = {
init: ['no message'],
init() {
return ['no message']
},
update(msg, state) {
switch (msg.type) {
case 'click':
Expand Down Expand Up @@ -145,7 +149,9 @@ <h1>Mocha Tests - Composi Runtime &amp; Union</h1>
}

const program = {
init: ['no message'],
init() {
return ['no message']
},
update(msg, state) {
switch (msg.type) {
case 'click':
Expand Down Expand Up @@ -179,7 +185,9 @@ <h1>Mocha Tests - Composi Runtime &amp; Union</h1>
effectResult = true
}
const program = {
init: [0, effect],
init() {
return[0, effect]
},
update() {
return [state]
},
Expand All @@ -206,7 +214,9 @@ <h1>Mocha Tests - Composi Runtime &amp; Union</h1>
}, 100)
}
const program = {
init: [0, effect],
init() {
return [0, effect]
},
update() {},
view() {},
done() {
Expand Down Expand Up @@ -245,7 +255,9 @@ <h1>Mocha Tests - Composi Runtime &amp; Union</h1>
}
let taggedEffectFired = false
const program = {
init: ['no message'],
init() {
return ['no message']
},
update(msg, state) {
return Msg3.match(msg, {
'click': () => {
Expand Down Expand Up @@ -293,7 +305,9 @@ <h1>Mocha Tests - Composi Runtime &amp; Union</h1>
}
let taggedEffectFired = ''
const program = {
init: ['no message'],
init() {
return ['no message']
},
update(msg, state) {
return Msg4.match(msg, {
'click': message => {
Expand Down

0 comments on commit 86669c1

Please sign in to comment.