Elixir for Programmers course - should we adopt Dave Thomas' way of organizing GenServers?

This might be related…

https://twitter.com/pragdave/status/997184002267246592?s=21

Can’t wait for the video!!

5 Likes

I never realised that I write elixir in a default way. :wink: Well, the talk could be debunked on this forum also. “Why Dave Thomas’ way is wrong.” With all respect. :wink:

1 Like

He already talked about his GenServer concerns back in ElixirDaze 2017 through Jeeves (Service in the talk) - so it might be something different.

2 Likes

It could be his style of the Replaceable Component Architecture that I am such a huge fan of then :003:

As discussed here and here :slight_smile:

2 Likes

This isn’t the code you’re looking for
Move on…

Edit:

The two subprojects Comp1 and Comp2 list in mix.exs:

  defp deps do
    [
      { :component, path: "../../component" },
    ]
  end
4 Likes

Whoo hoo I think that could be it :003:

Seems like our enthusiasm for his RCA ideas is rubbing back on to him too :purple_heart:

1 Like

wow that’s beautiful

1 Like

Dave gave a talk about components and something he called Noddy for component deployment at Empex the other day. It was interesting, and I’d love to hear what people think once the talks are online.

2 Likes

In my opinion the discussion here misses Dave’s point?

I think I agree with Robert/Sasa, etc IF you already know you need a genserver. The key thing is that often you are writing a module and you are following Sasa’s advice to start without storing state in the module, and so off you go… But then LATER you decide that you need to “upgrade” to storing state in the module… THIS is where Dave’s approach wins

So his approach makes more sense (to me) if we assume that we are using it from the point of view of writing a small module which DOES NOT store state or use a genserver. That gives us 2 modules, one for the public api and one for private implementation. The third module is what we get once you decide to inflate the public api to use some kind of state storage/genserver.

I thought his approach very elegant from this point of view. Equally I think if you already know you need to store some state and you have some clarity that the module is fairly small in scope, then it probably makes sense to start from Robert’s design…?

Link to Dave’s thoughts:
https://pragdave.me/blog/2017/07/13/decoupling-interface-and-implementation-in-elixir.html

3 Likes

I’d suspect from their point of view the evolution

if we assume that we are using it from the point of view of writing a small module which DOES NOT store state or use a genserver. That gives us 2 modules, one for the public api and one for private implementation. The third module is what we get once you decide to inflate the public api to use some kind of state storage/genserver.

as described isn’t something that happens very often if you’ve worked with the BEAM for a while.

You’d likely keep your processes small (just not too small). The stateless module to stateful server evolution doesn’t sound like a common scenario to me. For small processes, three files can seem a bit much unless you have a good reason to go that route.

Decouple. You know it makes sense.

I think that should have been

Decouple where and when it makes sense.

Edit:

Actually the more I think about it, the more dangerous this approach seems from a systems perspective. While it seems convenient from a code management perspective (however inconvenient two or three separate files per module/server may be) because you don’t need to change the client calls - consider that you are in fact:

  • ripping perfectly good intra-process sequential code out of the client process
  • and replacing it with calls across process boundaries

That transformation should never be done mindlessly. I’d much rather delete the old module and recreate the server under a new name - in the hopes that compilation will tell me where all the client’s are so that I can verify:

  • whether the client needs additional inter-process safeguards
  • or if we go with “let it crash”, whether the supervison tree needs to be adjusted to account for the additional failure modes.

Convenience over Correctness (2008)

3 Likes

Reminds of Robert’s KICAS principle, keep it consistent and simple

Another issue is that you are changing the handling of the state. For a stateless module then it is the caller which must handle the state but when you to a stateful server then it is the server which handles the state. This means that this change will by necessity entail a significant change in the caller code.

No, most definitely not, as it completely changes its behaviour in very many ways so it is no longer the same thing any more.

3 Likes

Unless you keep that fact hidden from the caller and return the pid in the return value as though it is that state, rather than a handle to it.

(I’m frankly still not sold of having methods, not messages, as the API but I need to experiment more before I allow a firm opinion to come out on this topic ;-))

6 posts were split to a new topic: Elixir for Programmers course - should we adopt Dave’s way of building our applications as components?