In our journey of building out our core infrastructure and advancing our CI/CD environment, storage is the silent engine that keeps everything moving. We have reached a point where we need to move beyond just having storage space and start understanding how to bridge the gap between our storage server and our compute resources.
In this guide, we are diving deep into the world of Network File System (NFS) on TrueNAS. We are going to explore how to connect our storage to both standalone Linux virtual machines and our virtualization host, Proxmox. By the end of this, we will understand not just how to click the buttons, but how permissions and persistent mounting work under the hood.
Understanding the NFS
Before we start running commands, we need to understand the "why" behind the process. NFS is a native protocol for Linux and Unix-like systems. Unlike SMB, which often relies on usernames and passwords, NFS identifies users by their UID (User ID) and GID (Group ID).
The Importance of Permission Mapping
NFS is a native file sharing protocol for Linux and UNIX-like systems. That matters because Linux tends to work with it more naturally than it does with something like SMB. When you mount an NFS share, you are mounting file-based storage that lives remotely on another system, but your Linux machine can interact with it almost like it is local.
When we connect a Linux machine to our storage server, the server doesn't necessarily ask who we are; it looks at the numeric ID of the user trying to write the file. If our local user has a UID of 1001, but the storage server only allows UID 1000 to write, we will face the dreaded "Permission Denied" error.
To solve this, we use mapping techniques:
- Maproot User/Group: This tells the server how to treat the "root" user from the client side.
- Mapall User/Group: This is a "catch-all" that maps every client user to a specific user on the storage server, ensuring consistent permissions across the board.
Another big part of NFS is deciding who is even allowed to access the export in the first place. In TrueNAS, that is usually controlled by IP address, subnet, or hostname restrictions. You can expose the share to an entire subnet, or you can lock it down to specific hosts. That matters because NFS is not really something you want to leave wide open. If a client is allowed to see and mount the export, then permissions become the next gate.
Setting the Stage in the Storage Environment
Before we can mount anything, our TrueNAS storage server must be ready. We ensure our datasets are using POSIX ACL types, as they play most natively with Linux environments. We also define which specific IP addresses or subnets are allowed to see our "exports." Even if someone is on our network, if their IP isn't on the list, the storage remains inaccessible to them.
Persistence is Key
When we mount a drive manually in Linux, it stays there until we reboot. To make our setup persist, we utilize the fstab (file systems table). This configuration file ensures that every time our server boots up, it automatically reaches out to the storage server and re-establishes the connection. We also include specific flags to tell the system to wait for the network to be active before trying to mount, preventing boot-time errors.
Hypervisor vs. Guest Mounting
We have two main ways to handle storage in a virtualized environment like Proxmox:
- Hypervisor Level: We mount the NFS share directly to Proxmox. This allows us to store ISOs, container templates, and virtual disks in a central location that all our nodes can access.
- Guest Level: We mount the NFS share directly inside a specific VM. This is great for application-specific data, like a media library or a database backup.
Designing our network and storage together is vital because if the network is congested, our storage performance will suffer. High-speed, low-latency connections are the backbone of a reliable homelab.
Command Reference Guide
This section serves as the command reference for the commands used in the video. Use these steps when you are ready to test the setup in your own environment.
1. Preparing the Linux Client
We first need to install the necessary utilities so our Linux machine can "speak" NFS on our TrueNAS. Server
- Install the NFS Client:
- apt install -y nfs-common
- Verify Connectivity:
- ping [your-storage-fqdn-or-ip]
- Discover Available Shares:
- showmount -e [your-storage-fqdn-or-ip]
2. Manual Mounting and Testing
We create a local directory (mount point) and link it to the remote share.
- Create the Mount Point:
- mkdir -p /mnt/nfs_share
- Mount the Share:
- mount -t nfs [server-ip]:/[remote-path] /mnt/nfs_share
- Verify the Mount:
- mount | grep nfs or df -h
3. Configuring Persistent Mounts
To ensure the share survives a reboot, we edit the /etc/fstab file. Add the following line to the end of that file:
- [server-ip]:/[remote-path] /mnt/nfs_share nfs defaults,_netdev 0 0
- Apply the Changes:
- systemctl daemon-reload
- mount -a
- Apply the Changes:
4. Proxmox Configuration Steps
Proxmox handles this a little differently, because now you are no longer just thinking about a client mounting storage for user access. Now you are thinking at the hypervisor level.
When you add an NFS share to Proxmox, you do it from the Datacenter level because it is external storage being presented to the hypervisor. Once Proxmox can see the TrueNAS export and is allowed to access it, you can add it as storage and define what it is allowed to hold. That could be ISO images, backups, templates, container data, or even VM disks.
- Navigate to Data Center > Storage > Add > NFS.
- ID: Give it a recognizable name (e.g., nfs_data).
- Server: Enter the FQDN or IP of your storage server.
- Export: Select the path from the dropdown (this will only populate if your Proxmox IP is allowed on the storage server).
- Content: Select what you want to store (Disk Images, ISOs, etc.).
This is where the design conversation gets interesting. Once storage is attached at the Proxmox level, you can create or place VM disks on that storage without having to log into each VM and mount network storage manually inside the guest. That makes management cleaner in a lot of situations. Instead of every VM managing its own NFS mount, Proxmox manages the storage and simply presents disks to the VMs.
That is often the cleaner design, but it depends on what you are trying to do. You could also choose to mount storage directly inside individual VMs instead. That gives the guest operating system direct awareness of the network share. Sometimes that is what you want. Sometimes it just adds complexity.
That is really the bigger takeaway from this whole process. Learning how to mount the storage is only step one. The real question is where you want that storage to live in your overall design.
A Note on Performance
Just because Proxmox can place VM disks on an NFS share does not automatically mean that it should be your answer for every workload. NFS is file-based storage. It works, and it works well in many cases, but workload type matters. For some use cases, especially when you want more direct block-level control, something like iSCSI may make more sense. That is a different design conversation and a different storage model.
The point here is not that NFS is bad. The point is that every storage type has a place, and understanding how they behave helps you choose the right one instead of just choosing the first one that works.
And that is really what this whole series is about. Not just getting something mounted, but understanding why you might choose one method over another as your environment grows.
Final Thoughts
At this point, you should have a solid understanding of how to connect a TrueNAS NFS share to both a Linux system and to Proxmox, but more importantly, you should have a better understanding of what is actually happening under the hood.
You are not just mounting a path. You are dealing with export visibility, identity mapping, permissions, client access, persistence, and design choices that affect how the rest of your environment will function.
That is what makes storage such a foundational piece of the build. It is not just about where data lives. It is about how your systems interact with it, depend on it, and perform because of it. When you start seeing it that way, you stop treating storage like an afterthought and start treating it like part of the architecture.