Getting value of a property and understanding FRP/RP #478

Closed
gyzerok opened this Issue Nov 28, 2014 · 11 comments

Projects

None yet

5 participants

@gyzerok
gyzerok commented Nov 28, 2014

Hello, guys!

I'm new to FRP (or RP, dont know exactly) and want to get in with bacon. The first thing I really cant understand is the Property. Documentations says:

One of the common first questions people ask is "how do I get the latest value of a stream or a property". There is no getLatestValue method available and will not be either. You get the value by subscribing to the stream/property and handling the values in your callback. If you need the value of more than one source, use one of the combine methods."

So what if I want to know its value in some later time after it arrives? What should I do? As I understand documentation says that I can get this value using some technics, but there are no examples describing them.

As most of bacon users I'm coming from MVC world. So the other question I have is: "How to organize large application?". All the examples I found are "one file program". What are the common technics to develop an app with several modules?

I there any guides from which I can get more solid knowledge about what FRP (or RP) is and how to use it in every day development?

@gyzerok gyzerok changed the title from Getting value of a property to Getting value of a property and understanding FRP/RP Nov 28, 2014
@benjycui
benjycui commented Dec 2, 2014

Here is an introduction of RP -> https://gist.github.com/staltz/868e7e9bc2a7b8c1f754

@gyzerok
gyzerok commented Dec 2, 2014

Thank you @benjycui
I've already read this. The problem about such topics is that they share same examples. I need something more solid.

@raimohanska
Contributor

Hello! Very good questions indeed!

If you want to use the value of a Property x later, you should probably define "later" as an event in some EventStream e. Now, you can, for example, use x.sampledBy(e) to get an event that has the value of x when e occurs.

How to organize large application? That seems to be a topic not very well covered in the internets and rewards a blog post or two. Maybe my next post will be on this. Anyway, what I personally do is something like this.

As with any other tecnology, I split my application into independent components with a single responsibility. I use EventStreams and Properties to connect the components together. This comes quite naturally when they are also internally composed from the same. For example, a ShoppingCart model component might look like this.

function ShoppingCart(initialContents) {
  var addBus = new Bacon.Bus()
  var removeBus = new Bacon.Bus()
  var contentsProperty = Bacon.update(initialContents,
    addBus, function(contents, newItem) { return contents.concat(newItem },
    removeBus, function(contents, removedItem { /* omitted */ }
  return {
    addBus: addBus,
    removeBus: removeBus,
    contentsProperty: contentsProperty
  }    
}

Now the external interface of this component exposes the addBus and removeBus Buses where you can plug external streams for adding and removing items. It also exposes the current contents of the cart as a Property.

Now you may define a view component that shows cart contents:

function ShoppingCartView(contentsProperty) {
  function updateContentView(newContents) { /* omitted */ }
  contentsProperty.onValue(updateContentView)
}

And a component that can be used for adding stuff to your cart:

function NewItemView() {
  var newItemProperty // property containing the item being added
  var newItemClick // clicks on the "add to cart" button
  var newItemStream = newItemProperty.sampledBy(newItemClick)
  return {
    newItemStream: newItemStream
  }
}

And you can plug these guys together as follows.

var cart = ShoppingCart([])
var cartView = ShoppingCartView(cart.contentsProperty)
var newItemView = NewItemView()
cart.addBus.plug(newItemView.newItemStream)

I hope this helps!

@gyzerok
gyzerok commented Dec 2, 2014

Big thanks, @raimohanska! This helps a lot!

There are a big lack of examples of using reactive programming for non-simple apps especially for back-end.
I don't know if reactive programming is the paradigm of the future, but I think that today any engineer must to be on the edge of technologies. So I'm trying to dive in.

Now I'm developing a simple rsa chat application just for practise. And want to use Bacon for both front-end and back-end. It would be great if you can review my code as soon as it would be ready so your advises can improve both my understanding of FRP and code quality. I suppose we can then add this code as one more solid example of using Bacon. You can find my code in https://github.com/gyzerok/reactive-cryptochat. Tell me if it's ok to contact you for reviewing as soon as its ready.

If we do so with my little chat I can try to develop more complex single page application with different routes and views on front-end and some business logic on back-end.

@raimohanska
Contributor

I strongly prefer questions on Stack Overflow or Google Groups to personal email and usually don't have the time to review people's code for free :)

@RoboTeddy
Contributor

I have viewmodels that look very similar to @raimohanska's ShoppingCart. I create buses for streams of requests from the user, and then compose those streams together into properties, and expose both the buses and the resultant properties.

I then pass the properties into React (via) https://github.com/irskep/BaconReactMixin to render the view declaratively. If a property changes, the DOM updates accordingly.

@gyzerok
gyzerok commented Dec 2, 2014

@raimohanska, mb you can advise someone who can help me?

@RoboTeddy, thank you for helping! Can you share your code?

@raimohanska
Contributor

Btw, I upgraded my answer above into a blog post: http://baconjs.blogspot.fi/2014/12/structuring-real-life-applications.html

@gyzerok
gyzerok commented Dec 2, 2014

@raimohanska it would be even better if you add this in the project wiki so everyone can find it later easily and dont have to scroll down the blog for ages :)

@phadej
Member
phadej commented Dec 2, 2014

... or bootstrap the cookbook or tutorials on the website :)

@raimohanska
Contributor

Good points. I guess the site might be the place for articles like this.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment