Templating in Vue: Separation of Concerns or Separation of Technology or something else?
They aren’t wrong, but I think they aren’t completely right either.
Single file components (SFCs), aka, what you almost always find used in React or VueJS apps to break down application logic, is what we’ll be circling around. I purposely avoided the “React vs. Vue” clickbait in the title, because this is a conceptual argument and not necessarily about React or Vue per se. But for sure, you’ll find these contradicting concepts playing out with Vue’s separation of HTML (in templates), CSS and JS and in React’s JSX. It is a heated discussion and this is my take on some of the argumentation being made (and I can’t avoid mentioning the two technologies as I go too).
The Real Concerns (or Responsibilities?)
HTML — Is the document structure. It is how the document will be displayed. It is the logic (markup) of how the content will be placed/ shown (roughly).
CSS — Is the code to determine how things will look. It is also the logic of how content will be placed, but more importantly, how it will be seen in detail. It determines the design. BTW, why did styling get “pulled out” of HTML to begin with? Hmmm…????
As you are probably (and hopefully) thinking, I am sort of defeating my own purpose above, by mentioning how these technologies actually do intertwine. I am doing it consciously, because anyone making argumentation about Separation of Concerns (SoC) says that separating these three technologies does nothing for SoC. It doesn’t support avoiding coupling. It doesn’t support cohesion. Blah blah blah. Yeah, they are all correct and yes, these technologies do intertwine.
The great Uncle Bob defines SRP as follows….
The Single Responsibility Principle (SRP) states that each software module should have one and only one reason to change
Now, anyone can argue that we are also already doing “modules” with SFCs. But, let’s take on the challenge Uncle Bob offers about “A single reason to change”. Why would anyone go to an SFC to change it? What could be the reasons? To change the structure? To change the design? To change the overall logic? Oh….and I haven’t even mentioned the data. Haha….that is the fourth responsibility within SFCs!
There was some more argumentation going back and forth over Twitter in the past about this concept and again, I am not wanting to get into a React vs. VueJS flame war. I’d rather just show how the diverging thoughts are playing out.
A dev argued that the To-do app from React was more complicated than the VueJS To-do app (Sorry, I tried to find the Tweets for reference, but couldn’t). Then the well known React/ Redux dev, Dan Abramov, basically replied (and I am paraphrasing), “just because a simple app may look more complicated, doesn’t mean a complicated app will also be more complicated.” This is undeniably true, but also shoots completely past the point being made.
If I am going to go to a component for a reason to change it, i.e. the structure, the design or the display (or even data) logic, what is going to be simpler for me? Looking at a wall of JSX (maybe), or the clear separation of HTML, CSS and JS? I’ll let you all make the final decision on that for yourselves. :-)
Developer Cognitive Load
The next argument against this separation is the extra “templating language” one must learn to work with templates in Vue. It’s said to be added cognitive load for the dev. Well, anyone that has done anything with templates, (like all of the server-side worlds combined) knows about using them and are familiar with the usual APIs to get display logic done within templates, like for-loops, filters, etc. Vue’s offering of its own template DSL is simple, sleek and relatively easy to learn. I’d say an experienced backend dev would learn it in a couple of hours and an experienced front-end dev might learn it in a day. It’s really not that hard.
What is hard is learning how to do JSX well.
Can we all agree that constraints in programming are one of the keys to cleaner and more understandable code? We see constraints in best practices and also in (well written) APIs (which is a paradox in programming and another interesting subject for discussion).
And this is where JSX breaks the bank and increases cognitive load a lot. This is where Dan didn’t completely finish the thought process in his Tweet. If a simple piece of code doesn’t look clean and understandable, then how can a more complex piece of code look clean and understandable?
You see, with Vue, some programmatic constraints are built in with its templating system. Yes, it is opinionation. But, the advantage to this opinionation is the ability for any Vue dev and even inexperienced Vue devs to jump into the code and get working with it faster. It all looks familiar and works fairly the same. With JSX, you simply do not have this nice little luxury and in the end, this causes a lot more cognitive load than learning the constraints Vue offers in its templating language.
As one developer put it, “ React code looks an awful lot like the PHP code I was told never to write again.”
It took years for PHP to come up with a good number of templating systems, like Smarty, Twig and Blade. And, there was a clear and proper purpose for this necessary evolution. It was to constrain the PHP language to only display logic. Nothing more and nothing less.
With JSX, one might argue that the same constraints aren’t necessary, since it is all happening in the browser. Still, I’ll refer back my statement…..
Constraints in programming are one of the keys to cleaner and more understandable code!
In other words, it is easy to write poor JSX code, because any constraints are “self-made” or borrowed and external. Best practices have to be explained and documented. This definitely leads to higher cognitive load, especially when these external constraints in form of best practices aren’t understood at first (and they always will be). Even a very experienced React dev might go to a different company, which also uses React, and find him or herself mind-boggled at what was written, simply because they thought their best practices should be different. Ah yes… the continual discussion about the value of best practices….LOL!
This is also not to say that Vue can’t be done wrong either. It certainly can. And there are some external best practices documented too. But, it’s harder to do poor code with Vue in general. The constraints are built in and ready to keep everyone in line, in basically doing things the same way. This affords standardization across all Vue applications and this is invaluable, when it comes to developer efficiency.
The built in constraints also afford quality in the code, which is invaluable to any business in the end. Again, this is not to say the same can’t be reached with React and JSX. It’s just a good bit harder.
Edit: Oh, and of course, if needed, Vue can do JSX in its render functions too. So the utmost in flexibility is also available in Vue.
Edit 2: One other thing I noticed but forgot to mention when writing this article was looking at the available component frameworks being stamped out of the ground for Vue and React. To me, and this is just my personal opinion, but the frameworks for Vue seem to be generally more professional. Two examples I can offer you straight off the top of my head are :
If anyone can show me a React component framework that has the depth of components and professional documentation and demos behind them like these two, I’d be greatly appreciative, because I honestly couldn’t find any.
Edit 3: I found an awesome article that sort of raises some more good argumentation for Vue’s way of doing things and indirectly supports my argumentation for separation of responsibilities and the value of having it.
You may agree or disagree with me on this. I’m not going to argue with you. But, any comments as to what you think of these concepts and their value either way would be appreciated. And let’s not get into any flame wars. Both Vue and React give us a great new paradigm for front-end applications. They just take slightly different directions for good or bad. As we all can also agree, there are always trade-offs.