Learn basics of React quickly

Mayank Choubey
Tech Tonic
Published in
19 min readApr 24, 2023

--

Introduction

Welcome to the world of React! With this article, I’m going to help you get started on the wonderful journey of React. This article is about the absolute basics of React. For example — How to set up a React project, what are React components, some basics of JSX, and states in React. I’m going to explain the basic React concepts by migrating a very simple vanilla HTML/CSS/JS app to React. I’ve kept the example app very simple, so that we can focus on the core concepts.

Audience

This article is about the very basics of React. If you know React already, this article is not for you. You’ll find it boring. If you don’t know anything about React, then you’re in the right place. If you like to learn by example, i.e. by converting a regular app to React, then this article is for you.

If you’re reading further, let’s you started with React.

React

React is a JavaScript library for building user interfaces. That’s it. This is the purpose of React. React makes the job easier. React makes the code easier to read, write, and maintain. React or React.js, as it is called sometimes, is a front-end library that has gradually become the go-to framework for modern web development within the JavaScript community.

The React framework is an open-source JavaScript framework and library originally developed by Facebook. It’s used for building interactive user interfaces and web applications quickly and efficiently with significantly less code than you would with vanilla JavaScript. As you write less code, you’ve less code to test and maintain. This is one of the key features of React.

In React, you develop your applications by creating reusable components that you can think of as independent blocks. These components are individual pieces of a final interface, which, when assembled, form the application’s entire user interface. The separation into components also separates the code, thereby making application code more readable & maintainable.

Going more deep into the definition: React’s primary role in an application is to handle the view layer of that application just like the V in a model-view-controller (MVC) pattern by providing the best and most efficient rendering execution. Rather than dealing with the whole user interface as a single unit, React encourages developers to separate these complex UIs into individual reusable components that form the building blocks of the whole UI. In doing so, the ReactJS framework combines the speed and efficiency of JavaScript with a more efficient method of manipulating the DOM to render web pages faster and create highly dynamic and responsive web applications.

Popularity of React

There is a reason why everyone wants to learn React. The reason is extreme popularity. React is the #1 JS framework in the world. Here are some stats:

Percent of stack overflow questions on topic

Credit: StackOverflow

Most used web framework in the world

Credit: Statista

GitHub stars

206K stars is pretty impressive. Comparatively, Node.js has about 95K stars.

There is no denying that React is still very popular in 2023. It’s nowhere close to getting outdated by a new technology. Not in the near future. If you’re a frontend developer or want to become one, you have to learn React. Your career will thank you for that.

That’s quite enough about the introduction to React. More about this can be read at the React’s official website or Wiki.

Now, let’s start our journey with the app I’ll be migrating to React. It’s a simple online UUID generator app. Simple enough to learn key concepts like components & state.

Online UUID Generator app

The idea of this app comes from a real app called online UUID generator that can be experienced here:

I’ve used it in the past whenever I needed to get a UUID. Of course, I can also get UUID by opening REPL on Node.js, but this site is more convenient. I’m going to write something similar in vanilla HTML, JS, and CSS. I’m going to use the basic features of this website. I’m going to run it in Node.js using Express.

Let’s get started with a typical application structure. There is an index.mjs file, which runs the Express static server. Then we’ve index.html which includes js/app.js and css/app.css. For most of the styling, I’m using bootstrap from the CDN. This is the typical folder structure for vanilla JS apps.

index.mjs

This starts the static file server that’ll serve all the static content like HTML, JS, CSS, images, etc. I don’t have any other routes for this app.

import express from "express";
const app = express();

app.use(express.static("public"));
app.listen(8080);

index.html

This is the main HTML file which contains all the HTML code. Bootstrap CSS library is included from the CDN. The main HTML file also includes app.js and app.css.

<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<meta name="description" content="">
<meta name="author" content="">

<title>Learn react by example - vanilla UUID generator app</title>

