Setting up a proxy on your Raspberry Pi

All of this started the week before Thanksgiving, while many of you were making plans to spend time with your family, I was trying to have the best setup at home in case there was a problem with Zulily.com during our busiest season of the year, and also to be able to quickly glance over Grafana to do quick checks during those days on the overall health of the system.

I have a PC at home with multiple monitors, so instead of opening my work computer, I wanted to walk by my computer and check how things looked, so not much of a problem, I just needed to set up the VPN in my PC and have a browser with a Grafana playlist and done.

I gave it a try, but it ended being more complicated than I expected, the way that the VPN Client is configured to work is that all connections go through the VPN. I did not have a way to only use the VPN for specific domains, so if I wanted to play a game, browse, or anything else for personal purposes, I needed to turn off the VPN.

I know that there are other ways, like running a Virtual Machine on my computer, maybe a routing solution in Windows or potentially using Windows Subsystem for Linux, but I wanted to do something different and have some fun, so I bought a Raspberry Pi 4 to run the VPN and act as a proxy.

After installing Raspbian and having the basic setup done I got the VPN running, that part was easy, I tried multiple approaches, and at the end, the solution was a lot simpler than I expected.

The Solution

To use ssh to act as a socks proxy (ssh -D), set it up as a service, create a Proxy Auto-Configuration (PAC) file, serve it using Nginx and point the automatic proxy configuration on windows to that URL.

Step 1. Set up SSH as a Socks Proxy running as a Service

After reading and googling for some time, this article gave me the solution, and here is the step by step with some variations.

First, on your Raspberry Pi, we will use systemctl to create a unit file, adding “force” to the edit command will create a new file.

Copy and paste the following code that sets up the proxy to listens to any IP address (0.0.0.0) on port 8000 and routes the traffic to your you Raspberry Pi (127.0.0.1):

  1. Be sure to change the user (pi), home folder (/home/pi) to match your user.
  2. The main difference with the solution in the article is that I added RestartSec=5 and Restart=always, this because the service will not work if this runs before the network is available, in my case, network-online.target did not work, I tried other options like network.target, but it did not work either, maybe because I was using WiFi and not ethernet, in the end, the simplest solution was to add the retry options.

Now we enable the unit

We start the unit

And then we check the status

If you later want to modify the service

And once you are done, you don’t need to restart you can just do

Step 2. Set up Nginx

Install Nginx in your Raspberry Pi

Find your Raspberry Pi IP using ip

You should get a response showing something like this

In this case, Raspberry Pi is connected to wi-fi, and you can find the IP on the wlan0 line, with the IP 10.66.77.100, if you are using ethernet, it would be on the eth0 line.

On your PC go to http://10.66.77.100, and you should see something like this

nginx welcome message
nginx welcome message

Step 3. Create your proxy.pac file

This turned out to be extremely simple, I used the Proxy Auto-Configuration (PAC) file article from Mozilla and is as simple as creating proxy.pac file to be served by Nginx and configure it properly.

The following is an example that assumes that:

  1. Your Raspberry Pi IP is 10.66.77.100, and the socks proxy is running in port 8000
  2. That you want to route traffic going to grafana.some.place.in.aws.com, in this case, a specific domain
  3. That you want to route all sub-domains of .company.internal, for example, git.company.internal or jira.tools.company.internal

Create the proxy.pac file

Add the following code to it and save the file

If you want to add more domains to be routed, keep adding

And replace {domain} with the one that you would like to route through the proxy.

Also, to ensure that everything works properly, we need to edit the Nginx mime.types

and at the end of the file before the closing bracket } add the following line

Then save and restart Nginx

And finally, check that everything is working properly

Remember to change 10.66.77.100 to your Raspberry Pi IP, or you can use 127.0.0.1, you should get something like

So you should be able to see the code that you added to the file and also that the Content-Type is application/x-ns-proxy-autoconfig.

Step 4. Set up the proxy file in Windows

Search for proxy setting

Search for proxy settings
Search for proxy settings

Open Proxy Settings and add the URL that points to your pac file, in this example http://10.66.77.100/proxy.pac and click save.

Proxy settings window
Proxy settings window

Step 5. Solve DNS problems

If you have challenges resolving internal company domains, you will see something like this on your PC.

This site can’t be reached error
This site can’t be reached error

An easy fix is to find out the IP address and add the domain to your Windows hosts file C:\Windows\system32\drivers\etc\hosts.

For example, if your company’s internal URL is jira.company.internal, go to your Raspberry Pi, and with your VPN connected, get that URL IP.

You will get the IP, for example, 10.10.1.6, copy that and now in your Windows machine go to C:\Windows\system32\drivers\etc\hosts and add the following line:

Repeat this for every domain.

Notes

I skipped the set up of the VPN, but for clarity, if your VPN is not running, the traffic will still be routed through your Raspberry Pi for the URLs defined in the proxy.pac file, what this means is that if you set a domain like google.com to go through the proxy, the traffic will be routed regardless of the status of your VPN.

Written by

I’m passionate about building great teams and ship game-changing products. http://pedrofuentes.com

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store