Qqwy

Qqwy

TypeCheck Core Team

GenFRP: Functional Reactive Programming in Elixir

Hey all,

This is a small and simple library I am developing, that will be part in a larger whole of libraries to hopefully at some point allow nice, functional native Graphical User Interfaces to be made from within elixir.

People who know about Elm: This is basically what Elm does as well.


GenFRP

Github, Hex

GenFRP is a library that allows for programming in elixir using the
Functional Reactive Programming method.

This is a way to store and dispatch information that is very readable and extensible.

The idea is as follows:

  1. Your FRP module contains use GenFRP, initial_state: some_useful_starting_state. (some_useful_starting_state can be anything you wish, of course)
  2. It implements the update(state, event) :: state function.
  3. It implements the render(state, last_rendered_state) :: any function.

update is called whenever an event is sent to the GenFRP process by using GenFRP.send_event(frp_pid, whatever_you_want_to_send).

render is called whenever you want to know its current state (in some representation format that is useful for the outside world, i.e. rendered).
GenFRP uses a very simple caching mechanism to ensure that render is only invoked when the internal state has changed since its last invocation.

Here is a very simple example (which can be found as GenFRP.Example.Map as well)

defmodule GenFRP.Example.Map do
  use GenFRP, initial_state: %{}


  def update(state, [{key, val}]) do
    Map.put(state, key, val)
  end

  def update(state, event) do
    IO.puts "Unrecognized event passed to `#{inspect(__MODULE__)}.update/2`: #{event}"
  end
  
  @doc """
  Returns the key-value pairs as strings, separated over multiple lines, in alphabetical order.
  """
  def render(state, last_rendered_state) do
  Enum.map(state, fn {key, val} ->
      "`#{key}`: `#{val}`"
    end)
  end
  Enum.join("\n")
end