<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0-alpha3/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-KK94CHFLLe+nY2dmCWGMq91rCGa5gtU4mk92HdvYe+M/SXH301p5ILy+dN9+nJOZ" crossorigin="anonymous">
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0-alpha3/dist/js/bootstrap.bundle.min.js" integrity="sha384-ENjdO4Dr2bkBIFxQpeoTz1HIcje39Wm4jDKdf19U8gI4ddQ3GYNS7NTKfAdVQSZe" crossorigin="anonymous"></script>
<link rel="stylesheet" href="css/app.css">

<script src="js/app.js"></script>
</head>

<body class="text-center" onload="createUUID()">

<nav class="navbar navbar-expand-md navbar-dark bg-secondary sticky-top">
<a class="navbar-brand" href="#">Online UUID Generator</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#online-uuid-nav-data" aria-controls="online-uuid-nav-data" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>

<div class="collapse navbar-collapse" id="online-uuid-nav-data">
<ul class="navbar-nav mr-auto">
<li class="nav-item active">
<a class="nav-link" href="#">Home</a>
</li>
<li class="nav-item">
<a class="nav-link" href="https://datatracker.ietf.org/doc/html/rfc4122">What is V4 UUID?</a>
</li>
</ul>
</div>
</nav>

<main role="main" class="container mt-5">
<div class="text-center">
<h1 class="display-3">Online UUID Generator</h1>
<p class="text-small">Your Version 4 UUID:</p>
<p>
<span class="display-6 align-middle" id="uuid"></span>
<button id="copy-button" class="btn btn-dark align-baseline" title="Copy the UUID to the clipboard." alt="Copy the UUID to the clipboard." onclick="copyUUID()">
<img src="data:image/svg+xml;utf8;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0iaXNvLTg4NTktMSI/Pgo8IS0tIEdlbmVyYXRvcjogQWRvYmUgSWxsdXN0cmF0b3IgMTkuMS4wLCBTVkcgRXhwb3J0IFBsdWctSW4gLiBTVkcgVmVyc2lvbjogNi4wMCBCdWlsZCAwKSAgLS0+CjxzdmcgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB4bWxuczp4bGluaz0iaHR0cDovL3d3dy53My5vcmcvMTk5OS94bGluayIgdmVyc2lvbj0iMS4xIiBpZD0iQ2FwYV8xIiB4PSIwcHgiIHk9IjBweCIgdmlld0JveD0iMCAwIDQ4OC4zIDQ4OC4zIiBzdHlsZT0iZW5hYmxlLWJhY2tncm91bmQ6bmV3IDAgMCA0ODguMyA0ODguMzsiIHhtbDpzcGFjZT0icHJlc2VydmUiIHdpZHRoPSIxNnB4IiBoZWlnaHQ9IjE2cHgiPgo8Zz4KCTxnPgoJCTxwYXRoIGQ9Ik0zMTQuMjUsODUuNGgtMjI3Yy0yMS4zLDAtMzguNiwxNy4zLTM4LjYsMzguNnYzMjUuN2MwLDIxLjMsMTcuMywzOC42LDM4LjYsMzguNmgyMjdjMjEuMywwLDM4LjYtMTcuMywzOC42LTM4LjZWMTI0ICAgIEMzNTIuNzUsMTAyLjcsMzM1LjQ1LDg1LjQsMzE0LjI1LDg1LjR6IE0zMjUuNzUsNDQ5LjZjMCw2LjQtNS4yLDExLjYtMTEuNiwxMS42aC0yMjdjLTYuNCwwLTExLjYtNS4yLTExLjYtMTEuNlYxMjQgICAgYzAtNi40LDUuMi0xMS42LDExLjYtMTEuNmgyMjdjNi40LDAsMTEuNiw1LjIsMTEuNiwxMS42VjQ0OS42eiIgZmlsbD0iI0ZGRkZGRiIvPgoJCTxwYXRoIGQ9Ik00MDEuMDUsMGgtMjI3Yy0yMS4zLDAtMzguNiwxNy4zLTM4LjYsMzguNmMwLDcuNSw2LDEzLjUsMTMuNSwxMy41czEzLjUtNiwxMy41LTEzLjVjMC02LjQsNS4yLTExLjYsMTEuNi0xMS42aDIyNyAgICBjNi40LDAsMTEuNiw1LjIsMTEuNiwxMS42djMyNS43YzAsNi40LTUuMiwxMS42LTExLjYsMTEuNmMtNy41LDAtMTMuNSw2LTEzLjUsMTMuNXM2LDEzLjUsMTMuNSwxMy41YzIxLjMsMCwzOC42LTE3LjMsMzguNi0zOC42ICAgIFYzOC42QzQzOS42NSwxNy4zLDQyMi4zNSwwLDQwMS4wNSwweiIgZmlsbD0iI0ZGRkZGRiIvPgoJPC9nPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+Cjwvc3ZnPgo=">
<span id="copy-button-text"></span>
</button>
</p>
<p>
<button id="refresh-button" class="btn btn-primary align-baseline" title="Generate a new UUID." alt="Generate a new UUID." onclick="createUUID()">
<img src="data:image/svg+xml;utf8;base64,PHN2ZyB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgZmlsbC1ydWxlPSJldmVub2RkIiBjbGlwLXJ1bGU9ImV2ZW5vZGQiPjxwYXRoIGQ9Ik03IDloLTd2LTdoMXY1LjJjMS44NTMtNC4yMzcgNi4wODMtNy4yIDExLTcuMiA2LjYyMyAwIDEyIDUuMzc3IDEyIDEycy01LjM3NyAxMi0xMiAxMmMtNi4yODYgMC0xMS40NS00Ljg0NC0xMS45NTktMTFoMS4wMDRjLjUwNiA1LjYwMyA1LjIyMSAxMCAxMC45NTUgMTAgNi4wNzEgMCAxMS00LjkyOSAxMS0xMXMtNC45MjktMTEtMTEtMTFjLTQuNjYgMC04LjY0NyAyLjkwNC0xMC4yNDkgN2g1LjI0OXYxeiIgZmlsbD0iI0ZGRkZGRiIvPjwvc3ZnPg==">
<span class="button-with-icon" id="refresh-button-text">Generate another UUID</span>
</button>
</p>
</div>
</main>

