This React-based single-page application was built using create-react-app in November 2020.
- React Hooks
- Typescript
- Prettier and ESLint using Airbnb Style Guide
- Material-UI version 5 components (still alpha)
- Page transitions via React Router
- External data retrieval via react-query version 3
- Tabular data display via react-table
- Global state management via Recoil
- "Loading" feedback via React Suspense
- Translations via i18next
- CORS workaround proxy
- A default error page
- A custom 404 page
- Testing with Jest and React Testing Library
- A sample test invokes an external service
- Because the example uses the proxy, you must start the app (npm run start) prior to running tests
-
nvm i lts/fermium
-
npx create-react-app react-spa --typescript
-
cd react-spa
-
echo lts/fermium > .nvmrc
npm i --save-dev eslint prettier eslint-config-airbnb-typescript-prettier typescript
npm i --save \
i18next i18next-browser-languagedetector i18next-http-backend react-i18next \
react-loader-spinner @types/react-loader-spinner \
recoil \
react-dom @types/react-dom \
react-router @types/react-router \
react-router-dom @types/react-router-dom \
react-query @types/react-query \
react-table @types/react-table \
jest-localstorage-mock \
request
# Material-UI 5
npm i --save \
typeface-roboto \
@material-ui/lab @emotion/react @emotion/styled @material-ui/core@next typeface-roboto
- Create .eslintrc.js
// For gatsby config, see https://github.com/d4rekanguok/gatsby-typescript/blob/master/.eslintrc.js
module.exports = {
overrides: [
{
// Plain JavaScript
files: ['*.{js,jsx}'],
extends: ['airbnb', 'airbnb/hooks', 'prettier', 'prettier/react', 'react-app', 'react-app/jest'],
plugins: ['prettier'],
},
{
// Typescript
// See https://github.com/toshi-toma/eslint-config-airbnb-typescript-prettier/blob/master/index.js
files: ['*.{ts,tsx}'],
extends: ['airbnb-typescript-prettier', 'react-app', 'react-app/jest'],
},
],
rules: {
'max-len': [
'error',
{
code: 120,
ignoreUrls: true,
},
],
},
};
- Create .eslintignore
# node_modules is ignored by default
build/
dist/
docs/
- Create .prettierrc.js
module.exports = {
printWidth: 120,
singleQuote: true,
trailingComma: 'all',
};
- Create .prettierignore
build/
dist/
node_modules/
- Modify package.json
11.1 Remove eslint section
11.2 Add format and lint scripts
"scripts": {
"lint": "tsc --noEmit && eslint --fix '*.{js,jsx,ts,tsx}'"
"format": "prettier . --write",
- Edit tsconfig.json
- set compilerOptions.target to esnext
This app was made possible by the contributions of many developers who kindly shared their knowledge, free of charge. I regret that not every reference has been cited. Here is a list of references that were invaluable for building this project.
Because React applications are bundled, it doesn't matter whether you use devDependencies. All dependencies are considered at build time. Modules that aren't needed are discarded. If you're building a reusable library, not including a @types module can cause issues for the module's users. Reference.