React JWT Authentication (without Redux) example – BezKoder

“could not find a required file.”

If you exclude or ignore necessary files from the package you will see a error similar this one:

In this case, ensure that the file is there with the proper lettercase and that’s not ignored on your local .gitignore or ~/.gitignore_global.

To do a manual deploy to Netlify’s CDN:

npm install netlify-cli
netlify deploy

Choose build as the path to deploy.

To setup continuous delivery:

With this setup Netlify will build and deploy when you push to git or open a pull request:

  1. Start a new netlify project
  2. Pick your Git hosting service and select your repository
  3. Click Build your site

Support for client-side routing:

To support pushState, make sure to create a public/_redirects file with the following rewrite rules:

When you build the project, Create React App will place the public folder contents into the build output.

Now offers a zero-configuration single-command deployment. You can use now to deploy your app for free.

“invalid host header” errors after configuring proxy

When you enable the proxy option, you opt into a more strict set of host checks. This is necessary because leaving the backend open to remote hosts makes your computer vulnerable to DNS rebinding attacks. The issue is explained in this article and this issue.

This shouldn’t affect you when developing on localhost, but if you develop remotely like described here, you will see this error in the browser after enabling the proxy option:

Invalid Host header

To work around it, you can specify your public development host in a file called .env.development in the root of your project:

If you restart the development server now and load the app from the specified host, it should work.

If you are still having issues or if you’re using a more exotic environment like a cloud editor, you can bypass the host check completely by adding a line to .env.development.local. Note that this is dangerous and exposes your machine to remote code execution from malicious websites:

We don’t recommend this approach.

#2.7. app.js

Open the “App.js” file in the “frontend” folder, then change it to the following:

import { BrowserRouter, Route, Switch } from "react-router-dom";
import Dashboard from "./components/Dashboard";
import Login from "./components/Login";
import Navbar from "./components/Navbar";
import Register from "./components/Register";

function App() {
  return (
    <BrowserRouter>
      <Switch>
        <Route exact path="/">
          <Login/>
        </Route>
        <Route path="/register">
          <Register/>
        </Route>
        <Route path="/dashboard">
          <Navbar/>
          <Dashboard/>
        </Route>
      </Switch>
    </BrowserRouter>
  );
}

export default App;

Adding assets outside of the module system

You can also add other assets to the public folder.

Note that we normally encourage you to import assets in JavaScript files instead.
For example, see the sections on adding a stylesheet and adding images and fonts.
This mechanism provides a number of benefits:

However there is an escape hatch that you can use to add an asset outside of the module system.

If you put a file into the public folder, it will not be processed by Webpack. Instead it will be copied into the build folder untouched. To reference assets in the public folder, you need to use a special variable called PUBLIC_URL.

Inside index.html, you can use it like this:

Only files inside the public folder will be accessible by %PUBLIC_URL% prefix. If you need to use a file from src or node_modules, you’ll have to copy it there to explicitly specify your intention to make this file a part of the build.

When you run npm run build, Create React App will substitute %PUBLIC_URL% with a correct absolute path so your project works even if you use client-side routing or host it at a non-root URL.

In JavaScript code, you can use process.env.PUBLIC_URL for similar purposes:

Keep in mind the downsides of this approach:

Adding custom environment variables

Note: this feature is available with [email protected] and higher.

Your project can consume variables declared in your environment as if they were declared locally in your JS files. By
default you will have NODE_ENV defined for you, and any other environment variables starting with
REACT_APP_.

The environment variables are embedded during the build time. Since Create React App produces a static HTML/CSS/JS bundle, it can’t possibly read them at runtime. To read them at runtime, you would need to load HTML into memory on the server and replace placeholders in runtime, just like described here. Alternatively you can rebuild the app on the server anytime you change them.

Note: You must create custom environment variables beginning with REACT_APP_. Any other variables except NODE_ENV will be ignored to avoid accidentally exposing a private key on the machine that could have the same name. Changing any environment variables will require you to restart the development server if it is running.

These environment variables will be defined for you on process.env. For example, having an environment
variable named REACT_APP_SECRET_CODE will be exposed in your JS as process.env.REACT_APP_SECRET_CODE.

There is also a special built-in environment variable called NODE_ENV. You can read it from process.env.NODE_ENV. When you run npm start, it is always equal to ‘development’, when you run npm test it is always equal to ‘test’, and when you run npm run build to make a production bundle, it is always equal to ‘production’.

