Tuesday, August 15, 2017

Modeling Implicit View Behaviors

Jared Sinclair:

The most critical reason why UI testing wasn’t the right choice for us is that it doesn’t make it easier to avoid breaking implicit behaviors in the first place. Over time, conditional statements pile up until it isn’t obvious from the code itself what the expected behaviors are. If a developer needs to make a change, it can be difficult to know where to begin and how to avoid introducing regressions. On our project, we sought an approach that substituted implicit behaviors with explicit behavior modeling — value types that can be passed between components and verified for correctness at compile time and in unit tests.


The evaluator returns three things: 1) an updated model, 2) a set of UI updates, and 3) a set of actions. The core replaces its current model with the updated model and performs all the actions in the actions set (if any). Lastly it forwards the UI update instructions to the view controller via a delegate protocol.


Because all the decision-making occurs inside the evaluator, and because the evaluator is a purely functional creature operating only on its inputs and always returning a value, we were able to unit test the evaluator for every event under all relevant conditions. Every property on the model struct — which is a comprehensive representation of the status of the entire system — is a value type, so it was trivial to establish special conditions for each test. As we discovered edge cases and added new features, we were able to extend the evaluator’s implementation and know immediately whether we had introduced any regressions.

Update (2017-08-16): See also: Andy Matuschak.

Comments RSS · Twitter

Leave a Comment