<footer class="footer">
<div class="container">
<span class="text-muted">The UUIDs generated by this site conform to RFC 4122 whenever possible. <a class="text-small" href="https://en.wikipedia.org/wiki/Universally_unique_identifier">Read more about UUIDs at Wikipedia.</a></span>
</div>
</footer>
</body>
</html>

app.js

There are two simple functions, one for each button: Generate UUID and Copy UUID.

function createUUID() {
const newUUID = crypto.randomUUID();
document.getElementById("uuid").textContent = newUUID;
}

function copyUUID() {
const copyText = document.getElementById("uuid");
navigator.clipboard.writeText(copyText.textContent);
document.getElementById("copy-button-text").textContent = "Copied!";
setTimeout(
() => document.getElementById("copy-button-text").textContent = "Copy",
1000,
);
}

app.css

This contains additional styling.

.footer {
position: absolute;
bottom: 0;
width: 100%;
height: 60px;
line-height: 60px;
background-color: #f5f5f5;
}

.button-with-icon {
margin-left: 5px;
}

That’s all about the vanilla app code. Pretty simple application. I’ve chosen a simple one to cover React concepts clearly. This is a beginners article.

The vanilla application can be started using Node.js (You can clone from GitHub repo: https://github.com/mayankchoubey/learn-react-by-example-gen-uuid-app):

> node index.mjs

Then open a browser window and point to http://localhost:8080. Our vanilla application looks like this:

Not bad at all! I’ve prepared a small GIF to show a quick test of this application.

We’re good. Our vanilla app works as expected. Now let’s move on to rewriting this app in React. After all, that’s the purpose of me writing and you reading this article. Before going into coding, we will need to set up a React development environment.

Setting up React environment

The very first step is to set up a React development environment. React is a complex framework with a number of dependencies. Setting up a React project manually is a tough work for beginners. If we go for manual setup, we’ll end up spending a long time in just bringing up the environment for a simple hello world app. Fortunately, we don’t have to do that.

There is a utility called create-react-app which, I believe, is the most popular way to get started with React. With create-react-app, you don’t need to learn and configure many build tools. All we’ve to do is give a single command. Instant reloads (code watcher) help you focus on development. When it’s time to deploy, your bundles are optimized automatically. Under the hood, webpack, Babel, ESLint, and other amazing projects are used to power your app. We don’t have to worry about all of that at this point. All we want is to get a development environment quickly.

In short, this is the best way to start the React journey. To create the default template project, use the following command:

> npx create-react-app react-app

The second argument (react-app) is the folder name where the app will be placed. The procedure of creating a React environment takes time. Be patient while the dependencies are installed. Here is the output of a typical run (Don’t pay attention to 1423 packages that gets installed :-)):

