Hello 小伙伴们,如果觉得本文还不错,记得给个 star , 小伙伴们的 star 是我持续更新的动力!GitHub 地址
一 目录
不折腾的前端,和咸鱼有什么区别
二 前言
Create React App 是一个官方支持的创建 React 单页应用程序的方法。它提供了一个零配置的现代构建设置。
本文 绝大多数、99% 内容来自 Create React App 的文档,1% 来自个人的整理。
如果对此话有所误解,请跳至文:十九 总结
可加 QQ 群:
798961601
,跟随 jsliang 一起折腾
- 参考文献:
三 安装及初始目录
- 下载 Node.js
- 安装 Create React App:
npm i create-react-app -g
- 开启新项目:
create-react-app todolist
cd todolist
npm start
- 打包项目:
npm build
- 项目目录:
- todolist
+ node_modules —————————— 项目依赖的第三方的包
- public ———————————————— 共用文件
- favicon.ico —— 网页标签左上角小图标
- index.html —— 网站首页模板
- mainfest.json —— 提供 meta 信息给项目,并与 serviceWorker.js 相呼应,进行离线 APP 定义
- src ——————————————————— 项目主要目录
- App.css —— 主组件样式
- App.js —— 主组件入口
- App.test.js —— 自动化测试文件
- index.css —— 全局 css 文件
- index.js —— 所有代码的入口
- logo.svg —— 页面的动态图
- serviceWorker.js —— PWA。帮助开发手机 APP 应用,具有缓存作用
- .gitignore ——————————— 配置文件。git 上传的时候忽略哪些文件
- package-lock.json ———— 锁定安装包的版本号,保证其他人在 npm i 的时候使用一致的 node 包
- package.json ————————— node 包文件,介绍项目以及说明一些依赖包等
- README.md ———————————— 项目介绍文件
复制代码
四 默认支持特性
支持所有现代浏览器(IE 9、10、11 除外,如果需要,请自行配置)
支持指数运算符 (ES2016)
支持
async
/await
(ES2017)支持
Object Rest
(剩余) /Spread
(展开) 属性 (ES2018)支持动态
import()
(stage 3 proposal)支持
Class
字段和静态属性 (part of stage 3 proposal)支持 JSX, Flow 和 TypeScript
支持 PostCSS,无需手动添加 CSS 前缀,Create React App 会自动补全
五 配合 VS Code 调试
可以通过 Visio Studio Code 的插件 Debugger for Chrome 调试 Create React App:
- 安装 -> Debugger for Chrome
- 调试 -> 添加配置:
launch.json
{
"version": "0.2.0",
"configurations": [
{
"name": "Chrome",
"type": "chrome",
"request": "launch",
"url": "http://localhost:3000",
"webRoot": "${workspaceRoot}/src",
"sourceMapPathOverrides": {
"webpack:///src/*": "${webRoot}/*"
}
}
]
}
复制代码
- 保存 -> 开始调试
- 通过上述步骤即可开始调试
如有问题可以参考下面资料
六 分析包大小
使用 source maps 分析 JavaScript 包。
这有助于你了解代码膨胀的来源,从而配合其他插件来减少每个包的大小,优化项目。
- 安装:
npm i source-map-explorer -S
- 修改 package.json:
package.json
"scripts": {
"analyze": "source-map-explorer build/static/js/main.*",
"start": "react-scripts start",
"build": "react-scripts build",
"test": "react-scripts test",
}
复制代码
- 分析:
npm run build
- 分析:
npm run analyze
七 模块引入 CSS
在 Create React App 中,如果你的 react-scripts
版本是 2.0 或者更高,你可以通过模块形式引入样式:
Button.js
import React, { Component } from 'react';
import styles from './Button.module.css'; // 将 css modules 文件导入为 styles
import './another-stylesheet.css'; // 导入常规 CSS 文件
class Button extends Component {
render() {
// 作为 js 对象引用
return <button className={styles.error}>Error Button</button>;
}
}
复制代码
这样子不会导致样式的冲突,就好比你 import JS 进来一样。
八 Sass 安装及使用
- 安装
node-sass
:npm i node-sass -S
- 引入:
@import 'styles/_colors.scss'; // 假设 styles 目录 在 src/ 目录下
九 添加图片、背景、SVG
- 添加图片:通过
import
引入即可。
import React from 'react';
import logo from './logo.png'; // 告诉 Webpack 这个 JS 文件使用了这个图片
console.log(logo); // /logo.84287d09.png
function Header() {
// 导入结果是图片的 URL
return <img src={logo} alt="Logo" />;
}
export default Header;
复制代码
- 引用背景:通过
url
引用即可。
.logo {
background-image: url(./logo.png);
}
复制代码
- 引用 SVG:
import React from 'react';
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" />
</header>
</div>
);
}
export default App;
复制代码
或者:
import { ReactComponent as Logo } from './logo.svg';
const App = () => (
<div>
{/* ReactComponent 导入名称是特殊的 */}
{/* Logo 是一个实际的 React 组件 */}
<Logo />
</div>
);
复制代码
十 public 文件夹
在 Create React App 创建的项目中,有个 public 文件夹,该文件夹下通常有:
- favicon.ico - 网页小标签
- index.html - 项目首页
- mainfest.json - 提供 meta 信息给项目,并与 serviceWorker.js 相呼应,进行离线 APP 定义
当然,它不仅可以拥有这些文件,还可以新增内容。
10.1 引用静态资源
index.html 可以引用静态资源。
在 index.html 中引用的静态资源不会被 Webpack 打包,而是被复制到打包目录中,使用方法:
<link rel="shortcut icon" href="%PUBLIC_URL%/favicon.ico">
复制代码
只需要加上 %PUBLIC_URL%/
表示引用 public 下的资源即可。
在 JavaScript 中:
render() {
return <img src={process.env.PUBLIC_URL + '/img/logo.png'} />;
}
复制代码
这样也会引用 public 中的资源,从而让图片 不会被 Webpack 打包。当然,需要牺牲的代价有:
- public 文件夹中的所有文件都不会进行后处理或压缩。
- 在编译时不会调用丢失的文件,并且会导致用户出现 404 错误。
- 结果文件名不包含内容哈希值,因此你需要添加查询参数或在每次更改时重命名它们(以便清除浏览器缓存)。
10.2 Mock 数据
此外,由于它内含 Node.js,所以还可以利用这点进行数据模拟(Mock),做法是:
- 在 public 文件夹中新建 api 目录,然后创建文件 headerList.json,引用 axios 后,通过:
axios.get('/api/headerList.json').then()
即可调用该文件进行 Mock。
api 下可以存放多个 json 文件
十一 代码打包分割
在 Create React App 中,我们可以使用 React Loadable 来进行代码的分割。
使用方式:
import Loadable from 'react-loadable';
const LoadableOtherComponent = Loadable({
loader: () => import('./OtherComponent'),
loading: () => <div>Loading...</div>,
});
const MyComponent = () => (
<LoadableOtherComponent/>
);
复制代码
- 参考文献:
十二 引用 TypeScript
- 使用 TypeScript 启动新的 Create React App项目:
npx create-react-app my-app --typescript
- 往 Create React App 现有项目中添加 TypeScript:
npm i typescript @types/node @types/react @types/react-dom @types/jest -S
。(记得修改所有 JS 文件为 TS 文件,例如src/index.js
->src/index.tsx
)
十三 React Router - 路由
由于 Create React App 并没有规定路由解决方案,然后市面上比较收欢迎的路由解决方案是 React Router,所以可以尝试使用:
- 安装:
npm i react-router-dom -S
- 使用:React Router
十四 自定义环境变量
- 定义环境变量:
process.env.REACT_APP_SECRET_CODE
- 获取特殊内置环境变量:
process.env.NODE_ENV
。值为:test
、development
、production
。对应三种环境。
render() {
return (
<div>
<small>You are running this application in <b>{process.env.NODE_ENV}</b> mode.</small>
<form>
<input type="hidden" defaultValue={process.env.REACT_APP_SECRET_CODE} />
</form>
</div>
);
}
复制代码
在开发环境,该页面渲染为:
<div>
<small>You are running this application in <b>development</b> mode.</small>
<form>
<input type="hidden" value="abcdef" />
</form>
</div>
复制代码
十五 测试
Create React App 使用 Jest 作为其测试运行器。
但是很不幸的是,工作中并没有用上,估计以后的工作也可能不会用上,所以咱们只需要知道有这回事,等有机会再进行尝试。
- 参考文献:
十六 开发环境代理
在开发项目的过程中,最担心的莫过于浏览器告诉你跨域了:后端端口在 4000,或者主机在另一个 IP 地址……
所以,我们需要在开发环境中配置代理。
嗯,你问为什么生产(部署)环境我们不做代理?因为那属于后端的活了,或许你是个 全栈 工程师,你可以自行解决下。
往 package.json 中添加字段:
package.json
"proxy": "http://localhost:4000",
复制代码
这样当你调用接口:fetch('/api/todos')
时,它会请求代理到 http://localhost:4000/api/todos
。
当然,有可能 proxy
不够灵活,小伙伴们可以尝试通过直接访问 Express,并连接项目的代理中间件,详情看参考文献。
- 参考文献:
十七 使用 Ajax 请求获取数据
在 Create React App 中,可以通过下面两种方法获取 Ajax 数据:
-
fetch()
API -
axios
库
当然,没有限制死必须使用这两种。
这两种调用 Ajax 请求获取数据的方式便捷在它返回 Promise 供链式调用数据。
十八 Title 和 Meta
- 动态更新 Title:
document.title
API - 根据 React 组件更改 Title:
React Helmet
等第三方库 - 动态更新 Meta:
<!doctype html>
<html lang="en">
<head>
<meta property="og:title" content="__OG_TITLE__">
<meta property="og:description" content="__OG_DESCRIPTION__">
</head>
<body>
</body>
</html>
复制代码
然后读取 index.html 并将 __OG_TITLE__
和 __OG_DESCRIPTION__
替换掉即可。