代理错误:无法将myapp.herokuapp.com的请求/ getThing代理到http:// localhost:3001

时间:2018-03-11 04:52:37

标签: node.js reactjs express heroku create-react-app

我有一个使用Facebook的Create-React-App模板和Nodejs / Express构建的MERN堆栈应用程序。我正在使用Heroku's Nodejs Buildpack。我可以在"Dangerously Disabling Host Check"之后将我的应用部署到Heroku。

Reproducible Demo(自述文件中的说明)

我的网站显示信息,但对我的后端的请求不起作用(服务器和React都在同一个Heroku应用程序上运行)。当我的站点尝试向端点(例如/ getThing)发出请求时,浏览器控制台会显示以下内容:

XML Parsing Error: syntax error
Location: https://myapp.herokuapp.com/getThing
Line Number 1, Column 1:
getThing:1:1
Error: Request failed with status code 500

我的Heroku logs给了我这个(仅包含相关部分):

2018-03-11T04:27:01.058036+00:00 heroku[router]: at=info method=POST path="/getThing" host=myapp.herokuapp.com request_id=e587a6ee-1dbf-4a2d-9caf-07d9478b5a39 fwd="128.84.126.1
26" dyno=web.1 connect=1ms service=32ms status=500 bytes=297 protocol=https
2018-03-11T04:27:01.032269+00:00 heroku[router]: at=info method=GET path="/static/js/bundle.js.map" host=myapp.herokuapp.com request_id=a4fd078d-07f1-4796-b0fe-555f8f389920 fwd="128.84.126.126"
 dyno=web.1 connect=0ms service=7ms status=304 bytes=176 protocol=https
2018-03-11T04:27:01.055673+00:00 app[web.1]: Proxy error: Could not proxy request /getThing from myapp.herokuapp.com to http://localhost:3001/.
2018-03-11T04:27:01.055735+00:00 app[web.1]: See https://nodejs.org/api/errors.html#errors_common_system_errors for more information (ECONNREFUSED).
2018-03-11T04:27:01.055787+00:00 app[web.1]:
2018-03-11T04:27:02.212247+00:00 heroku[router]: at=info method=GET path="/sockjs-node/info?t=1520742420523" host=myapp.herokuapp.com request_id=91c5363e-dbf3-4d15-9482-b44bc1dc3205 fwd="128.84
.126.126" dyno=web.1 connect=0ms service=3ms status=200 bytes=363 protocol=https

第4行是错误所在。我在我的package.json中已经using a proxy,但我读过Heroku忽略了这一点,所以它应该不是问题。我的package.json包含在下面。

{
  "name": "myapp",
  "version": "0.1.0",
  "private": true,
  "proxy": "http://localhost:3001/",
  "dependencies": {
    "@sendgrid/mail": "^6.2.1",
    "async": "^2.6.0",
    "aws-sdk": "^2.205.0",
    "axios": "^0.14.0",
    "body-parser": "~1.17.1",
    "cookie-parser": "~1.4.3",
    "cors": "^2.8.4",
    "debug": "^2.6.9",
    "dotenv": "^5.0.1",
    "express": "~4.15.2",
    "express-fileupload": "^0.4.0",
    "font-awesome": "^4.7.0",
    "foreman": "^2.0.0",
    "history": "^4.7.2",
    "marked": "^0.3.17",
    "milligram": "^1.3.0",
    "milligram-react": "0.0.0",
    "mongodb": "^2.2.35",
    "mongoose": "^4.13.11",
    "morgan": "~1.8.1",
    "nodemailer": "^4.6.0",
    "nodemon": "^1.17.1",
    "react": "^16.2.0",
    "react-bootstrap": "^0.32.1",
    "react-dom": "^16.2.0",
    "react-fontawesome": "^1.6.1",
    "react-icons": "^2.2.7",
    "react-onclickoutside": "^6.7.1",
    "react-router": "^4.2.0",
    "react-router-dom": "^4.2.2",
    "react-scripts": "1.0.17",
    "react-table": "^6.8.0",
    "sendgrid-web": "0.0.5",
    "serve-favicon": "~2.4.2",
    "supports-color": "^5.3.0"
  },
  "engines": { "node": "6.11.3", "npm": "5.7.1"},
  "scripts": {
    "start": "react-scripts start | node server.js",
    "start-dev": "set DEBUG=* & nodemon server.js",
    "build": "react-scripts build",
    "test": "react-scripts test --env=jsdom",
    "eject": "react-scripts eject"
  }
}

这是启动服务器的服务器代码:

const port = process.env.PORT || 3001;
app.listen(port, function () {
    debug(`api running on port ${port}`);
});

我甚至在任何地方都允许cors

const cors = require('cors');
app.use(cors());

文件结构:

任何想法都将不胜感激。如果您需要任何其他信息,请与我们联系。

1 个答案:

答案 0 :(得分:1)

所以你在这里遇到的问题很少。

  

Heroku会自动为您运行一个web dyno,但默认情况下其他进程类型不会启动。要启动工作人员,您需要将其扩展为一个dyno:

默认情况下,您的API dyno甚至没有启动。您需要执行以下命令来启动它

heroku ps:scale api=1

但是它也不会有帮助,因为,您的API不能http可以访问且web dyno无法知道api的位置。有可能这样做,但我不会为这个答案进入解决方案

您可以在下面找到更多详细信息

https://devcenter.heroku.com/articles/dyno-dns-service-discovery

您可能需要更改server.js,如下所示

const host = process.env.HEROKU_PRIVATE_IP || '0.0.0.0';
//starts the server and listens for requests
app.listen(port, host, function () {
    debug(`api running on port ${port}`);
});

并将package.json更新为

"proxy": "http://<apidnsname>:3001"

但正如我所说,我不喜欢这个解决方案,因为它需要对dnsname中的package.json进行硬编码。

实际修复

  • 删除Procfile(heroku将自动运行npm start
  • 添加并发包npm add concurrently
  • start脚本更改为"start": "concurrently \"react-scripts start\" \"PORT=3001 node server.js\""。这样做有两件事。修复了api服务器进程的PORT。并且还在相同的dyno中启动服务器,因此可以通过相同的localhost网络
  • 访问它

部署应用程序,现在可以正常运行

Deployed heroku app

下面是一个示例工作应用程序供您检查,该应用程序将暂停一段时间,然后我将其删除

https://soproxyapp.herokuapp.com/