This can be used as follows:

    {:ok, pid} = GenFRP.start_link(GenFRP.Example.Map)
    # ... maybe some other code here...
    GenFRP.send_event(pid, {:foo, :bar})
    # ... maybe some more code here...
    GenFRP.send_event(pid, {:baz, 42})
    # ... maybe yet some other code here...
    GenFRP.render(pid)
    "`foo`: `bar`
    ``baz`: `42`
    "

This is the first, 0.1.0 version release. I wanted to get this out quickly, to get some feedback from the community.
Expect things to be still somewhat unfinished, and don’t worry: I will run Credo on the code to make it nicer :stuck_out_tongue_winking_eye:.

But: any feedback is greatly appreciated. Is this programming interface understandable? Are there things that the library is glaringly lacking?

Thank you,

~Qqwy

Most Liked

StefanHoutzager

StefanHoutzager

Nice! I don’t know about frp, so I’m reading about it now. Maybe interesting for others also

FRP is about "datatypes that represent a value 'over time' ". Conventional imperative programming
captures these dynamic values only indirectly, through state and mutations. 

Here is a short intro (look for the copied text above to read the whole text): http://stackoverflow.com/questions/1028250/what-is-functional-reactive-programming

OvermindDL1

OvermindDL1

This could be used as the basis to make an elm’y clone in ElixirScript for both server-driven and client-driven page handling. ^.^

Now if only a type system. ^.^

Qqwy

Qqwy

TypeCheck Core Team

Yes, it was… (I need to get some sleep).

Yup, that would be amazing. I’m not sure how far ElixirScript is right now with supporting processes; there were some caveats earlier if I remember correctly, but yes, I am sold on this idea :slight_smile: .


As for the native GUI idea: I’m now working on a semi-direct (and thus stateful) wrapper to :wx_widgets called Wex (which is far from finished, because :wx_widgets is HUGE, and there are some design choices that still need to be made). Another to-be-written library that has the WIP-name Candlelight will wrap Wex with its own structs that are stateless representations of a certain GUI. Candlelight will use MapDiff to check for changes in theis GUI representation, and run the required Wex functions to update the changes.

To the end user, this means that a GUI can be constructed and altered by nesting the Candlelight structs (or functions/macros(?) that create them) in a very simple and clear manner.
Very similar to how Elm allows the creation of HTML content using its HTML DSL. However, GUI elements in WxWidgets are a lot more complicated than a HTML representation (which is just ‘text’; we let the browser figure out how it should look) so there is a lot of work to be done :grin: .

Qqwy

Qqwy

TypeCheck Core Team

There have been multiple ideas floating around here at the company that would work better with a simple native client than by wrapping Phoenix and interfacing through a local port with the application. So while it is not ‘soon’, Candlelight is made with a practical use in mind, yes.

bobbypriambodo

bobbypriambodo

Hmm, the Github link both on your post and hex page seems broken. It returns 404 for me. Is it still private?

Btw I think this is neat. FRP model such as in Elm and Redux is a nice way to solve some problems. Looking forward to using this in the future if a problem demands it.

Where Next?

Popular in Libraries Top

Qqwy
TypeCheck: Fast and flexible runtime type-checking for your Elixir projects. Core ideas Type- and function specifications are const...
336 13801 100
New
RobertDober
Earmark is a pure-Elixir Markdown converter. It is intended to be used as a library (just call Earmark.as_html), but can also be used as...
239 11851 134
New
tmbb
I’ve been working on two packages (not on hex.pm yet) to build admin interfaces for phoenix apps: bureaucrat - which contains a bunch ...
New
tompave
Hello there, I would like to share a feature toggles library (AKA feature flags) I’ve been working on. The main package is FunWithFlags...
New
nikokozak
Hello all, I’ve been working on Svonix - a library for quickly integrating Svelte components into Phoenix views. It’s a much-needed succ...
New
kelvinst
Hey everyone! Well, we made this lib a while ago and now we decided to finally go out and public with it! It’s a tool for creating and m...
New
danschultzer
In short Plug n’ play OAuth 2.0 provider library. Just set up a resource owner schema with Ecto (your user schema), install the dependen...
New
aditya7iyengar
Rummage.Ecto and Rummage.Phoenix provide ways to perform Searching, Sorting and Pagination over Ecto queries and Phoenix collections. Fo...
New
Jskalc
Hi! Today, after a couple weeks of development I’ve released v0.1 of LiveVue. It’s a seamless integration of Vue and Phoenix LiveView, i...
New
versilov
Could not wait for the missing Elixir ML libraries to appear, so, I wrote one myself, taking https://github.com/sdwolfz/exlearn as a foun...
New

Other popular topics Top

Brian
What is the proper way to load a module from a file in to IEX? In the python world, doing something like this pretty standard: from ....
New
dotdotdotPaul
Okay, I'm having a heck of a time trying to figure out how to best handle the validation of belongs_to associations in Ecto. I'm sure I'...
New
vonH
In asking this question I am more interested about the expressiveness of the language itself and less concerned about the availability of...
New
lessless
I believe there are people here who are dealing with CSV files import on the daily basis, and since Excel is a really popular tool there ...
New
joaquinalcerro
Hi there, I am working with Ecto-Postgresql and I need to call all of the records from a specific table but the table has 40,000 record...
New
malloryerik
Hi, this is for people who, like me, have had some friction using .html.heex templates in VSCode. The solution seems to be, in a hyphena...
New
vonH
When I run the Plug and I recompile I wind up having to use Ctrl C to quit iex and start again. Witht the help of rlwrap I can use the cu...
New
chrisalley
ExUnit now has describe blocks which is a welcome addition coming from RSpec. In the docs, it states that nested hierarchies of describe ...
New
aesmail
Hello guys, I have finally made it. I created an admin interface for a framework. It’s been on my todo list for years and with the curre...
New
jay1
Why is it that the mnesia database isn’t the most preferred database for use in Elixir/Phoenix?
New

Sub Categories:

We're in Beta

About us Mission Statement