SSD Nodes Learn Hosting plans →
मार्गदर्शक Matt Connorद्वारे Matt Connor · अपडेटेड 2026-08-30

VPS वर Podman आणि Docker मध्ये नेमका फरक काय?

Podman daemon शिवाय आणि default rootless चालतो. VPS वर यामुळे compose files, quadlets, ports आणि volume ownership मध्ये नेमके कोणते बदल होतात ते जाणून घ्या.

Podman आणि Docker मध्ये प्रत्यक्षात काय फरक आहे

Podman आणि Docker VPS वर समान OCI (open container initiative) images चालवतात. त्यामुळे कोणते software चालवता येईल, हा निवडीचा मुद्दा नाही. फरक process model मध्ये आहे. Docker असा root daemon चालवतो जो प्रत्येक container चे व्यवस्थापन करतो. `docker command हा त्या daemon ला काम करण्यास सांगणारा लहान client आहे. Podman मध्ये daemon नसतो. podman run` command container सुरू करते आणि तो ज्या process ने command चालवली त्याचा child process म्हणून, तुमच्या स्वतःच्या unprivileged user अंतर्गत चालतो.

या एका फरकामुळे इतर सर्व बाबी ठरतात. Auto-start ची जबाबदारी daemon ऐवजी systemd ची असते. Volume ownership user namespace मधून जाते. त्यामुळे host वर `ls -l ने दिसणारा owner हा container ला दिसणारा owner नसतो. Kernel setting बदलल्याशिवाय 1024 पेक्षा कमी ports वर bind करता येत नाही. docker` CLI (command line interface) wrapper मार्फत कार्यरत राहते; मात्र एखाद्या घटकाला Docker socket आवश्यक असेल तेव्हा ही सुसंगतता संपते.

No daemon: कंटेनर सुरू केल्यावर प्रत्यक्षात काय चालते

Docker host वर, pstree -a root म्हणून dockerd दाखवते, त्याच्या शेजारी containerd दाखवते आणि प्रत्येक चालू container साठी एक containerd-shim-runc-v2 दाखवते. तुमचे application त्या shim चे child असते आणि shim हा PID 1 चा child असतो. Container आणि तो सुरू करणारा shell यांच्यात कोणतेही थेट कनेक्शन नसते. daemon थांबवल्यास त्या host वरील सर्व container साठीचे control plane गमावता. Default live-restore setting बंद असल्यास, systemctl restart docker तुमचे container देखील पुन्हा सुरू करते.

Podman मध्ये यासारखी equivalent process नसते. Container सुरू केल्यावर एक conmon (container monitor) process मिळते. ही process container ची मुख्य process सांभाळते आणि command चालवणाऱ्या user च्या मालकीची असते.

podman run -d --name web -p 8080:80 docker.io/library/caddy:2
ps -o user,pid,ppid,args -C conmon
curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:8080

ps ने तुमचा login user म्हणून चालणारी conmon दाखवली पाहिजे; ती root म्हणून दाखवली जाऊ नये. curl ने 200 दाखवले पाहिजे. Container ची मालकी कोणत्याही central service कडे नसल्यामुळे, sudo apt upgrade podman आधीपासून चालू असलेली कोणतीही गोष्ट थांबवत नाही. तसेच एका container चा monitor crash झाल्यास इतर container देखील त्याच्यासोबत थांबत नाहीत.

Daemon नसल्यामुळे काही मर्यादा देखील येतात. Reboot नंतर तुमचे container सुरू करणारी कोणतीही process नसते. Docker चे --restart=always हे boot वेळी daemon पूर्ण करणारे वचन आहे. Podman त्याऐवजी systemd वापरते. खालील quadlet section यासाठीच आहे.

