React and Angular — A Contrast

A lot has been written about React and Angular in the last few years. Finding a comparison between the two most popular ways to write a modern web application is not hard at all.

Why do we need another comparison then? Easy. I’ve found that comparisons are mostly without statistics and a proper methodology to show the difference between the two. Let’s get started.

Who is this contrast for?

Are you a manager whose team is talking about React and Angular? Read on. If you’re a seasoned UI developer, well, be kind with your comments… Sincerely, this is for everyone and I appreciate all feedback.

High level

Right off the bat you should know that React and Angular are not comparable. The reason for this is simple. React, by Facebook’s own definition, is a ‘UI library’. Whereas Angular is an all-in-one framework.

A quick look at their respective websites will remind you of this fact.

⚛️ React — https://facebook.github.io/react/ — A JavaScript library for building user interfaces.

🅰️ Angular — https://angular.io/ — One framework. Mobile & desktop.

If you’re coming from a Java background you may appreciate this analogy:

React is to Hibernate as Angular is to Spring

With that said, you can use Spring’s Object Relational Mapping capabilities. However, you may choose to use Hibernate, an Object Relational Mapping library.

What is a framework for a front-end web UI?

In general, what we’re talking about here is a series of modules or features that fills out the Model-View-Controller (MVC) pattern. In terms of React, the out of the box functionality is just the View part of MVC. Whereas, Angular has built solutions for all parts of MVC. A full framework is going to have solutions for these concepts: intra-page routing, whole app state management, and UI rendering / templating.

Popularity

Angular 1.x is on 8.3% of the top 10,000 sites by traffic (BuiltWith). React is on 1.7% of the top 10,000 sites by traffic (BuiltWith). Angular 2.x is on less than 0.1% of the top 10,000 sites by traffic (BuiltWith). A Google Trends comparison of search terms ‘angular’ and ‘react’ shows that Angular is a more popular search term. While it is unknown what is ultimately being searched for (i.e. interest in angular/react versus I need help with angular/react) it’s clear that Angular has more adoption when you intersect the Google Trends data with the BuiltWith data (Google Trends). It should be noted that Angular 2, which this contrast is built on, is less popular than React, but the reasons for that could be related to the upgrade cycle from Angular 1.x to 2.x requires more effort than dropping in the new version of code. Angular 2 is a major rewrite the requires extensive developer effort to get from 1.x to 2.x.

Areas of Contrast

Methodology

A fair number of the reviews that I’ve seen rely on quality attribute comparisons; performance, scalability, etc. I haven’t seen them all, of course, but feel confident that this contrast is different than others. I will document some of the features that are different between the two solutions, but I will also show you the difference in code on the same application.

I decided that the only way to fairly show the differences is to code the same requirements into the two solution formats. However, I didn’t need to code from scratch on both solutions. I just needed to find something that was already coded. Since we know that Angular is a full framework, Angular would have the best implementation of all the features in its own tutorial. Therefore, all I need to do is to code a version of the Angular Tour of Heroes tutorial in React. The results of that code can be seen here, https://github.com/halversondm/react-tour-of-heroes . Thus, the analysis of that coding into React from Angular is in this contrast.

What’s included?

Back to the feature set, this is what you get with each out of the box.

Angular

Routing
Routing here refers to the movement around components of an individual page. If you needed to show an entirely new page, you could still redirect to a new location as you have always been able to do. However, that has a performance implication as you must render the entire page anew. This is the Controller in MVC. Angular has built a module to Route to different components.

Whole Application State Management
Angular has a built-in method to manage the state of the data in the application. This is the Model in MVC.

HTML Templating
Angular uses a special syntax that marks up the HTML to achieve the necessary templating. This is the View in MVC.

Locally scoped CSS
Angular has created an easy method to scope your CSS to a given component. This is especially useful to create a slightly different experience in your component within the page without any effort.

React

HTML Templating
React uses a newer concept called JSX or JavaScript XML. JSX places the required HTML inside the JavaScript and allows you to use plain JavaScript to template variables or repetitive components. This is the View in MVC.

In component state management
React can maintain a model of the data for your application at the single component level. Each component can have its own state. In general, the one state is derived from another state via property pass. However, in a full application this leaves a hole for the need to manage the state in its entirety. This is the Model in MVC to some degree.

Above, I mentioned components. Components have a varying degree of granularity. They can be as coarse (or coarser) as a grouping of input boxes to collect data from a user, a form, or as fine as one of those input boxes in that form that has specific functionality. The form itself is then a component of components. These concepts are both implementable in React and Angular. Components drive reusability across a larger application.

What do you need to get to full strength?

Both software solutions need helpers to get a developer productive in his day to day usage. Further, some recommendations are for the benefit of the development lifecycle.

Both Need

