Unidirectional Data Flow in Xamarin/UWP

Oleksandr Leushchenko
3 min readAug 11, 2017

Uni-directional architecture (UDA) patterns are quite popular nowadays. Most of our colleagues working in the native mobile development are familiar with this concept and for some of them it has become a silver bullet. I would argue any silver bullet existence, however the popular concepts and tools along with applying them appropriately is what defines the true professionals.

Unidirectional Data Flow is not a single architecture pattern, but a set of patterns joint by the same idea — the data must always flow in one direction. We will focus on pattern called Redux.

Before we dig into UDA let’s see why should we bother at all? Xamarin and UWP developers are lucky — MVVM was our mainstream architecture pattern almost since the beginning of times. It is great but there are two typical challenges:

  • bidirectional databinding
  • ViewModel interactions

I am sure you are able to recall a few more issues with MVVM, but let’s focus on these two for now. Both of them are related to the “multiple states” problem. Two-way binding is especially tricky and fun when it occurs on different threads in both directions simultaneously. And I’m sure you know at least two or three patterns on how to pass a value from child ViewModel to its parent.

With UDA you will not face those problems, cause you have only one “source of Truth” — model called Store. Views should be binded directly to the Store model with One-Way binding. In order to change the Model, View should create a special object called Action. Actions should be processed by the Dispatcher, which asks corresponding Reducer to create a new Store’s state.

View creates Action, Action is being processed by Dispatcher, Dispatcher creates new Store’s state via Reducer’s function, Store notifies View

There are several UDA frameworks for .Net. The most popular are redux.NET and YAXL.Redux, but since the overall idea is very simple you may not use any of them and implement unidirectional data flow pattern by your own. In order to illustrate that let’s use one of common Redux examples and create an app that counts!

Our app should contain a label with current counter’s value and provide a possibility to change it. I think two buttons (for increment and for decrement) should be enough for this purpose.

First of all we need to define our State. It should be immutable, so in C# we can write something like this:

Let’s create increment and decrement Action classes.

Actions are processed by Dispatcher(s), which operates Reducers. The only one purpose of reduce function is to create a new application state based on current state and an action.

As you might have guessed, this class is the heart of your app. Please do your best by covering it with unit tests before release. Pro tip: tracing might be a good idea too.

The last thing we need to implement is a Store. It holds application’s state and serves as an entry point for all Actions.

I know, I know… Not the best implementation of INotifyPropertyChanged. I hope you use Fody in your apps, but let’s KISS here.

Now you have to bind the View to the State (one-way binding only, right?). The View should not update its own components, but should create Actions and pass them to the Store’s Dispatcher. I will leave this for you as homework, but feel free to get sample here:

Counter app works now, but our unidirectional data flow implementation is far from the release version. Dispatch method is not thread-safe, so in concurrent environment the app can fall into the unpredictable state (hint: ConcurrentQueue to the rescue). We have one more problem, so called “God object”. The whole application state is stored in a single object — CounterState. This is the nature of Redux pattern. While it may work for small projects (like our counter app), I would highly recommend splitting the Store’s State into several state classes. It is a good idea to do the same with Dispatcher. But let’s keep such questions for the next post.

--

--