type Msg = Update Model (Cmd Msg) (Sub Msg) update : Msg -> Model -> ( Model, Cmd Msg ) update msg model = case msg of Update model cmd sub -> ( { model | subscription = sub }, cmd )
view : Dosar -> (Dosar -> Cmd msg -> Sub msg -> msg) -> Html msg view (Dosar data) callback = let c data = callback (Dosar data) in div [] [ h1 [] [ text "Dosar nou" ] , Temei.view data.temei (\v -> c { data | temei = v }) , DocumentExecutoriu.view data.documentExecutoriu (\v -> c { data | documentExecutoriu = v } Cmd.none Sub.none) , Actiune.view data.actiune (\v -> c { data | actiune = v }) ]
unlabeledTextField : String -> (String -> msg) -> List (Html msg) unlabeledTextField defaultValue callback = [ input [ value defaultValue , onInput callback ] [] ]
--
You received this message because you are subscribed to the Google Groups "Elm Discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email to elm-discuss+unsubscribe@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.
Without using Cmds and/or Subs it is an interesting approach if you use it for managing very small bits of state (the open/close status of a dropdown) but I'm afraid that it might bring performance problems if you use it for the entirety of the app.
You basically have to computer all the possible future states of the app.
--
You received this message because you are subscribed to the Google Groups "Elm Discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email to elm-discuss...@googlegroups.com.
On of the key recommendations of Elm Architecture is to have your messages be just data.
Your approach is somewhat similar to the approach of elm-sortable-table (except for the Cmds and Subs).
Without using Cmds and/or Subs it is an interesting approach if you use it for managing very small bits of state (the open/close status of a dropdown) but I'm afraid that it might bring performance problems if you use it for the entirety of the app.
You basically have to computer all the possible future states of the app.
Won't this break the reactor/debugger? You can't really tell what sort of messages is being passed around in your application with this model, if you want to export message history, it would fail as well I believe.
I think a better way would be to not have nested components. Keep your entire message hierarchy, and model structure, flat.
Ignoring the commands and subscriptions part, I think this could be summarized as being built around having any of the things that would send a message instead send a new state. This eliminates the level of indirection of wrapping the desire to change the state into a message and then unwrapping the message to actually do the state change.
It is entirely based on data and hence should be compatible with message recording for the debugger.
On the other hand, the messages will lack semantic information. (One could work around that by adding a logging text field that was set when building the update message but ignored when applying it.)
Where this would seem to fall down is commands and subscriptions. Those are going to produce asynchronous results and would risk baking in a stale model state. This is particularly true for commands. Imagine, for example, wiring up a tick command that will increment a tick field in the model after five seconds. Since the command will be constructed to send the single "set the state" message and since the only model it will have access to is the one that existed when the command was constructed, it basically becomes a "reset the state to where it was five seconds ago" command. If subscriptions really do get rebuilt after every cycle of the update loop, then this isn't a problem for them but the closure construction for each subscription is an expense. If they don't get rebuilt — and the code in the initial posting suggests that instead we're caching a subscriptions value — then as with commands, it would seem easy to end up with code that resurrects stale states.
I can second Mark's point. At my company we had a little experiment where chunks of state where sent in the messages. Not the whole model but not a single unit either. It seemed really promising for a moment and quite clean but then we started getting bugs which were very hard to understand. Turned out to be exactly what Mark suggested. Between messages and commands we'd have multiple copies of the same chunk of state in flight, each based on some original value but each ignorant of the changes that the other were representing. The end result was to just get the last state and lose anything associated with other messages or commands happening around the same time.We moved back to the standard strategy and all is well.
You basically have to computer all the possible future states of the app.Not sure what you mean here. Could you please expand, or maybe point to an example in the code? 🤔
--
One other note: If you don't care about Reactor and the Debugger but do care about async problems, you could get almost the same structure by passing back Model -> Model functions instead of Model values.
type Msg= Set Modelupdate : Msg -> Model -> Modelupdate (Set newModel) model =newModel
... onClick (Set { model | counter = model.counter + 1 }) ...
type Msg= Apply (Model -> Model)update : Msg -> Model -> Modelupdate (Apply fn) model =fn model
... onClick (Apply (\model -> { model | counter = model.counter + 1 })) ...
But if one did that, one might as well have an IncrementCounter message and handle it in the update function.... onClick (Apply incrementCounter) ...incrementCounter : Model -> ModelincrementCounter model ={ model | counter = model.counter + 1 }
--
You received this message because you are subscribed to the Google Groups "Elm Discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email to elm-discuss+unsubscribe@googlegroups.com.
To unsubscribe from this group and stop receiving emails from it, send an email to elm-discuss...@googlegroups.com.
Oh wow! This looks super cool! 🤓…and it seems this would also cover for the issue that Peter mentioned: this gives me the ability to have a real onClick callback without pre-computing the expected-after-click state! 🤠 — Right Peter? 🤔
In my app I have a large data entry form where initial fields determine which subsequent fields will be. It’s my understanding that every change to the model should be its own message. So far I have 50 fields in total (and there will probably be more) — does this mean that I need to have 50 things in my Msg? Or am I seeing it wrong? 🤓
onClick : (String -> msg) -> Html.Attribute msg onClick callback = Html.Events.on "click" (Json.Decode.map callback Html.Events.targetValue)
--
You received this message because you are subscribed to the Google Groups "Elm Discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email to elm-discuss+unsubscribe@googlegroups.com.