<?xml version="1.0" encoding="UTF-8"?><rss version="2.0" xmlns:content="http://purl.org/rss/1.0/modules/content/"><channel><title>Rodrigo Rosenfeld Rosas — front-end</title><description>Articles tagged with front-end</description><link>https://rosenfeld.page/</link><language>en-us</language><item><title>The missing bit in the React community: a common interface</title><link>https://rosenfeld.page/articles/front-end/2018_01_25_the_missing_bit_in_the_react_community_a_common_interface/</link><guid isPermaLink="true">https://rosenfeld.page/articles/front-end/2018_01_25_the_missing_bit_in_the_react_community_a_common_interface/</guid><pubDate>Thu, 25 Jan 2018 17:52:00 GMT</pubDate><content:encoded>&lt;p&gt;I use Ruby for server-side programming, so I&amp;#39;ll illustrate the issue in the Ruby community but
it basically applies to all server-side languages. Even JavaScript I&amp;#39;d guess, although I haven&amp;#39;t
used JavaScript for server-side programming yet.&lt;/p&gt;
&lt;p&gt;When it&amp;#39;s time to deploy our Ruby web application, we&amp;#39;re free to choose a web server from multiple
options without requiring any changes to the application code most of the time. That&amp;#39;s possible
because all of them support the Rack specifications, which acts like an interface between Ruby
apps and Rack web servers. When we choose a process-based server such as Unicorn, we can benefit
from several advantages over thread-based ones, such as Puma, but the opposite is just as true,
since a thread-based approach also has benefits over a process-based one. Other web servers are
more suited to applications requiring long-live connections and would take yet another approach
to connections handling.&lt;/p&gt;
&lt;p&gt;The simple fact that we can easily switch the web server without changing our code to test the
impact of different in our application is awesome, but Rack will also make it easier for new
Ruby frameworks to be built and inter-operate with each other pretty easily. For example, you
can mount Rodauth, which is a Roda authentication app, in a Rails or Sinatra app in a very
straightforward way.&lt;/p&gt;
&lt;p&gt;It&amp;#39;s not really news that competition is awesome for consumers, and we, software developers,
are consumers of libraries and frameworks, so we really enjoy competition of frameworks and
libraries, right?&lt;/p&gt;
&lt;p&gt;So, how could that be related to React in any way? After all, one might argue that React is
competing with Angular, jQuery and others, right? Well, in that sense, competition still
exists in the JavaScript framework/library market, but that&amp;#39;s just not enough. I&amp;#39;ll explain.&lt;/p&gt;
&lt;h2&gt;The Components problem&lt;/h2&gt;
&lt;p&gt;The way we build and use components are the biggest issue we currently experience in the
JavaScript world. For example, the Material UI library doesn&amp;#39;t compete with ng-bootstrap,
for example. How could them? The components interface are completely different in React
apps when compared to Angular apps. In that sense, we could consider React and Angular as
two different languages. One wouldn&amp;#39;t expect to be able to use the Ruby&amp;#39;s Rack gem in the
Go language, right?&lt;/p&gt;
&lt;p&gt;So, yes, it leads to duplicate efforts to build great common components such as date pickers,
sliders and so on. We have jQuery UI for jQuery, ng-bootstrap for Angular and Material UI for
React (among many more options for sure). But it kind of makes sense to me that components
implementation could be quite different because jQuery, Angular and React take completely
different approaches. One might argue that we could concentrate the efforts on pure JavaScript
solutions and build wrappers around it for each major library, such as React, Angular or jQuery.
But I don&amp;#39;t really think it would be that simple, so I&amp;#39;m not trying to suggest something like that.&lt;/p&gt;
&lt;p&gt;When one creates a new programming language, it will take quite some time before it gets widely
adopted. One of the reasons is that there&amp;#39;s no ecosystem around that language initially. When
Elixir was created, for example, there was no web framework available for it, of course. Ruby
not only has a lot of choices for web frameworks but also offer several libraries for all sort
of things you might need. Or Java. Or JavaScript, C++, whatever. Well stablished languages will
take advantage over new ones exactly because of this existing libraries, making it hard for
new languages to get traction. Unfortunately, I don&amp;#39;t think there&amp;#39;s something we could do to
make it easier for new languages to be created and take advantage of existing libraries from
other languages. But, fortunately, the React issue is much simpler to fix, if the community
wants to.&lt;/p&gt;
&lt;h2&gt;What is different in React?&lt;/h2&gt;
&lt;p&gt;When React was born, it was really a game changer.&lt;/p&gt;
&lt;p&gt;I&amp;#39;m not saying everyone should be leaving jQuery or Angular or whatever to jump to the React boat.
There&amp;#39;s no one-size-fits-all solution for creating applications. Angular, jQuery and React take
completely different approaches when creating applications. Angular 1 has tried two-way data
binding but gave up on it since version 2. Both Knockout.js and Vue.js still support two-way data
binding. There are plenty of people that enjoy that feature. And for some use cases, it&amp;#39;s
certainly quicker to build some use cases with it when compared to newer Angular or React.&lt;/p&gt;
&lt;p&gt;However, it&amp;#39;s clear to me that React got way more traction than its competitors in the past few
years. And there are plenty of reasons for that. I really think React did a great job in teaching
us a new way to think about applications. It&amp;#39;s not a secret that programming is mostly complicated
because of state management, right? I still prefer OO programming over functional one, but I do
agree with the most used argument from functional programming fans: managing state is hard. They
claim functional programming is easier because it&amp;#39;s easy to understand and test pure functions.
It&amp;#39;s the same sort of argument used by supporters of micro-services that will tell us that it&amp;#39;s
much easier to write and test micro apps than a big monolithic one.&lt;/p&gt;
&lt;p&gt;And their arguments are not wrong. Just incomplete from my point of view. Because they hide the
fact that they have moved the complexity to the integration part. By the way, it&amp;#39;s perfectly
possible to create modular monolithic applications whose parts can be tested and released
independently while keeping the integration much simpler than with micro-services. I&amp;#39;m not saying
one should never adopt the micro-services approach either. There&amp;#39;s no silver bullet. The
complexity will always exist somewhere and our job is to see what makes more sense for our project.&lt;/p&gt;
&lt;p&gt;Anyway, I&amp;#39;ll not get into this discussion in this article, but just want to highlight that the
most complicated part when creating applications is state management. Truth be told, trying to
keep your model and view in sync using jQuery has always been a nightmare, right? That&amp;#39;s why we
see several alternatives to jQuery for many reasons, like Knockout.js, Angular and many others.
The main difference between them and jQuery is that they will let us manage the state outside of
the DOM and will make sure that the DOM will change accordingly to the app&amp;#39;s state. That&amp;#39;s a big
win over jQuery or any other DOM-based library.&lt;/p&gt;
&lt;p&gt;So, why did React get much more traction than the alternatives? In my opinion, React is much
simpler than the alternatives, while remaining flexible and fast. For example, Knockout.js,
initial versions of Ember (I&amp;#39;m not following the current development, so I can&amp;#39;t talk about recent
versions) and Angular would all try to extend the HTML in sophisticated ways. They have to parse
either the HTML template itself or some special tag properties and evaluate some special
constructions. Knockout, for instance, would evaluate &amp;quot;data-bind&amp;quot; attributes, which resembles
very closely a JavaScript object declaration. Both Ember and Angular would also offer their
own control flow extensions instead of using plain JavaScript, because they preferred declarative
(logic-less) templates. Maybe that description is not fully accurate as I never worked with
Angular or Ember, but this is what I remember from the articles I&amp;#39;ve read back in those days.&lt;/p&gt;
&lt;p&gt;React took a completely different approach, making the JavaScript developer life much simpler in
several ways. At first, I (and many others) were scared by the JSX thing, when it seemed an
heresy to embed HTML in the JavaScript, bringing memories from PHP and ASP to the mind. However,
I (and many others) realized that it actually made sense. After all, I often ended up doing that
myself in several cases using other methods. It might seem scaring at first, but quickly we
get used to it and it makes sense. We&amp;#39;ll even mix CSS and JS these days (also known as CSS in JS).&lt;/p&gt;
&lt;p&gt;But JSX wasn&amp;#39;t the main reason why people adopted React. I guess there are many people who
actually adopted React despite the JSX thing, rather than because of it. There are two key
ideas that set React apart and were responsible for its success in my opinion. And I&amp;#39;m not
talking about documentation or component-driven programming because the alternatives also offered
those.&lt;/p&gt;
&lt;p&gt;One of them is the realization that keeping the model and view in sync is the major issue to be
fixed by library authors. Approaches taken by Knockout, Angular and Ember seemed too complicated.
Trying to figure out what has to be changed in the view when the application state changed was
really tricky. Then, React decided to try a much simpler approach. What if we just rebuilt the
entire app from scratch after any changes to the application? Well, of course the alternative
frameworks could also implement that brilliant idea that simplifies a lot the implementation.
Except that it would be painfully slow to do that.&lt;/p&gt;
&lt;p&gt;So, that&amp;#39;s the second idea, which allowed the first one to succeed, was the key for the revolution
we&amp;#39;ve seen in the JavaScript scenario after React was born. The realization that JavaScript is
pretty fast nowadays, as long as we can avoid the DOM, which is the slow part. And that&amp;#39;s how
the concept of virtual DOM became popular and today we have tons of alternative virtual DOM
implementations. The realization that comparing an in-memory DOM was really fast allowed a
not too complicated algorithm to update the DOM in a very efficient way to reflect the state of the
virtual DOM. Of course, there are much more optimizations applied by React and similar
alternatives, but the implementation of the virtual DOM diff algorithm allowed developers to
quickly understand how to build React apps. It was much simpler to reason about than the
alternatives, in my opinion.&lt;/p&gt;
&lt;p&gt;And to make things even better, they adopted modern JavaScript, which allowed us to write
Object Oriented programming in JavaScript without having to resort to CoffeeScript and
alternative transpiled languages. When we add bundle builders as sophisticated as Webpack,
things get quickly unbeatable. Now we&amp;#39;re able to write modular conflict-less apps, using
OO component-based programming, with an easy syntax to mix HTML in JavaScript. We can even
even import CSS from JS or apply code splitting with Webpack. Or use some of the CSS in JS
alternatives, such as JSS. But, again, the biggest gain is that we no longer need to touch
the DOM directly, without having to learn a new template syntax. We just use plain JavaScript.&lt;/p&gt;
&lt;h2&gt;React is awesome, I know, so what is the issue after all?&lt;/h2&gt;
&lt;p&gt;The issue is that React is not just an implementation. It&amp;#39;s a powerful idea and mind set. The
concepts are so simple, that we now have many alternative to React which are mostly compatible
with it. There are Dio.js, Inferno.js, Preact and NervJS to name some well known alternatives.
Each of them could be competing with each other but unfortunately it&amp;#39;s not that simple.&lt;/p&gt;
&lt;p&gt;Why is that? Because you can&amp;#39;t simply use some UI library designed to work with React in any
of the alternatives. For one to be able to do that, they would have to use something like
Webpack aliases, so that whenever the code imports &amp;#39;react&amp;#39;, &amp;#39;react-dom&amp;#39; or &amp;#39;create-react-class&amp;#39;
they would be actually importing some compatibility layer around the alternatives. Something
like &amp;#39;inferno-compat&amp;#39;. What if we wanted to mix apps which are lazily loaded but developed by
separate teams? Maybe one team is using React for a reason, while another team is using Inferno
or Dio.js for another reason. Then the webpack rules get way more complicated to manage.&lt;/p&gt;
&lt;p&gt;What if we could set up a common interface supported by all react-like implementations.
Something like Ruby&amp;#39;s Rack but for React components? UI libraries are basically React components.
Basically they rely on JSX (not all of them, though) and React.Component. Both interfaces are
very well known. JSX is already independent from React, but it still needs to know which pragma to
use when parsing JSX. When using Babel, one can easily add a plugin that will include
additional imports automatically so that you shouldn&amp;#39;t be forced to &amp;quot;import React&amp;quot; in order to use
JSX. But it would be great if we didn&amp;#39;t have to resort to such things when targeting
interoperability.&lt;/p&gt;
&lt;p&gt;For React like programming I believe there&amp;#39;s a fixed set of methods that should be enough for
most apps. Functions such as like createElement (for JSX support, also known as &amp;quot;h&amp;quot; by some
implementations), render, Component, createPortal and findDOMNode. What if we could create a meta
package to provide us such method? Then all React-like alternatives could compete with each other
by providing the implementation for such functions.&lt;/p&gt;
&lt;p&gt;For example, let&amp;#39;s suppose we create a new &amp;quot;react-like&amp;quot; package. We could set up which library
to use like this:&lt;/p&gt;
&lt;pre&gt;&lt;code class=&quot;language-javascript&quot;&gt;import ReactLike from &amp;#39;react-like&amp;#39;;
import dio from &amp;#39;dio.js&amp;#39;;
ReactLike.assign(dio); // or assign({createElement: dio.createElement, createPortal: dio.createPortal ...})
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Then, instead of &amp;quot;import React from &amp;#39;react&amp;#39;&amp;quot;, component libraries, such as Material UI, could use
it like:&lt;/p&gt;
&lt;pre&gt;&lt;code class=&quot;language-javascript&quot;&gt;import React from &amp;#39;react-like&amp;#39;;

export default Button extends React.Component {
  render() {
    return &amp;lt;button className=&amp;quot;my-special-class&amp;quot;&amp;gt;{ this.props.children }&amp;lt;/button&amp;gt;;
  }
}
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;It would be even better if those libraries used yet another abstraction with a fallback to
&amp;#39;react-like&amp;#39;, so that we would be able to use Inferno for some library and Dio.js for another one,
for example.&lt;/p&gt;
&lt;p&gt;Currently it&amp;#39;s not an easy for us to pick up one of the great React alternatives out there because
almost all component libraries seem to assume React is being used. Wouldn&amp;#39;t it be awesome if
we could provide a common interface to be used by components libraries and promote the competition
among React alternatives?&lt;/p&gt;
</content:encoded></item></channel></rss>