> npx create-react-app react-app

Creating a new React app in /Users/mayankc/Work/source/learn-react-by-example/react-app.

Installing packages. This might take a couple of minutes.
Installing react, react-dom, and react-scripts with cra-template...


added 1423 packages in 54s

235 packages are looking for funding
run `npm fund` for details

Installing template dependencies using npm...

added 62 packages, and changed 1 package in 3s

235 packages are looking for funding
run `npm fund` for details
Removing template package using npm...


removed 1 package, and audited 1485 packages in 1s

235 packages are looking for funding
run `npm fund` for details

6 high severity vulnerabilities

To address all issues (including breaking changes), run:
npm audit fix --force

Run `npm audit` for details.

Success! Created react-app at /Users/mayankc/Work/source/learn-react-by-example/react-app
Inside that directory, you can run several commands:

npm start
Starts the development server.

npm run build
Bundles the app into static files for production.

npm test
Starts the test runner.

npm run eject
Removes this tool and copies build dependencies, configuration files
and scripts into the app directory. If you do this, you can’t go back!

We suggest that you begin by typing:

cd react-app
npm start

Happy hacking!

Once this gets installed, we can do a round of testing. You can go inside the just created react app and run npm start to build the code & start the development server.

> cd react-app
> npm start
Compiled successfully!

You can now view react-app in the browser.

Local: http://localhost:3000
On Your Network: http://192.168.10.63:3000

Note that the development build is not optimized.
To create a production build, use npm run build.

webpack compiled successfully

We’ll worry about the ‘compilation’ and ‘webpack’ a bit later. For now, React needs a build step as it uses a new syntax called JSX. The build step con verts JSX to JS that browsers can understand.