Socket हा या रचनेचा दुसरा भाग आहे. /var/run/docker.sock हा root च्या मालकीचा API (application programming interface) endpoint आहे. त्यावर write करू शकणारी कोणतीही process host filesystem mount करणारा privileged container सुरू करू शकते. एखाद्या user ला docker group मध्ये जोडल्यास त्या user ला अप्रत्यक्ष मार्गाने root access मिळतो. याची तुलना प्रत्येक service account ला आवश्यक तेवढाच access देणे यासोबत करणे उपयुक्त ठरेल. तुम्ही स्पष्टपणे मागणी केल्याशिवाय Podman कोणताही socket expose करत नाही. मिळणारा socket /run/user/<uid>/podman/podman.sock वरील एका user च्या मालकीचा असतो.

Ubuntu 24.04 वर Podman स्थापित करा आणि rootless प्रत्यक्षात कार्यरत आहे याची पुष्टी करा

sudo apt update
sudo apt install -y podman uidmap
podman --version
podman info | grep -i rootless

uidmap पॅकेज newuidmap आणि newgidmap उपलब्ध करून देते. हे setuid सहाय्यक आहेत. ते सामान्य वापरकर्त्याला subordinate IDs ची श्रेणी वापरण्याची परवानगी देतात. त्यांच्याशिवाय rootless containers सुरू होत नाहीत. podman info ने rootless: true दाखवले पाहिजे.

ऑगस्ट 2026 मध्ये तपासल्याप्रमाणे, Ubuntu 24.04 मध्ये Podman 4.9 आणि Debian 13 मध्ये Podman 5.x उपलब्ध आहे. हा फरक महत्त्वाचा आहे, कारण quadlet files साठी 4.4 किंवा त्यानंतरची आवृत्ती आवश्यक आहे आणि .pod quadlet files साठी 5.0 आवश्यक आहे. upstream documentation मधील उदाहरण कॉपी करण्यापूर्वी podman --version चालवा.

प्रत्येक rootless वापरकर्त्याला subordinate ID ची श्रेणी आवश्यक असते:

grep "$USER" /etc/subuid /etc/subgid

Ubuntu वर adduser ने तयार केलेल्या वापरकर्त्याला ही श्रेणी आपोआप मिळते. useradd -M ने किंवा configuration tool द्वारे तयार केलेल्या वापरकर्त्याला ती अनेकदा मिळत नाही. त्यावेळी त्रुटीमध्ये हे स्पष्ट दिसते:

Error: cannot find UID/GID for user deploy: no subuid ranges found for user "deploy" in /etc/subuid - check rootless mode in man pages.

श्रेणी नियुक्त करा. त्यानंतर नवीन mapping वापरली जावी यासाठी त्या वापरकर्त्याचे storage reset करा:

sudo usermod --add-subuids 100000-165535 --add-subgids 100000-165535 deploy
podman system migrate

पहिल्यांदा चालवताना आणखी एक अनपेक्षित बाब आढळते. Podman Docker Hub गृहीत धरत नाही. लहान image name चे निराकरण /etc/containers/registries.conf मधील unqualified-search-registries विरुद्ध केले जाते. Terminal जोडलेले नसलेल्या script मध्ये pull केल्यास short-name resolution enforced but cannot prompt without a TTY त्रुटी येते. प्रत्येक वेळी पूर्ण name लिहा. nginx ऐवजी docker.io/library/nginx:1.27 वापरा.

भाड्याच्या सर्व्हरवर rootless containers प्रत्यक्षात काय फायदे देतात

Rootless container user namespace मध्ये चालतो. ही kernel ची सुविधा process ला user IDs चा स्वतंत्र खासगी नकाशा देते. Namespace च्या आत container मधील superuser हा UID (user ID) 0 असतो. Namespace च्या बाहेर, तुमच्या VPS वर, तोच process तुमचा सामान्य login user असतो. Container मधील root हा host वरील root नसतो.

या फायद्याची खरी व्याप्ती एवढीच आहे. एखादी image root म्हणून चालण्याचा आग्रह धरत असेल, एखाद्या web application मध्ये remote code execution ची त्रुटी असेल किंवा बाहेर UID 0 असण्यावर अवलंबून असलेला escape असेल, तरी त्या सर्वांना मशीनच्या permissions ऐवजी तुमच्या unprivileged user च्या permissions मिळतात. मात्र rootless तुम्हाला kernel मधील bugs पासून संरक्षण देत नाही. ते तुमच्या स्वतःच्या files चेही संरक्षण करत नाही, कारण escaped process तुमच्या user म्हणून चालत असतो आणि तुम्ही वाचू शकता ते सर्व तो वाचू शकतो. UID mapping इतकेच isolation चे unit देखील महत्त्वाचे आहे. हे पुढील तुम्ही लहान मशीनप्रमाणे प्रशासित करत असलेल्या संपूर्ण userland ला वेढणाऱ्या FreeBSD jail मध्ये अधिक स्पष्टपणे दिसते; registry मधून आणलेल्या layered image मध्ये ते तितके स्पष्ट दिसत नाही.

Docker देखील rootless पद्धतीने चालवता येतो. dockerd-rootless-setuptool.sh install प्रत्येक user साठी daemon सेट करतो आणि तो चांगले काम करतो. फरक default कोणत्या दिशेने असतो यात आहे. Podman वापरल्यावर rootless आपोआप मिळते; त्यामुळे तुमची पहिली अडचण port 80 bind करू न शकणारा container असतो, दोन वर्षे शांतपणे root म्हणून चालणारी service नाही.

माझ्या volume मधील फाइल्स UID 100999 च्या मालकीच्या का आहेत?

हे त्याच user namespace मुळे होते. Container मधील UID 0 तुमच्या host UID शी map होतो. Container मधील UID 1 तुमच्या subuid range मधील पहिल्या ID शी map होतो आणि त्यानंतर संख्या क्रमाने वाढते. Range 100000 पासून सुरू होत असल्यास, container मधील UID 1000 host वर 100999 म्हणून दिसतो.

mkdir -p "$PWD/data"
podman run --rm --user 1000 -v "$PWD/data:/data" docker.io/library/alpine:3 sh -c 'id -u; touch /data/f'
ls -ln "$PWD/data"

Container `1000 दाखवतो. Host वरील listing मध्ये मालक 100999 दिसतो, कारण 100000 अधिक 1000 वजा 1 म्हणजे 100999. काहीही बिघडलेले नाही. साधा chown` हे दुरुस्त करणार नाही, कारण namespace च्या बाहेर तुमच्या unprivileged user ला फाइलची मालकी बदलता येत नाही.

यातून बाहेर पडण्याचे चार मार्ग:

  • `podman unshare chown 1000:1000 "$PWD/data"` त्याच user namespace मध्ये chown चालवतो. त्यामुळे संख्यांचा अर्थ container साठी योग्य राहतो.
  • `-v "$PWD/data:/data:U"` Podman ला source directory ची मालकी तुमच्यासाठी दुरुस्त करण्यास सांगतो. हा पर्याय नवीन directory वर वापरा; महत्त्वाच्या डेटावर वापरू नका.
  • `--userns=keep-id` तुमचा host UID container मधील त्याच UID शी map करतो. त्यामुळे नवीन फाइल्स तुमच्या मालकीच्या म्हणून तयार होतात.
  • `-v appdata:/data` सारखा named volume हा प्रश्नच टाळतो, कारण Podman तो तुमच्या स्वतःच्या storage मध्ये आधीच योग्य मालकीसह तयार करतो.

Docker मध्ये ही समस्या आली असेल, तर हा त्याच समस्येचा एक स्तर वरचा प्रकार आहे. अनेक images उपलब्ध करून देत असलेले PUID आणि PGID variables container मधील process कोणता UID वापरतो ते ठरवतात. Rootless Podman अंतर्गत तो UID पुन्हा एकदा map होतो. Rootless container मधील `PUID=1000` वापरून लिहिलेल्या host फाइल्स तरीही 100999 च्या मालकीच्या असतात. हा दुसरा mapping लक्षात घेऊन संख्या निवडा किंवा डेटा named volume मध्ये हलवा आणि हा प्रश्न टाळा.

