Hacker News new | ask | show | jobs
by simulate-me 1494 days ago
One thing that I like about this is the implementation of returning state from the Update function. My only experience with Elm-style architecture is with react / redux which involves meticulously copying pieces of the state object to return two distinct before / after states. Using a Go struct with copy semantics makes this extremely easy and more natural to write in an imperative fashion. One limitation of this is that the model structure can only contain value type (e.g. no pointers, arrays, or maps).
2 comments

Just curious, I'm not familiar with Go. Will it copy the references anyway, meaning both structures now have a pointer to the same object? That's the way it works in other languages I'm familiar with, so you have to be careful about what you copy and how you use it.
Yes, but it doesn't actually matter. You can use pointers for models, return the same pointer, and it will re-render fine. We do this for our CLI at https://www.inngest.com for creating new serverless functions via a quick walkthrough.

It's actually the `tea.Msg` that causes re-renders. Here's the code: https://github.com/charmbracelet/bubbletea/blob/v0.20.0/tea.....

tea.Msg is, in Redux land, an "action" that triggers some state updates and _always_ triggers a re-render, even if nothing changes.

This is elm-like, but we have to understand the limitations of what we're working with: a terminal with no way of (nicely) updating elements in place. It's essentially an immediate-mode UI, and so it always paints.

Well, it does matter, or rather, it could matter.

For example, say you needed an undo/redo mechanism. If the model were guaranteed to be immutable model, you could simply hang on to the previous models as a sequence of state changes; undoing/redoing is trivial. If the model is mutable, then the undo/redo system has to defensively make a copy before update is called

Do note, however, that paints will only occur if the output changes, and only lines that have changed will be redrawn.
>Will it copy the references anyway, meaning both structures now have a pointer to the same object?

Correct. A value copy is a simple shallow copy. Deep copy requires use of reflection (if you don't want to manually manage copying).

yes, that's what it does in go
>One limitation of this is that the model structure can only contain value type (e.g. no pointers, arrays, or maps)

How does one manage dynamically sized lists of elements, if arrays are disallowed?

You can use arrays, but if you want to maintain the Elm-like model of before and after states, then you need to explicitly copy the array into the new state rather than rely on Go copying just the pointer.