跳到主要内容

部署

npm run buildbuild 目录下为你的应用创建了生产环境构建版本。设置你喜欢的 HTTP 服务器,以便访问者能够通过 index.html 访问你的站点,并向 /static/js/main.<hash>.js 这种静态路径进行请求,以获得 /static/js/main.<hash>.js 文件内容。有关更多信息,请查阅生产环境构建部分。

静态服务器

对于使用Node的环境,最简单的解决途径是安装 serve,并让其处理剩下的内容:

npm install -g serve
serve -s build

上面显示的最后一个命令将在 5000 端口上为你的静态站点提供服务。与 serve 的许多内部设置一样,可以使用 -l--listen 选项来调整端口:

serve -s build -l 4000

运行此命令以获取可用选项的完整列表:

serve -h

其他解决方案

你不一定需要静态服务器来在生产环境下运行 Create React App 项目,将其集成至已有的服务端应用程序时也能很好的工作。

这是一个使用NodeExpress的程序示例:

const express = require('express');
const path = require('path');
const app = express();

app.use(express.static(path.join(__dirname, 'build')));

app.get('/', function(req, res) {
res.sendFile(path.join(__dirname, 'build', 'index.html'));
});

app.listen(9000);

服务器软件的选择并不重要。因为 Create React App 完全不依赖于平台,所以并不是一定要使用 Node。

build 文件夹下的静态 assets 是 Create React App 生成的唯一输出。

但是,这对于使用客户端路由来说还远远不够。阅读下一章节,以了解如何在你的单页面应用中支持像 /todos/42 之类的 URLs。

通过客户端路由提供服务

如果你使用基于 HTML5 pushState history API 构建的路由(例如搭配 browserHistoryReact Router),许多静态服务器都将报错。如果你混用 React Router 与路径 /todos/42,开发服务器将会正确响应 localhost:3000/todos/42,但是将其部署在 Express 服务器上时则不会正确响应。

这是因为当我们为 /todos/42 生成新页面时,服务器找不到名为 build/todos/42 的文件。需要修改服务器配置以通过 index.html 响应针对 /todos/42 的请求。例如,我们可以修改上述 Express 实例,为所有未知路径提供 index.html

 app.use(express.static(path.join(__dirname, 'build')));

-app.get('/', function (req, res) {
+app.get('/*', function (req, res) {
res.sendFile(path.join(__dirname, 'build', 'index.html'));
});

如果你使用的是 Apache HTTP 服务器,则需要在 public 文件夹中创建一个 .htaccess 文件,如下所示:

    Options -MultiViews
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.html [QSA,L]

当你执行 npm run build 时,它会被复制到 build 文件夹。

如果你使用的是 Apache Tomcat,则需要参照这篇 Stack Overflow 答案

现在,所有对 todos/42 的请求在开发和生产环境中都会得到正确的处理。

在生产环境构建版本中,当你选择开启 PWA 时,service worker 将会自动处理所有导航请求,像 /todos/42 这种就会提供一个 index.html 的缓存拷贝。service worker 导航路由可以进行相关配置,或通过 ejecting 禁用,然后修改 SWPrecachePlugin 配置项中的 navigateFallbacknavigateFallbackWhitelist

当用户将你的应用安装至设备主屏幕时,默认配置将会提供一个 /index.html 快捷方式。对于希望通过 / 来提供应用的客户端路由来说可能会导致失效。在 public/manifest.json 上修改 web 应用清单,并修改 start_url 以匹配所需的 URL scheme,例如:

  "start_url": ".",

相对路径构建

默认情况下,Create React App 会生成一个假定你的应用被托管在服务器根目录下的构建。

要覆盖此设置,请指定 package.json 中的 homepage 项,例如:

  "homepage": "http://mywebsite.com/relativepath",

这将使 Create React App 正确判断要生成的 HTML 文件中该使用的根路径。

注意:如果你使用的是 react-router@^4,则可以在任何 <Router> 上使用 basename 属性生成 <Link>

更多信息请参阅此处

例如:

<BrowserRouter basename="/calendar"/>
<Link to="/today"/> // renders <a href="/calendar/today">

对不同路径提供相同的构建

注意:该功能仅支持 react-scripts@0.9.0 及以上版本。

如果你没有调用 HTML5 pushState history API 或根本没有使用客户端路由,则无需指定解析应用的 URL。作为代替,你可以将其放在 package.json 中:

  "homepage": ".",

这将确保所有 asset 路径都是相对于 index.html 的。你可以在不重新构建将应用程序从 http://mywebsite.com 移动到 http://mywebsite.com/relativepath,甚至是 http://mywebsite.com/relative/path

为任意构建环境定制环境变量

你可以通过创建自定义 .env 文件来创建一个定制构建环境,并使用 env-cmd 对其进行加载。

例如,要为 staging 环境创建构建环境:

  1. 创建一个名为 .env.staging 的文件
  2. 像设置其他 .env 文件一样设置环境变量(例如 REACT_APP_API_URL=http://api-staging.example.com
  3. 安装 env-cmd
    $ npm install env-cmd --save
    $ # or
    $ yarn add env-cmd
  4. 在你的 package.json 中添加一个新脚本,使用新环境进行构建:
    {
    "scripts": {
    "build:staging": "env-cmd -f .env.staging npm run build"
    }
    }

现在你可以运行 npm run build:staging 以使用 staging 环境配置进行构建。 你可以用相同的方式指定其他环境。

.env.production 中的变量将用作后备选项,因为构建时 NODE_ENV 将始终被设定为 production

AWS Amplify

AWS Amplify 控制台通过 serverless backends 为现代 Web 应用(单页应用和静态网站生成器)提供持续性部署与托管。Amplify Console 提供了全球可用的 CDNS,自定义域名设置,功能分支部署以及密码保护。

  1. 这里登入 Amplify 控制台
  2. 连接你的 Create React App 仓库并选择一个分支。如果你在寻找 Create React App + Amplify 的入门选择,请尝试create-react-app-auth-amplify 入门程序,它演示了如何在 10 分支内使用 Create React App 设置身份验证。
  3. Amplify Console 自动检测构建设置,点击下一步。
  4. 选择 保存并部署

如果构建成功,该应用会被部署并托管至拥有 amplifyapp.com 域名的全局 CDN 上。现在,你可以将更改持续部署至你的前端或后端。持续部署允许开发人员在每次修改代码并提交至 Git 仓库时,将更新自动部署至前端与后端。

Azure

查阅这篇博文以了解如何将 React 应用部署至 Microsoft Azure。

查阅这篇博文这个仓库,以了解自动部署至 Azure App Service 的方法。

Firebase

如果尚未安装 Firebase 命令行工具,请执行 npm install -g firebase-tools。注册一个 Firebase 账户并创建一个新项目。运行 firebase login 并使用你先前创建的 Firebase 账户登入。

随后在项目的根目录下执行 firebase init 命令。你需要选择 Hosting: Configure and deploy Firebase Hosting sites,然后选择上一步创建的 Firebase 项目。你需要统一创建的 database.rules.json,选择 build 作为公共目录,并选择 y 以同意 Configure as a single-page app

    === Project Setup

First, let's associate this project directory with a Firebase project.
You can create multiple project aliases by running firebase use --add,
but for now we'll set up a default project.

? What Firebase project do you want to associate as default? Example app (example-app-fd690)

=== Database Setup

Firebase Realtime Database Rules allow you to define how your data should be
structured and when your data can be read from and written to.

? What file should be used for Database Rules? database.rules.json
✔ Database Rules for example-app-fd690 have been downloaded to database.rules.json.
Future modifications to database.rules.json will update Database Rules when you run
firebase deploy.

=== Hosting Setup

Your public directory is the folder (relative to your project directory) that
will contain Hosting assets to uploaded with firebase deploy. If you
have a build process for your assets, use your build's output directory.

? What do you want to use as your public directory? build
? Configure as a single-page app (rewrite all urls to /index.html)? Yes
✔ Wrote build/index.html

i Writing configuration info to firebase.json...
i Writing project information to .firebaserc...

✔ Firebase initialization complete!

重要提示:你需要在 firebase.json 文件中为 service-worker.js 设置正确的 HTTP 缓存报头,否则你无法在第一次以后的部署中看到更改(issue #2440)。应该如下所示将其添加到 host 中:

{
"hosting": {
...
"headers": [
{"source": "/service-worker.js", "headers": [{"key": "Cache-Control", "value": "no-cache"}]}
]
...

现在,执行 npm run build 创建生产环境版本后,可以通过执行 firebase deploy 来部署它。

    === Deploying to 'example-app-fd690'...

i deploying database, hosting
✔ database: rules ready to deploy.
i hosting: preparing build directory for upload...
Uploading: [============================== ] 75%✔ hosting: build folder uploaded successfully
✔ hosting: 8 files uploaded successfully
i starting release process (may take several minutes)...

✔ Deploy complete!

Project Console: https://console.firebase.google.com/project/example-app-fd690/overview
Hosting URL: https://example-app-fd690.firebaseapp.com

请查阅 Firebase 托管以了解更多相关信息。

GitHub Pages

注意:该功能仅支持 react-scripts@0.2.0 及以上版本。

步骤 1:将 homepage 添加到 package.json

以下步骤非常重要!

如果你跳过它,你的应用可能无法被正常部署。

打开你的 package.json 文件,并为你的项目添加 homepage 字段:

  "homepage": "https://myusername.github.io/my-app",

或 Github user 页面:

  "homepage": "https://myusername.github.io",

或自定义域名页面:

  "homepage": "https://mywebsite.com",

Crete React App 使用 homepage 字段来确定被构建的 HTML 文件的根 URL。

步骤 2:安装 gh-pages 并将 deployscripts 添加至 package.json

现在,每当你执行 npm run build,你都会看到一个关于如何部署到 GitHub Pages 的备忘单。

要在 https://myusername.github.io/my-app 上发布,执行:

npm install --save gh-pages

或者你可以使用 yarn 代替:

yarn add gh-pages

将下列脚本添加到 package.json 中:

  "scripts": {
+ "predeploy": "npm run build",
+ "deploy": "gh-pages -d build",
"start": "react-scripts start",
"build": "react-scripts build",

predeploy 将在 deploy 命令执行前自动运行。

如果要部署到 Github user 页面,而不是项目页面,则需要添加一个额外修改:

  1. 调整你的 package.json 脚本以将部署推送至 master
  "scripts": {
"predeploy": "npm run build",
- "deploy": "gh-pages -d build",
+ "deploy": "gh-pages -b master -d build",

步骤 3:执行 npm run deploy 以部署站点

随后执行:

npm run deploy

步骤 4:对于项目页面,确保你的项目设置中使用 gh-pages

最后,确保将 GitHub 项目设置中的 Github Pages 选项设定为使用 gh-pages 分支:

gh-pages branch setting

步骤 5:配置域名(可选)

你可以通过将 CNAME 文件添加至 public/ 文件夹中为 GitHub Pages 配置自定义域名。

你的 CNAME 文件应该如下所示:

mywebsite.com

有关客户端路由的说明

Github Pages 不支持使用基于 HTML5 pushState history API 的路由(例如,使用 browserHistory 的 React Router)。这是因为当通过类似于 http://user.github.io/todomvc/todos/42 这样的 url 访问新页面时,/todo/42 是前端路由,Github Pages 服务器会返回 404,因为它完全不了解 /todos/42 的相关信息。如果要为托管在 GitHub Pages 上的项目添加路由的话,有以下两种解决方案:

你可以从调用 HTML5 history API 转至使用哈希路由。如果使用 React Router,可以切换至 hashHistory 来达到这种效果,但是 URL 会变得更长且更复杂(例如, http://user.github.io/todomvc/#/todos/42?_k=yknaj)。阅读此文以了解更多关于 React Router 中不同历史记录实现的详细说明。 或者,你可以使用黑魔法来告诉 GitHub Pages 如何处理 404,方法是使用自定义的重定向参数以重定向至你的 index.html 页面。在部署项目之前,你需要将带有重定向代码的 404.html 文件添加到 build 文件夹中,且需要在 index.html 中添加处理重定向参数的代码。你可以在这篇指南中找到有关此技巧的详细说明。

故障排除

"/dev/tty: No such a device or address"

如果在部署时看到 /dev/tty: No such a device or address 或与之类似的错误,请尝试以下操作:

  1. 创建一个新的个人访问 Token
  2. git remote set-url origin https://<user>:<token>@github.com/<user>/<repo> .
  3. 再次执行 npm run deploy

"Cannot read property 'email' of null"

如果在部署时看到 Cannot read property 'email' of null,请尝试以下操作:

  1. git config --global user.name '<your_name>'
  2. git config --global user.email '<your_email>'
  3. 再次执行 npm run deploy

Heroku

使用为 Create React App 定制的 Heroku 构建工具

你可以在零配置部署 React中找到说明。

解决 Heroku 部署错误

有时 npm run build 运行在本地,但是在线上部署至 Heroku 时失败。以下是最常见的情况。

"Module not found: Error: Cannot resolve 'file' or 'directory'"

如果你得到这样的信息:

remote: Failed to create a production build. Reason:
remote: Module not found: Error: Cannot resolve 'file' or 'directory'
MyDirectory in /tmp/build_1234/src

这意味着你需要确保 import 的文件或目录本身的字母大小写和文件系统或 GitHub 上的字母大小写相匹配。

这很重要,因为 Linux(Heroku 所使用的操作系统)区分大小写。因此,MyDirectorymydirectory 代表着两个不同的目录,同样的,即使项目在本地构建,大小写的差异也会导致 Heroku 远程服务器上的 import 语句被破坏。

"Could not find a required file."

如果你从包中排除或忽略了必要的文件,你将会看到类似这样的错误:

remote: Could not find a required file.
remote: Name: `index.html`
remote: Searched in: /tmp/build_a2875fc163b209225122d68916f1d4df/public
remote:
remote: npm ERR! Linux 3.13.0-105-generic
remote: npm ERR! argv "/tmp/build_a2875fc163b209225122d68916f1d4df/.heroku/node/bin/node" "/tmp/build_a2875fc163b209225122d68916f1d4df/.heroku/node/bin/npm" "run" "build"

在这种情况下,请确保文件大小写正确,且不会在本地 .gitignore~/.gitignore_global 中被忽略。

Netlify

要手动部署到Netlify的CDN:

npm install netlify-cli -g
netlify deploy

选择“ build”作为部署路径。

要配置持续部署:

按照以下步骤执行,以使 Netlify 在你推送到 git 或开启 pull request 时自动构建并部署:

  1. 开启一个新的 netlify 项目
  2. 选择你的 Git 托管服务,然后选择你的仓库
  3. 点击 Build your site

客户端路由支持:

为了支持 pushState,请确保使用以下重写规则创建 public/_redirects 文件:

/*  /index.html  200

在构建项目时,Create React App 将把 public 文件夹内容置入构建输出中。

ZEIT Now

ZEIT Now 是一个针对网站和 serverless APIs 的云平台,可用于将你的 Create React App 项目部署个人域名(或免费的 .now.sh 后缀 URL)。

该指南将像你展示快速入门的相关步骤:

步骤 1:安装 Now 命令行工具

要使用 npm 安装命令行工具,请执行以下命令:

npm i -g now

步骤 2:部署

你可以通过在项目目录的根路径下执行以下命令来部署应用程序:

now

或者,你也可以使用他们的 GitHubGitLab 集成。

这样就可以了!

现在将会部署你的站点,同时你将会收到类似以下内容的链接:https://react.now-examples.now.sh

开箱即用,同时你已经自动配置了客户端路由兼容与适当的默认缓存头部。这种行为可以被这样覆盖

Render

Render 提供免费静态站点托管,该托管具备 SSL,全局 CDM 以及来自 GitHub 的持续自动部署。

遵循 Create React App 开发指南,短时间内即可完成你的应用部署。

使用邀请码 cra 进行注册或使用该链接

S3CloudFront

有关如何将 React 应用部署至 Amazon Web Service S3 和 CloudFront 的相关信息,请查阅这篇博文。如果你要添加自定义域名、HTTPS 和持续部署,请参阅这篇博文

Surge

如果尚未安装 Surge 命令行工具,请执行 npm install -g surge。运行 surge 命令以登入或创建一个新账户。

当询问有关项目路径的信息时,请确保指定 build 文件夹,像这样:

       project path: /path/to/project/build

请注意,为了兼容基于 HTML5 pushState API 的路由,你可能需要在部署到 Surge 前将 build 文件夹中的 index.html 文件重命名为 200.html。这样能确保每个 URL 都能回退到该文件

将组件发布至 npm

Create React App 不提供任何将组件发布至 npm 的内置功能。如果你准备从项目中提取组件,以便其他人可以使用它,我们建议将其移动到项目外部的单个文件夹中,然后使用 nwb 这样的工具进行发布前准备。