Mounts संदर्भात आणखी दोन नोंदी. Fedora आणि RHEL उदाहरणांमध्ये दिसणारे `:z आणि :Z` flags हे SELinux relabel पर्याय आहेत. Ubuntu मध्ये AppArmor वापरले जाते, त्यामुळे तेथे या flags मुळे काहीही होत नाही. Rootless Podman तुमचा user वाचू शकत नसलेली host directory mount करू शकत नाही. ही मर्यादा अपेक्षित आहे; ती दोष नाही.

rootless Podman पोर्ट 80 publish करण्यास नकार का देतो?

कारण 1024 पेक्षा कमी पोर्टशी bind करण्यासाठी तुमच्या user कडे नसलेला privilege आवश्यक असतो. Error मध्ये उपाय स्पष्ट दिलेला असतो:

Error: rootlessport cannot expose privileged port 80, you can add 'net.ipv4.ip_unprivileged_port_start=80' to /etc/sysctl.conf (currently 1024), or choose a larger port number (>= 1024): listen tcp 0.0.0.0:80: bind: permission denied

दोन्हीपैकी कोणताही उपाय कार्य करतो. संपूर्ण host साठी threshold कमी करा:

echo 'net.ipv4.ip_unprivileged_port_start=80' | sudo tee /etc/sysctl.d/99-podman.conf
sudo sysctl --system
sysctl net.ipv4.ip_unprivileged_port_start

शेवटच्या command ने 80 परत echo केले पाहिजे. ही setting नेमके काय करते, हे स्पष्ट समजून घ्या: आता मशीनवरील प्रत्येक user 80 आणि 443 वर bind करू शकतो; फक्त containers चालवणारा userच नाही. एका administrator असलेल्या VPS वर हा स्वीकार्य तडजोडीचा पर्याय आहे. इतर लोकांची accounts असलेल्या server वर हा योग्य पर्याय नाही. दुसरा उपाय म्हणजे 8080 वर publish करून समोर reverse proxy ठेवणे. तसेच nginx वर certbot ने certificates जारी करून त्यांचे renewal करणे अपेक्षित असल्याने हा पर्याय अधिक योग्य ठरतो.

rootless publishing मुळे तुमच्या application ला दिसणारी माहितीही बदलते. Podman 4.x मध्ये rootlesskit port handler सह slirp4netns हे default वापरले जाते. Forward केलेल्या connections मध्ये source address बदललेला असतो. त्यामुळे access log मध्ये प्रत्येक visitor 10.0.2.100 म्हणून नोंदवला जातो. Podman 5.0 मध्ये default pasta करण्यात आले. यामुळे मूळ client address कायम राहतो. 4.x मध्ये --network slirp4netns:port_handler=slirp4netns वापरल्यास खरा source address परत मिळतो; मात्र throughput काही प्रमाणात कमी होतो.

यामध्ये एक चांगली बाब आहे. rootless published port हा सामान्य process च्या मालकीचा ordinary listening socket असतो. त्यामुळे तुमच्या firewall चे input rules त्याला लागू होतात. Docker ports publish करताना NAT (network address translation) rules आणि स्वतःचे forwarding accepts लिहितो. म्हणूनच तुम्ही अडवण्यासाठी लावलेला ufw rule published Docker port वर लागू होत नाही. Rootful Podman समान plumbing वापरतो आणि त्याच अडचणीचा परिणाम त्यावरही होतो. rootless मध्ये ही अडचण येत नाही.

Podman अंतर्गत माझ्या Docker Compose फाइल्स अजूनही कार्य करतील का?

बहुतेक वेळा, दोन वेगवेगळ्या पद्धतींनी. पहिली पद्धत म्हणजे podman-compose. ही स्वतंत्र अंमलबजावणी समान फाइल वाचते आणि Podman CLI चालवते:

sudo apt install -y podman-compose
podman-compose up -d
podman ps

दुसरी पद्धत म्हणजे Podman च्या Docker-सुसंगत API शी प्रति-वापरकर्ता socket द्वारे संवाद साधणारे खरे Docker Compose:

systemctl --user enable --now podman.socket
export DOCKER_HOST="unix:///run/user/$(id -u)/podman/podman.sock"
docker compose up -d
podman ps

