Upload
jlongster2
View
2.722
Download
0
Tags:
Embed Size (px)
Citation preview
Communicating with Channels JAMES LONG
Who am I
ChannelsCommunicating Sequential Processes
and
(not Content Security Policy)
Outline• Explain channels in more detail • Show some examples of integration with React components • Show how Flux can be re-envisioned with channels
Making Ravioli
PUTputs a value
TAKEtakes a value
GOstarts a process
CHANcreates a channel
let { chan, go, take, put } = require('js-csp');let ch = chan();!
go(function*() { while(true) { console.log(yield take(ch)); }});!
go(function*() { yield put(ch, 1); yield put(ch, 2); yield put(ch, 3);});!
// Output: 1 2 3
https://github.com/ubolonton/js-csp
let { chan, go, take, put } = require('js-csp');let ch = chan();!
go(function*() { while(true) { console.log(yield ch); }});!
go(function*() { yield put(ch, 1); yield put(ch, 2); yield put(ch, 3);});!
// Output: 1 2 3
https://github.com/ubolonton/js-csp
(livecode)
Additional Features
Promise Channels (coming soon) let ch = promiseChan();
yield put(ch, 5);!
// Somewhere else...yield take(ch); // <- 5yield take(ch); // <- 5
Additional Features
Closing a Channel ch.close();!
yield take(ch); // <- csp.CLOSEDyield put(ch, 5); // <- false
Advanced Usage
Higher-order Operations multmixmergepipeline
Advanced Usage
Custom Buffering let ch1 = chan(5);let ch2 = chan(csp.buffers.dropping(10));let ch3 = chan(csp.buffers.sliding(1));
Advanced UsageTransducers let { compose, map, filter, take } = require(‘transducers.js’);!
let ch = chan(1, map(x => x * 2));let ch = chan(1, compose( map(x => x.amount), filter(x => x > 0), take(10)));
Why isn’t this used?
•Generators not available until recently •An idea from Go/Clojure that simply hasn’tbeen tried yet
•Susceptible to deadlocks
Component EVENT HANDLINGwith channels
Example #1: Simple List
App
MessageCreator
Input
onChange/onKeyDown
onCreate
(code walkthrough)
ChannelsMixin
Adds send method !
•Creates an event handler •Takes a name and arguments •If method exists with same name, simply forwards events with supplied arguments
•Otherwise sends events onto a named channel
ChannelsMixin
Adds getEventChannel method !
•Takes a name and returns the named channel
Benefits & Disadvantages
•Good: Transducer-compatible API •Bad: More verbose •Neutral: Not really much different
Example #2: Recording the Mouse
(code walkthrough)
Events
•onMouseMove handles mouse events •extracts data •dispatches
•velocityRecord sticks temporal state oncomponent instance
Channels
•mouseCoord channel instead of onMouseMove event •data extraction with transducer •no dispatching required
•velocityRecord uses lexical scoping to keep state
Benefits & Disadvantages
•Good: separation of concerns, modular •Good: data flow as a first-class value •Good: no leaking state •Bad: Still more verbose
Example #3: Tooltip
(code walkthrough)
Channels
•cancellation and timeout signals •more complex UIs would compose with data flow (think modal that sends back data)
Benefits & Disadvantages
•Good: very clear workflow •Good: tiny amount of code •Good: avoids tracking tons of UI state
More Possibilities
•Cross-component channels •Allow arbitrary types of channels: mix, mult, pub/sub
Takeaways
Using event handlers for simple events is fine
Channels allow more complex composition ofsignals and async workflows
They also help separate related logic into a single place
FLUXwith channels
(code walkthrough)
Transactions
Uncategorized
Other Component
Dispatcher
TransactionStore
TotalStore
BudgetStore
UncategorizedStore
Notes about Flux
• Extracts out data into “one source of truth” • Explicit forward flow • Separates data into logical units • Serves two purposes: • Allows data dependencies • Optimizes rendering
Transactions
Uncategorized
Other Component
Data Blob
App
Re-using Abstractions
• pub/sub channels for firing actions fromcomponents
• cursors for watching for data changes
(code walkthrough)
Transactions
Uncategorized
Other Component
pub/sub
Transaction Add Process
Transaction Update Process
Other Process
Transactions Cursor
Budget Cursor
Potential Advantages
• Composability of event flows • Cursor abstraction removes need for emitting
change events • Potential global app state structure • Component subscribing to events
Disadvantages
• Cursors can be invalidated easily, needs work • Doesn’t enforce as much structure • May not need any event composability
Thanks!@jlongster
https://github.com/ubolonton/js-csp