These environment variables can be useful for displaying information conditionally based on where the project is
deployed or consuming sensitive data that lives outside of version control.

First, you need to have environment variables defined. For example, let’s say you wanted to consume a secret defined
in the environment inside a <form>:

During the build, process.env.REACT_APP_SECRET_CODE will be replaced with the current value of the REACT_APP_SECRET_CODE environment variable. Remember that the NODE_ENV variable will be set for you automatically.

When you load the app in the browser and inspect the <input>, you will see its value set to abcdef, and the bold text will show the environment provided when using npm start:

Adding images, fonts, and files

With Webpack, using static assets like images and fonts works similarly to CSS.

You can import a file right in a JavaScript module. This tells Webpack to include that file in the bundle. Unlike CSS imports, importing a file gives you a string value. This value is the final path you can reference in your code, e.g. as the src attribute of an image or the href of a link to a PDF.

To reduce the number of requests to the server, importing images that are less than 10,000 bytes returns a data URI instead of a path. This applies to the following file extensions: bmp, gif, jpg, jpeg, and png. SVG files are excluded due to #1153.

Here is an example:

This ensures that when the project is built, Webpack will correctly move the images into the build folder, and provide us with correct paths.

This works in CSS too:

Webpack finds all relative module references in CSS (they start with ./) and replaces them with the final paths from the compiled bundle. If you make a typo or accidentally delete an important file, you will see a compilation error, just like when you import a non-existent JavaScript module.

Please be advised that this is also a custom feature of Webpack.

It is not required for React but many people enjoy it (and React Native uses a similar mechanism for images).An alternative way of handling static assets is described in the next section.

Analyzing the bundle size

Source map explorer analyzes
JavaScript bundles using the source maps. This helps you understand where code
bloat is coming from.

To add Source map explorer to a Create React App project, follow these steps:

npm install --save source-map-explorer

Alternatively you may use yarn:

yarn add source-map-explorer

Then in package.json, add the following line to scripts:

Then to analyze the bundle run the production build then run the analyze
script.

Boilerplate application

To get the boilerplate application going I used this guide which uses create-react-app with some tweaks to add an express server. Then I followed this guide to get react-router running.

I also made sure I had Mongoose installed and connected in my server code and MongoDB running on my computer:

const mongoose = require('mongoose');const mongo_uri = 'mongodb://localhost/react-auth';mongoose.connect(mongo_uri, function(err) {
if (err) {
throw err;
} else {
console.log(`Successfully connected to ${mongo_uri}`);
}
});

Then, using Express, I created two routes that look like this:

app.get('/api/home', function(req, res) {
res.send('Welcome!');
});
app.get('/api/secret', function(req, res) {
res.send('The password is potato');
});

For the frontend I created two components with their own corresponding routes which will fetch those messages from the back-end:

import React, { Component } from 'react';
import { Link, Route, Switch } from 'react-router-dom';
import Home from './Home';
import Secret from './Secret';
export default class App extends Component {
render() {
return (
<div>
<ul>
<li><Link to="/">Home</Link></li>
<li><Link to="/secret">Secret</Link></li>
</ul>
<Switch>
<Route path="/" exact component={Home} />
<Route path="/secret" component={Secret} />
</Switch>
</div>
);
}
}

And here is an example of my Home component (the Secret component is almost identical):

export default class Home extends Component {
constructor() {
super();
//Set default message
this.state = {
message: 'Loading...'
}
}
componentDidMount() {
//GET message from server using fetch api
fetch('/api/home')
.then(res => res.text())
.then(res => this.setState({message: res}));
}
render() {
return (
<div>
<h1>Home</h1>
<p>{this.state.message}</p>
</div>
);
}
}

Which ends up looking like this:

Now with this working we can get to the fun part!

Button.js

This is not required for React but many people find this feature convenient. You can read about the benefits of this approach here. However you should be aware that this makes your code less portable to other build tools and environments than Webpack.

In development, expressing dependencies this way allows your styles to be reloaded on the fly as you edit them. In production, all CSS files will be concatenated into a single minified .css file in the build output.

If you are concerned about using Webpack-specific semantics, you can put all your CSS right into src/index.css. It would still be imported from src/index.js, but you could always remove that import if you later migrate to a different build tool.

Changing the page <title>

You can find the source HTML file in the public folder of the generated project. You may edit the <title> tag in it to change the title from “React App” to anything else.

