如何使用swagger-ui在Express Server中启用CORS allow-origin标头

时间:2019-04-04 08:46:25

标签: express cors swagger-ui swagger-2.0 access-control

我的API服务器没有更改或覆盖Access-Control-Allow-Origin标头。

我有一个带有Express / Swagger-UI API的Angular 2+应用程序。

API中的Access-Control-Allow-Origin标头不能为*,因为我在请求中使用了“ withCredentials”,并在浏览器中触发了错误。

我已经使用'cors'来设置CORS标头。像这样:

'use strict';

var configuration = require('./configuration');
var SwaggerExpress = require('swagger-express-mw');
var app = require('express')();
var mongoose = require('mongoose');
var bluebird = require('bluebird');
var bodyParser = require('body-parser');
var jwt = require('jsonwebtoken');
var compression = require('compression');
var cors = require('cors');

app.use(bodyParser.json({ limit: '50mb' }));
app.use(compression());

SwaggerExpress.create(config, function(err, swaggerExpress) {
  if (err) { throw err; }

  swaggerExpress.register(app);
  var port = process.env.PORT || 10010;
  mongoose.Promise = bluebird;
  mongoose.connect(appConfig.dbConection());
  mongoose.connection.on('error', console.error.bind(console, 'connection error: '));
  mongoose.set('debug', true);
  mongoose.connection.once('open', function() {
    app.listen(port);
  })
});
const swaggerUi = require('swagger-ui-express');
const YAML = require('yamljs');
const swaggerDocument = YAML.load('./api/swagger/swagger.yaml');

app.use('/api-docs', swaggerUi.serve, swaggerUi.setup(swaggerDocument));
var allowedOrigins = ['http://localhost:4200', 'http://127.0.0.1:10010'];
app.use(cors({
    origin: (origin, callback) => {
        if (!origin) return callback(null, true);
        if (allowedOrigins.indexOf(origin) === -1) {
            return callback(new Error('The CORS policy for this site does not allow the specified Origin'), false);
        }
        return callback(null, true);
    },
    exposedHeaders: ['Origin', 'X-Requested-With', 'Content-Type', 'Accept', 'Authorization', 'api_key', 'x-api-key'],
    credentials: true
}));

Access-Control-Allow-Origin应该与允许的主机数组匹配。

当我从浏览器调用API时,它首先发出一个看起来正确的OPTIONS请求,如下所示:

Request URL: http://localhost:10010/v1/loginApp
Request Method: OPTIONS
Status Code: 204 No Content
Remote Address: [::1]:10010
Referrer Policy: no-referrer-when-downgrade

Access-Control-Allow-Credentials: true
Access-Control-Allow-Headers: x-api-key
Access-Control-Allow-Methods: GET,HEAD,PUT,PATCH,POST,DELETE
Access-Control-Allow-Origin: http://localhost:4200
Access-Control-Expose-Headers: Origin,X-Requested-With,Content-Type,Accept,Authorization,api_key,x-api-key
Connection: keep-alive
Content-Length: 0
Date: Thu, 04 Apr 2019 08:25:53 GMT
Vary: Origin, Access-Control-Request-Headers
X-Powered-By: Express

但是随后发出GET / POST请求,然后再次具有默认标题:

Request URL: http://localhost:10010/v1/loginApp
Request Method: GET
Status Code: 200 OK
Remote Address: [::1]:10010
Referrer Policy: no-referrer-when-downgrade

Access-Control-Allow-Credentials: true
Access-Control-Allow-Origin: *
Access-Control-Expose-Headers: Origin,X-Requested-With,Content-Type,Accept,Authorization,api_key,x-api-key
Content-Length: 770
Content-Type: application/json; charset=utf-8
Date: Thu, 04 Apr 2019 08:25:53 GMT
ETag: W/"302-BwX5DjK/lUY+ueP6UZ9TgWOTw/s"
Vary: Origin
X-Powered-By: Express

我认为某些内容(可能是swagger-UI)正在覆盖我的标头配置,但我无法弄清楚。

2 个答案:

答案 0 :(得分:0)

您需要 Swagger GET / POST处理程序之前注册CORS中间件。

OPTIONS请求成功,因为Swagger没有注册OPTIONS处理程序,因此请求到达了中间件。

在Swagger处理程序接受请求之前,GET / POST请求失败,然后该请求到达CORS中间件。

app.use(cors({...移动到之前 app.use('/api-docs', swaggerUi...

答案 1 :(得分:0)

swagger-express-mw似乎内置了CORS支持,请参阅swagger_controllers中的config/default.yaml。我遇到了同样的问题,并通过从其中删除cors来解决了这个问题。


像您一样,我怀疑它正在覆盖Access-Control-Allow-Origin标头,但没有时间对其进行正确检查。