STFN

Building the tiniest NAS with ZFS using a Raspberry Pi Zero

30 minutes

Some time ago I came across this article about making a NAS from a Raspberry Pi Zero 2W. After reading, it dawned at me that I can make something similar, but turn it up to 11. I decided to make a NAS with a Raspberry Pi Zero W, that will have a ZFS mirror pool made from two USB drives.

Why? Because I wanted to see what would happen, and learn exactly how bad it would be.

I have a Pi Zero W, it was the first Pi I ever bought, but now it was just sitting in my cupboard waiting for a new idea. I broke it’s camera connector, so it wasn’t in the best shape. I also have the OTG cable for cable, a powered USB hub, and two very cheap 128GB USB drives, that are so slow they cannot be used for any real work. Combining those parts together sounded like a perfect usecase for parts that would serve no other purpose.

Setting up

First I burned a Raspbian Lite 32 bit on one of my smaller microSD cards. I always run my Zeros headless, so I set up SSH and Wi-Fi. I powered the board on, sshed (yes, that is a word, I say so, therefore it is) into it, did the typical apt update && apt upgrade, and started to look for a way to install ZFS.

After checking some options like building the binaries from scratch, I went with the simplest and laziest option:

>> sudo apt install zfsutils-linux

And I waited. And waited. Turned out that this way, the ZFS utils were being installed for every kernel version I had on the Pi, and there were four of them. Not sure why, I am not well versed in this low-level Linux kernel stuff. Anyway, after five hours it still did not finish installing.

It was getting late and I really wanted to go to bed and turn off my not-so-quiet desktop, so I canceled the build process, and went with plan B: I sshed to the Pi with my phone using Termius, and run the install process again from there by running sudo dpkg --configure -a. The phone kept the ssh session running. Thinking about it now, I could have just connected the Pi to a monitor and keyboard, but that would mean fighting with the cable organization behind the monitor, and again, this was a project driven by laziness.

When I woke up the next day, the ZFS utils were already installed. So it looks like installing NFS on a Raspberry Pi Zero takes between five and eight hours. Oh, and at the beginning you get an error message saying that you should not do it on a 32 bit system. But as they young people are saying: YOLO the police.

Creating the pool

Running a few basic ZFS commands like zfs get all or zpool list confirmed the ZFS was installed on the Pi. Now it was time to create the pool. At first I decided the create the mirror pool on my desktop to save time, and import it on the Pi.

Le nope

I connected the USB drives to the hub, and the hub to the OTG cable connecting it to the Pi. And nothing. Both lsusb and lsblk did not see any drives. The drives did not light up their LEDs. I suspected it’s maybe because I created the pool on a x86 64 bit machine and was trying to run it on a 32 bit ARM architecture? I reformatted the drives to ext4 and tried again. Still nothing.

Turned out the Pi did not see my hub at all. I tried all possible combinations, running the hub powered off, powered on, plugging it after the Pi was turned on, plugging it when the Pi was off, nothing helped. Googling (actually Qwanting in my case) showed that the Pi Zeros are very finicky when it comes to accepting USB hubs, so it looked like my hub just wasn’t the right one.

Plan B

With the hub not working, and not having another one to try out, I went with plan B, running a single disk ZFS pool. This turned out to be super simple.

First I checked the ID of the USB drive:

>> ls -l /dev/disk/by-id
lrwxrwxrwx 1 root root  9 Jan 20 09:31 usb-Wilk_USB_DISK_3.0_070125F69F331078-0:0 

And then, as root, created the pool using the ID:

All commands below were run as root

>> zpool create thepool usb-Wilk_USB_DISK_3.0_070125F69F331078-0:0

I checked where it got mounted:

>> zfs get mountpoint thepool
NAME     PROPERTY    VALUE       SOURCE
thepool  mountpoint  /thepool    default

I could have change the default mount point, but it was fine for this test project.

To see if it actually works and can store data, I downloaded an image from JWST to the pool folder.

cd /thepool
wget https://stsci-opo.org/STScI-01G8GZHGM987XCHJZ846YRHWGF.tif

And it worked! Now it was time for the final step in making my NAS, setting up sharing.

ZFS and NFS

First I installed the NFS server, and then I configured the ZFS pool to enable accessing the pool over the network.

apt install nfs-kernel-server
zfs set sharenfs=on thepool

On my desktop I created a share mountpoint and connected to the NFS share on the Pi:

sudo mkdir -p /mnt/shared-test
sudo mount -t nfs <ip-of-the-pi>:/thepool /mnt/shared-test

So, now I have a tiny NAS that runs a ZFS single disk pool, and shares it over NFS, and is extremely slow, has no data redundancy, and uses USB drives I would not trust even to carry throwaway data from one room to another.

How slow is it?

I uploaded to the pool 16GB of data in files of different size, and it took 4 hours, so write speeds are around 1MB/s. Reading was only a bit faster, but not passing 2MB/s. The bottleneck was for sure the CPU, ZFS uses a lot of processing power, and a single 1GHz core is not a typical ZFS system.

Not exactly a speed daemon, but it was a fun little weekend project. Hope you liked it!

If you know from experience any USB hubs that are known to work with a Pi Zero, please let me know.

Thanks for reading, and if you really, really liked, you could consider helping me with funding my future projects by supporting me on these crowdfunding sites: