Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Investigate (F)RP literature #88

Closed
steveklabnik opened this issue Feb 27, 2014 · 10 comments
Closed

Investigate (F)RP literature #88

steveklabnik opened this issue Feb 27, 2014 · 10 comments

Comments

@steveklabnik
Copy link

Breifly discussed this with @domenic last night, but I see many parallels to this proposal and functional reactive programming. There may be lessons to be learned from that literature or JavaScript implementations of it (bacon.js, Rx).

I'm interested in doing some of this, as I've written an FRP implementation in Ruby. I need to dig into the details of the spec first.

@domenic
Copy link
Member

domenic commented Feb 27, 2014

Related: #86. Also /cc @Raynos who I know has gone down this rabbit hole in the past.

Previously I have maintained that there is an impedance mismatch here, especially as it relates to factors like buffering-by-default, backpressure, and push-vs-pull. But as you pointed out last night, FRP is supposed to be more about setting up a declarative graph than about those kind of implementation-level details, which gave me new hope.

One route forward might be figuring out what map, filter, etc. methods would look like, probably as a subclass (class FRPReadableStream extends ReadableStream). I think I can see how to do this.

@Raynos
Copy link

Raynos commented Feb 27, 2014

FRP is not about list like higher order functions over streams. Mind you there are many things you can learn from reducers and elmjs
raw destination without intermediate streams dropping those messages.

Then again using streams for FRP is a bad idea, go build suitable data structures from the ground up for the thing you want. I've abused streams in the past for FRP, bad idea.

@steveklabnik
Copy link
Author

Can you elaborate further on why this is a 'bad idea'?

The reason I thought of this is that event streams, transforming the events, and then hooking them up to an output is how FRP-like libraries tend to work, and that was one of @domenic's examples. Like I said, still have to dig into the spec, and re-read the theory.

@Raynos
Copy link

Raynos commented Feb 27, 2014

@steveklabnik a whatwg streams implementation is 1000 loc.

A Signal data type written for the purpose of FRP is 30 loc.

For my usecase of FRP my data type is push based, signals are push, streams are pull. I don't need any of the buffering machinery that is in whatwg/streams, and the pull system is just not a good match.

You could build on top of whatwg/streams but that's just a golden hammer mindset, use multiple data types that are optimized for each use case, dont use one data type to rule them all.

@steveklabnik
Copy link
Author

Thank you, I understand better what you're talking about now.

signals are push, streams are pull.

Right. I am not sure this is actually supported by the literature. My understanding of a signal is "a continuous-time-varying value." Nothing about push vs pull in there: that's an implementation detail.

I am also not saying "whatwg streams should be implemented via FRP," I am saying "we should learn the lessons from those who have come before, in the same way that there was argument over if Promises should be monadic or not." Theory informs practice.


Anyway, I have a few moments, so I'll start. A cursory search in fact reveals http://conal.net/papers/push-pull-frp/push-pull-frp.pdf , from Elliot himself.

Section 1:

While FRP has simple, pure, and composable semantics, its ef-
ficient implementation has not been so simple. In particular, past
implementations have used demand-driven (pull) sampling of reac-
tive behaviors, in contrast to the data-driven (push) evaluation typ-
ically used for reactive systems, such as GUIs.

So, even with just a few minutes of research, it seems to imply that historically, FRP implementations were in fact pull, not push, which is in line with my understanding. And it can be either!

his paper demonstrates that it is indeed possible
to get the best of both worlds,

Hopefully I'll have more time to investigate this further over the weekend, including the rest of this paper.

@Raynos
Copy link

Raynos commented Feb 27, 2014

@steveklabnik there are lessons to be learned. If we can find any and apply them then that's a good idea.

However its more important that whatwg/streams learns lessons from say node, go & dart stream implementations as they are far closer to what whatwg/streams actually aims to do.

@puffnfresh
Copy link

FRP is a specific form of stream processing. Make a good stream processing library (I recommend looking at scalaz-stream, stream and machines) and you'll be able to generalise FRP.

@domenic
Copy link
Member

domenic commented Mar 17, 2014

I was told by someone at Manhattan.js that "CSP" is especially relevant to this spec, and in particular that it matches the model we're using better than traditional (F)RP. I'm pretty sure that they were referring to http://en.wikipedia.org/wiki/Communicating_sequential_processes but the Wikipedia article and linked primary sources are pretty dense and hard to connect to what we're doing here. If anyone is familiar with recent or practical applications of CSP that could help bring this connection closer I would be appreciative.

@Raynos
Copy link

Raynos commented Mar 17, 2014

@domenic they probably took inspiration from clojure & core.async

See rich hickey talking about CSP with core.async

@domenic
Copy link
Member

domenic commented Mar 17, 2015

As this spec becomes more constrained by the need to efficiently wrap byte sources and sinks while still presenting a general interface, it's clearer that it's best for streams to harmonize with FRP libraries or paradigms in ECMAScript, but not necessarily be based on or implement them. Kris Kowal's GTOR goes into some more details on how this might work, and I am optimistic especially that as ES gains e.g. async iterators the integration will be fluid and simple---while not sacrificing our focus on being able to efficiently wrap low-level byte sources and sinks. Closing, but thanks for the prompting and discussion, all!

@domenic domenic closed this as completed Mar 17, 2015
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

No branches or pull requests

4 participants