Note that normally you wouldn’t edit files in the public folder very often. For example, adding a stylesheet is done without touching the HTML.

If you need to dynamically update the page title based on the content, you can use the browser document.title API. For more complex scenarios when you want to change the title from React components, you can use React Helmet, a third party library.

If you use a custom server for your app in production and want to modify the title before it gets sent to the browser, you can follow advice in this section. Alternatively, you can pre-build each page as a static HTML file which then loads the JavaScript bundle, which is covered here.

Configuration

The default Jest coverage configuration can be overriden by adding any of the following supported keys to a Jest config in your package.json.

Supported overrides:

Example package.json:

{
  "name": "your-package",
  "jest": {
    "collectCoverageFrom" : [
      "src/**/*.{js,jsx}",
      "!<rootDir>/node_modules/",
      "!<rootDir>/path/to/dir/"
    ],
    "coverageThreshold": {
      "global": {
        "branches": 90,
        "functions": 90,
        "lines": 90,
        "statements": 90
      }
    },
    "coverageReporters": ["text"],
    "snapshotSerializers": ["my-serializer-module"]
  }
}

Displaying lint output in the editor

Note: this feature is available with [email protected] and higher.
It also only works with npm 3 or higher.

Some editors, including Sublime Text, Atom, and Visual Studio Code, provide plugins for ESLint.

They are not required for linting. You should see the linter output right in your terminal as well as the browser console. However, if you prefer the lint results to appear right in your editor, there are some extra steps you can do.

You would need to install an ESLint plugin for your editor first. Then, add a file called .eslintrc to the project root:

Now your editor should report the linting warnings.

Note that even if you edit your .eslintrc file further, these changes will only affect the editor integration. They won’t affect the terminal and in-browser lint output. This is because Create React App intentionally provides a minimal set of rules that find common mistakes.

If you want to enforce a coding style for your project, consider using Prettier instead of ESLint style rules.

Filename conventions

Jest will look for test files with any of the following popular naming conventions:

  • Files with .js suffix in __tests__ folders.
  • Files with .test.js suffix.
  • Files with .spec.js suffix.

The .test.js / .spec.js files (or the __tests__ folders) can be located at any depth under the src top level folder.

We recommend to put the test files (or __tests__ folders) next to the code they are testing so that relative imports appear shorter. For example, if App.test.js and App.js are in the same folder, the test just needs to import App from ‘./App’ instead of a long relative path. Colocation also helps find tests more quickly in larger projects.

Folder structure

After creation, your project should look like this:

For the project to build, these files must exist with exact filenames:

  • public/index.html is the page template;
  • src/index.js is the JavaScript entry point.

You can delete or rename the other files.

You may create subdirectories inside src. For faster rebuilds, only files inside src are processed by Webpack.You need to put any JS and CSS files inside src, otherwise Webpack won’t see them.

Only files inside public can be used from public/index.html.Read instructions below for using assets from JavaScript and HTML.

You can, however, create more top-level directories.They will not be included in the production build so you can use them for things like documentation.

Formatting code automatically

Prettier is an opinionated code formatter with support for JavaScript, CSS and JSON. With Prettier you can format the code you write automatically to ensure a code style within your project. See the Prettier’s GitHub page for more information, and look at this page to see it in action.

To format our code whenever we make a commit in git, we need to install the following dependencies:

npm install --save husky lint-staged prettier

Alternatively you may use yarn:

yarn add husky lint-staged prettier

Now we can make sure every file is formatted correctly by adding a few lines to the package.json in the project root.

Add the following line to scripts section:

Next we add a ‘lint-staged’ field to the package.json, for example:

Now, whenever you make a commit, Prettier will format the changed files automatically. You can also run ./node_modules/.bin/prettier –single-quote –write “src/**/*.{js,jsx}” to format your entire project for the first time.

Next you might want to integrate Prettier in your favorite editor. Read the section on Editor Integration on the Prettier GitHub page.

Further reading

Fullstack CRUD:– React Spring Boot MySQL– React Spring Boot PostgreSQL– React Spring Boot MongoDB– React Node.js Express MySQL– React Node.js Express PostgreSQL– React.js Node.js Express MongoDB– React Django

Another way to implement Form Validation:React Form Validation example with Formik and Yup

Generating dynamic <meta> tags on the server

Since Create React App doesn’t support server rendering, you might be wondering how to make <meta> tags dynamic and reflect the current URL. To solve this, we recommend to add placeholders into the HTML, like this:

Then, on the server, regardless of the backend you use, you can read index.html into memory and replace __OG_TITLE__, __OG_DESCRIPTION__, and any other placeholders with values depending on the current URL. Just make sure to sanitize and escape the interpolated values so that they are safe to embed into HTML!

If you use a Node server, you can even share the route matching logic between the client and the server. However duplicating it also works fine in simple cases.

Getting started with styleguidist

Styleguidist combines a style guide, where all your components are presented on a single page with their props documentation and usage examples, with an environment for developing components in isolation, similar to Storybook. In Styleguidist you write examples in Markdown, where each code snippet is rendered as a live editable playground.

First, install Styleguidist:

npm install --save react-styleguidist

Alternatively you may use yarn:

yarn add react-styleguidist

Then, add these scripts to your package.json:

Then, run the following command inside your app’s directory:

After that, follow the instructions on the screen.

Learn more about React Styleguidist:

Home route

Now when we’ve setup most of our routing. Let’s look at a special route called the HomeRoute. This route itself doesn’t do anything. But acts as a “marker”, to indicate where to redirect to when logging in and logging out.

So in order to specify where we want to end up when we log out, open up app.js and change the:

Into:

Now when logging out, the Stormpath SDK will know that it should redirect to the ‘/’ path. Now, to specify where to redirect when logging out, change the AuthenticatedRoute that we created in the previous step:

So that it looks like:

Notice how the AuthenticatedRoute wraps the HomeRoute. This is used to indicate the authenticated route that we want to redirect to after login.

Making a progressive web app

By default, the production build is a fully functional, offline-first
Progressive Web App.

Progressive Web Apps are faster and more reliable than traditional web pages, and provide an engaging mobile experience:

The sw-precache-webpack-plugin
is integrated into production configuration,
and it will take care of generating a service worker file that will automatically
precache all of your local assets and keep them up to date as you deploy updates.

Npm run build exits too early

It is reported that npm run build can fail on machines with limited memory and no swap space, which is common in cloud environments. Even with small projects this command can increase RAM usage in your system by hundreds of megabytes, so if you have less than 1 GB of available memory your build is likely to fail with the following message:

The build failed because the process exited too early. This probably means the system ran out of memory or someone called kill -9 on the process.

If you are completely sure that you didn’t terminate the process, consider adding some swap space to the machine you’re building on, or build the project locally.

Npm run build fails to minify

Some third-party packages don’t compile their code to ES5 before publishing to npm. This often causes problems in the ecosystem because neither browsers (except for most modern versions) nor some tools currently support all ES6 features. We recommend to publish code on npm as ES5 at least for a few more years.

To resolve this:

  1. Open an issue on the dependency’s issue tracker and ask that the package be published pre-compiled.
  1. Fork the package and publish a corrected version yourself.

  2. If the dependency is small enough, copy it to your src/ folder and treat it as application code.

In the future, we might start automatically compiling incompatible third-party modules, but it is not currently supported. This approach would also slow down the production builds.

Npm run eject

Note: this is a one-way operation. Once you eject, you can’t go back!

If you aren’t satisfied with the build tool and configuration choices, you can eject at any time. This command will remove the single build dependency from your project.

Instead, it will copy all the configuration files and the transitive dependencies (Webpack, Babel, ESLint, etc) right into your project so you have full control over them. All of the commands except eject will still work, but they will point to the copied scripts so you can tweak them. At this point you’re on your own.

You don’t have to ever use eject. The curated feature set is suitable for small and middle deployments, and you shouldn’t feel obligated to use this feature. However we understand that this tool wouldn’t be useful if you couldn’t customize it when you are ready for it.

Other solutions

You don’t necessarily need a static server in order to run a Create React App project in production. It works just as fine integrated into an existing dynamic one.

Here’s a programmatic example using Node and Express:

The choice of your server software isn’t important either. Since Create React App is completely platform-agnostic, there’s no need to explicitly use Node.

The build folder with static assets is the only output produced by Create React App.

However this is not quite enough if you use client-side routing. Read the next section if you want to support URLs like /todos/42 in your single-page app.

Proxying api requests in development

Note: this feature is available with [email protected] and higher.

People often serve the front-end React app from the same host and port as their backend implementation.For example, a production setup might look like this after the app is deployed:

Such setup is not required. However, if you do have a setup like this, it is convenient to write requests like fetch(‘/api/todos’) without worrying about redirecting them to another host or port during development.