Webpack or similar module bundler
Webpack is an effort to bring together multiple packages of JavaScript into fewer bundles. If you’re coming from a Java background, Webpack is similar Maven’s Assembly plugin or WAR plugin. This step is necessary to bring cohesion to the build and version process as you develop more complicated workflows.

TypeScript
In general, TypeScript is optional for both Angular and React. However, you might strongly consider using this if your developers are full stack and coming from a strongly typed language background (e.g. Java, .NET, etc). TypeScript helps to add the typing that those developers are accustomed to and attempts to remove bugs by including typing at compile time. Of course, at runtime, the code still operates in a type-less fashion.

For Angular, TypeScript is a first-class citizen as the Angular team has built Angular in TypeScript.

For React, there are plenty of tutorials and code helpers out there to get you started on TypeScript.

ES6 Transpiler (Babel or TypeScript)
Transpiling is simply ‘transform and compile’. The point of it is to transform code written in the standards (also known as ECMAScript) that have been proposed and passed, but not adopted by the browsers. These features can range from simple syntax changes to new concepts, but in the end, can be ‘transformed’ back into JavaScript that all browsers understand.

Included in this topic is transpiling of JSX. JSX is not able to be run in the browser directly. The React website makes mention that JSX is not required. Most developer’s opt-in to JSX for its readability and appearance in the code.

React

Whole Application State Management
Again, this is only referring to the state of the front-end or the Model in MVC. Two common state containers for React are Flux and Redux.

In application routing
As the Controller in MVC, you may need the ability to completely replace a component with another component to speed the rendering of your UI. Routing is not moving from page to page or redirecting. A redirection cause a complete load of the page. That page has its own lifecycle that does not communicate with the originating page. React Router is a module that can be used to perform this work.

Locally Scoping CSS to a Component
This is a feature that I found particularly useful in Angular that React does not have out of the box. The concept is that for a given CSS selector it only applies to the component that you assign the CSS to. You can create your own solution for this or use React CSS Modules.

HTTP Management
Another optional module to React is the notion of Promise or Observable HTTP requests. I won’t get into the details of those concepts, but let just say that they are refinements on the standard asynchronous XMLHttpRequest. You can create your own solution here with a Promise or Observable. Another popular option is the newer ‘fetch’ spec that is appearing in browsers except for Internet Explorer.

Code organization

In this section, we are going to show some code and discuss the differences between Angular and Reacts approaches.

Files

In Angular, you would follow a pattern where you would split out your files per UI component domain and contents.

File organization in an Angular project

Above, we have the Dashboard component of the Angular 2 Tour of Heroes tutorial. The Dashboard component is made up of three files for logic (dashboard.component.ts), templating (dashboard.component.html) and styling (dashboard.component.css). The logic file brings it all together through a pair of statements to refer to the template and style. You can ignore this pattern and put all three parts into the same file. This split out pattern gives you smaller file sizes for easier readability and maintainability.

In React, you would generally have one file for the logic and templating and one file for the CSS.

File organization in a React project

Above, in the React version of Tour of Heroes, HeroDashboard.tsx is the logic and template while HeroDashboard.css is the styling.

React HeroDashboard and Angular 2 Dashboard components are equivalent in their functionality on the screen.

Templating

As noted before, Angular combines its own syntax and regular HTML to make an HTML template render at runtime and React uses JSX. Let’s look at some samples.

Angular

<h2>My Heroes</h2>
<ul class="heroes">
<li *ngFor="let hero of heroes"
[class.selected]="hero === selectedHero"
(click)="onSelect(hero)">
<span class="badge">{{hero.id}}</span> {{hero.name}}
</li>
</ul>
<div *ngIf="selectedHero">
<h2>
{{selectedHero.name | uppercase}} is my hero
</h2>
<button (click)="gotoDetail()">View Details</button>
</div>

React

<div data-heroes>
<h2 data-heroes>My Heroes</h2>
<ul data-heroes className="heroes">
{this.props.heroes.map((hero: Hero) => {
return <li data-heroes key={hero.id}
className={this.state.hero.id === hero.id ? "selected" : ""}
onClick={this.setSelected.bind(this, hero)}><span
data-heroes className="badge">{hero.id}</span> {hero.name}</li>
})}
</ul>
</div>

Above, the two snippets are equivalent in their functionality in the UI. Let’s look at a few pieces to note the syntax differences.

Looping

Angular achieves a loop to create a series of HTML with the line <li *ngFor=”let hero of heroes”. When the Angular JavaScript reads this, it will create the requisite number of <li> (or list items) that the ‘heroes’ array contains from the model.

React achieves a loop to create a series of HTML with the line this.props.heroes.map(…). Ultimately this is already JavaScript, so the React JavaScript is not reading this and outputting HTML. Rather, the browser is.

Attribute Binding

Angular uses {{hero.id}}. React uses {hero.id}. A value is output from the reference to the object and attribute in the model in both cases.

Events

Angular employs ‘(click)=”onSelect(hero)”’ syntax and React uses onClick={this.setSelected.bind(this, hero)} syntax. React’s syntax is more clear and recognized by IDEs as JavaScript.

Logic

In general, the logic formats are similar or can be made to be similar with the usage of TypeScript. Below are the examples of Angular and React code to give you a feeling of what coding looks like.

Angular

import {Component, OnInit} from '@angular/core';
import {Router} from '@angular/router';

import {Hero} from './hero';
import {HeroService} from './hero.service';

@Component({
moduleId: module.id,
selector: 'my-heroes',
templateUrl: './heroes.component.html',
styleUrls: ['./heroes.component.css']
})
export class HeroesComponent implements OnInit {
heroes: Hero[];
selectedHero: Hero;

constructor(private router: Router,
private heroService: HeroService) {
}

getHeroes(): void {
this.heroService.getHeroes().then(heroes => this.heroes = heroes);
}

ngOnInit(): void {
this.getHeroes();
}

onSelect(hero: Hero): void {
this.selectedHero = hero;
}

gotoDetail(): void {
this.router.navigate(['/detail', this.selectedHero.id]);
}
}


/*
Copyright 2016 Google Inc. All Rights Reserved.
Use of this source code is governed by an MIT-style license that
can be found in the LICENSE file at http://angular.io/license
*/

React

"use strict";

import * as React from "react";
import Hero from "./Hero";
import "../styles/HeroList.css";

export interface HeroListProps {
heroes: Array<Hero>;
setSelected: (hero: Hero) => void;
}

interface HeroListState {
hero: Hero
}

export class HeroList extends React.Component<HeroListProps, HeroListState> {

state: HeroListState;

constructor(props: HeroListProps) {
super(props);
this.setSelected = this.setSelected.bind(this);
this.state = {hero: {id: 0, name: ""}};
}

setSelected(hero: Hero) {
this.setState({hero: hero});
this.props.setSelected(hero);
}

render() {
return (
<div data-heroes>
<h2 data-heroes>My Heroes</h2>
<ul data-heroes className="heroes">
{this.props.heroes.map((hero: Hero) => {
return <li data-heroes key={hero.id}
className={this.state.hero.id === hero.id ? "selected" : ""}
onClick={this.setSelected.bind(this, hero)}><span
data-heroes className="badge">{hero.id}</span> {hero.name}</li>
})}
</ul>
</div>
);
}
}

Organization

Both React and Angular are using current ES6 module formats with import and export statements. Angular and React are using the class format that is very popular today as well. The class format has allowed for the transition of developers from other languages (such as Java and .NET) to be easier since the format is recognizable.

Flow

One difference to note is that Angular is expecting to retrieve data from a HeroService. React is expecting that another component is going to pass to HeroList the data that it needs to know. Both solutions allow for the passing of data to other components.

Routing

In both cases, Routing is handled by dedicated code that declaratively creates the routes that you are trying to achieve.

Angular

import { NgModule }             from '@angular/core';
import { RouterModule, Routes } from '@angular/router';

import { DashboardComponent } from './dashboard.component';
import { HeroesComponent } from './heroes.component';
import { HeroDetailComponent } from './hero-detail.component';

const routes: Routes = [
{ path: '', redirectTo: '/dashboard', pathMatch: 'full' },
{ path: 'dashboard', component: DashboardComponent },
{ path: 'detail/:id', component: HeroDetailComponent },
{ path: 'heroes', component: HeroesComponent }
];

@NgModule({
imports: [ RouterModule.forRoot(routes) ],
exports: [ RouterModule ]
})
export class AppRoutingModule {}


/*
Copyright 2016 Google Inc. All Rights Reserved.
Use of this source code is governed by an MIT-style license that
can be found in the LICENSE file at http://angular.io/license
*/

React

ReactDOM.render(
<Provider store={store}>
<Router history={browserHistory}>
<Route path="/" component={App}>
<IndexRedirect to="/dashboard"/>
<Route path="/dashboard" component={HeroDashboard}/>
<Route path="/heroes" component={TourOfHeroes}/>
<Route path="/detail" component={HeroDetail}/>
</Route>
</Router>
</Provider>
, document.getElementById("anchor"));

Above you’ll see that the path’s that you are trying to achieve in the browser’s URL bar are mapped to individual components. Further, a default route is declared when the user attempts the standard http://somehostname.com/ entry point.

Whole App State Management

Referring only to your front-end application, whole app state management is performed in two different ways between React and Angular. Angular’s approach is a bit hands-off, baked-in compared to React’s configure it yourself. Angular also supports two-way data binding. This is where a change can be made to the model/state without the need for the view to update the change through user implemented code.

With React you have a few choices to implement whole application state management. Two of the popular implementations are Flux and Redux. With the React Tour of Heroes application I wrote, I used Redux. I find that Redux is less verbose and easier to understand the flow of the data.

Locally Scoped CSS

A feature that I found very useful in Angular that is automatically configured is locally scoped CSS. Locally scoped CSS is the ability to create a set of CSS selectors that apply to only the component that refers to that CSS. In general, CSS is global over the whole document. You can still achieve global CSS by placing a link tag in your HTML page with Angular.

In Angular, with locally scoped CSS, your CSS files are post-processed to place an additional attribute selector to each selector in your file and then that attribute is placed on all the HTML tags in the template for the component.

This feature does not exist in React out of the box. You can perform the exact same behavior in React that Angular is doing, but you have code it into your templates and CSS by hand. I did find some potential modules to snap in to handle this behavior, but I did not spend the time to research those. React CSS Modules is one of those plugins.

Ramp Up / Training Time

While it’s completely impossible to gauge the full ramp up time for every developer, it’s logical to note the training courses offered that would get a developer started. I did choose two sites that ultimately have a cost associated with the programs, but what I was looking for was the time to complete those programs.

Angular

Udemy — Angular 2 — The Complete Guide — 16.5 hours
Pluralsight — Angular 2 Fundamentals — 10 hours

React

Udemy — Modern React with Redux — appears to cover all of the topics for a full framework model of React — 22.5 hours
Pluralsight — Building Applications with React and Redux in ES6 — appears to cover all of the topics for a full framework model — 6.25 hours

Modern web development — courses on TypeScript, Bundlers and Transpilers.

TypeScript

Udemy — Understanding TypeScript — 7 hours
Pluralsight — TypeScript Fundamentals and Advanced TypeScript — two courses for full understanding 7.25 hours

Bundlers

Udemy — Webpack 2: The Complete Developers Guide — 5.5 hours
Pluralsight — Webpack Fundamentals — 2.5 hours

Transpilers

If you use TypeScript a transpiler is included. Training time would be included in the about TypeScript courses. If you use Babel, a very popular transpiler for React, training time is as follows.

Udemy — ECMAScript 2015 (ES6), Babel and Webpack Explained — there isn’t a Babel only course on Udemy so this class includes ES6 information too, a bonus — 4.5 hours
Pluralsight — Babel: Get Started — 2 hours

It’s also worthwhile to note that if your development team is a traditional service based Java or .NET team, it would be a huge benefit to the product being developed if the developers would also take basic JavaScript courses. In the end, it is very important that the developers understand functional programming and the basic constructs of the JavaScript language. For every course and framework above, the discussion all tracks back to basic JavaScript skills to understand the syntax being placed in front of them.

Other Considerations

If you’re going to take it beyond the browser or if you really like React and Angular, you may consider these points too.

Mobile Frameworks

React and Angular both offer an integration framework for delivering your application in native and web browser formats. If your application needs a bit more than what a mobile browser can offer, then you can begin to look at integration with the Ionic SDK for Angular and React Native for React.

I have some experience with React Native and I can tell you that it is not write-once, run multiple ways. Rather, the lift you get with React Native is a reusable skill set. A component in React for the browser is a component in React Native. How you divide your web application and mobile application into logical chunks, components, is also the same. The one noted difference between React and React Native is the inability to use CSS in a mobile application. Since CSS is naturally baked into your React web application via JSX, you would need to write the React Native application with its screen formatting syntax separately.

To note, Ionic is a separate company that is using Angular and other JavaScript features for its framework. Conversely, React Native is developed and maintained by Facebook.

Did you know?

If you love React, but want more of the framework features that Angular provides, you can use React with Angular. React in this setup would manage all the HTML Templating we reviewed above. Angular would manage whole application state and routing.

Summary

We’ve covered a lot of ground in this contrast. Overall, the key points to consider about a front-end framework include, HTML Templating, Whole Application State Management and Intra-page Routing. React and Angular have solutions for each of those topics. While those solutions are different they do solve the same problem. The routes to get to where you need the code to be, a shippable product, will come by different means. However, it is important to note that both solutions will give you the desired effect of creating said shippable product for today and beyond. Neither of these solutions are fly-by-night, disappearing tomorrow, flavors of the month, etc.

I’ve largely stayed away from opinion in the above text on the basis that if you are reading this then you can and will make your own decisions given the information presented.

At this point, I think it’s valuable to note that you cannot go wrong with either choice. Both solutions have a large following in the JavaScript community. Overall, both solutions provide the ability to manage large applications in a defined way that allow for the ease of development.