|
| 1 | +# Combinators |
| 2 | +## InjectSources |
| 3 | +## SwitchForEach |
| 4 | +## SwitchCase |
| 5 | +## List |
| 6 | +- all items will emit sinks |
| 7 | +- all item components should be passed an id in settings |
| 8 | +## Router |
| 9 | +## StateChart (EHFSM) |
| 10 | +``` |
| 11 | +StateChart({ |
| 12 | + intents : Hash{intentIdentifier :: sources -> settings -> source}, |
| 13 | + actionResponses : [SinkIdentifier] - must match sinks returned by action, |
| 14 | + action : State a-> State b -> State err -> Event -> Guard -> Action |
| 15 | + where Action :: event -> model -> sinks |
| 16 | +}) |
| 17 | +``` |
| 18 | +Drivers for action must be wrapped into a higher-order function which will |
| 19 | +add a unique token serving to identify the request. The response will only be |
| 20 | + accepted as matching a request if both have the same token. |
| 21 | +## m |
| 22 | + |
| 23 | +# Driver |
| 24 | +## Store Driver - for now likely key/value store |
| 25 | + |
| 26 | +# Examples |
| 27 | +## TODO list app |
| 28 | +### Funcional specifications |
| 29 | +- three routes : active todos, completed todos, all todos |
| 30 | +- one field `what needs to be done?` to enter new todo |
| 31 | +- list of entered todos |
| 32 | +- for each entered todos, delete button, completed radio, text input with |
| 33 | +todo description |
| 34 | +- one label with `x` items left |
| 35 | +- three labels `All`, `Active`, `Completed` being emphasized according to route |
| 36 | +- authentication required to view active or all route |
| 37 | +- no authentication required to view completed route |
| 38 | +### Technical specifications |
| 39 | +#### Data structures |
| 40 | +TodoList :: [TodoItem] |
| 41 | +TodoItem :: {active : Boolean, description : String} |
| 42 | +AppState :: TodoList |
| 43 | +#### Drivers |
| 44 | +- auth$ : returns true or false if the user is logged in or not respectively |
| 45 | +- route$ : navigates to a given route, emit new route events |
| 46 | +- DOM |
| 47 | +- Store |
| 48 | +#### Constants and properties |
| 49 | +- IS_LOGGED_IN |
| 50 | +- ALL |
| 51 | +- ACTIVE |
| 52 | +- COMPLETED |
| 53 | +#### Components |
| 54 | +- LogIn : display a dummy message, one button which logs in and reroutes |
| 55 | +### Implementation through combinators |
| 56 | +const sinks = [TODO] |
| 57 | +App({sinks : sinks}, [ |
| 58 | + OnRoute('/', SwitchCase({ |
| 59 | + on : 'auth$' |
| 60 | + }, [ |
| 61 | + Case({when: IS_LOGGED_IN}, [ |
| 62 | + TodoComponent({routeState : ALL}) // actually will require flip or |
| 63 | + // curry and R.__ |
| 64 | + ]), |
| 65 | + Case({when: complement(IS_LOGGED_IN}, [ |
| 66 | + LogIn({redirect: '/'}) |
| 67 | + ]) |
| 68 | + ] |
| 69 | + )), |
| 70 | + OnRoute('/active', SwitchCase({ |
| 71 | + on : 'auth$', sinks : sinks |
| 72 | + }, [ |
| 73 | + Case({when: IS_LOGGED_IN}, [ |
| 74 | + TodoComponent({routeState : ACTIVE}) // actually will require flip or |
| 75 | + // curry and R.__ |
| 76 | + ]), |
| 77 | + Case({when: complement(IS_LOGGED_IN}, [ |
| 78 | + LogIn({redirect: '/active'}) |
| 79 | + ]) |
| 80 | + ] |
| 81 | + )), |
| 82 | + OnRoute('/completed', TodoComponent({routeState: COMPLETED}) |
| 83 | + ) |
| 84 | +]) |
| 85 | +TodoComponent=curry(flip( |
| 86 | + StateChart({ |
| 87 | + intents : |
| 88 | + }) |
| 89 | +)) |
0 commit comments