So you’ve sifted through the seemingly infinite sea of JavaScript frameworks, and finally settled on React. But then you realise that React only solves half the problem, and everyone is now using Flux for the other half. But that’s ok — if Flux came from the same place as React, it should have a simple and easy-to-learn API, right?
Wrong.
Flux is like a framework for frameworks – frameworkception, as one redditor put it. There are as many implementations as there are opinions, all with their own strengths and weaknesses, and none of them with authority.
So what is a developer to do? Contribute to the malaise by rolling your own, like I did? Don’t do it! Instead, use Redux.
Wait, is it really that simple? Yes, it really is! But since you’re still reading, you’re probably not someone who is easily convinced. And that’s why I’ve prepared this comparison for you:
The Criteria
I scoured a number of online communities for the things which people place the most value on in a Flux implementation. I then condensed these down to four criteria:
- Community: Will you regret choosing the implementation if the maintainer gets hit by a bus?
- Simplicity: Simpler code generally results in a shorter learning curve and easier maintenance. However, too much magic can make things confusing.
- Functionality: Does this Flux implementation actually provide Flux-like features, including debuggability and easy handling of async data?
- Documentation: No matter how great the functionality is, it is no good if you can’t figure out how to use it.
The Competitors
There are a lot of flux implementations – possibly hundreds – and so we need a way to narrow down the field. Luckily, our community criteria allows us to do just that.
I used GitHub’s star count to get a rough idea of the size of each implementation’s community. At the time of writing, Facebook’s repository has 8000 stars – so let’s create an arbitrary cut-off of 2000. This gives us four competitors, all of which are in active development, have been used in production code, and support isomorphic JavaScript:
The Shootout
Facebook’s Flux
If Facebook both invented Flux and provide a Flux repository, you may be wondering why we’re having this conversation at all?
Somewhat surprisingly, Facebook itself uses multiple implementations internally. This indicates that Facebook’s Flux repository is not meant as a canonical implementation. Supporting this is the fact that until recently, Facebook only provided an implementation of the flux Dispatcher, with stores, actions and containers left as an exercise to the reader.
Community
Given that this project is where Flux started, it is no surprise that it has a large following in the community. In fact, Facebook’s Dispatcher
is used in a number of alternative Flux implementations – so it isn’t going to be disappearing any time soon. As a bonus, Facebook’s Dispatcher is the same one they use in production.
Simplicity
Facebook recently expanded their Flux repository with tools to ease the implementation of stores and containers. However, the simplicity comes at a cost: you still can’t get started without a significant amount of boilerplate.
Functionality
Given that this is the original Flux implementation, you may think that it would be the embodiment of Fluxiness. But while it does facilitate writing a Fluxy application, it still leaves a lot to the imagination. For example – Facebook’s Flux doesn’t provide any tools to work with action creators. Additionally, you may find yourself stuck when you need to handle async data.
Documentation
Flux’s documentation is a little thin. Given enough time, it’ll certainly teach you what you need to know — but it can be a little hard to grasp for beginners. It can also be hard to distinguish between documentation for Flux as a pattern, and for Facebook’s implementation.
Reflux
Reflux is one of the older Flux implementations, with its first commit being checked in on the 2nd of July, 2014. As such, it didn’t benefit from the hindsight that a number of newer implementations have.
Reflux advertises itself as “A simple library for unidirectional dataflow architecture inspired by ReactJS Flux.”
Community
Being one of the first Flux implementations, Reflux has grown a sizeable community, with almost 4000 stars on GitHub. But while size does matter, its growth has ground to a halt in recent months.
Simplicity
Reflux initially feels a lot simpler than Flux. It achieves this by merging Flux’s Dispatcher
with its action objects and action creator functions, creating the new concept of action functions. This simplifies your code by eliminating Flux’s enormous switch
statements and singleton Dispatcher
. It also makes actions a lot easier to create.
But while actions may feel simpler, Reflux replaces waitFor
with two new concepts: joins and aggregate data stores. And despite spending a lot of time reading Reflux’s code, I still don’t understand them.
Functionality
While Reflux’s action functions may feel simpler than Flux’s action creators, they come at the expense of functionality. The most obvious manifestation of this is how Reflux complicates the process of dispatching multiple actions at a time – a pattern which is often used with async code. Additionally, the lack of a central Dispatcher makes it difficult to log, inspect and replay user actions — eliminating Flux’s debugging benefits.
Documentation
Reflux has a reasonably comprehensive README. Unfortunately, if the information you need isn’t in the README, you’re going to have trouble googling for it amongst all the information on Acid Reflux.
Alt
Alt — like Reflux — places emphasis on terseness. Unlike Reflux, it still places emphasis on being Flux.
Community
Alt has a smaller community than the two implementations we’ve already looked at. However, despite the smaller community, it has almost twice as many Pull Requests as Reflux.
The thing that struck me during my research is that it feels like the people who like Alt really like Alt. Even if the community is small, I can’t see it disappearing anytime soon.
Simplicity
Alt feels simple. There are two reasons for this:
- Alt’s API has been designed around ES6, and supports ES7 decorators. As a result, Alt-based apps look pretty (to my ES7-trained eyes).
- Alt merges Flux’s action creators and action objects into action functions. However, unlike Reflux, it still makes use of Flux’s
Dispatcher
.
Functionality
Alt provides you with most of the benefit of Flux, but with a nicer syntax. The only caveat is that if you want meaningful logs in production, you’ll need to ensure that action function names aren’t mangled by your minifier.
Documentation
Alt’s documentation is excellent. I wish I had access to Alt’s documentation when I was learning Flux.
Redux
With its first commit dated May this year, Redux is the new kid on the block. But despite this, it now seems more popular than Flux itself.
An interesting piece of trivia about Redux: A number of people will tell you that it isn’t actually Flux. Not that it really matters, given it solves the same problems.
Community
Redux’s README starts with this quote from Bill Fisher, one of Flux’s creators:
I asked for comments on Redux in FB’s internal JS discussion group, and it was universally praised. Really awesome work.
And if that isn’t enough appeal to authority, the authors of the popular Flux implementations MartyJS and Flummox both bowed out of the race in favour of Redux.
Simplicity
Redux is by far the simplest of the frameworks I’ve discussed. It achieves this by making additional assumptions beyond those of Flux itself. Chief amongst these is the assumption that you never mutate your data. With this knowledge, you no longer need the Flux Dispatcher
. It also makes it possible to describe changes to your data with plain old functions instead of a giant switch
statement.
Functionality
The brilliance of Redux is that while it is in many ways simpler than Flux, it doesn’t lose out on any of the functionality.
Action objects are still created with action creators. You still have a central store
object which allows you to inspect and debug user input. And with the help of redux-thunk, it is still possible to dispatch multiple actions from one action creator.
Documentation
But while the community, simplicity and functionality of Redux are worth getting excited about, the documentation is bloody amazing.
The Verdict
And the winner of the award for the most simple, well documented Flux implementation with the largest community is … Alt! But why limit ourselves to Flux?
The motivation behind Flux is to simplify our application architecture, making it easier to reason about and maintain. And unless you have a really unusual use case, Redux is currently the best way to achieve this.
Of course, knowing how to structure your application’s data is only half the battle. What about structuring your CSS, your build system and your routes?
In return for your e-mail address, I’ll also send you guides to CSS, build systems and routing tools as they’re released. As a bonus you’ll also immediately receive three print-optimised PDF cheatsheets – on React (see preview), ES6 and JavaScript promises.
I will send you useful articles, cheatsheets and code.
One more thing – I love hearing from readers. If you have something to say, send @james_k_nelson a tweet, or send me an e-mail at james@jamesknelson.com. Thanks for reading!
I would also consider Cerebral. It feels to me the most “natural” https://christianalfoni.com/cerebral/#/0
Any chance you’ve taken a look at FluxThis (https://www.fluxthis.io)? I’d be interested in your thoughts on it. It seems to accomplish some of the same things as Redux (less boilerplate, more immutability), though I’m less equipped to say for sure because I haven’t used Redux myself.
You need also to consider the flux without flux approach using freezer.js
https://medium.com/@arqex/react-the-simple-way-cabdf1f42f12
Probably the simplest approach
Why do you start by saying “use Redux” and conclude by saying Alt is the winner?
For me, Redux is clearly the winner.
I probably could have put it a little clearer, but if you keep reading about two more sentences I say that Redux is in fact the implementation you should use – it just might not actually be Flux.
No one’s explained this better to me than you did so – thank you! 🙂
Thanks for great article James, but what is your opinion of https://optimizely.github.io/nuclear-js/ ?
This is a terrific write-up. Thank you.
Just getting into React. Saw some interesting presentations about Relay. How does that fit into the Flux implementation question?
Thanks for the article. Choosing a flux implementation is a nightmare
thanks for your efforts, really well written
Keep this article updated over time, as sure shortcomings of Redux will be filled by some one or by itself, want to compare about that too
On the Reflux part, yo put “Redux replaces waitFor with two…” it has to be “Reflux” right?