在之前的文章中提到,我使用了 MergeFS 来扩容磁盘,但是随着性能需求的不断提升(和新 HomeLab 的硬盘空位太多以及二手企业 CMR 磁盘越来越便宜),我决定还是使用更主流的 RAID 来同时完成容灾和扩容,毕竟 MergerFS 这类 union fs 本质和 RAID0 一样,很难抵御突然故障的风险。
最初我的安排是将家里的磁盘分为两个可用级别,第一个是需要比较高质量的可靠存储,另一个则是对数据丢失有较高容忍度的不可靠存储。顺着这个思路,我把手里的 6 块 SSD 安排成了这样:
- 高可靠存储:RAIDz2,由四块来自狗东的全新 WD DC HC310 6TB SATA 机械硬盘组成,提供共计 12TB 的存储空间;
- 低可靠存储:ZFS mirror,由两块来自咸鱼的二手 WD DC HC530 6TB SAS 机械硬盘组成,提供共计 12TB 的存储空间;
过了一阵子后,我鬼迷心窍突然想玩玩 PT,下载的东西越来越多,最终对低可靠存储的需求也越来越大,不得不又买了两块 12TB 的硬盘来给这个 pool 扩容。
整个过程其实可以很简单:掏四块盘出来新建新的 pool,然后 zfs send | zfs receive
拷贝一下内容,就好啦。但是我并没有闲置的四个硬盘来创建新的 pool,于是就得想一些 tricky 的办法绕一绕:RAIDz2 至少需要四块硬盘,其中两个盘存放校验,剩下的 N-2 块硬盘存放数据,所以其实这个模式是允许只有两个硬盘在线的,那么思路就有了:先用真的硬盘和假的文件打个哈哈创建出 pool,再离线掉那俩文件,就可以得到一个降级运行(degraded)的 pool 了,最终的全过程如下:
- 在 /tmp 里
truncate
出两个 12TB 的文件,和两个新买的 12TB 硬盘组 RAIDz2 - offline 掉两个 tmp 里的文件,此时新 pool 进入 degraded 状态,但是还能用
- 把老的 pool send 到新的 pool 里
- 拆掉老 pool 里的一个磁盘,然后 replace 掉一个 tmp 文件,等待重建
- 拆掉老 pool 里的另一个磁盘并 replace,等待重建
最终这波操作耗时约 4 天,期间几乎没有 downtime,仅仅替换磁盘期间重启过几次 NAS,整体效果极好。
当然风险是存在的,如果在这套流程中磁盘出现了故障,搞不好可能所有的数据就都上云了(