trustmaster / goflow

Flow-based and dataflow programming library for Go (golang)
MIT License
1.6k stars 125 forks source link

Array ports #3

Closed trustmaster closed 10 years ago

trustmaster commented 12 years ago

FBP doesn't allow connecting a single output to multiple inputs, though it allows for explicit replicator components in the network.

Currently it isn't very easy to write components operating on generic data in Go without writing too many type assertions, so generic components would require a code generator tool.

Though, an idea of broadcast ports replicating data to multiple subscribers is worth considering.

davidkbainbridge commented 10 years ago

I agree, it would be valuable to have a series of load balancing components with different strategies, round robin, random, feedback based. Even with extendable strategies.

Is this being planned? Worked on?

trustmaster commented 10 years ago

Technically, you can connect the same output to multiple inputs in GoFlow (sh-h, don't tell anyone in the FBP community!) and the consumer processes read from the same input just like from a FIFO.

There hasn't been much progress on load balancing components, but those will appear with the practical necessity of such in real applications. For now you can easily write your own balancers for a specific application, while generic components is Go is almost terra incognita.

trustmaster commented 10 years ago

Actually now that I have reviewed #14 and the existing code, I see that multiple consumers on a single output channel needs to be explicitly implemented in the Connect() method so that Connect() would support following cases:

  1. Connecting a chan output port "src" to a chan input port "dst". The "src" channel is nil, so create a new channel and connect "src" with "dst".
  2. Connecting a chan output port "src" to a chan input port "dst". The "src" channel is not nil and exists already. This means that we are trying to add another consumer to the channel. Connect the existing "src" channel to the "dst" output port and let it act as FIFO.
  3. Connecting a slice of chan output port "src" to a chan input port "dst". Assume that the source process is a load balancer, so add a new channel to the slice and connect it to "dst".

With pull request #14 we have 1 and 3 implemented, 2 isn't hard to add too.

davidkbainbridge commented 10 years ago

With respect to 2, do we want to do this? This sounds incorrect with respect to FBP. What is accomplished by hooking up multiple consumers to a single producer channel? According to https://code.google.com/p/go/issues/detail?id=247 if a channel has multiple receivers then the results are non-deterministic and vary by implementation. I would rather see goflow be deterministic and ensure that all 1 to many communication happen via an explicit component essentially implementing an explicit policy. That being the case, I wouldn't think goflow should support case 2, i.e. when you connect A to B there is a new channel created.

trustmaster commented 10 years ago

I was probably wrong in my expectations of Go behavior, but my idea for case 2 was to use it as the fastest implementation of a balancer with more or less random distribution. If it makes no sense, then it isn't worth it.

trustmaster commented 10 years ago

This feature is actually called "Array ports" in the original FBP book. And thanks to @davidkbainbridge we now have it implemented.