如何使用 Iron 路由器提供静态内容(图像、字体等)

Posted

技术标签:

【中文标题】如何使用 Iron 路由器提供静态内容(图像、字体等)【英文标题】:How to serve static content (images, fonts etc.) using iron router 【发布时间】:2014-02-15 22:56:32 【问题描述】:

我刚开始在流星上使用铁路由器。我需要在主页上显示图像。我能够使用客户端路由为“家”配置路由。对于静态文件,我尝试 google 并发现添加服务器端路由可能会有所帮助。因此,我在服务器的 router.js 上添加了以下代码。

Router.map(function() 
    this.route('files', 
        path: '/files/:path(*)',
        action: function() 
            var path = this.params.path;

            console.log('will serve static content @ '+path);
            this.response.sendfile(path);
        
    );
);

当我尝试访问http://localhost:3000/files/someImage.png 时,它说没有为/files/someImage.png 定义路由。难道我做错了什么?有没有其他方法可以使用 Iron Router 提供静态文件?

【问题讨论】:

注意不要使用这个来服务大文件,它不能很好地处理大文件。 【参考方案1】:

您可以将文件放在您的public 目录下,而不是执行所有这些操作。如果添加文件:

myApp/public/images/kitten.png

您可以从您的模板中访问它,例如:

<img src="/images/kitten.png">

不需要任何路线来完成这项工作。

小心忽略前导斜线。

<img src="images/kitten.png">

上面的示例将在 /books 等***路由中工作,这很容易错过,但在 /books/pages 上失败。

【讨论】:

在迁移到 Iron-router 之前,这就是我用来管理静态文件的方式。但是,现在我的应用程序变成了多页,我转向了 Iron-router。 Iron 路由器将来自 /images/kitten.png 的请求视为另一条路由,并在找不到时抛出 404。因此,我的问题是如何在运动后提供任何静态内容。 当时 Iron-router 的配置方式有问题。在没有看到整个配置的情况下,我无法说出它是什么,但您可以尝试删除所有路由并一次添加一条,直到找到问题为止。 我正在尝试使用iron router doc 中提到的概念。截至目前,我没有任何其他路线。甚至没有客户端路由。 那么可能是另一个包。反向调试问题可能很有用 - 从一个空白项目开始并添加代码和包,直到你看到它崩溃。如果你像这样系统地工作,我相信你会发现问题的。 好的,不,我认为这是正确的行为。链接器分支进入后,public 被编译到一个带有清单的文件夹中:program.json,其中包含哈希、位置等,因此在部署后添加的文件不再动态可用。【参考方案2】:

您可能只需要确保路由位于客户端和服务器上都可见的公共区域(此路由实际上在服务器上运行)并指定where: 'server'。此外,我们需要从磁盘加载实际文件,这意味着我们需要服务器上文件的实际路径,并且我们需要加载“fs”。

var fs = Npm.require('fs');

Router.map(function() 
  this.route('files', 
    path: '/files/:path(*)',
    where: 'server',
    action: function() 
        var path = this.params.path;
        var basedir = '~/app/';

        console.log('will serve static content @ '+ path);

        var file = fs.readFileSync(basedir + path);

      var headers = 
        'Content-type': 'image/png',
        'Content-Disposition': "attachment; filename=" + path
      ;

      this.response.writeHead(200, headers);
      return this.response.end(file);
    
  );
);

一些注意事项:您可能应该将实际下载代码移动到仅服务器函数中,然后调用它,将响应传递给函数。

您还应该对路径进行一些验证,以免任何人在您的服务器上随意下载文件。

此外,这是明确设置内容类型,您可能希望为图像执行此操作,但可能不适用于其他内容类型。对于泛型类型,您可以将其设置为 application/octet-stream

当然,如前所述,如果您的唯一目标是在部署时提供一些静态内容,您应该只使用/public 目录。

【讨论】:

【参考方案3】:

这是一个bug in iron-router,他们说它已修复,但我仍然遇到这个问题,其他人已经报告了那个 github 问题,它仍然是一个问题。

编辑:它似乎适用于直接位于 /public 中的文件,但不适用于 /public 文件夹中的文件。

【讨论】:

我在 /public/images/ 中有 jpg 文件,并使用 有效。

以上是关于如何使用 Iron 路由器提供静态内容(图像、字体等)的主要内容,如果未能解决你的问题,请参考以下文章

使用 Iron Router,“未定义路由器”

如何使用 Meteor 模板助手编辑 Iron-Router 中作为参数传递的值?

使用 Iron Router 路由到 Meteor autoform 提交的新数据?

Meteor js,iron-router,在服务器端使用 Route.go('...') 进行单元测试不起作用

Iron Router 部署时显示启动页面,在本地工作正常

使用 Iron:router 将某些功能或事件的输出返回到 Meteor 中的某个新页面或模板