Skip to content

API design #7

Description

@edkelly303

This looks really interesting!

I am an Elixir noob who wrote his first GenServer last weekend, so this feedback may be very naive and stupid; please ignore it if so.

Although the API is very much simpler and more streamlined than the traditional GenServer, it still has a few moving parts and I wonder if they're totally necessary. From my reading of the readme, it sounds like there are exactly 3 things that you might want to do when you interact with a component:

  1. Update the state of the component
  2. Get a reply from the component
  3. Update the state and get a reply

With the current API, there are two things that the user needs to do to achieve these results:

  1. Choose between one_way and two_way (2 options)
  2. Choose whether to use set_state, set_state_and_return, or neither (3 options)

That gives you 6 possible combinations of things you could write, but only 4 of them will do what you want.

two_way -> OK (replies without updating the state)
two_way + set_state -> OK (updates the state and replies with the new state)
two_way + set_state_and_return -> OK (updates the state and replies with something else)
one_way -> OK (updates the state without replying)
one_way + set_state -> ?
one_way + set_state_and_return -> ?

Would it be possible/desirable to have an API that was more like this?

defmodule KV do

  use Component.Strategy.Dynamic,
      state_name:    :kv_store,
      initial_state: %{}

  handle add(kv_store, key, value) do
    %{state: Map.put(kv_store, key, value)}
  end

  handle get(kv_store, key) do
    %{reply: Map.get(kv_store, key)}
  end

  handle merge_and_tell_me_the_new_value(kv_store, key, new_value) do
    new_kv_store = Map.update(kv_store, key, new_value, fn old_value -> old_value + new_value end)
    merged_value = Map.get(new_kv_store, key)
    %{
      state: new_kv_store,
      reply: merged_value
    }
  end
end

That way, the user doesn't have to think about which type of function they're writing - they just need to specify what they want to get out of it - a new state, a reply, or both.

Activity

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

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions