【问题标题】:res.sendFile absolute pathres.sendFile 绝对路径
【发布时间】:2014-10-17 06:37:45
【问题描述】:

如果我做一个

res.sendfile('public/index1.html'); 

然后我收到服务器控制台警告

表示不推荐使用res.sendfile:改用res.sendFile

但它在客户端工作正常。

但是当我把它改成

res.sendFile('public/index1.html');

我收到一个错误

TypeError: path must be absolute or specified root to res.sendFile

并且index1.html 未呈现。

我无法弄清楚绝对路径是什么。我的public 目录与server.js 处于同一级别。我正在使用server.js 执行res.sendFile。我还声明了app.use(express.static(path.join(__dirname, 'public')));

添加我的目录结构:

/Users/sj/test/
....app/
........models/
....public/
........index1.html

这里要指定的绝对路径是什么?

我正在使用 Express 4.x。

【问题讨论】:

  • 如果您使用express.static 中间件为您的公共目录提供服务,为什么需要res.sendFile 发送public/index1.html
  • 我正在从app.get('/', function(req, res){res.sendFile("...")}) 内部调用res.sendFile 按需发送。

标签: node.js express path


【解决方案1】:

express.static 中间件与res.sendFile 是分开的,因此使用public 目录的绝对路径对其进行初始化不会对res.sendFile 做任何事情。您需要直接对res.sendFile 使用绝对路径。有两种简单的方法:

  1. res.sendFile(path.join(__dirname, '../public', 'index1.html'));
  2. res.sendFile('index1.html', { root: path.join(__dirname, '../public') });

注意: __dirname 返回当前执行脚本所在的目录。在您的情况下,看起来server.jsapp/ 中。因此,要到达public,您需要先退出一层:../public/index1.html

注意: path is a built-in module 必须是 required 才能使上述代码工作:var path = require('path');

【讨论】:

  • res.sendFile('../public/index.html', {root: __dirname}); 也可以,而且更短
  • 使用 express 和 webstorm ide:console.log(path.join(__dirname, '../public', 'index.html')); 没有错误,但 res.sendFile(path.join(__dirname, '../public', 'index.html')); 仅适用于 var path = require('path');
  • 有没有办法预先定义绝对路径以便在sendFile中使用?
  • res.sendFile('../public/index.html', {root: __dirname}); 不再起作用,因为它返回 403 Forbidden 由于超出根目录。请改用res.sendFile('public/index.html', {root: path.dirname(__dirname)});
【解决方案2】:

试试这个吧:

res.sendFile('public/index1.html' , { root : __dirname});

这对我有用。 root:__dirname 将获取上面示例中 server.js 所在的地址,然后到达 index1.html(在这种情况下)返回的路径是到达 public 文件夹所在的目录。

【讨论】:

  • 为什么没有记录这个选项?
【解决方案3】:
res.sendFile( __dirname + "/public/" + "index1.html" );

__dirname 将管理当前执行脚本 (server.js) 所在目录的名称。

【讨论】:

  • 这个解决方案非常简单。感谢您的帮助。我想知道为什么人们建议使用“路径”包来做同样的事情。
  • @TheThird 我猜,使用path 使其独立于操作系统。
【解决方案4】:

另一种方法是编写更少的代码。

app.use(express.static('public'));

app.get('/', function(req, res) {
   res.sendFile('index.html');
});

【讨论】:

  • 这会产生“TypeError: path must be absolute or specified root to res.sendFile”
【解决方案5】:

我试过了,效果很好。

app.get('/', function (req, res) {
    res.sendFile('public/index.html', { root: __dirname });
});

【讨论】:

    【解决方案6】:

    另一种尚未列出但对我有用的替代方法是简单地将 path.resolve 与单独的字符串或仅与整个路径一起使用:

    // comma separated
    app.get('/', function(req, res) {
        res.sendFile( path.resolve('src', 'app', 'index.html') );
    });
    

    或者

    // just one string with the path
    app.get('/', function(req, res) {
        res.sendFile( path.resolve('src/app/index.html') );
    });
    

    (节点 v6.10.0)

    创意来自https://stackoverflow.com/a/14594282/6189078

    【讨论】:

      【解决方案7】:

      process.cwd() 返回项目的绝对路径。

      然后:

      res.sendFile( `${process.cwd()}/public/index1.html` );
      

      【讨论】:

        【解决方案8】:

        如果您想设置一次并在任何地方使用它,只需配置您自己的中间件。在设置应用程序时,请使用以下内容在响应对象上定义新函数:

        app.use((req, res, next) => {
          res.show = (name) => {
            res.sendFile(`/public/${name}`, {root: __dirname});
          };
          next();
        });
        

        然后按如下方式使用:

        app.get('/demo', (req, res) => {
          res.show("index1.html");
        });
        

        【讨论】:

          【解决方案9】:

          根据其他答案,这是一个如何完成最常见要求的简单示例:

          const app = express()
          app.use(express.static('public')) // relative path of client-side code
          app.get('*', function(req, res) {
              res.sendFile('index.html', { root: __dirname })
          })
          app.listen(process.env.PORT)
          

          这也是respond with index.html on every request 的一种简单方法,因为我使用星号* 来捕获在您的静态(公共)目录中找不到的所有文件;这是网络应用程序最常见的用例。更改为 / 以仅返回根路径中的索引。

          【讨论】:

          • 不错。简洁明了。
          【解决方案10】:

          我使用 Node.Js 并且遇到了同样的问题...我解决了只是在每个脚本的开头添加一个“/”并链接到一个 css 静态文件。

          之前:

          <link rel="stylesheet" href="assets/css/bootstrap/bootstrap.min.css">
          

          之后:

          <link rel="stylesheet" href="/assets/css/bootstrap/bootstrap.min.css">
          

          【讨论】:

          • 您必须设置 express 静态服务器才能使其工作
          【解决方案11】:

          您可以使用 send 代替 sendFile,这样您就不会遇到错误! 这对你有帮助!

          fs.readFile('public/index1.html',(err,data)=>{
          if(err){
            consol.log(err);
          }else {
          res.setHeader('Content-Type', 'application/pdf');
          

          用于告诉浏览器您的响应是 PDF 类型

          res.setHeader('Content-Disposition', 'attachment; filename='your_file_name_for_client.pdf');
          

          如果您希望该文件在用户下载后立即在同一页面上打开。请在上面的代码中写入“内联”而不是附件。

          res.send(data)
          

          【讨论】:

            【解决方案12】:

            以下对我有用

            res.sendFile(path.resolve(__dirname,'./path_to_file_from_current_directory'));
            

            【讨论】:

              猜你喜欢
              • 2015-01-14
              • 2016-03-16
              • 2016-09-29
              • 1970-01-01
              • 2018-02-04
              • 1970-01-01
              • 2012-01-11
              • 2010-09-15
              相关资源
              最近更新 更多