To tell the development server to proxy any unknown requests to your API server in development, add a proxy field to your package.json, for example:

Running tests

Note: this feature is available with [email protected] and higher.
Read the migration guide to learn how to enable it in older projects!

Create React App uses Jest as its test runner. To prepare for this integration, we did a major revamp of Jest so if you heard bad things about it years ago, give it another try.

Jest is a Node-based runner. This means that the tests always run in a Node environment and not in a real browser. This lets us enable fast iteration speed and prevent flakiness.

While Jest provides browser globals such as window thanks to jsdom, they are only approximations of the real browser behavior. Jest is intended to be used for unit tests of your logic and your components rather than the DOM quirks.

We recommend that you use a separate tool for browser end-to-end tests if you need them. They are beyond the scope of Create React App.

Secure passwords

Obviously we can’t just store passwords in plain text, that’s how bad things happen.

To secure our passwords we will use a nice little library called bcrypt. This will allow us to hash our passwords (if you don’t know what that means read this).

npm install --save bcrypt

Src/setuptests.js

Now you can write a smoke test with it:

Unlike the previous smoke test using ReactDOM.render(), this test only renders <App> and doesn’t go deeper. For example, even if <App> itself renders a <Button> that throws, this test will pass.

Shallow rendering is great for isolated unit tests, but you may still want to create some full rendering tests to ensure the components integrate correctly. Enzyme supports full rendering with mount(), and you can also use it for testing state changes and component lifecycle.

You can read the Enzyme documentation for more testing techniques. Enzyme documentation uses Chai and Sinon for assertions but you don’t have to use them because Jest provides built-in expect() and jest.fn() for spies.

Here is an example from Enzyme documentation that asserts specific output, rewritten to use Jest matchers:

All Jest matchers are extensively documented here.Nevertheless you can use a third-party assertion library like Chai if you want to, as described below.

Additionally, you might find jest-enzyme helpful to simplify your tests with readable matchers. The above contains code can be written simpler with jest-enzyme.

To enable this, install jest-enzyme:

npm install --save jest-enzyme

Alternatively you may use yarn:

Import it in src/setupTests.js to make its matchers available in every test:

Static server

For environments using Node, the easiest way to handle this would be to install serve and let it handle the rest:

npm install -g serve
serve -s build

The last command shown above will serve your static site on the port 5000. Like many of serve’s internal settings, the port can be adjusted using the -p or –port flags.

Run this command to get a full list of the options available:

Token provider

As I mentioned before, our first step is creating the token provider. The token provider will work directly with local storage and all changes of token we will do through it. It will allow us to listen to changes from anywhere and immediately notify the listeners about changes (but about it a bit later). The interface of the provider will have the next methods:

Function createTokenProvider() will create an instance of the token provider with the described interface:

const createTokenProvider = () => {

    /* Implementation */

    return {
        getToken,
        isLoggedIn,
        setToken,
        subscribe,
        unsubscribe,
    };
};

All the next code should be inside the createTokenProvider function.

Let’s start by creating a variable for storing tokens and restoring the data from local storage (to be sure that the session will not be lost after page reload):

let _token: { accessToken: string, refreshToken: string } = 
    JSON.parse(localStorage.getItem('REACT_TOKEN_AUTH') || '') || null;

Now we need to create some additional functions to work with JWT tokens. At the current moment, the JWT token looks like a magic string, but it is not a big deal to parse it and try to extract the expiration date. The function getExpirationDate() will take a JWT token as a parameter and return expiration date timestamp on success (or null on failure):

const getExpirationDate = (jwtToken?: string): number | null => {
    if (!jwtToken) {
        return null;
    }

    const jwt = JSON.parse(atob(jwtToken.split('.')[1]));

    // multiply by 1000 to convert seconds into milliseconds
    return jwt && jwt.exp && jwt.exp * 1000 || null;
};

And one more util function isExpired() to check is the timestamp expired. This function returns true if the expiration timestamp presented and if it is less than Date.now().

const isExpired = (exp?: number) => {
    if (!exp) {
        return false;
    }

    return Date.now() > exp;
};

Time to create first function of the token provider interface. Function getToken() should return token and update it if it is necessary. This function should be async because it may make a network request to update token.

Using created earlier functions we can check is the access tokens expired or not (isExpired(getExpirationDate(_token.accessToken))). And in the first case to make a request for updating token. After that, we can save tokens (with the not implemented yet function setToken()). And finally, we can return access token:

const getToken = async () => {
    if (!_token) {
        return null;
    }

    if (isExpired(getExpirationDate(_token.accessToken))) {
        const updatedToken = await fetch('/update-token', {
            method: 'POST',
            body: _token.refreshToken
        })
            .then(r => r.json());

        setToken(updatedToken);
    }

    return _token && _token.accessToken;
};

Function isLoggedIn() will be simple: it will return true if _tokens is not null and will not check for access token expiration (in this case we will not know about expiration access token until we get fail on getting token, but usually it is sufficient, and let us keep function isLoggedIn synchronous):

const isLoggedIn = () => {
    return !!_token;
};

I think it is a good time to create functionality for managing observers. We will implement something similar to the Observer pattern, and first of all, will create an array to store all our observers. We will expect that each element in this array is the function we should call after each change of tokens:

let observers: Array<(isLogged: boolean) => void> = [];

Now we can create methods subscribe() and unsubscribe(). The first one will add new observer to the created a bit earlier array, second one will remove observer from the list.

const subscribe = (observer: (isLogged: boolean) => void) => {
    observers.push(observer);
};

const unsubscribe = (observer: (isLogged: boolean) => void) => {
    observers = observers.filter(_observer => _observer !== observer);
};

Updating to new releases

Create React App is divided into two packages:

  • create-react-app is a global command-line utility that you use to create new projects.
  • react-scripts is a development dependency in the generated projects (including this one).

You almost never need to update create-react-app itself: it delegates all the setup to react-scripts.

When you run create-react-app, it always creates the project with the latest version of react-scripts so you’ll get all the new features and improvements in newly created apps automatically.

To update an existing project to a new version of react-scripts, open the changelog, find the version you’re currently on (check package.json in this folder if you’re not sure), and apply the migration instructions for the newer versions.

In most cases bumping the react-scripts version in package.json and running npm install in this folder should be enough, but it’s good to consult the changelog for potential breaking changes.

We commit to keeping the breaking changes minimal so you can upgrade react-scripts painlessly.

Using third party assertion libraries

We recommend that you use expect() for assertions and jest.fn() for spies. If you are having issues with them please file those against Jest, and we’ll fix them. We intend to keep making them better for React, supporting, for example, pretty-printing React elements as JSX.

However, if you are used to other libraries, such as Chai and Sinon, or if you have existing code using them that you’d like to port over, you can import them normally like this:

and then use them in your tests like you normally do.

Version control integration

By default, when you run npm test, Jest will only run the tests related to files changed since the last commit. This is an optimization designed to make your tests run fast regardless of how many tests you have. However it assumes that you don’t often commit the code that doesn’t pass the tests.

Jest will always explicitly mention that it only ran tests related to the files changed since the last commit. You can also press a in the watch mode to force Jest to run all tests.

Jest will always run all tests on a continuous integration server or if the project is not inside a Git or Mercurial repository.

What other .env files can be used?

Note: this feature is available with [email protected] and higher.

  • .env: Default.
  • .env.local: Local overrides. This file is loaded for all environments except test.
  • .env.development, .env.test, .env.production: Environment-specific settings.
  • .env.development.local, .env.test.local, .env.production.local: Local overrides of environment-specific settings.

Files on the left have more priority than files on the right:

  • npm start: .env.development.local, .env.development, .env.local, .env
  • npm run build: .env.production.local, .env.production, .env.local, .env
  • npm test: .env.test.local, .env.test, .env (note .env.local is missing)

These variables will act as the defaults if the machine does not explicitly set them.Please refer to the dotenv documentation for more details.

Note: If you are defining environment variables for development, your CI and/or hosting platform will most likely need
these defined as well. Consult their documentation how to do this. For example, see the documentation for Travis CI or Heroku.

Pre-rendering into static html files

If you’re hosting your build with a static hosting provider you can use react-snapshot or react-snap to generate HTML pages for each route, or relative link, in your application. These pages will then seamlessly become active, or “hydrated”, when the JavaScript bundle has loaded.

There are also opportunities to use this outside of static hosting, to take the pressure off the server when generating and caching routes.

The primary benefit of pre-rendering is that you get the core content of each page with the HTML payload—regardless of whether or not your JavaScript bundle successfully downloads. It also increases the likelihood that each route of your application will be picked up by search engines.

You can read more about zero-configuration pre-rendering (also called snapshotting) here.

Похожее:  Личный кабинет КаменскТелеком: регистрация

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *