Search code examples
elmelm-signal

Understanding this signal code


I am reading this bit of code since yesterday and trying to come up with a reasonable explanation, could you please check that my assumptions are correct.

This code comes from here.

port requests : Signal (Task x ())
port requests =
  Signal.map lookupZipCode query.signal
    |> Signal.map (\task -> Task.toResult task `andThen` Signal.send results.address)

Line 1 defines a port, is returns a Signal which is composed by a Task, a type identified by x and an empty value (this doesn't make sense to me, and I suppose it's plain wrong).

Line 4 and 5 make use of the forward function application construct, so the result of line 4 is passed as argument to line 5, but what is happening in detail in those lines?

To learn about functional reactive programming I'm going through this post is it a good resource?

I've read the documentation about signals but I can't really get the point here. An explanation in plain english with an example would be much appreciated, many thanks to anyone who would help me!


Solution

  • A port is the way Elm communicates with the JS world.

    Signal (Task x ()) means that is a signal of Task that have an error type x and return a Unit

    The second line defines the port and it basically means that this port will be used for communication towards JS rather than from JS.

    If we look at the definition of lookupZipCode we can see that it takes a String and returns a Task String (List String). Looking at its code I can see that it will execute a Http request on the query string and return either an Error of type String OR a list of Strings (list of names of towns).

    So Signal.map lookupZipCode query.signal produces a Signal of these tasks that interrogate the zipcode server.

    In the next Signal.map, we take the above tasks and convert them so that:

    1. the error and the result of the http query are joined together in a Result type. (this means that the new task will never fail).
    2. andThen this Result type will be sent to the results.address.

    The resulting Task that is actually being sent for execution in JS land will have no error (this is why you see the x there) and will result in the Unit type (this is the signature of Signal.send).

    When the Task gets actually executed in JS, the result of the execution will end up in results.address as an Result type.