Let’s open a browser and verify the application (http://localhost:3000):

Great! The development environment is up. As mentioned earlier, the environment runs under a file watcher, which means that any changes made to source will get applied immediately. Here ‘apply’ means the source will run through a build.

Before moving ahead, let’s take a look at the application that has been created by the create-react-app. The following is the folder structure along with markings about what is going to be interesting for us (in other words, what we’re going to change very soon).

I’ve marked index.js as interesting. We may choose to change it mostly for loading common stuff like bootstrap. Or, we can change App.js to load common stuff, it’s upto us. I’ll be making changes to App.js instead of index.js. Just my personal choice.

When we start migrating the vanilla app, we’ll add more files to this boiler template. The existing files that we’ll be changing are highlighted (except for index.js). It might be interesting for you to note that we won’t be changing index.html at all. Isn’t that a bit unusual? In the vanilla world, index.html is an important file. In React world, index.html is mostly a container that gets data from something called Components.

As our development environment is ready, let’s move on to the next section, Components.

React components

This is one of the most important paradigm brought in by React. React recommends dividing your application into small, reusable components. Rather than writing a big monolith index.html which contains the complete code for that page, React recommends dividing the application into logical components that gets managed independently. How to divide into components is upto the application writer. The components are independently managed by React. They are rendered and re-rendered when certain conditions are met. Of course, it is entirely fine to put the complete app inside a single component. But that’ll defeat the purpose of React.

A typical vanilla app structure is something like this (we’ve used the same in our vanilla app too):

We’ve a big index.html file (of course, not that big for our app) that includes two local dependencies: js/app.js that contains all the JS code and css/app.css that contains all the styling.

This is not how React approaches an app. React suggests dividing the application into small, logical, reusable components. The smaller they are, the manageable they become. A component is independent enough to have its own:

  • HTML
  • JS
  • CSS
  • Event handling, etc.

This way, a component can be included anywhere in the application. An example will help understand it better. Let’s take our vanilla app and divide it in components. I’ve chosen three components (have a look below):

There is a header, main, and footer component. The header & footer are common components that can be included anywhere in the application. Both header and footer are static components, i.e. they don’t have any dynamic elements in it. No event handling is required for static components.

With this information, the app structure changes to:

The index.html includes index.js, which includes App.js, which includes the components like Header, Main, and Footer. With this background, let’s start writing React code in App, Header, Main, and Footer. The App.js came with boiler, so will need an update. We’ll be writing new code in Header.js, Main.js, and Footer.js. While writing code in App, we also need to include bootstrap as a dependency because we won’t be using CDN. Also, while writing, we’ll learn about JSX which makes React great!

App component

The App component is the main component of our application. This is like a container component. A component in react usually goes in it’s own file (usually called ComponentName.js) with a corresponding css (usually called ComponentName.css). For example, the JS+HTML goes in App.js and the CSS goes in App.css. It is up for debate where CSS should be placed. I’m placing it along with the code.

A component in React is a JavaScript function that returns JSX which can be rendered. So, what is JSX? JSX stands for JavaScript XML. JSX allows us to write HTML in React. JSX makes it easier to write and add HTML in React. We can write HTML directly into JS code. The HTML can include the standard tags as well as other components. Unlike the vanilla app, where HTML generally includes/contains JS, in react world, the JS generally contains HTML. The React world is quite opposite of the vanilla world. The official React docs provides a good overview of JSX.

A typical component code looks something like this:

function SomeComponent() {

/* JS CODE GOES HERE */

return (
/* JSX(HTML) CODE GOES HERE */
);
}

export default SomeComponent;

The App component that came with the create-react-app is a simple component, i.e. it doesn’t have any children. Consider the default App.js:

import logo from './logo.svg';
import './App.css';

function App() {
return (
<div className="App">
<header className="App-header">
<img src={logo} className="App-logo" alt="logo" />
<p>
Edit <code>src/App.js</code> and save to reload.
</p>
<a
className="App-link"
href="https://reactjs.org"
target="_blank"
rel="noopener noreferrer"
>
Learn React
</a>
</header>
</div>
);
}

export default App;

It’s weird to see HTML tags directly present inside the JS code. I won’t even believe that this will work. It won’t work on the browsers because they only understand JavaScript. That’s where the ‘build’ step of React comes into picture. The build step of React converts the JSX into regular JS that can get executed in the browsers.

First, we need to include bootstrap as we won’t be loading it from CDN. The required bootstrap libraries can be included through NPM.

> npm install react-bootstrap bootstrap --save

Now we can use the bootstrap library from the local instead of CDN. Let’s update the App.js to include bootstrap. Also, for now, I’ll assume that the child components are present in a components folder. The new App.js looks like this:

import './App.css';
import Header from "./components/Header";
import Main from "./components/Main";
import Footer from "./components/Footer";
import 'bootstrap/dist/css/bootstrap.min.css';

function App() {
return (
<div className="App">
<Header />
<Main />
<Footer />
</div>
);
}

export default App;

The app level (or you can call it root level) JSX simply contains a container div with three components inside it. A component can be included inside any JSX using the following syntax:

<SomeComponent />

Thats’ll for the App component. It’s a container component only. It includes whatever is required on the page.

Note: In JSX, className is used instead of class

Note: In JSX, onClick is used instead of onclick

Header component

Let’s start with the first child component, the header component. The Header component is a static component. The only thing present in this component is the HTML code. The code looks like this:

function Header() {
return (
<nav className="navbar navbar-expand-md navbar-dark bg-secondary sticky-top">
<a className="navbar-brand" href="#">Online UUID Generator</a>
<button className="navbar-toggler" type="button" data-toggle="collapse" data-target="#online-uuid-nav-data" aria-controls="online-uuid-nav-data" aria-expanded="false" aria-label="Toggle navigation">
<span className="navbar-toggler-icon"></span>
</button>

<div className="collapse navbar-collapse" id="online-uuid-nav-data">
<ul className="navbar-nav mr-auto">
<li className="nav-item active">
<a className="nav-link" href="#">Home</a>
</li>
<li className="nav-item">
<a className="nav-link" href="https://datatracker.ietf.org/doc/html/rfc4122">What is V4 UUID?</a>
</li>
</ul>
</div>
</nav>
);
}

export default Header;

In the Header component, there is nothing special in the HTML. It’s a simple copy a part of HTML from vanilla’s index.html with modification of class to className.

Footer component

Just like Header, Footer is also a static component. All it contains is a static HTML code. The only thing different is inclusion of a custom CSS which comes from the Footer.css file. The code looks like:

Footer.js

import './Footer.css';

function Footer() {
return (
<footer className="footer">
<div className="container">
<span className="text-muted">The UUIDs generated by this site conform to RFC 4122 whenever possible.
<a className="text-small" href="https://en.wikipedia.org/wiki/Universally_unique_identifier">
Read more about UUIDs at Wikipedia.
</a>
</span>
</div>
</footer>
);
}

export default Footer;

Footer.css

.footer {
position: absolute;
bottom: 0;
width: 100%;
height: 60px;
line-height: 60px;
background-color: #f5f5f5;
}

Note that the ‘button-with-icon’ CSS class from app.css of vanilla app didn’t make it to Footer.css. This is because button-with-icon is used by Main component, so it’ll be placed in Main.css.

Main component

This is the main application component which contains dynamic elements & interactivity. This is the place where React can truly shine. The main component has a span element containing the generated UUID. This span gets updated whenever the ‘Generate’ button is used. There is another button ‘Copy’ which copies the current UUID to clipboard. On pressing the copy button, it changes the label to Copied, which changes back to Copy after a second. This requires us to maintain something called state in React. Let’s spend few minutes on state before writing code for the Main component.

The state is a built-in React object that is used to contain data or information about the component. A component’s state can change over time; whenever it changes, the component re-renders. The change in state can happen as a response to user action, system-generated events, API response, etc. These state changes determine the behavior of the component and how it will render. A simple diagram will help understand it better.

A component can have one or more states. The state gets used inside the HTML part of the component. Whenever the JS part of component updates the state, the component gets re-rendered. In short, the component ‘reacts’ to state change. Of course, there was a reason why React is called React.

A state in React is created using React.useState hook. React.useState is basically an API provided by React. You can read about it in detail here. The useState API generally returns two interesting items:

  • The data of the state
  • The function that should be used to update the state (Very important)

Note that we must use the provided function to update the state. Must. We can set the state variable directly, but that won’t trigger a component re-rendering. Consider the following code where I’m creating a React state that is initialized with 0 (state could be an JS type). I’m saving the state data in count and the update function in setCount. I can use the count variable anywhere in my code, including HTML. If I want to update the count, I have to use setCount. The state can be used inside JSX through curl braces, {stateVar}. Note that the returned function, that updates the state, can be called with any name. The usual convention is to give it a meaningful name that indicates the operation being performed.

const [count, setCount] = React.useState(0);

// ... somewhere down the line

return (
// some JSX
<label>{count}</label>
// some more JSX
)

Let’s apply this knowledge to our Main component. What are the variables in our app? There are two variables:

  • UUID
  • Button text of the copy button (copy <-> copied)

As there are two variables, I’ll be using two states. It is also totally fine to use a single state data that is a JS object, but here I’m using two different states.

Here is a rough idea about the Main component design:

  • Create a state that stores the current UUID. Save state data in uuid & update function in setUuid
  • Create a state that stores the current text for the copy button (There are two values possible: Copy and Copied!). We can call it copyText and setCopyText.
  • Use the state data uuid to render data in span called uuid (Any state variable or JS code can be used with curly brackets inside HTML)
  • Use the state data copyText to render the text for the button copy-button-text
  • Add handleClick handlers for both the buttons
  • The Generate button click handler will use setUuid to update the state
  • The Copy button click handler will use uuid variable to copy it into clipboard. Also, it’ll change copyText variable to Copied! A timeout will be set to reset copyText back to Copy.
  • The setUuid will update the state and trigger a component re-rendering
  • The setCopyText will update the state and trigger a component re-rendering

With all this information, the code of the Main component looks something like this:

import React from 'react';
import './Main.css';

function Main() {
const [uuid, setUuid] = React.useState(getUuid());
const [copyText, setCopyText] = React.useState("Copy");

function copyUUID() {
navigator.clipboard.writeText(uuid);
setCopyText("Copied!");
setTimeout(
() => setCopyText("Copy"),
1000,
);
}

function createUUID() {
setUuid(getUuid());
}

function getUuid() {
return crypto.randomUUID();
}

return (
<main role="main" className="container mt-5">
<div className="text-center">
<h1 className="display-3">Online UUID Generator</h1>
<p className="text-small">Your Version 4 UUID:</p>
<p>
<span className="display-6 align-middle" id="uuid">{uuid}</span>
<button id="copy-button" className="btn btn-dark align-baseline button-with-icon" title="Copy the UUID to the clipboard." alt="Copy the UUID to the clipboard." onClick={copyUUID}>
<img src="data:image/svg+xml;utf8;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0iaXNvLTg4NTktMSI/Pgo8IS0tIEdlbmVyYXRvcjogQWRvYmUgSWxsdXN0cmF0b3IgMTkuMS4wLCBTVkcgRXhwb3J0IFBsdWctSW4gLiBTVkcgVmVyc2lvbjogNi4wMCBCdWlsZCAwKSAgLS0+CjxzdmcgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIiB4bWxuczp4bGluaz0iaHR0cDovL3d3dy53My5vcmcvMTk5OS94bGluayIgdmVyc2lvbj0iMS4xIiBpZD0iQ2FwYV8xIiB4PSIwcHgiIHk9IjBweCIgdmlld0JveD0iMCAwIDQ4OC4zIDQ4OC4zIiBzdHlsZT0iZW5hYmxlLWJhY2tncm91bmQ6bmV3IDAgMCA0ODguMyA0ODguMzsiIHhtbDpzcGFjZT0icHJlc2VydmUiIHdpZHRoPSIxNnB4IiBoZWlnaHQ9IjE2cHgiPgo8Zz4KCTxnPgoJCTxwYXRoIGQ9Ik0zMTQuMjUsODUuNGgtMjI3Yy0yMS4zLDAtMzguNiwxNy4zLTM4LjYsMzguNnYzMjUuN2MwLDIxLjMsMTcuMywzOC42LDM4LjYsMzguNmgyMjdjMjEuMywwLDM4LjYtMTcuMywzOC42LTM4LjZWMTI0ICAgIEMzNTIuNzUsMTAyLjcsMzM1LjQ1LDg1LjQsMzE0LjI1LDg1LjR6IE0zMjUuNzUsNDQ5LjZjMCw2LjQtNS4yLDExLjYtMTEuNiwxMS42aC0yMjdjLTYuNCwwLTExLjYtNS4yLTExLjYtMTEuNlYxMjQgICAgYzAtNi40LDUuMi0xMS42LDExLjYtMTEuNmgyMjdjNi40LDAsMTEuNiw1LjIsMTEuNiwxMS42VjQ0OS42eiIgZmlsbD0iI0ZGRkZGRiIvPgoJCTxwYXRoIGQ9Ik00MDEuMDUsMGgtMjI3Yy0yMS4zLDAtMzguNiwxNy4zLTM4LjYsMzguNmMwLDcuNSw2LDEzLjUsMTMuNSwxMy41czEzLjUtNiwxMy41LTEzLjVjMC02LjQsNS4yLTExLjYsMTEuNi0xMS42aDIyNyAgICBjNi40LDAsMTEuNiw1LjIsMTEuNiwxMS42djMyNS43YzAsNi40LTUuMiwxMS42LTExLjYsMTEuNmMtNy41LDAtMTMuNSw2LTEzLjUsMTMuNXM2LDEzLjUsMTMuNSwxMy41YzIxLjMsMCwzOC42LTE3LjMsMzguNi0zOC42ICAgIFYzOC42QzQzOS42NSwxNy4zLDQyMi4zNSwwLDQwMS4wNSwweiIgZmlsbD0iI0ZGRkZGRiIvPgoJPC9nPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+CjxnPgo8L2c+Cjwvc3ZnPgo="/>
<span id="copy-button-text">{copyText}</span>
</button>
</p>
<p>
<button id="refresh-button" className="btn btn-primary align-baseline button-with-icon" title="Generate a new UUID." alt="Generate a new UUID." onClick={createUUID}>
<img src="data:image/svg+xml;utf8;base64,PHN2ZyB3aWR0aD0iMjQiIGhlaWdodD0iMjQiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyIgZmlsbC1ydWxlPSJldmVub2RkIiBjbGlwLXJ1bGU9ImV2ZW5vZGQiPjxwYXRoIGQ9Ik03IDloLTd2LTdoMXY1LjJjMS44NTMtNC4yMzcgNi4wODMtNy4yIDExLTcuMiA2LjYyMyAwIDEyIDUuMzc3IDEyIDEycy01LjM3NyAxMi0xMiAxMmMtNi4yODYgMC0xMS40NS00Ljg0NC0xMS45NTktMTFoMS4wMDRjLjUwNiA1LjYwMyA1LjIyMSAxMCAxMC45NTUgMTAgNi4wNzEgMCAxMS00LjkyOSAxMS0xMXMtNC45MjktMTEtMTEtMTFjLTQuNjYgMC04LjY0NyAyLjkwNC0xMC4yNDkgN2g1LjI0OXYxeiIgZmlsbD0iI0ZGRkZGRiIvPjwvc3ZnPg=="/>
<span id="refresh-button-text">Generate another UUID</span>
</button>
</p>
</div>
</main>
);
}

export default Main;

That’s all about migrating the vanilla app to React. There is nothing else left to do. React is reactive!

Before running the new app, let me do some markings in Main.js for better understanding. In the marked code, I’ve suppressed the icon base 64 SVG to make it more readable.

At this point, we should note the power of React. I have not written any code to get data from an HTML element. I’ve not written any code to update the contents of an HTML element. All I’ve done is created a state, used it, and updated it. Based on the state changes, React manages component(s) re-rendering. Again, there is a reason why React is called React.

Running the React app

Once all changes are done, the new app structure looks like this:

Time to run your first react application. Just go the root folder and run:

Great! It looks exactly like the vanilla app. Here is a GIF while playing with it:

Everything works perfectly! We’ve successfully migrated a vanilla app to React. You might be wondering about the point of migrating such a simple app to React. Did we gain anything? It looks like we’re doing things the harder way with React. It it much simpler with vanilla JavaScript. Agreed. The doubt is coming only because our vanilla app was very small. Imagine an app with hundreds of components that runs over thousands of lines of JS code. React will make life easy when the app gets complex.

How can you try it out?

I’ve created a GitHub repo that contains both the apps. The repo is here:

git clone https://github.com/mayankchoubey/learn-react-by-example-gen-uuid-app.git

This repo has two apps:

  • Vanilla app
  • React app

To run vanilla app

cd vanilla-app
npm i
npm start

Open a browser with URL http://localhost:8080

To run React app:

cd react-app
npm i
npm start dev

Open a browser with URL http://localhost:3000

That’s all about it. I hope this article has been helpful to kick start your React journey.

Please provide suggestions in the comments. This is a beginner’s article. I would be interested in hearing your suggestions on the parts that weren’t explained well.

--

--