Facebook图片存储系统Haystack——存小文件,本质上是将多个小文件合并为一个大文件来降低io次数,meta data里存偏移量

简介:

转自:http://yanyiwu.com/work/2015/01/04/Haystack.html

一篇14页的论文Facebook-Haystack, 看完之后我的印象里就四句话:

  • 因为【传统文件系统的弊端】
  • 因为【缓存无法解决长尾问题】
  • 所以【多个图片信息(Needle)存在同一个文件(SuperBlock)中】
  • 所以【显著提高性能】

传统文件系统的弊端

传统的 POSIX 文件系统不适合高性能的图片存储, 主要原因是基于该文件系统来存储的话,是讲每个图片存储成某目录下的一个文件, 每次读取文件的时候需要有N次磁盘IO,当目录下文件数是K级别是, 读取一次文件需要超过10次的文件IO,即使目录下的文件数是0.1K级别时, 也需要3次的文件IO(1:读取目录元数据,2:读取inode,3:读取文件内容)。

缓存无法解决长尾问题

图片存储的应用场景如图:

在 PhotoStorage 之前还有一些 CDN 保驾护航, CDN 就是靠缓存吃饭的,对于那些热门的图片都能被 CDN 很好的缓存下来, 所以需要访问的 PhotoStorage 一般都是非热门图片, 所以在这样的场景之下, 在 PhotoStorage 改进缓存显然是无法解决问题的。 你懂的,缓存对于长尾问题基本上都是束手无策的。 因为如果缓存能解决的问题,就不叫长尾问题了。

多个图片信息存在同一个文件中

每次读取一个图片需要多次磁盘IO的原因是因为一个图片存成一个文件, 文件系统里面每次读取文件需要先读取文件的元信息等,导致多次磁盘IO, 而当我们将多个图片信息存在同一个文件中, 当然这个文件会很大, 然后在内存中存储该图片存储在文件中的偏移地址和图片大小, 所以每次读取图片的时候, 根据偏移地址直接读取读取, 大部分情况下能做到只需要一次磁盘IO即可。 从而显著提高性能。

转载请注明出处: Facebook图片存储系统Haystack

 

 

基于这个思想,haystack 设计者绕过了 POSIX 文件系统这块,把 haystack 变成了一个 KV FS,即 NOFS。每个图片对应一个 FID,不再单独存放文件系统中,而是同一个物理卷 Volume 图片全部写入一个文件中,由 Volume Server 内存维护 FID : <Volume Machine, Offset, Size> 映射关系,Volume Server 内存中维护打开的文件句柄,读取图片时只需一次 IO 顺序读操作。


haystack架构图

架构比较简单,分为三部份:Haystack Directory, Haystack Cache, Haystack Store

Directory: 即所谓的 Meta Server

1. 生成 FID,维护 logical volume 与 physical volume 映射关系,解决上传时的负载均衡问题。

2. 新加入的 Store Server 要在这里注册。

3. 维护 logical volume 的 read-only 属性,只读的 logical volume 不再接受 upload 请求。

4. 决定请求走 CDN 还是内部 Haystack Cache Server.

Cache: 所谓的内部 CDN

1. 对图片 FID 采用一致性 hash 算法保存。

2. 只缓存用户请求,而不是来自 CDN 的请求。

3. 只缓存 write-enabled store 图片,由于上传的时间序,相当于只缓存最新生成的图片。比如说用户刚上传的图片,可能就会存到 Cache 中预热。

Store: 最终落地存储服务

1. 图片顺序追加到一个大文件中,内存中维护图片在文件中的 Offset 和 Size 的索引信息。

2. 为了解决重启快速加载问题,索引信息会单独保存到一个 Index File 中。





















本文转自张昺华-sky博客园博客,原文链接:http://www.cnblogs.com/bonelee/p/6516500.html ,如需转载请自行联系原作者


相关实践学习
Serverless极速搭建Hexo博客
本场景介绍如何使用阿里云函数计算服务命令行工具快速搭建一个Hexo博客。
相关文章
|
7天前
|
Java 测试技术 Maven
Maven clean 提示文件 java.io.IOException
在使用Maven进行项目打包时,遇到了`Failed to delete`错误,尝试手动删除目标文件也失败,提示`java.io.IOException`。经过分析,发现问题是由于`sys-info.log`文件被其他进程占用。解决方法是关闭IDEA和相关Java进程,清理隐藏的Java进程后重新尝试Maven clean操作。最终问题得以解决。总结:遇到此类问题时,可以通过任务管理器清理相关进程或重启电脑来解决。
|
1月前
|
搜索推荐 索引
【文件IO】实现:查找文件并删除、文件复制、递归遍历目录查找文件
【文件IO】实现:查找文件并删除、文件复制、递归遍历目录查找文件
35 2
|
1月前
|
编解码 Java 程序员
【文件IO】文件内容操作
【文件IO】文件内容操作
49 2
|
1月前
|
存储 Java API
【文件IO】文件系统操作
【文件IO】文件系统操作
43 1
|
2月前
|
Java 大数据 API
Java 流(Stream)、文件(File)和IO的区别
Java中的流(Stream)、文件(File)和输入/输出(I/O)是处理数据的关键概念。`File`类用于基本文件操作,如创建、删除和检查文件;流则提供了数据读写的抽象机制,适用于文件、内存和网络等多种数据源;I/O涵盖更广泛的输入输出操作,包括文件I/O、网络通信等,并支持异常处理和缓冲等功能。实际开发中,这三者常结合使用,以实现高效的数据处理。例如,`File`用于管理文件路径,`Stream`用于读写数据,I/O则处理复杂的输入输出需求。
|
1月前
|
存储 Java 程序员
【Java】文件IO
【Java】文件IO
37 0
|
2月前
|
Linux C语言
C语言 文件IO (系统调用)
本文介绍了Linux系统调用中的文件I/O操作,包括文件描述符、`open`、`read`、`write`、`lseek`、`close`、`dup`、`dup2`等函数,以及如何获取文件属性信息(`stat`)、用户信息(`getpwuid`)和组信息(`getgrgid`)。此外还介绍了目录操作函数如`opendir`、`readdir`、`rewinddir`和`closedir`,并提供了相关示例代码。系统调用直接与内核交互,没有缓冲机制,效率相对较低,但实时性更高。
|
3月前
|
存储 监控 Linux
性能分析之从 IO 高定位到具体文件
【8月更文挑战第21天】性能分析之从 IO 高定位到具体文件
43 0
性能分析之从 IO 高定位到具体文件
|
3月前
IO流拷贝文件的几种方式
IO流拷贝文件的几种方式
36 1
|
2月前
crash —— 获取系统的磁盘IO统计数据
crash —— 获取系统的磁盘IO统计数据