【问题标题】:How can I support cors when using restify使用restify时如何支持cors
【发布时间】:2012-12-29 14:34:51
【问题描述】:

我有一个使用 restify 模块创建的 REST api,我想允许跨域资源共享。最好的方法是什么?

【问题讨论】:

标签: node.js cors restify


【解决方案1】:
const restify = require('restify');
const corsMiddleware = require('restify-cors-middleware');

const cors = corsMiddleware({
  origins: ['*']
});

const server = restify.createServer();
server.pre(cors.preflight);
server.use(cors.actual);

server.get('/api/products', (request, response) => {
  response.json({ message: 'hello REST API' });
});

server.listen(3000, () => console.info(`port 3000`));

... 是一种蛮力解决方案,但您应该非常小心。

【讨论】:

    【解决方案2】:

    我使用的是 Restify 7.2.3 版本,这段代码非常适合我。 您需要安装 restify-cors-middleware 插件。

    const corsMiddleware = require('restify-cors-middleware')
    
    const cors = corsMiddleware({
        preflightMaxAge: 5, //Optional
        origins: ['http://ronnie.botsnbytes.com', 'http://web.myapp.com'],
        allowHeaders: ['API-Token'],
        exposeHeaders: ['API-Token-Expiry']
    })
    
    server.pre(cors.preflight)
    server.use(cors.actual)
    

    【讨论】:

      【解决方案3】:

      这适用于我的 restify 7

      server.pre((req, res, next) => {
      
          res.header('Access-Control-Allow-Origin', req.header('origin'));
          res.header('Access-Control-Allow-Headers', req.header('Access-Control-Request-Headers'));
          res.header('Access-Control-Allow-Credentials', 'true');
          // other headers go here..
      
          if(req.method === 'OPTIONS') // if is preflight(OPTIONS) then response status 204(NO CONTENT)
              return res.send(204);
      
          next();
      
      });
      

      【讨论】:

        【解决方案4】:
           const cors = require('cors');
        
        
           const server = restify.createServer();
        
           server.use(cors());
        

        这对我有用

        【讨论】:

          【解决方案5】:

          如果有人在 2018 年 2 月遇到此问题,似乎存在已引入的错误,我无法让 restify-cors-middleware 工作。

          我现在正在使用这个解决方法:

          server.pre((req, res, next) => {
             res.header("Access-Control-Allow-Origin", "*");
             next();
          });
          

          【讨论】:

          • 这是目前在 07/2021 有效的唯一解决方案,其他一切都已过时或有错误,也是“新”中间件。 restify 是一团糟,我建议任何新手不要使用它。
          • 所以不只是我对插件有问题!唷。
          • 顺便说一句,当我使用它时,我的端点上会出现 404。 :(
          【解决方案6】:

          以前的大多数答案都来自 2013 年,并且使用了已弃用的示例! 解决方案(至少在 2017 年)如下:

          npm install restify-cors-middleware
          

          然后在你的服务器 javascript 文件中:

          var corsMiddleware = require('restify-cors-middleware');
          
          var cors = corsMiddleware({
            preflightMaxAge: 5,
            origins: ['*']
          });
          
          var server = restify.createServer();
          
          server.pre(cors.preflight);
          server.use(cors.actual);
          

          并添加任何其他适合您的选项。我的用例是创建一个 localhost 代理来解决开发过程中的浏览器 CORS 问题。仅供参考,我使用 restify 作为我的服务器,但是我从服务器(以及到服务器)的 POST 与 Axios 一起使用。我的偏好在那里。

          npm listing for restify-cors-middleware

          【讨论】:

          • 不起作用,它被窃听,损坏或其他任何东西
          【解决方案7】:

          CORS 插件已弃用,取而代之的是 https://github.com/Tabcorp/restify-cors-middleware。 (来源:https://github.com/restify/node-restify/issues/1091。)

          下面是一个关于如何使用的示例代码

          const corsMiddleware = require('restify-cors-middleware')
          
          const cors = corsMiddleware({
            preflightMaxAge: 5, //Optional
            origins: ['http://api.myapp.com', 'http://web.myapp.com'],
            allowHeaders: ['API-Token'],
            exposeHeaders: ['API-Token-Expiry']
          })
          
          server.pre(cors.preflight)
          server.use(cors.actual)
          

          【讨论】:

            【解决方案8】:

            Restify 最新版本提供a plugin to handle CORS

            所以你现在可以像这样使用它:

            server.use(restify.CORS({
            
              // Defaults to ['*'].
              origins: ['https://foo.com', 'http://bar.com', 'http://baz.com:8081'], 
            
              // Defaults to false.
              credentials: true,
            
              // Sets expose-headers.
              headers: ['x-foo']   
            
            }));
            

            【讨论】:

            • 哪个版本的restify? (你说“restify 的最新版本......”)
            • @Jean-MichelTrayaud:这对我不起作用...我得到 Origin 192.168.2.124 is not allowed by Access-Control-Allow-Origin。任何帮助将不胜感激:)
            • 认为我们需要更多信息... GET 或 POST 第一次(POST 对 CORS 来说真的是一场噩梦)
            • 单独使用 restify.CORS() 对 Restify 3.0.3 进行测试就足够了。不需要restify.fullResponse(),但是在请求中,需要指定Origin header。相关代码注释见cors.js
            • 这个插件有一个奇怪的行为。如果源与数组之一匹配,它将在响应标头中返回匹配的源,这是预期的。但是,如果它不匹配,它将返回一个通配符。如果您发出经过认证的 cors 请求,它仍然会失败,因为来源不能是 *.但是为什么要返回 * 呢?
            【解决方案9】:

            为了启用 CORS 进行基本身份验证,我执行了以下操作。在使用 .pre 方法而不是 .use 方法之前,它不起作用

            server.pre(restify.CORS({
              origins: ['https://www.allowedip.com'],  // defaults to ['*']
              credentials: true,
              headers: ['X-Requested-With', 'Authorization']
            }));
            server.pre(restify.fullResponse());
            
            function unknownMethodHandler(req, res) {
                if (req.method.toLowerCase() === 'options') {
                  var allowHeaders = ['Accept', 'Accept-Version', 'Content-Type', 'Api-Version', 'Origin', 'X-Requested-With', 'Authorization']; // added Origin & X-Requested-With & **Authorization**
            
                  if (res.methods.indexOf('OPTIONS') === -1) res.methods.push('OPTIONS');
            
                  res.header('Access-Control-Allow-Credentials', true);
                  res.header('Access-Control-Allow-Headers', allowHeaders.join(', '));
                  res.header('Access-Control-Allow-Methods', res.methods.join(', '));
                  res.header('Access-Control-Allow-Origin', req.headers.origin);
            
                  return res.send(200);
               } else {
                  return res.send(new restify.MethodNotAllowedError());
               }
            }
            
            server.on('MethodNotAllowed', unknownMethodHandler);
            

            【讨论】:

            • 错字警告:最后一个 else 需要一个额外的括号
            【解决方案10】:

            这对我有用:

            var restify = require('restify');
            
            var server = restify.createServer();
            
            server.use(restify.CORS());
            
            server.opts(/.*/, function (req,res,next) {
                res.header("Access-Control-Allow-Origin", "*");
                res.header("Access-Control-Allow-Methods", req.header("Access-Control-Request-Method"));
                res.header("Access-Control-Allow-Headers", req.header("Access-Control-Request-Headers"));
                res.send(200);
                return next();
            });
            
            server.get('/test', function (req,res,next) {
            
                res.send({
                    status: "ok"
                });
                return next();
            });
            
            server.listen(3000, function () {
                console.log('%s listening at %s', server.name, server.url);
            });
            

            【讨论】:

            • 由于某种原因,其他答案对我不起作用。你的做到了。我想知道这是否与对最新版本的 restify 所做的更改有关。
            【解决方案11】:

            我在我的 restify 基础应用上这样做:

            //setup cors
            restify.CORS.ALLOW_HEADERS.push('accept');
            restify.CORS.ALLOW_HEADERS.push('sid');
            restify.CORS.ALLOW_HEADERS.push('lang');
            restify.CORS.ALLOW_HEADERS.push('origin');
            restify.CORS.ALLOW_HEADERS.push('withcredentials');
            restify.CORS.ALLOW_HEADERS.push('x-requested-with');
            server.use(restify.CORS());
            

            您需要先使用restify.CORS.ALLOW_HEADERS.push 方法将您想要的标头推送到restify,然后使用CORS中间件启动CORS功能。

            【讨论】:

            • 我正在使用 Restify v2.8.3,其中一些标头已默认启用。查看./node_modules/restify/lib/plugins/cors.js 中的默认设置。
            【解决方案12】:

            这对我来说就足够了:

            var server = restify.createServer();
            server.use(restify.fullResponse());
            server.get('/foo',  respond(req, res, next) {
               res.send('bar');
               next();
            });
            

            没有必要server.use(restify.CORS()); 此外,似乎server.use() 调用必须在server.get() 调用之前才能工作。

            【讨论】:

              【解决方案13】:

              这对我有用:

              function unknownMethodHandler(req, res) {
                if (req.method.toLowerCase() === 'options') {
                    console.log('received an options method request');
                  var allowHeaders = ['Accept', 'Accept-Version', 'Content-Type', 'Api-Version', 'Origin', 'X-Requested-With']; // added Origin & X-Requested-With
              
                  if (res.methods.indexOf('OPTIONS') === -1) res.methods.push('OPTIONS');
              
                  res.header('Access-Control-Allow-Credentials', true);
                  res.header('Access-Control-Allow-Headers', allowHeaders.join(', '));
                  res.header('Access-Control-Allow-Methods', res.methods.join(', '));
                  res.header('Access-Control-Allow-Origin', req.headers.origin);
              
                  return res.send(204);
                }
                else
                  return res.send(new restify.MethodNotAllowedError());
              }
              
              server.on('MethodNotAllowed', unknownMethodHandler);
              

              我这段代码取自https://github.com/mcavage/node-restify/issues/284

              【讨论】:

              • 这对我有用,但我还需要在调用 server.on(...) 之前添加 server.use(restify.fullResponse());
              • 这几乎对我有用。我不得不使用server.opts({path: '/customers', version: '0.0.1'}, unknownMethodHandler);。使用on,该方法没有被调用。
              • 这避免了来自 restify 的 404“方法不允许”响应 OPTIONS 预检请求。 CORS 跨域问题必须单独处理——请参阅上面的“crossOrigin 函数以解决该问题。
              【解决方案14】:

              您必须设置服务器以设置跨源标头。不知道有没有内置的使用函数,所以我自己写了。

              server.use(
                function crossOrigin(req,res,next){
                  res.header("Access-Control-Allow-Origin", "*");
                  res.header("Access-Control-Allow-Headers", "X-Requested-With");
                  return next();
                }
              );
              

              我从本教程中找到了这个。 http://backbonetutorials.com/nodejs-restify-mongodb-mongoose/

              【讨论】:

              • 由于这个答案已经存在了一段时间并且人们在其他问题下面询问 cmets 中的版本,我想报告这个答案对我仍然有效 Restify 4.1.0。
              • 我使用的是restify 5.0.1,找不到关于CORS的解决方案
              • 我用 6.0.1
              猜你喜欢
              • 2020-01-01
              • 2013-09-22
              • 2019-06-09
              • 2015-11-02
              • 2013-04-22
              • 2013-12-30
              • 2015-06-16
              • 2014-09-14
              相关资源
              最近更新 更多