docker compose ps आणि podman ps यांनी समान containers दाखवले पाहिजेत, कारण containers चा एकच संच असतो. Name resolution देखील कार्य करते. Podman चा default network backend, netavark, aardvark-dns चालवतो. त्यामुळे user-defined network वरील containers एकमेकांना नावाने शोधू शकतात.

काही मर्यादा प्रत्यक्षात आहेत. /var/run/docker.sock mount करणाऱ्या कोणत्याही घटकाला Podman socket कडे निर्देशित करावे लागते किंवा तो काढून टाकावा लागतो. User namespace अंतर्गत network_mode: host चे वर्तन वेगळे असते. condition: service_healthy सह depends_on चे समर्थन podman-compose च्या आवृत्तीनुसार असमान आहे. restart: always स्वतःहून reboot नंतर सुरू राहत नाही; पुढील विभागात त्याचे निराकरण केले आहे. एका फाइलमध्ये multi-container stack वर्णन करण्यासाठी Compose अजूनही उपयुक्त आहे आणि Podman अंतर्गत ते translation layer म्हणून कार्य करते. अनेक वर्षे टिकवून ठेवायच्या stack साठी ती quadlets मध्ये रूपांतरित करा आणि दोन abstraction ऐवजी एकच abstraction व्यवस्थापित करा.

Pods: Docker कडे ज्याचे उत्तर नाही अशी संकल्पना

Pod म्हणजे एकाच network namespace share करणाऱ्या containers चा समूह. Podman हा namespace सक्रिय ठेवण्यासाठी एक लहान infra container सुरू करतो. त्यानंतर हे सदस्य कोणतेही user-defined network किंवा service discovery न वापरता 127.0.0.1 वर एकमेकांशी संपर्क साधतात.

podman pod create --name app -p 8080:80
podman run -d --pod app --name app-cache docker.io/library/redis:7
podman run -d --pod app --name app-web docker.io/library/nginx:1.27
podman pod ps
podman ps --pod

podman pod ps ने infra container धरून तीन containers असलेला pod Running दाखवला पाहिजे. आता web container Redis शी 127.0.0.1:6379 वर संपर्क साधतो, app-cache:6379 वर नाही. Shared namespace मुळे दोन नियम लागू होतात: ports pod वर publish करा, सदस्यावर कधीही करू नका; तसेच कोणतेही दोन सदस्य एकाच port वर listen करू शकत नाहीत.

ही Kubernetes ची पद्धत आहे आणि Podman तिचा पुरेपूर वापर करतो. चालू असलेल्या घटकांवरून podman kube generate app > app.yaml Kubernetes manifest लिहितो. जुन्या packages मध्ये त्याचे नाव podman generate kube असे लिहिलेले आढळते. podman kube play app.yaml हा manifest दुसऱ्या host वर पुन्हा तयार करतो. Quadlet मध्ये .kube unit type आहे, जो अशी file systemd service म्हणून चालवतो. Services गटबद्ध करण्याची ही खरोखर वेगळी पद्धत आहे. Kubernetes भविष्यात वापरण्याची शक्यता असल्यास Podman निवडण्याचे हे सर्वात मजबूत कारण आहे.

डेमनशिवाय स्वयंचलित सुरूवात: quadlet units

Quadlet हा systemd generator आहे. कंटेनरचे वर्णन करणारी लहान फाइल तो boot वेळी प्रत्यक्ष systemd service मध्ये रूपांतरित करतो. Rootless user साठी फाइल्स ~/.config/containers/systemd/ मध्ये, तर root साठी /etc/containers/systemd/ मध्ये ठेवतात.

~/.config/containers/systemd/caddy.container:

[Unit]
Description=Caddy web server
After=network-online.target

[Container]
Image=docker.io/library/caddy:2
ContainerName=caddy
PublishPort=8080:80
Volume=caddy-data.volume:/data
Environment=TZ=UTC
AutoUpdate=registry

[Service]
Restart=always
MemoryMax=512M

[Install]
WantedBy=default.target

~/.config/containers/systemd/caddy-data.volume जवळजवळ रिकामी असू शकते, कारण section header मुळेच volume तयार होते:

[Volume]
systemctl --user daemon-reload
systemctl --user start caddy
systemctl --user status caddy
journalctl --user -u caddy -n 50

Service चे नाव filename वरून येते: caddy.container चे रूपांतर caddy.service मध्ये होते. systemctl --user enable caddy चालवू नका. Generated units enable करता येत नाहीत आणि systemd Failed to enable unit: Unit /run/user/1000/systemd/generator/caddy.service is transient or generated. असे उत्तर देते. [Install] section मुळे boot वेळी container सुरू होतो, तर फाइलमध्ये बदल केल्यानंतर unit पुन्हा तयार करण्याचे काम daemon-reload करते.

आता जवळजवळ प्रत्येकाला अडचणीत आणणारी setting:

sudo loginctl enable-linger deploy
loginctl show-user deploy --property=Linger

Linger=yes अपेक्षित आहे. Linger नसल्यास तुमचे शेवटचे SSH connection बंद झाल्यावर systemd संपूर्ण user session बंद करते. त्यामुळे सर्व rootless containers त्यासोबत थांबतात आणि boot वेळी त्यांपैकी एकही पुन्हा सुरू होत नाही. तुम्ही logout केल्यावर containers नाहीसे होत असतील, तर याचे कारण नेहमी हेच असते.

Container हा सामान्य service unit मधील मुख्य process असल्यामुळे systemd ची स्वतःची controls थेट लागू होतात. [Service] section मधील MemoryMax= आणि CPUQuota= हे systemd द्वारे नियंत्रित केलेल्या इतर कोणत्याही service प्रमाणेच कार्य करतात. यासाठी cgroup v2 (control group version 2) आवश्यक आहे. Ubuntu मध्ये 22.04 पासून ते default आहे. podman info | grep -i cgroup वापरून खात्री करा.

Updates साठी यासोबत जुळणारी यंत्रणा आहे. AutoUpdate=registry आणि systemctl --user enable --now podman-auto-update.timer एकत्र वापरल्यास त्याच tag साठी registry मध्ये नवीन image आहे का ते तपासले जाते, unit पुन्हा सुरू केला जातो आणि नवीन container सुरू होण्यात अपयशी ठरल्यास मागील image वर rollback केला जातो. त्यातून कोणते बदल होतील हे आधी पाहण्यासाठी podman auto-update --dry-run चालवा. जुना podman generate systemd command अजूनही उपलब्ध आहे, परंतु तो deprecated आहे. त्यामुळे नवीन कामासाठी quadlets लिहा.

Docker alias कुठे लागू होतो आणि कुठे लागू होत नाही

sudo apt install -y podman-docker
sudo touch /etc/containers/nodocker
docker ps

podman-docker एक /usr/bin/docker wrapper install करतो, जो Podman ला call करतो. nodocker file नसल्यास, प्रत्येक call आधी Emulate Docker CLI using podman. Create /etc/containers/nodocker to quiet msg. छापतो. हा wrapper तुम्ही दिवसभर टाइप करत असलेल्या commands साठी लागू होतो: run, ps, logs, exec, build, pull, push, inspect, cp, volume, network.

मात्र काही महत्त्वाच्या गोष्टी लागू होत नाहीत. Swarm mode साठी कोणताही समतुल्य पर्याय नाही. त्यामुळे Swarm stack चालवण्यासाठी Podman मध्ये जागा नाही. Docker socket शी संवाद साधणाऱ्या tools साठी Podman socket export केलेले असणे आवश्यक आहे. तरीही काही tools मधील फरक लक्षात येतो. Traefik चा Docker provider /run/user/<uid>/podman/podman.sock कडे निर्देश केल्यास कार्य करतो. Watchtower साठी मात्र कोणताही उपयोग नाही, कारण ते काम podman auto-update करतो. Storage स्वतंत्र असते. त्यामुळे Docker ने आधी pull केलेल्या images Podman ला दिसत नाहीत. तसेच व्यस्त Docker host वरील podman images सुरुवातीला रिकामा असतो.

चालू stack चे टप्प्याटप्प्याने स्थलांतर

  1. कंटेनरचे मालकत्व असलेला unprivileged user तयार करा किंवा निवडा आणि /etc/subuid मध्ये त्याच्यासाठी range आहे याची खात्री करा.
  2. Registry मधून घेतलेल्या सर्व गोष्टी fully qualified names वापरून पुन्हा pull करा. Podman चे स्वतःचे image store असते; ते Docker चे image store वाचत नाही.
  3. स्थानिक पातळीवर build केलेल्या images docker save app:1.4 | podman load वापरून दुसरीकडे हलवा.
  4. Docker container थांबवा, प्रत्येक volume मधील contents /var/lib/docker/volumes/<name>/_data मधून बाहेर copy करा आणि नंतर podman unshare chown -R 1000:1000 <path> वापरून ownership दुरुस्त करा.
  5. Port बाबतचा निर्णय घ्या: reverse proxy मागे 1024 पेक्षा मोठा port publish करा किंवा net.ipv4.ip_unprivileged_port_start सेट करा.
  6. प्रत्येक container साठी एक quadlet file लिहा, systemctl --user daemon-reload चालवा आणि प्रत्येक service सुरू करा.
  7. sudo loginctl enable-linger <user> चालवा, VPS reboot करा, पुन्हा login करा आणि podman ps मध्ये सर्व services पुन्हा सूचीबद्ध आहेत का ते तपासा.

दोन्ही engines कोणतीही गोष्ट share करत नाहीत: image storage आणि networks स्वतंत्र असतात. त्यामुळे स्थलांतर सुरू असताना दोन्ही engines चालू ठेवता येतात. त्यांच्यात संघर्ष होऊ शकतो तो फक्त host port number साठी. एक service हलवा, तिचे एक दिवस निरीक्षण करा आणि त्यानंतर पुढील service हलवा.

Podman विरुद्ध Docker: तुमच्या VPS वर कोणते असावे?

तुमचा stack इतर लोकही maintain करत असलेल्या compose files मध्ये असेल किंवा Docker socket शी संवाद साधणाऱ्या tooling वर तुमचे अवलंबित्व असेल, तर Docker वरच राहा. इतर सर्वजण जे लिहितात त्याच्याशी compatibility हे खरे feature आहे आणि Docker मध्ये ते अधिक आहे. तुमच्या team मधील सर्व laptops Docker चालवत असतील, तर production मध्येही तेच engine चालवल्याने ठोस फायदा होतो.

VPS वर तुम्ही end-to-end नियंत्रित करत असलेल्या काही services असतील किंवा प्रत्येक application स्वतंत्र unprivileged user अंतर्गत चालवायचे असेल आणि host वर docker group अजिबात नको असेल, तर Podman कडे वळा. Distribution alignment देखील महत्त्वाचे आहे: RHEL आणि त्याच्या rebuilds मध्ये समर्थित engine म्हणून Podman releases केले जाते. त्यामुळे त्या systems वर Podman हा कमी अनपेक्षित अडचणींचा मार्ग आहे. तरीही यापैकी एखाद्या host वर Docker हवे असल्यास, Rocky Linux आणि AlmaLinux वरील dnf मार्ग तेथे आधीपासून docker command चे ownership असलेला podman-docker wrapper हटवून सुरू होतो. इतर सर्व गोष्टी systemd units ने supervise करत असाल, तर quadlets हे शिकण्यासाठी आणखी एक नवीन tool वाटणार नाहीत; ते गहाळ असलेला भाग मिळाल्यासारखे वाटतील.

एक मधला पर्यायही उल्लेख करण्यासारखा आहे. Rootful Podman Docker सारखेच वागते, wrapper मार्फत docker command ठेवते आणि तरीही सतत चालणारा daemon काढून टाकते. मात्र यामध्ये rootless भाग नसतो. तुमच्या security position मध्ये बदल घडवणारा हाच भाग आहे. त्यामुळे याकडे अंतिम उपाय म्हणून नव्हे, तर पुढील टप्प्याकडे जाणारा मधला टप्पा म्हणून पाहा.

तुमचा पहिला container host अजून तयार करत असाल, तर नवीन VPS वरील Docker setup आणि hardening चा मार्ग अधिक लहान आहे आणि त्यातून मिळालेले ज्ञान वाया जाणार नाही. दोन्ही engines अंतर्गत images आणि volumes हेच objects असतात. त्यामुळे पुढील migration मध्ये तुमच्या services supervise करण्याची पद्धत बदलेल; बाकी फारच कमी बदल होईल.

FAQ

Podman हे Docker चे drop-in replacement आहे का?

तुम्ही टाइप करता त्या commands च्या दृष्टीने ते जवळपास तसेच आहे. podman-docker install केल्यावर /usr/bin/docker wrapper मिळतो आणि run, ps, build, logs आणि exec त्याच पद्धतीने कार्य करतात. मात्र ते daemon चे replacement नाही. Swarm साठी समतुल्य पर्याय नाही. /var/run/docker.sock शी जोडणाऱ्या tools ना per-user Podman socket कडे निर्देशित करावे लागते. तसेच Docker ने pull केलेल्या images Podman ला दिसत नाहीत, कारण दोन्ही स्वतंत्र storage वापरतात.

SSH मधून logout केल्यावर माझे rootless Podman containers का थांबतात?

तुमचे शेवटचे login बंद झाल्यावर systemd user session आणि त्यासोबत त्यातील प्रत्येक user service थांबवते. sudo loginctl enable-linger <user> चालवा आणि त्यानंतर loginctl show-user <user> --property=Linger चे output Linger=yes आहे का ते तपासा. Linger मुळे active session नसतानाही त्या user चे systemd instance सुरू राहते. त्यामुळे reboot नंतर containers पुन्हा सुरू होतात.

माझ्या volume मधील files च्या मालकीचा UID 100999 का आहे?

Rootless Podman container UID 0 ला तुमच्या host user शी map करते. त्यानंतर container UID 1 आणि पुढील UIDs तुमच्या subuid range वर map केले जातात. 100000 पासून सुरू होणाऱ्या range मध्ये container UID 1000 हा host वर 100999 होतो. podman unshare chown 1000:1000 /path/to/data वापरून namespace च्या आतून ते दुरुस्त करा. पहिल्या run वेळी :U flag वापरून mount करा. किंवा --userns=keep-id वापरा, ज्यामुळे container UIDs तुमच्या स्वतःच्या UID शी जुळतात.

Podman सोबत docker-compose.yml वापरत राहता येईल का?

होय, दोन मार्ग आहेत. podman-compose ही file वाचते आणि Podman CLI थेट चालवते. किंवा systemctl --user enable --now podman.socket वापरून compatibility socket enable करा, DOCKER_HOST=unix:///run/user/$(id -u)/podman/podman.sock set करा आणि त्यावर खरे docker compose चालवा. network_mode: host बाबत, Docker socket mount करणाऱ्या services बाबत आणि restart: always बाबत काही अडचणी अपेक्षित आहेत. reboot नंतर टिकून राहण्यासाठी restart: always ला quadlet unit आणि linger आवश्यक असतात.

Rootless मुळे containers खरोखर अधिक सुरक्षित होतात का?

यामुळे एक विशिष्ट धोका कमी होतो: rootless container मधून बाहेर पडणाऱ्या process कडे root चे permissions नसून तुमच्या unprivileged user चे permissions असतात. हा लाभ महत्त्वाचा आहे. म्हणूनच root-equivalent docker group ला rootless Podman मध्ये समतुल्य पर्याय नाही. मात्र यामुळे kernel vulnerabilities थांबत नाहीत. तुमचा स्वतःचा user वाचू शकतो अशा files चे संरक्षणही होत नाही. त्यामुळे कोणत्याही server वर कराल ते उर्वरित hardening उपाय येथेही लागू ठेवा.