Nodejs 快递,Heroku CORS

Posted

技术标签:

【中文标题】Nodejs 快递,Heroku CORS【英文标题】:Nodejs express, Heroku CORS 【发布时间】:2017-10-10 11:10:51 【问题描述】:

我的应用程序的服务器端是使用带有 express 的 Node 构建的,

它在本地运行良好,但现在我已上传到 Heroku

我收到了 CORS 错误,尽管我已经在应用程序中处理了它

index.js

var express = require('express');
var bodyParser = require('body-parser');

var http = require('http');
var path = require('path');
var twit = require('twitter');
var app = express();
var port = process.env.PORT || 3000;

var twitter = new twit(
  consumer_key:  'myKey',
  consumer_secret: 'mySecret',
  access_token_key: 'myKey',
  access_token_secret: 'mySecret'
);
app.set('port', (port));
var server = http.createServer(app).listen(port, function() 
  console.log('Server listening on port ' + port);
);
app.use(bodyParser.urlencoded(extended: true));

app.use(function (req, res, next) 
    res.setHeader('Access-Control-Allow-Origin', '*');
    res.setHeader('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept');
    res.setHeader('Access-Control-Allow-Methods', 'POST, GET, PATCH, DELETE, OPTIONS');
    next();
);

app.get('/gettweets', function (req, res) 
  twitter.get('statuses/user_timeline',  id: 23445555, count: 3 , function(err, tweets, response) 
      if (!err) 
         res.json(tweets);
      
      else 
        return res.status(500).json(
          title: 'An error has occured',
          error: err
        )
      
    )
)

在我的 http 调用中

export class SocialService 

  private url = 'https://myserver.herokuapp.com/';
  constructor(private http: Http)  

  initialise()
    var headers = new Headers();
        headers.append('Content-Type', 'application/json');

    return this.http.get(this.url+'gettweets', headers: headers)
        .map((response: Response) => 
        console.log(response.json());
          return response.json();
        )
        .catch((error: Response) =>  Observable.throw(error.json()) )

  

以及来自 Heroku 的构建日志

-----> Node.js app detected
-----> Creating runtime environment

       NPM_CONFIG_LOGLEVEL=error
       NPM_CONFIG_PRODUCTION=true
       NODE_VERBOSE=false
       NODE_ENV=production
       NODE_MODULES_CACHE=true
-----> Installing binaries
       engines.node (package.json):  unspecified
       engines.npm (package.json):   unspecified (use default)

       Resolving node version 6.x via semver.io...
       Downloading and installing node 6.10.3...
       Using default npm version: 3.10.10
-----> Restoring cache
       Loading 2 from cacheDirectories (default):
       - node_modules
       - bower_components (not cached - skipping)
-----> Building dependencies
       Installing node modules (package.json)
-----> Caching build
       Clearing previous node cache
       Saving 2 cacheDirectories (default):
       - node_modules
       - bower_components (nothing to cache)
-----> Build succeeded!
-----> Discovering process types
       Procfile declares types     -> (none)
       Default types for buildpack -> web
-----> Compressing...
       Done: 17.8M
-----> Launching...
       Released v5
       https://myserver.herokuapp.com/ deployed to Heroku

浏览器出错

XMLHttpRequest cannot load https://myserver.herokuapp.com/gettweets.
Response to preflight request doesn't pass access control check:
No 'Access-Control-Allow-Origin' header is present on the requested resource.
Origin 'http://localhost:4200' is therefore not allowed access. The response had HTTP status code 503.

这是我从 Heroku 得到的错误,与我请求的路径有关

2017-05-11T12:54:05.960151+00:00 heroku[router]: at=error code=H10 desc="App crashed" method=OPTIONS path="/gettweets" host=maleonserver.herokuapp.com request_id=5c052790-67df-4677-be8b-14cc2bc71292 fwd="5.67.244.130" dyno= connect= service= status=503 bytes= protocol=https

【问题讨论】:

您的应用似乎在 OPTIONS 请求(这是一个 CORS 预检)上崩溃,这很奇怪,因为我认为不会为 GET 请求发出预检请求。跨度> @robertklep heroku 可能会添加额外的保护层吗?去检查一下 @echonax 好吧,是浏览器决定是否应该发出预检请求。我无法想象 Heroku 会自己发出这样的请求。 【参考方案1】:

尝试同时允许凭据:

app.use(function(req, res, next) 
    res.header("Access-Control-Allow-Origin", '*');
    res.header("Access-Control-Allow-Credentials", true);
    res.header('Access-Control-Allow-Methods', 'GET,PUT,POST,DELETE,OPTIONS');
    res.header("Access-Control-Allow-Headers", 'Origin,X-Requested-With,Content-Type,Accept,content-type,application/json');
    next();
);

编辑:

如果你想在你的 Heroku 应用中进行本地 http 调用; 改变

private url = 'https://myserver.herokuapp.com/';

private url = '/';

【讨论】:

他们似乎正在通过请求跨域(来源为http://localhost:4200)来测试CORS是否有效。 @robertklep 哦,你的意思是 OP 正在尝试从本地应用程序向部署在 heroku 上的应用程序发出请求? 是的,在我看来就是这样 :D 是的,我正在尝试从本地主机访问它,我添加了凭据部分但仍然没有,还更新了问题 @Roy 只是想知道,这里提供的解决方案对您有用吗?【参考方案2】:

您好,我发现这是因为 Heroku 只会从您的依赖项中安装包

我需要的是我的 devDependencies,所以一旦我作为依赖项重新安装它就可以了!

【讨论】:

【参考方案3】:

另一个可能的原因是缺少 .env 变量。部署 heroku 服务器时,所有 .env 变量都必须通过 heroku 的 config vars 设置。

如果路由需要缺少 .env,由于某种原因,它会作为 CORS 错误返回。

在我的例子中,jsonwebtoken 正在寻找 process.env.secretkey,所以所有调用 jsonwebtoken 的路由都返回了 CORS 错误,而不需要它的路由工作得很好。

【讨论】:

【参考方案4】:

我遇到了同样的问题。我在 Heroku 上遇到了 cors 错误。原因是我的服务器在 Heroku 上产生了一些错误。检查我在 Heroku 上的应用程序日志,发现未定义生产环境变量的错误。所以我定义了我的环境变量和宾果游戏!没有进一步的 cors 错误。

【讨论】:

以上是关于Nodejs 快递,Heroku CORS的主要内容,如果未能解决你的问题,请参考以下文章

快递 CORS 不工作

Cors 不适用于 XMLhttprequest 节点/快递

无法在我的快递应用中解决 CORS 政策

NodeJS + Keycloak 没有快递

JQuery POST 到 NODEJS(快递)

javascript nodejs主路由文件示例(快递)