如果你正在关注企业级存储、分布式架构和 EDS 技术实践,欢迎先点个关注 + 点赞 + 收藏。后续我会继续拆解纠删码、数据分层、pNFS 和多路径等常见技术问题。
存储项目里经常会遇到一种反差:设备带宽不低,硬盘数量也不少,连续读写大文件时表现正常,一换成几 KB、几十 KB 的小文件,性能马上掉下来。文件数量继续增长后,打开目录、创建文件、读取属性和删除文件也会逐渐变慢。
这类问题不能只靠增加硬盘解决。小文件带来的压力不只在数据量,还包括频繁的空间分配、元数据更新、随机写入和纠删码计算。一次业务写入很小,存储系统在后台完成的工作却不一定少。
深信服 EDS 处理这类负载的一个重要思路,是先接住零散的小文件和小 I/O,经过排序、合并和追加写,再以更适合底层介质和纠删码条带的方式持久化。理解这条写入链路,比单看“小文件性能”参数更有意义。
一、小文件小在哪里,压力又大在哪里
“小文件”和“小 I/O”不是同一个概念。
- 小文件描述的是文件本身容量较小,例如数 KB 到数百 KB;
- 小 I/O 描述的是应用每次向存储发出的读写请求较小;
- 一个大文件也可能由大量 4KB 随机写组成;
- 一个小文件除了数据,还会产生文件名、目录、权限、时间戳、位置映射等元数据操作。
所以,保存 1TB 的大视频和保存 1TB 的图片切片,消耗的有效容量可能接近,给存储造成的压力却完全不同。后者需要创建和管理数量更多的文件对象,每个文件都伴随元数据访问和空间分配,底层写入也更加零散。
典型场景包括:
- EDA 工程目录、编译文件和仿真中间结果;
- 基因测序产生的样本切片和分析结果;
- AI 数据清洗、标注和训练样本;
- 医疗影像索引及切片;
- 测绘建模生成的瓦片和中间文件;
- 产线质检产生的图片和日志。
在这些场景里,容量通常不是第一个暴露的问题。目录遍历变慢、并发创建文件卡顿、计算节点等待存储,往往更早出现。
二、写放大是怎么产生的
可以先看一个简化模型。
假设底层以固定大小的空间单元分配数据,而应用只写入一小段内容。如果每次小写入都单独占用一个较大的空间单元,未使用部分就可能形成内部碎片。与此同时,系统还要更新空间映射、校验信息和相关元数据。
应用写入: 4KB
空间分配: [4KB 数据 | 大量未充分利用的空间]
后台动作: 分配空间 + 更新映射 + 更新元数据 + 数据保护
“应用只写了 4KB”不代表存储后端只做了 4KB 的工作。应用写入量与底层实际写入量之间的差距,就是讨论写放大时需要关注的核心。
纠删码场景还会增加一层复杂度。完整条带可以直接计算数据分片和校验分片;零散的小写入如果不能形成完整条带,系统可能需要进行额外的读取、计算和更新。小 I/O 越分散,越难发挥顺序写和满条带写入的效率。
需要注意,写放大并不只有一个固定公式。文件系统、块大小、条带宽度、对齐方式、纠删码配比、写入模型和介质特性都会影响最终结果,不能只用一个数字概括所有场景。
三、为什么要先合并,再追加写
处理小 I/O 的基本思路并不复杂:先把零散请求聚合起来,再用较大的 I/O 持久化。
业务产生大量小文件或小 I/O
↓
高性能写入区域接收请求
↓
排序、聚合并形成较大的连续数据
↓
以追加写方式形成更完整的写入单元
↓
写入底层持久化空间或纠删码条带
图:业务侧仍然访问独立文件。元数据路径维护目录、属性和逻辑位置映射;数据路径将零散的小 I/O 排序、聚合为较大的追加写,再进入持久化空间并按存储池策略进行纠删码或副本保护。具体介质、缓存和保护方式取决于产品形态、软件版本与存储池配置。
EDS 5.3.x 全闪统一存储会根据 I/O 大小选择不同的落盘路径:大 I/O 可以直接完成纠删码编码并进入持久化介质;小 I/O 先以多副本方式进入日志型 Cache,待聚合为完整 EC 条带后再异步回刷。这样可以减少小 I/O 直接进行纠删码写入带来的延迟和写惩罚。
图:EDS 5.3.x 混合 I/O 自适应落盘逻辑。大 I/O 完成纠删码编码后直接落盘;小 I/O 先以三副本形式进入日志型 Cache,在 Cache 中聚合为完整 EC 条带后异步回刷。图中使用 EC 4+2 说明条带结构;副本数、EC 配比和大小 I/O 判断阈值应以目标版本和存储池配置为准。
这条链路主要解决三个问题:
1. 减少碎片和无效空间占用
多个小写入合并后,可以更充分地利用分配到的空间,避免每个小请求都留下难以利用的空隙。
2. 把随机写转换为更友好的顺序写
机械盘尤其依赖顺序写,即使在全闪环境中,较大的连续写入通常也更容易进行条带化、校验计算和后台调度。追加写还能减少对已经持久化数据的原地覆盖。
3. 降低纠删码小写惩罚
数据聚合到更接近完整条带后再编码,可以减少零散小写引起的额外读改写操作。它不能消除所有编码成本,但能让纠删码更适合海量小文件场景。
EDS 将这类机制称为“小文件合并”或“全局 I/O 动态整合”。在混闪架构中,可以由 SSD 承接小文件,合并后再顺序写入 HDD 容量层;全闪产品的介质和持久化路径有所不同,但核心思路相同:先聚合小 I/O,再形成更大的持久化写入。
四、数据合并了,文件还能单独访问吗
很多人第一次听到“小文件合并”,会担心业务目录里的文件是不是也被合成了一个大文件。
业务看到的文件语义并没有改变。应用仍然通过原来的文件名、目录和协议访问数据。系统内部通过元数据记录文件属性、逻辑位置和实际数据之间的映射,再从聚合后的数据中找到对应内容。
可以把它理解成仓库管理:
- 业务看到的仍然是一个个独立包裹;
- 存储系统把多个小包裹装进适合运输的标准箱;
- 元数据负责记录每个包裹在哪个箱子、哪个位置;
- 读取时根据索引找到目标内容。
因此,小文件性能不能只看数据写入。元数据服务能否快速处理创建、查询、打开、关闭和删除,同样重要。
EDS 文件系统将元数据与数据分开处理,并使用分布式元数据能力承载大规模文件访问。小文件合并解决数据写入效率,元数据架构解决“文件数量很多以后还能不能快速找到”的问题,两者缺一不可。
五、为什么全闪存储也要关心写放大
全闪存储没有机械磁头寻道,随机 I/O 能力明显更强,但写放大并不会自动消失。
一方面,闪存需要进行擦写和垃圾回收,长期的小块随机写会影响介质效率和寿命;另一方面,分布式存储仍要完成网络传输、元数据更新、数据保护和故障域放置。纠删码也不会因为换成 NVMe SSD 就取消校验计算。
所以,全闪解决的是介质时延和并发能力,小 I/O 聚合解决的是写入形态与后端处理效率。两者解决的问题不同。
六、几个容易混淆的判断
小文件合并不等于压缩
合并改变的是底层数据组织和写入方式,压缩减少的是数据内容占用,两者不是一回事。
追加写不等于业务只能追加
“追加写”描述的是存储内部的持久化策略。业务仍可按照文件协议允许的方式创建、修改和删除文件。
小文件性能不等于只看 IOPS
文件访问还包括目录、权限、锁和元数据操作。块设备的随机 IOPS 不能直接代表文件系统的小文件处理能力。
纠删码利用率高不等于小写性能一定高
纠删码能降低容量冗余,但会增加编码和重建成本。理解其小写性能时,还要同时考虑小 I/O 聚合、故障域、容量水位和恢复窗口。