Skip to content

Instantly share code, notes, and snippets.

@rstacruz
Last active January 18, 2018 11:22
Show Gist options
  • Save rstacruz/708689876fba38e0167af109d84523c2 to your computer and use it in GitHub Desktop.
Save rstacruz/708689876fba38e0167af109d84523c2 to your computer and use it in GitHub Desktop.
Redux.ex (elixir)
defmodule Redux do
@moduledoc """
Like redux.js, but more elixir-like
store = create_store fn state, action -> ... end
store |> get_state()
store |> dispatch(%{ type: "publish" })
"""
defstruct reducer: nil, state: nil
@doc """
Creates a store
"""
def create_store(reducer, initial_state \\ nil) do
%Redux{reducer: reducer, state: initial_state}
|> dispatch(%{ type: :"@@redux/INIT" })
end
@doc """
Returns the current state
"""
def get_state(store) do
store.state
end
@doc """
Dispatches an action
"""
def dispatch(store, action) do
store
|> Map.put(:state, store.reducer.(get_state(store), action))
end
end
defmodule Example do
import Redux
def reducer(state, action) do
case action.type do
:set ->
action.value
:add ->
state + action.value
_ ->
state
end
end
def run do
store = create_store(&reducer/2)
store = store |> dispatch(%{ type: :set, value: 2 })
IO.puts(store |> get_state()) #=> 2
store = dispatch(store, %{ type: :add, value: 10 })
IO.puts(store |> get_state()) #=> 12
end
end
Example.run
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment