我需要设置一些 VPS 来提供静态内容(许多小文件)。我计划为此使用 Nginx,并希望对其进行设置,以便我们能够相对轻松地进行横向扩展。要求是:
- 许多文件(至少数十万)。
- 小文件大小(小于 10KB)。
- 相邻服务器上的应用程序不断添加文件。
- 新文件必须立即可供所有 Nginx 服务器使用。
我目前的计划是:
- 拥有一个带有包含所有文件的 NFS 共享的“主”服务器。
- 生成新文件的应用程序仅与 master 交互。
- 让多个 Nginx 服务器挂载此 NFS 共享。
- 跨 Nginx 实例的负载平衡。
一个明显的问题是“主”服务器是单点故障(对此有什么补救措施吗?)。 还有其他我忽略的潜在问题吗?这里是否存在无法以这种方式很好地扩展的元素?有人会建议另一种方法吗?
关于内存要求,我假设我应该尽可能多地给每个 Nginx 服务器,以便可以缓存热文件(通过操作系统?Nginx?)而不必不断地从 NFS 共享请求。
最后,我疯了不使用 CDN 吗?
NFS 不缩放。它增加了每个请求的延迟,最终会成为一个太大的瓶颈。我们在工作中遇到了类似的问题,但有照片(因此,文件更大)并编写了我们自己的软件来分片和分发它们。对于像您这样的几 GB 文件,您可以通过对所有服务器执行 HTTP PUT 并在服务器离线时执行重新同步来完成上传过程。
或者以另一种方式解决它:拥有一个(一组)中央服务器,其中包含所有文件和缓存反向代理(squid、pound、varnish),这些服务器实际上为客户提供文件。
而且你不使用 CDN 并不疯狂。如果你不调查它是否值得,你就是疯了:-)
使用cachefilesd(和最近的 linux 内核,带有 cachefs)将 NFS 文件缓存到本地 HD。这样,nfs 中的每次读取都会将文件复制到 /var/cache/fs 目录,下一次读取将从那里传送,内核会在 nfs 中检查内容是否仍然有效。
这样你就可以拥有一个中央 NFS,但不会损失本地文件的性能
Cachefilesd 将在可用大小/inode 达到配置级别时负责清理旧文件,因此您可以提供来自 NFS 的不常见数据和来自 HD 的常见请求
设置好之后,使用清漆来传递内容,它会缓存最常用的请求,从而节省大量对 nginx/NFS 的请求。
这是一个小的 cachefilesd howto。
我建议为此获得一个(可能是专用的)服务器,而不是使用多个单独的 VPS 服务器和
nginx
通过nfs
. 如果您正在考虑使用 VPS 和 NFS,我认为您对可伸缩性的担忧是不合理的。nginx
几乎所有的缓存都是通过机器的文件系统完成的,所以,如果你打算为此使用 nginx,你必须确保拥有一个具有出色文件系统性能和缓存的操作系统。确保你的内核有足够的vnodes
等等。如果您仍在考虑单独的机器(如上所述,我的建议是使用一台机器和一个 nginx),那么调查
varnish
. Varnish 在虚拟内存中进行所有缓存,因此,您不必担心较小文件的 vnode 或缓存效率低下。因为它使用虚拟内存,它的缓存可以和物理内存+交换一样大。我强烈建议不要吃鱿鱼。如果您想知道原因,只需查看一个 varnish 演示文稿,它描述了为什么虚拟内存是加速代理的最佳方式。但是 varnish 只做加速,所以如果你使用一个带有静态文件和良好文件系统缓存的主机(例如 FreeBSD),那么 nginx 可能是最好的选择(否则,使用 varnish,你最终会得到相同的内容在多个地方双重缓存)。
任何生产服务器设计都不能有单一故障点。
因此你至少需要两台机器作为负载均衡器,你可以使用像HAProxy这样的负载均衡器。它具有您可能需要的所有功能,请查看此 HAproxy 架构示例。您将面临的实际请求负载是 NFS 存储系统上的“大量小文件请求”。
缓存的数量取决于您的资源和客户端请求。HAProxy 可以配置为添加或删除缓存服务器。
NFS 文件请求是要求最高的操作,因此您需要在“缓存”机器中使用一种缓存形式。
缓存服务器有 3 个存储层,您希望最常见的文件在本地可用,最好在 RAM 中。
这可以通过 nginx、squid 或 varnish 来解决。
nginx 可以使用SlowFs缓存本地文件,这是一个很好的慢 fs 教程
带有此系统的 Nginx 将文件存储在本地文件系统磁盘中并从那里提供它们。您可以使用 PURGE 从缓存中删除修改过的文件。它就像在请求字符串中使用“purge”一词发出请求一样简单。
具有慢速 FS 的 Nginx 使用操作系统提供的 ram,增加操作系统可用的 nginx ram 将提高请求的平均速度。但是,如果您的存储超过服务器内存大小,您仍然需要将文件缓存在本地文件系统中。
Nginx 是一个多用途服务器,它不是非常快。至少不如 squid 或 varnish 等静态缓存服务器快。但是,如果您的问题是 NFS,那么 Nginx 可以解决 90% 的问题。
Squid 和 Varnish 非常快,并且具有从缓存中删除文件的 API。
Squid 使用 ram 和本地文件系统进行缓存。Varnish 使用 ram 作为缓存。
Squid 很旧,大多数基准测试表明清漆比 squid 调度静态文件更快。
然而,当 varnish 崩溃时,内存缓存丢失,整个服务器可能需要很长时间才能恢复。因此崩溃是清漆的大问题。
Squid 可以更好地处理崩溃,因为它也使用本地存储磁盘,并且可以从那里重新启动一些缓存而不是使用 NFS。
为了获得服务于小型静态文件的最佳性能,您可以使用 Nginx 和 Squid 或 Varnish。
其他文件大小需要不同的方法。