Networking Azure

Privoxy on Ubuntu 24.04 on Azure User Guide

| Product: Privoxy on Ubuntu 24.04 LTS on Azure

Overview

This image runs Privoxy, a non caching web proxy with advanced filtering capabilities for enhancing privacy, filtering web page content, managing HTTP cookies, controlling access, and removing ads, banners and other unwanted junk. Privoxy sits between a browser (or any HTTP client) and the web and rewrites or blocks requests and responses according to a flexible rule set. The service is fully configured and security hardened, so you can filter web traffic for your network within minutes of launch without hand editing the proxy configuration.

The image is secure by default and is not an open forward proxy. Privoxy binds to the loopback address only (127.0.0.1:8118) and layers a restrictive client access list that admits the loopback address and the RFC1918 private ranges (10.0.0.0/8, 172.16.0.0/12, 192.168.0.0/16) and nothing else. An open forward proxy is quickly abused as an abuse relay, so the appliance ships closed: no machine can use the proxy until you explicitly widen the bind to your own subnet. Even after you widen it, the access list still confines clients to private networks, so the proxy can never be reached from the public internet as shipped.

Privoxy's internal configuration pages (http://config.privoxy.org/ and the short alias http://p.p/) are reachable only through the proxy, never as a public web server, and they are kept read only (enable-edit-actions 0) so the filtering rules cannot be edited remotely. On the first boot of every deployed VM, a one shot service records the proxy details, the server's private IP and the exact commands to open the proxy, in a root only information file.

What is included:

  • Privoxy 3.0.34 (Ubuntu 24.04 noble archive) running as the privoxy system service on 127.0.0.1:8118
  • Secure by default: loopback only bind plus a permit-access client list restricted to loopback and RFC1918
  • Ad blocking and content filtering active out of the box via Privoxy's default action and filter rules
  • Read only internal config pages (enable-edit-actions 0, enable-remote-toggle 0) — not editable or togglable remotely
  • privoxy-access management tool in /usr/local/sbin (status, listen, allow, deny) with an open proxy guardrail
  • Per VM first boot initialisation writing proxy details to /root/privoxy-info.txt
  • All packages from the Ubuntu archive — clean open source, no third party repository
  • 24/7 cloudimg support

Prerequisites

Before you deploy this image you need:

  • An active Microsoft Azure subscription where you can create virtual machines
  • An SSH key pair for administrator access to the VM
  • A virtual network and subnet in the target region. Proxy clients connect over the private network, so put your clients in the same VNet (or a peered one)
  • A network security group (NSG) that allows inbound TCP 22 from your administrator network, and (only once you open the proxy to your clients) inbound TCP 8118 from the client subnets that will use the proxy
  • The Azure CLI installed locally if you plan to deploy from the command line

Standard_B2s (2 vCPU / 4 GiB RAM) is a balanced default; size the VM to the number of clients and the throughput you expect. Privoxy uses a single service port, TCP 8118.

Step 1: Deploy from the Azure Marketplace

Sign in to the Azure Portal, choose Create a resource, and search the Marketplace for Privoxy by cloudimg. Select the listing and choose Create.

On the Basics tab pick your subscription and resource group, a region, and a VM size (Standard_B2s or larger). Under Administrator account select SSH public key, set the username, and paste your public key. Under Inbound port rules allow SSH (22) for administration; you will add the proxy rule (TCP 8118) scoped to your client subnets after you open the proxy. Select Review + create, then Create. First boot initialisation completes within a few seconds of the VM reaching the Running state.

Step 2: Deploy from the Azure CLI

The following block creates a VM from the cloudimg Privoxy image into an existing VNet and subnet. Replace the placeholders with your own values.

az vm create \
  --resource-group <your-rg> \
  --name privoxy \
  --image <marketplace-image-urn> \
  --size Standard_B2s \
  --admin-username azureuser \
  --ssh-key-values ~/.ssh/id_ed25519.pub \
  --vnet-name <your-vnet> --subnet <your-subnet> \
  --public-ip-sku Standard

# Once you widen the proxy, allow 8118 from your client subnet only — never from the internet.
az vm open-port --resource-group <your-rg> --name privoxy --port 8118 --priority 1010

Step 3: Connect as the Administrator over SSH

Connect to the VM with SSH as the administrator user you set at deploy time (azureuser by default on Ubuntu). The administrator account is SSH key only.

ssh azureuser@<vm-public-ip>

Step 4: Confirm the Proxy is Running

Privoxy starts automatically on boot. Confirm the service is active, check that it is bound to the loopback address only, and inspect the shipped hardened configuration:

systemctl is-active privoxy.service
sudo ss -tlnp | grep ':8118'
grep -E '^\s*(listen-address|permit-access|enable-edit-actions|enable-remote-toggle)\s' /etc/privoxy/config

The listener line shows 127.0.0.1:8118 — the proxy is bound to loopback only, which is the secure default. The configuration shows the permit-access client list restricted to loopback and the RFC1918 ranges, and enable-edit-actions 0 so the rules cannot be edited remotely.

The privoxy service is active, bound to the loopback address 127.0.0.1:8118 only, with the shipped hardened configuration showing the loopback plus RFC1918 client access list and read only config pages

Step 5: Test the Proxy Round Trip

Prove the proxy works directly on the server. First request Privoxy's own internal admin page through the proxy (Privoxy generates this page itself, so it needs no outbound connection), then fetch a real web page through the proxy:

curl -sx 127.0.0.1:8118 http://p.p/ | grep -i '<title>'
curl -sx 127.0.0.1:8118 -o /dev/null -w 'show-status: HTTP %{http_code}\n' http://p.p/show-status
curl -x 127.0.0.1:8118 http://www.example.com/ | grep -i '<title>'

The admin page title (Privoxy@localhost) confirms the proxy is accepting and intercepting requests, and the Example Domain title confirms a real page fetched cleanly end to end through the proxy.

Requesting Privoxy's internal admin page through the proxy returns the Privoxy admin page, and a real fetch of example.com through the proxy returns HTTP 200 with the Example Domain page, proving the proxy works end to end

Step 6: Ad Blocking and Content Filtering

Privoxy's default action and filter rules are active out of the box. You can inspect the actions that apply to any URL with the show-url-info page, which reports what Privoxy would do without ever fetching the URL, then confirm a known ad server is blocked:

curl -sx 127.0.0.1:8118 'http://p.p/show-url-info?url=http://ads.doubleclick.net/adj/track.js' | sed 's/<[^>]*>//g' | grep -oE '[{][^{}]*block[^{}]*[}]' | sort -u
curl -sx 127.0.0.1:8118 -o /dev/null -w 'ads.doubleclick.net through the proxy: HTTP %{http_code}\n' http://ads.doubleclick.net/adj/track.js

The matched {block} actions show the request is caught by the ad blocking rules, and the blocked request returns HTTP 403 — Privoxy served its own block page and never connected out to the ad server. Add your own rules in /etc/privoxy/user.action (block lists) and /etc/privoxy/user.filter (content filters), then reload with sudo systemctl reload privoxy.

Privoxy blocks a known ad server: the show-url-info page reports the matched block actions and a live request to ads.doubleclick.net through the proxy returns HTTP 403 from Privoxy's block page, with the default action and filter rule files loaded

Step 7: Secure by Default — Open the Proxy to Your Client Network

Read the first boot information file and the proxy summary at any time. The file records the server's private IP and the exact commands to open the proxy to your clients:

sudo cat /root/privoxy-info.txt
sudo privoxy-access status

The image ships with Privoxy bound to 127.0.0.1 only and the client list restricted to loopback plus RFC1918. This is deliberate: no client on the network can use the proxy until you widen the bind. When you are ready, use the privoxy-access tool to bind to the VM's private IP and permit your client subnet. Use your own client subnet's CIDR — the value below is only an example:

sudo privoxy-access listen private          # bind to this VM's private IP on :8118
sudo privoxy-access allow 10.1.0.0/24        # permit your client subnet (RFC1918)
sudo privoxy-access status

An open proxy is refused as a hard guardrail: privoxy-access allow 0.0.0.0/0 and privoxy-access listen 0.0.0.0:8118 are both rejected, so you cannot accidentally expose the proxy as an abuse relay to the whole internet. After you widen the bind, scope the NSG rule for TCP 8118 to your client subnets only.

The secure by default posture: privoxy-access status shows the loopback bind and the loopback plus RFC1918 client list, the guardrail refuses a world open access list and an all interfaces bind, and the config pages are read only

Step 8: Point a Client at the Proxy

Once you have widened the bind and permitted the client subnet, point a client's HTTP and HTTPS proxy at the server's private IP address on port 8118 (shown in /root/privoxy-info.txt). For a quick test from a Linux client in the allowed network:

# On the client, using the server's private IP:
curl -x http://<server-private-ip>:8118 http://www.example.com/

# Or set it for the whole shell session:
export http_proxy=http://<server-private-ip>:8118
export https_proxy=http://<server-private-ip>:8118
curl http://www.example.com/

To configure a browser, set its HTTP and HTTPS proxy to <server-private-ip>:8118. To apply the proxy system wide on Ubuntu or Debian clients, set http_proxy / https_proxy in /etc/environment or drop an apt proxy file into /etc/apt/apt.conf.d/.

Step 9: Managing the Proxy

The privoxy-access tool is the primary interface to the bind and the client access list:

Command Purpose
privoxy-access status Show the listen address, the client access list and the service state
privoxy-access listen loopback Bind to 127.0.0.1:8118 (the closed default)
privoxy-access listen private Bind to this VM's private IP on :8118
privoxy-access allow <CIDR\|host> Permit a client network (added to permit-access)
privoxy-access deny <CIDR\|host> Block a client network (added to deny-access)

You can also edit /etc/privoxy/config directly and run sudo systemctl reload privoxy to apply changes; the privoxy-access guardrails only apply to the tool. Revoke a client network when it no longer needs the proxy:

sudo privoxy-access deny 10.1.0.0/24

Step 10: Hardening Notes

The image is hardened out of the box: Privoxy binds to loopback only, its client access list admits loopback and RFC1918 only, the internal config pages are read only, and the privoxy-access tool refuses an open proxy configuration. Keep it locked down in production: bind to the private IP rather than all interfaces, keep the client access list scoped to the narrowest CIDR ranges you trust, scope the NSG rule for TCP 8118 to only the client subnets that need the proxy, never expose 8118 to the internet, and keep the OS patched (sudo apt update && sudo apt upgrade). Review your user.action and user.filter rules periodically, and consult the Privoxy user manual for the full action and filter reference.

Support

This image is backed by 24/7 cloudimg support. Contact us by email and chat for help with Privoxy configuration, the client access list, ad blocking and content filter rules, opening the proxy to your client network, and forward proxy architecture on Azure.

All product and company names are trademarks or registered trademarks of their respective holders. Use of them does not imply any affiliation with or endorsement by them.