Running Tor Node Inside Docker
Over last few weeks I have been playing around with creating docker container to host a Tor node on one of my VPS servers.
As a result of those efforts I created a Github repository: https://github.com/wlk/docker-tor-relay with the Docker image, it’s also hosted on DockerHub here: https://hub.docker.com/r/wlkx/docker-tor-relay/ (and configured as automated build
)
Both DockerHub and Github README provide enough information on how to use it, so I won’t go into details here, but I’ll focus on 2 Docker features that I used in this toy project.
There are many Tor images out there, but in my case I have made 2 changes.
Mounting volumes to persist state between container restarts
This is a well known Docker feature, you can share local volumes (directories or files) with the container and configure read or write access. This way when you restart the container or start new image with the same container, as long as you setup the same mount options your files will not be lost.
In this project I’m using volumes to persist Tor configuration and state across restarts, you can read more about this feature here: https://docs.docker.com/engine/tutorials/dockervolumes/#/mount-a-host-directory-as-a-data-volume
Running Docker container in a separate network
To achieve better security and isolation of the containers running on my host (remember that Tor container can be a one of many containers running on the same host) I have setup separate network to host Tor containers.
This feature is documented here: https://docs.docker.com/engine/userguide/networking/ if you’d like to know more, but I’m going to show how I configured it in my project:
-
Create separate network:
docker network create --driver bridge tor_network
This creates a separate network named tor_network
, you can see that it was created correctly:
$ docker network ls
NETWORK ID NAME DRIVER SCOPE
9a142fb1d58a bridge bridge local
3d0b9d3ee2f6 host host local
1e28dc8c71af none null local
f90795b99524 tor_network bridge local
The bridge
is the default one, so all containers started without network parameter specified will run in the same, default network
-
Run container in isolated network:
docker run -d \ --network=tor_network \ --restart always \ -p 9001:9001 \ wlkx/docker-tor-relay
Parameter --network=tor_network
specifies that the container will be run in tor_network
- Verifying that it works
To check if this is working as expected I have inspected 2 containers on separate networks and I saw their IPs as:
Docker container: 172.19.0.2
Other container: 172.17.0.2
As you can see, these containers are running in separate networks without any connection between them, executing ping from one to the other fails with timeout, same for any network connectivity.
Summary
Using more advanced Docker features I was able to achieve better isolation between containers and in result better security.
The docker-tor-relay
is a very straightforward and save way if you’d like to help Tor network by running your own relay node.