Apakah Anda bekerja dengan Docker di jaringan perusahaan, di server dengan akses terbatas, atau ingin agar kontainer Anda terhubung ke internet melalui IP tertentu? Tanpa pengaturan proxy yang benar, Docker tidak akan dapat mengunduh gambar dari Docker Hub atau registry lainnya. Dalam artikel ini, kita akan membahas semua tingkatan proxy — dari daemon hingga kontainer terpisah.
Mengapa Docker Membutuhkan Proxy
Docker adalah alat yang terus-menerus mengakses sumber daya eksternal. Setiap kali docker pull atau docker build, daemon mengakses Docker Hub, GitHub Container Registry, Google Container Registry, atau registry pribadi Anda. Dan di sinilah masalah mulai muncul.
Situasi di mana proxy diperlukan:
- Jaringan perusahaan dengan firewall — semua lalu lintas harus melalui server proxy perusahaan, jika tidak, koneksi akan diblokir.
- Geo-restriksi — Docker Hub atau registry tertentu tidak tersedia dari negara atau pusat data Anda.
- Server terbatas tanpa akses langsung ke internet — VPS dalam jaringan tertutup, di mana internet hanya tersedia melalui gateway.
- Kontrol lalu lintas keluar dari kontainer — Anda ingin aplikasi di dalam kontainer terhubung ke jaringan melalui IP tertentu, misalnya untuk pengambilan data, permintaan API, atau pengujian konten yang bergantung pada lokasi.
- Anonimisasi permintaan — menyembunyikan IP asli server saat mengakses layanan eksternal dari kontainer.
- Rate limiting — Docker Hub membatasi jumlah permintaan tarik untuk pengguna anonim (100 tarik dalam 6 jam). Melalui proxy dengan rotasi IP, Anda dapat menghindari batasan ini.
Penting untuk memahami bahwa Docker bukanlah satu aplikasi, tetapi sistem yang terdiri dari beberapa komponen. Daemon (dockerd) berjalan di host dan melakukan tarik gambar. Kontainer adalah proses terisolasi dengan pengaturan jaringan mereka sendiri. Oleh karena itu, pengaturan proxy untuk daemon dan untuk kontainer adalah dua tugas yang berbeda, yang diselesaikan dengan cara yang berbeda.
Tiga Tingkat Proksy di Docker
Sebelum masuk ke konfigurasi, Anda perlu memahami arsitektur. Di Docker ada tiga tingkat independen, masing-masing memerlukan pengaturan proxy yang terpisah:
| Tingkat | Apa yang Dilakukan | Di Mana Dikonfigurasi |
|---|---|---|
| Docker daemon | Mengunduh gambar (docker pull), mengakses registry | systemd override atau daemon.json |
| Docker build | Menjalankan perintah saat membangun gambar (RUN apt-get, pip install, dll.) | ARG dan ENV di Dockerfile atau --build-arg |
| Kontainer Runtime | Aplikasi yang sedang berjalan yang melakukan permintaan HTTP | ENV saat docker run atau di docker-compose.yml |
Kesalahan umum adalah mengatur proxy hanya pada satu tingkat dan bingung mengapa gambar tetap tidak dapat diunduh atau aplikasi tidak melihat proxy. Mari kita bahas setiap tingkat secara rinci.
Pengaturan Proxy untuk Docker Daemon (menarik gambar)
Ini adalah pengaturan paling penting jika Anda ingin menarik gambar melalui proxy. Docker daemon adalah layanan sistem yang dijalankan melalui systemd. Variabel lingkungan pengguna Anda atau bahkan root tidak dapat dilihat olehnya. Anda perlu mengirimkan proxy ke lingkungan layanan.
Metode 1: melalui systemd override (disarankan)
Buat direktori untuk menimpa pengaturan layanan:
sudo mkdir -p /etc/systemd/system/docker.service.d
Buat file /etc/systemd/system/docker.service.d/http-proxy.conf dengan konten berikut:
[Service] Environment="HTTP_PROXY=http://username:password@proxy-host:port" Environment="HTTPS_PROXY=http://username:password@proxy-host:port" Environment="NO_PROXY=localhost,127.0.0.1,::1,your-private-registry.example.com"
Jika proxy tanpa autentikasi — cukup hapus username:password@. Setelah membuat file, muat ulang konfigurasi systemd dan mulai ulang Docker:
sudo systemctl daemon-reload sudo systemctl restart docker
Periksa apakah pengaturan telah diterapkan:
sudo systemctl show --property=Environment docker
Dalam output, variabel HTTP_PROXY dan HTTPS_PROXY Anda harus muncul.
Metode 2: melalui ~/.docker/config.json (Docker Desktop dan versi baru)
Mulai dari Docker Engine 23.0, ada cara yang lebih nyaman — pengaturan proxy melalui file konfigurasi klien. Buat atau edit file ~/.docker/config.json:
{
"proxies": {
"default": {
"httpProxy": "http://username:password@proxy-host:port",
"httpsProxy": "http://username:password@proxy-host:port",
"noProxy": "localhost,127.0.0.1,::1"
}
}
}
Metode ini nyaman karena tidak memerlukan hak akses root dan tidak perlu memulai ulang daemon. Pengaturan secara otomatis diteruskan ke kontainer saat membangun sebagai argumen build. Namun, untuk mengelola permintaan tarik dari daemon itu sendiri, metode melalui systemd tetap diperlukan.
💡 Penting tentang NO_PROXY
Selalu tambahkan alamat registry dan layanan internal Anda ke NO_PROXY. Jika tidak, Docker akan mencoba mengaksesnya melalui proxy dan mendapatkan kesalahan koneksi. Daftar tipikal: localhost,127.0.0.1,::1,10.0.0.0/8,172.16.0.0/12,192.168.0.0/16
Proxy di Dalam Kontainer saat Membangun (waktu pembangunan)
Ketika Docker membangun gambar dan menjalankan perintah seperti RUN apt-get install, RUN pip install, atau RUN npm install — perintah ini dijalankan di dalam kontainer sementara. Secara default, kontainer ini tidak memiliki akses ke proxy host. Anda perlu secara eksplisit meneruskan proxy melalui argumen build.
Meneruskan Proxy melalui --build-arg
docker build \ --build-arg HTTP_PROXY=http://proxy-host:port \ --build-arg HTTPS_PROXY=http://proxy-host:port \ --build-arg NO_PROXY=localhost,127.0.0.1 \ -t my-image .
Pengaturan di Dockerfile
Jika proxy hanya diperlukan selama tahap pembangunan dan Anda tidak ingin itu masuk ke gambar akhir — gunakan ARG, bukan ENV:
FROM ubuntu:22.04 # Mendeklarasikan argumen build ARG HTTP_PROXY ARG HTTPS_PROXY ARG NO_PROXY # Menggunakannya dalam perintah RUN apt-get update && apt-get install -y curl wget # Setelah blok ini, proxy tidak akan ada di ENV kontainer
Namun, jika proxy juga diperlukan di dalam kontainer yang sedang berjalan — gunakan ENV:
FROM python:3.11 ENV HTTP_PROXY=http://proxy-host:port ENV HTTPS_PROXY=http://proxy-host:port ENV NO_PROXY=localhost,127.0.0.1 RUN pip install requests beautifulsoup4 CMD ["python", "app.py"]
⚠️ Peringatan: Keamanan
Jangan hardcode login dan password proxy langsung di Dockerfile jika gambar akan bersifat publik atau masuk ke repositori. Gunakan --build-arg dan kirimkan nilai dari variabel lingkungan sistem CI/CD. Perintah docker history dapat menunjukkan nilai ARG, jadi untuk rahasia gunakan Docker BuildKit secrets.
Proxy untuk Kontainer yang Sedang Berjalan (runtime)
Ini adalah skenario paling umum untuk aplikasi yang melakukan permintaan HTTP selama runtime — pengambil data, bot, mikroservis yang memerlukan akses melalui IP tertentu. Di sini pengaturannya sangat sederhana: Anda perlu meneruskan variabel lingkungan saat menjalankan kontainer.
Melalui docker run
docker run \ -e HTTP_PROXY=http://username:password@proxy-host:port \ -e HTTPS_PROXY=http://username:password@proxy-host:port \ -e NO_PROXY=localhost,127.0.0.1 \ my-image
Sebagian besar pustaka HTTP populer secara otomatis mengambil variabel HTTP_PROXY dan HTTPS_PROXY: Python requests, curl, wget, Go's net/http, Node.js https-proxy-agent, dan lainnya. Tidak perlu menulis tambahan dalam kode.
Melalui file .env
Lebih nyaman untuk menyimpan pengaturan dalam file .env dan meneruskannya secara keseluruhan:
# file .env HTTP_PROXY=http://username:password@proxy-host:port HTTPS_PROXY=http://username:password@proxy-host:port NO_PROXY=localhost,127.0.0.1
docker run --env-file .env my-image
Proxy SOCKS5 di dalam kontainer
Jika Anda menggunakan proxy SOCKS5 (misalnya, proxy residensial sering kali mendukung protokol ini), sintaksisnya sedikit berbeda:
docker run \ -e ALL_PROXY=socks5://username:password@proxy-host:port \ my-image
Harap dicatat: tidak semua pustaka mendukung SOCKS5 melalui variabel lingkungan tanpa ketergantungan tambahan. Python requests memerlukan instalasi requests[socks], curl harus dibangun dengan dukungan libcurl-socks.
Proxy di Docker Compose
Dalam proyek nyata, jarang menggunakan docker run secara langsung. Lebih sering menggunakan Docker Compose, di mana beberapa layanan dijelaskan dalam satu file. Pengaturan proxy di sini dilakukan pada tingkat setiap layanan atau melalui file variabel.
Opsi 1: environment di docker-compose.yml
version: '3.8'
services:
scraper:
image: my-scraper:latest
environment:
- HTTP_PROXY=http://username:password@proxy-host:port
- HTTPS_PROXY=http://username:password@proxy-host:port
- NO_PROXY=localhost,127.0.0.1
restart: unless-stopped
api:
image: my-api:latest
# Layanan ini tanpa proxy — hanya mengakses sumber daya internal
ports:
- "8080:8080"
Opsi 2: melalui file .env (disarankan)
Buat .env di direktori dengan docker-compose.yml. Docker Compose secara otomatis mengambil file ini:
# .env PROXY_HOST=proxy-host PROXY_PORT=8080 PROXY_USER=username PROXY_PASS=password
version: '3.8'
services:
scraper:
image: my-scraper:latest
environment:
- HTTP_PROXY=http://${PROXY_USER}:${PROXY_PASS}@${PROXY_HOST}:${PROXY_PORT}
- HTTPS_PROXY=http://${PROXY_USER}:${PROXY_PASS}@${PROXY_HOST}:${PROXY_PORT}
- NO_PROXY=localhost,127.0.0.1
Proxy saat Membangun di Compose
Jika di Compose ada bagian build dan perlu meneruskan proxy pada tahap pembangunan:
version: '3.8'
services:
app:
build:
context: .
dockerfile: Dockerfile
args:
HTTP_PROXY: http://${PROXY_USER}:${PROXY_PASS}@${PROXY_HOST}:${PROXY_PORT}
HTTPS_PROXY: http://${PROXY_USER}:${PROXY_PASS}@${PROXY_HOST}:${PROXY_PORT}
environment:
- HTTP_PROXY=http://${PROXY_USER}:${PROXY_PASS}@${PROXY_HOST}:${PROXY_PORT}
- HTTPS_PROXY=http://${PROXY_USER}:${PROXY_PASS}@${PROXY_HOST}:${PROXY_PORT}
Jenis Proxy yang Harus Dipilih untuk Docker
Pemilihan jenis proxy tergantung pada tugas. Untuk lingkungan Docker, ada tiga jenis utama, masing-masing memiliki niche sendiri:
| Jenis Proxy | Kecepatan | Anonimitas | Skenario Terbaik untuk Docker |
|---|---|---|---|
| Data Center | ⚡ Tinggi | Sedang | Menarik gambar, pipeline CI/CD, menghindari rate limiting Docker Hub |
| Residensial | 🔄 Sedang | Tinggi | Pengambilan data situs dengan perlindungan, API dengan geo-restriksi, pengujian |
| Mobile | 🔄 Sedang | Maksimal | Aplikasi yang bekerja dengan API mobile (Instagram, TikTok) |
Untuk menarik gambar dan CI/CD proxy data center adalah yang paling optimal — mereka memberikan kecepatan maksimum saat mengunduh gambar besar (beberapa gigabyte) dan koneksi yang stabil untuk pembangunan yang lama.
Untuk kontainer pengambil data, yang perlu menghindari perlindungan situs dan terlihat seperti pengguna biasa, proxy residensial lebih cocok. Mereka memiliki IP pengguna rumah yang nyata, yang mengurangi kemungkinan pemblokiran bahkan dengan permintaan yang intensif.
Untuk aplikasi yang bekerja dengan platform mobile — Instagram Graph API, TikTok API, versi mobile dari layanan — pertimbangkan untuk menggunakan proxy mobile. Mereka menggunakan IP operator seluler dan menimbulkan sedikit kecurigaan dari sistem anti-bot.
Protokol: HTTP vs SOCKS5
Docker daemon hanya mendukung proxy HTTP/HTTPS — SOCKS5 tidak berfungsi untuk menarik gambar. Jika Anda memiliki proxy SOCKS5 dan perlu mengunduh gambar, Anda harus menggunakan konverter lokal seperti privoxy atau microsocks, yang akan menerima HTTP dan memproksikan melalui SOCKS5.
Untuk kontainer runtime, situasinya lebih baik: sebagian besar pustaka HTTP mendukung SOCKS5 secara langsung melalui variabel ALL_PROXY=socks5://....
Kesalahan Umum dan Cara Memperbaikinya
Mari kita bahas masalah yang paling umum dihadapi saat mengatur proxy di Docker:
Kesalahan 1: Proxy Dikonfigurasi di Host, tetapi Docker Tidak Melihatnya
Gejala:
Error response from daemon: Get "https://registry-1.docker.io/v2/": dial tcp: connection refused
Penyebab: Docker daemon dijalankan sebagai layanan sistem dan tidak mewarisi variabel lingkungan pengguna saat ini, bahkan jika Anda telah mengatur export HTTPS_PROXY=... di terminal.
Solusi: Atur proxy melalui systemd override (metode 1 dari bagian di atas). Pastikan untuk menjalankan systemctl daemon-reload && systemctl restart docker.
Kesalahan 2: apt-get / pip / npm Tidak Bekerja Saat Membangun
Gejala:
Err:1 http://archive.ubuntu.com/ubuntu focal InRelease
Could not connect to archive.ubuntu.com:80
Penyebab: Pengaturan proxy untuk daemon tidak secara otomatis menyebar ke perintah dalam RUN di Dockerfile. Ini adalah dua konteks yang berbeda.
Solusi: Kirimkan proxy melalui --build-arg atau gunakan ~/.docker/config.json dengan bagian proxies (Docker 23.0+, secara otomatis meneruskan argumen saat membangun).
Kesalahan 3: Layanan Internal Tidak Tersedia Melalui Proxy
Gejala:
curl: (7) Failed to connect to internal-service.local port 8080: Connection refused
Penyebab: Proxy mencoba memproksikan permintaan ke alamat internal yang tidak dapat diakses dari luar.
Solusi: Tambahkan semua domain dan subnet internal ke NO_PROXY. Untuk jaringan perusahaan, daftar tipikal: localhost,127.0.0.1,::1,.internal,.local,10.0.0.0/8,172.16.0.0/12,192.168.0.0/16
Kesalahan 4: Autentikasi Proxy Tidak Bekerja — Karakter Khusus dalam Password
Jika password mengandung karakter khusus (@, #, %), URL tidak diparsing dengan benar.
Solusi: Encode password dalam URL-encoding. Misalnya, p@ss#word → p%40ss%23word. Di Python, Anda dapat dengan cepat mendapatkan versi encoded:
python3 -c "from urllib.parse import quote; print(quote('p@ss#word', safe=''))"
# Output: p%40ss%23word
Kesalahan 5: Proxy Berfungsi, tetapi Sertifikat SSL Tidak Diverifikasi
Proxy perusahaan sering melakukan inspeksi SSL (MITM) dan mengganti sertifikat. Docker akan memberikan kesalahan:
x509: certificate signed by unknown authority
Solusi: Tambahkan sertifikat root perusahaan ke dalam daftar tepercaya di host dan mulai ulang Docker. Di Ubuntu/Debian:
sudo cp corporate-ca.crt /usr/local/share/ca-certificates/ sudo update-ca-certificates sudo systemctl restart docker
Kesalahan 6: Kubernetes / Docker Swarm — Proxy Tidak Bekerja di Semua Node
Di lingkungan cluster, proxy perlu diatur di setiap node secara terpisah. Untuk Kubernetes, Anda juga perlu mengatur variabel lingkungan dalam manifest pod atau melalui ConfigMap. Ini dapat diotomatisasi melalui Ansible atau alat manajemen konfigurasi lainnya.
Kesimpulan
Pengaturan proxy di Docker bukanlah satu pengaturan, tetapi tiga tingkat independen: daemon untuk menarik gambar, waktu pembangunan untuk membangun, dan runtime untuk kontainer yang sedang berjalan. Dengan memahami arsitektur ini, Anda dapat dengan fleksibel mengelola lalu lintas mana yang melewati proxy dan mana yang langsung.
Daftar periksa singkat untuk pengaturan yang benar:
- ✅ Untuk menarik gambar — atur systemd override dengan variabel HTTP_PROXY dan HTTPS_PROXY
- ✅ Untuk pembangunan — kirimkan proxy melalui
--build-argatau~/.docker/config.json - ✅ Untuk runtime — gunakan variabel lingkungan melalui
-eatau--env-file - ✅ Selalu atur NO_PROXY untuk alamat internal
- ✅ Jangan simpan password proxy di Dockerfile — gunakan build-args dan file .env
- ✅ Untuk pipeline CI/CD, pilih proxy data center yang cepat
- ✅ Untuk kontainer pengambil data — proxy residensial atau mobile
Jika aplikasi kontainer Anda melakukan permintaan ke layanan eksternal, mengambil data, atau bekerja dengan API yang memiliki geo-restriksi, kami merekomendasikan untuk menggunakan proxy residensial — mereka memberikan tingkat kepercayaan yang tinggi dari layanan dan risiko pemblokiran yang minimal bahkan dengan pekerjaan yang intensif.