I recently ran into an issue while setting up a self-hosted instance of n8n on a virtual private server (VPS). My workflow included a final step that wrote a file to a folder on the host machine via a Docker bind mount:

volumes:
  - n8n_data:/home/node/.n8n
  - ./local-files:/files

Before starting the containers for the first time, I created the local-files directory in the same location as the docker-compose.yml file. I had done this previously on a Raspberry Pi, where I was also hosting an instance of n8n, and it seemed like the proactive thing to do. Turns out, it wasn’t a good idea.


User IDs and Docker#

By default, Docker runs containers as user ID 1000, unless specified otherwise. You can confirm this by running the following command (assuming your n8n service is named n8n):

docker compose exec n8n sh -c 'id -u'

The problem was that on the VPS, I wasn’t user 1000—I was user 1001. You can verify your user ID with:

id

This meant the local-files directory was owned by me (user ID 1001) and couldn’t be accessed by the container running as user 1000.


Fixing the Issue#

The simplest fix would be to run the container as my user:

services:
  n8n:
    image: docker.n8n.io/n8nio/n8n
    user: "1001:1001"

However, when I tried that, n8n wouldn’t start. I suspect this was because files had already been created by user 1000 in the Docker volume that stores n8n’s application data. The new user (1001) didn’t have permission to access those files. I could have deleted the volume and started fresh, but I had already defined workflows I didn’t want to recreate. In hindsight, exporting the workflows to JSON and reimporting them would have been a better approach—but I didn’t think of that at the time.

Instead, I chose to change the ownership of the local-files directory to UID 1000.

First, find the username associated with UID 1000:

getent passwd 1000

On my system, it was ubuntu. Then, create a group so both ubuntu and my current user (myuser) can access the directory:

sudo groupadd n8n_local
sudo usermod -aG n8n_local ubuntu
sudo usermod -aG n8n_local myuser

Next, change the ownership and permissions of the local-files directory:

chown 1000:n8n_local ./local-files
chmod 770 ./local-files

After that, n8n was able to write to the directory. I didn’t even need to restart the Docker container.


Conclusion#

If I were doing this all over again, I would have simply let Docker create the local-files directory when the container first started, rather than creating it manually. But if you’ve already done what I did, the steps above should help you resolve the issue.