使用 express 后端将 create-react-app 部署到 heroku 在浏览器中返回无效的主机标头
Posted
技术标签:
【中文标题】使用 express 后端将 create-react-app 部署到 heroku 在浏览器中返回无效的主机标头【英文标题】:deploying create-react-app to heroku with express backend returns invalid host header in browser 【发布时间】:2019-03-21 14:20:13 【问题描述】:标题说明了一切。我在这里构建了一个最小的工作示例:https://github.com/sehailey/proxytest
我已经尝试过了,所以可能我已经记不清了(尽管它们存储在提交中)。我保证,一旦我得到答案,就会跟进数十个提出这个问题的已回答线程。
【问题讨论】:
【参考方案1】:看起来他们改变了create-react-app
使用代理的方式。从package.json
中删除proxy
。那么……
添加这个包:
npm i -S http-proxy-middleware
然后在src
中创建一个setupProxy.js
:
src/setupProxy.js
const proxy = require("http-proxy-middleware");
module.exports = app =>
app.use(proxy("/api/*", target: "http://localhost:5000/" ));
;
现在从 React 组件内部,你可以这样做:
src/App.js
import React, Component from "react";
import logo from "./logo.svg";
import "./App.css";
export default class App extends Component
state =
message: "",
error: "",
eee: "",
text: ""
;
componentDidMount = () => this.fetchAPIMessage();
fetchAPIMessage = async () =>
try
const res = await fetch(`/api/message`);
const message = await res.json();
this.setState( message );
catch (err)
console.error(err);
;
render = () => (
<div className="App">
<header className="App-header">
<img src=logo className="App-logo" />
<p>WELCOME CREATE REACT APP!</p>
<div className="App-link">this.state.message</div>
</header>
</div>
);
index.js(我添加了npm i -D morgan
,这是一个方便的日志框架——当请求到达 API 时,它会在控制台中显示它)。
const path = require("path");
const express = require("express");
const app = express();
const morgan = require("morgan");
app.use(morgan("tiny")); // logging framework
// Serve our api message
app.get("/api/message", async (req, res, next) =>
try
res.status(201).json( message: "HELLOOOOO FROM EXPRESS" );
catch (err)
next(err);
);
if (process.env.NODE_ENV === "production")
// Express will serve up production assets
app.use(express.static("build"));
// Express will serve up the front-end index.html file if it doesn't recognize the route
app.get("*", (req, res) =>
res.sendFile(path.resolve("build", "index.html"))
);
// Choose the port and start the server
const PORT = process.env.PORT || 5000;
app.listen(PORT, () => console.log(`Mixing it up on port $PORT`));
package.json(使用node
提供生产资产——参见“启动”脚本)
"name": "proxytest",
"version": "0.1.0",
"private": true,
"homepage": "https://proxytest2.herokuapp.com/",
"dependencies":
"concurrently": "^4.0.1",
"express": "^4.16.4",
"http-proxy-middleware": "^0.19.0",
"react": "^16.5.2",
"react-dom": "^16.5.2",
"react-scripts": "2.0.5",
"serve": "^10.0.2"
,
"scripts":
"start": "NODE_ENV=production node index.js",
"build": "react-scripts build",
"test": "react-scripts test",
"client": "react-scripts start",
"server": "nodemon server",
"eject": "react-scripts eject",
"dev": "concurrently --kill-others-on-fail \"npm run server\" \"npm run client\"",
"heroku-postbuild": "npm run build"
,
"eslintConfig":
"extends": "react-app"
,
"browserslist": [
">0.2%",
"not dead",
"not ie <= 11",
"not op_mini all"
]
在production
中运行时您将在控制台中看到的内容:
m6d@m6d-pc:~/Desktop/proxytest-master$ npm start
> proxytest@0.1.0 start /home/m6d/Desktop/proxytest-master
> NODE_ENV=production node index.js
Mixing it up on port 5000
GET / 200 2057 - 6.339 ms
GET /static/css/main.068b9d02.chunk.css 304 - - 1.790 ms
GET /static/js/1.9a879072.chunk.js 304 - - 0.576 ms
GET /static/js/main.e3ba6603.chunk.js 304 - - 0.605 ms
GET /api/message 201 36 - 4.299 ms
GET /static/media/logo.5d5d9eef.svg 304 - - 0.358 ms
其他说明:
确保将您的客户端 src 与 API 分开(例如,将前端 React 应用程序中的所有内容放入具有自己依赖项的client
文件夹中)。
从您的 API 的package.json
中删除所有 React 依赖项
【讨论】:
很棒的答案,干得好,谢谢!我将与其他数十人分享,希望它可以在未来为其他人节省一些挫败感。 所以,我使用 localhost:3000 来托管我的 CRA 客户端和 localhost:3001 来托管我的 Express Server。在我的 client/src 文件夹中添加src/setupProxy.js
并指向 app.use(proxy("/api/*", target: "http://localhost:3001/" ));
目前不起作用。有什么想法吗?
因为我没有你的代码,所以我不能确定你的问题出在哪里。
我实际上在 Azure 上遇到了同样的问题:***.com/questions/52970371/…
代理应该指向后端。在上面的示例中,后端在端口 5000 (http://localhost:5000/api
) 上提供服务。在生产中,当所有东西都在一个端口上提供服务时,如果它们共享相同的路由名称,仅使用 /
可能会干扰客户端路由——这就是为什么我在所有后端路由后附加 /api
。以上是关于使用 express 后端将 create-react-app 部署到 heroku 在浏览器中返回无效的主机标头的主要内容,如果未能解决你的问题,请参考以下文章
如何以 Node JS 作为后端将 Mysql 数据获取并显示到 ReactJS 前端?
使用 SQL Server 后端将图片插入到 Access 表中
如何使用 Ruby 作为后端将 React 上的图像上传到 Google Cloud Storage