Skip to content

Instantly share code, notes, and snippets.

@eulerfx
Last active August 29, 2015 14:02
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save eulerfx/7a1e59a428861817b140 to your computer and use it in GitHub Desktop.
Save eulerfx/7a1e59a428861817b140 to your computer and use it in GitHub Desktop.
Rx effectful observers

Synchronous

  • () -> (() -> a) - sequence (IEnumerable)

with arrows reversed:

  • (a -> ()) -> () - observable (IObservable)

Everything is fine and we have duality between pull and push. In particular, () -> a is dual to a -> ().

Effectful

  • () -> (() -> IO a) - async sequence (AsyncSeq in F#, Source in scalaz-stream)

with arrows reversed:

  • (IO a -> ()) -> () - dual of async sequence, but is not async observable!

Note the co-Kleisli IO a -> ().

An async observable would be:

  • (a -> IO ()) -> () - this is async observable

Note the Kleisli a -> IO ().

The issue is that an async observable makes use of Kleisli and so cannot be dual to async sequence which also uses Kleisli. In particular, () -> IO a is not dual to a -> IO (). More technically, this is an issue of variance.

Interpretation

The reason this is interesting is that for an Rx model to have async observers, it can no longer be dual to async sequences. This is not in itself a problem but raises some concerns for implementing async observers. Intuitively, if observers represent a push-based or data-driven source, then it may not make sense for observers to be async.

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