VPS లో Podman vs Docker: అసలు తేడాలు ఏమిటి?
VPS లో Podman మరియు Docker మధ్య ఉన్న ప్రాథమిక వ్యత్యాసాలను తెలుసుకోండి. Daemon-less ఆర్కిటెక్చర్, rootless మోడ్, Quadlets, మరియు వాల్యూమ్ పర్మిషన్ల వంటి కీలక అంశాల పూర్తి విశ్లేషణ.
Podman మరియు Docker మధ్య ఉన్న అసలు తేడాలు ఏమిటి
Podman మరియు Docker రెండూ VPS పై ఒకే రకమైన OCI (open container initiative) images ను రన్ చేస్తాయి, కాబట్టి మీరు ఏ సాఫ్ట్వేర్ను రన్ చేయగలరు అనేది ఇక్కడ ప్రశ్న కాదు. వీటి మధ్య ఉన్న ప్రధాన వ్యత్యాసం వాటి process model లో ఉంది. Docker ఒక root daemon ను రన్ చేస్తుంది, ఇది ప్రతి container ను నియంత్రిస్తుంది; docker కమాండ్ అనేది ఒక చిన్న క్లయింట్ మాత్రమే, ఇది ఆ daemon కు పనులను అప్పగిస్తుంది. Podman కు ఎటువంటి daemon ఉండదు: podman run కమాండ్, కంటైనర్ను పిలిచిన process కు child process గా, మీ స్వంత unprivileged user కింద ప్రారంభిస్తుంది.
మిగిలినవన్నీ ఈ ఒక్క అంశంపైనే ఆధారపడి ఉంటాయి. Auto-start అనేది daemon బాధ్యత కాకుండా systemd బాధ్యతగా మారుతుంది. Volume ownership అనేది user namespace ద్వారా జరుగుతుంది, కాబట్టి హోస్ట్ మెషీన్ మీద ls -l తో మీరు చూసే owner, కంటైనర్ లోపల కనిపించే owner ఒకటే కాదు. మీరు kernel సెట్టింగ్ను మార్చే వరకు 1024 కంటే తక్కువ ఉన్న ports bind అవ్వవు. docker CLI (command line interface) ఒక wrapper ద్వారా పనిచేస్తూనే ఉంటుంది, కానీ ఏదైనా అప్లికేషన్ Docker socket ను కోరినప్పుడు మాత్రం ఇబ్బందులు ఎదురవుతాయి.
Daemon లేకపోవడం: మీరు కంటైనర్ను ప్రారంభించినప్పుడు వాస్తవానికి ఏమి రన్ అవుతుంది
Docker హోస్ట్లో, pstree -a కమాండ్ dockerd ను root గా, దాని పక్కన containerd ను, మరియు రన్ అవుతున్న ప్రతి కంటైనర్కు ఒక containerd-shim-runc-v2 ను చూపిస్తుంది. మీ అప్లికేషన్ ఆ shim యొక్క చైల్డ్ ప్రాసెస్, మరియు ఆ shim అనేది PID 1 యొక్క చైల్డ్ ప్రాసెస్. కంటైనర్ను ప్రారంభించిన షెల్కు, కంటైనర్కు మధ్య ఎటువంటి సంబంధం ఉండదు. మీరు daemon ను ఆపివేస్తే, ఆ బాక్స్లోని ప్రతి కంటైనర్ యొక్క కంట్రోల్ ప్లేన్ను కోల్పోతారు. డిఫాల్ట్ live-restore సెట్టింగ్ ఆఫ్ అయి ఉంటే, systemctl restart docker మీ కంటైనర్లను కూడా రీస్టార్ట్ చేస్తుంది.
Podman లో దీనికి సమానమైన ప్రాసెస్ ఏదీ ఉండదు. మీరు ఒక కంటైనర్ను ప్రారంభించినప్పుడు, కంటైనర్ యొక్క ప్రధాన ప్రాసెస్ను కలిగి ఉండే ఒక conmon (కంటైనర్ మానిటర్) ప్రాసెస్ మాత్రమే ఉంటుంది. ఇది కమాండ్ను రన్ చేసిన యూజర్ ఆధీనంలో ఉంటుంది.
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:8080ps కమాండ్ మీ లాగిన్ యూజర్ ద్వారా రన్ అవుతున్న conmon ను చూపాలి, root ద్వారా కాదు. అలాగే curl కమాండ్ 200 ను ప్రింట్ చేయాలి. కంటైనర్ను నియంత్రించే కేంద్ర సర్వీస్ ఏదీ లేనందున, sudo apt upgrade podman ఇప్పటికే రన్ అవుతున్న వాటిని ఆపదు. ఒక కంటైనర్ మానిటర్ క్రాష్ అయినా, అది మిగిలిన కంటైనర్లపై ప్రభావం చూపదు.
ఈ daemon లేకపోవడం వల్ల కొన్ని పరిమితులు కూడా ఉన్నాయి. రీబూట్ తర్వాత మీ కంటైనర్లను ఆటోమేటిక్గా ప్రారంభించేది ఏదీ ఉండదు. Docker లోని --restart=always అనేది బూట్ సమయంలో daemon ఇచ్చే హామీ. Podman లో దీనికి బదులుగా systemd ను ఉపయోగిస్తారు, దీని గురించే కింద ఉన్న quadlet విభాగం వివరిస్తుంది.
Socket అనేది ఈ విషయంలో మరో ముఖ్యమైన అంశం. /var/run/docker.sock అనేది root ఆధీనంలో ఉండే ఒక API (application programming interface) ఎండ్పాయింట్. దీనికి రైట్ యాక్సెస్ ఉన్న ఏ ప్రాసెస్ అయినా, హోస్ట్ ఫైల్సిస్టమ్ను మౌంట్ చేయగల ప్రివిలేజ్డ్ కంటైనర్ను ప్రారంభించగలదు. ఒక యూజర్ను docker గ్రూప్లో చేర్చడం అంటే, ఆ యూజర్కు పరోక్షంగా root యాక్సెస్ ఇచ్చినట్లే. దీని గురించి ప్రతి సర్వీస్ అకౌంట్కు అవసరమైన యాక్సెస్ మాత్రమే ఇవ్వడం విభాగంలో చదవడం మంచిది. Podman లో మీరు కోరితే తప్ప ఎటువంటి socket ఎక్స్పోజ్ అవ్వదు. ఒకవేళ మీరు socket ను ఉపయోగిస్తే, అది /run/user/<uid>/podman/podman.sock వద్ద ఒకే యూజర్కు చెంది ఉంటుంది.
Ubuntu 24.04లో Podman ఇన్స్టాల్ చేయడం మరియు rootless మోడ్ పనితీరును నిర్ధారించడం
sudo apt update
sudo apt install -y podman uidmap
podman --version
podman info | grep -i rootlessuidmap ప్యాకేజీ newuidmap మరియు newgidmap లను అందిస్తుంది. ఇవి setuid helpers, ఇవి సాధారణ వినియోగదారునికి subordinate ID పరిధిని కేటాయించడానికి అనుమతిస్తాయి; ఇవి లేకపోతే rootless containers ప్రారంభం కావు. podman info కమాండ్ rootless: true ను అవుట్పుట్గా చూపాలి.
ఆగస్టు 2026 నాటికి, Ubuntu 24.04 లో Podman 4.9 మరియు Debian 13 లో Podman 5.x వెర్షన్లు ఉన్నాయి. ఈ వెర్షన్ల మధ్య వ్యత్యాసం ముఖ్యమైనది, ఎందుకంటే quadlet ఫైళ్లకు 4.4 లేదా అంతకంటే కొత్త వెర్షన్ అవసరం, మరియు .pod quadlet ఫైళ్లకు 5.0 వెర్షన్ అవసరం. మీరు అప్స్ట్రీమ్ డాక్యుమెంటేషన్ నుండి ఏదైనా ఉదాహరణను కాపీ చేసే ముందు podman --version కమాండ్ను రన్ చేయండి.
ప్రతి rootless వినియోగదారునికి ఒక subordinate ID పరిధి అవసరం:
grep "$USER" /etc/subuid /etc/subgidUbuntu లో adduser ద్వారా సృష్టించబడిన వినియోగదారుకు ఈ పరిధి స్వయంచాలకంగా లభిస్తుంది. useradd -M ద్వారా లేదా ఇతర కాన్ఫిగరేషన్ టూల్స్ ద్వారా సృష్టించబడిన వినియోగదారుకు ఇది తరచుగా లభించదు, అప్పుడు ఈ క్రింది విధంగా వైఫల్యం సంభవిస్తుంది:
Error: cannot find UID/GID for user deploy: no subuid ranges found for user "deploy" in /etc/subuid - check rootless mode in man pages.ఒక పరిధిని కేటాయించండి, ఆపై ఆ వినియోగదారు నిల్వను (storage) రీసెట్ చేయండి, తద్వారా కొత్త మ్యాపింగ్ ఉపయోగించబడుతుంది:
sudo usermod --add-subuids 100000-165535 --add-subgids 100000-165535 deploy
podman system migrateమొదటిసారి రన్ చేసినప్పుడు ఎదురయ్యే మరో ఆశ్చర్యం: Podman డిఫాల్ట్గా Docker Hub ను పరిగణనలోకి తీసుకోదు. చిన్న ఇమేజ్ పేరును /etc/containers/registries.conf లోని unqualified-search-registries ద్వారా రిజాల్వ్ చేస్తుంది. టెర్మినల్ లేని స్క్రిప్ట్లో, ఈ pull ప్రక్రియ short-name resolution enforced but cannot prompt without a TTY ఎర్రర్తో విఫలమవుతుంది. ప్రతిసారీ పూర్తి పేరును రాయండి. nginx కి బదులుగా docker.io/library/nginx:1.27 ని ఉపయోగించండి.
అద్దె సర్వర్పై rootless containers మీకు నిజంగా ఏమి అందిస్తాయి
Rootless container అనేది user namespace లోపల నడుస్తుంది. ఇది ఒక kernel ఫీచర్, ఇది ఒక ప్రాసెస్కు దాని స్వంత ప్రైవేట్ యూజర్ IDల మ్యాప్ను అందిస్తుంది. ఆ namespace లోపల, కంటైనర్ యొక్క superuser అనేది UID (user ID) 0. కానీ బయట, మీ VPS పైన, అదే ప్రాసెస్ మీ సాధారణ లాగిన్ యూజర్గా ఉంటుంది. కంటైనర్లోని root అనేది హోస్ట్ మెషీన్ మీద root కాదు.
ఇదే దీని వల్ల కలిగే అసలైన ప్రయోజనం. root గానే రన్ అవ్వాలని పట్టుబట్టే ఇమేజ్, remote code execution బగ్ ఉన్న వెబ్ అప్లికేషన్, లేదా బయట UID 0 గా ఉండటంపై ఆధారపడే escape - ఇవన్నీ మెషీన్ యొక్క పూర్తి అధికారాలను పొందే బదులు, మీ unprivileged యూజర్ యొక్క అనుమతులను మాత్రమే పొందుతాయి. అయితే, rootless అనేది kernel బగ్స్ నుండి మిమ్మల్ని రక్షించదు. అలాగే, ఇది మీ స్వంత ఫైళ్లను కూడా కాపాడదు, ఎందుకంటే బయటపడిన (escaped) ప్రాసెస్ మీ యూజర్ పేరుతోనే నడుస్తుంది కాబట్టి, మీరు చదవగలిగే దేనినైనా అది చదవగలదు.
Docker కూడా rootless గా నడవగలదు. dockerd-rootless-setuptool.sh install ప్రతి యూజర్కు ఒక daemon ను సెటప్ చేస్తుంది మరియు ఇది బాగా పనిచేస్తుంది. తేడా ఏమిటంటే, డిఫాల్ట్గా ఏది ఎంచుకుంటుంది అనే దానిలోనే ఉంది. Podman తో మీరు అడగకుండానే rootless సౌకర్యం లభిస్తుంది. కాబట్టి, రెండేళ్లుగా నిశ్శబ్దంగా root గా నడుస్తున్న సర్వీస్ కంటే, port 80ని bind చేయలేని కంటైనర్ రూపంలో మీకు మొదటి వైఫల్యం ఎదురవుతుంది.
నా వాల్యూమ్ ఫైల్స్ UID 100999 కి ఎందుకు చెందుతున్నాయి?
ఇది అదే user namespace కారణంగా జరుగుతుంది. కంటైనర్ లోని UID 0 మీ హోస్ట్ UID కి మ్యాప్ అవుతుంది. కంటైనర్ లోని UID 1 మీ subuid పరిధిలోని మొదటి ID కి మ్యాప్ అవుతుంది, అక్కడి నుండి సంఖ్యలు పెరుగుతూ వెళ్తాయి. 100000 తో మొదలయ్యే పరిధిలో, కంటైనర్ UID 1000 అనేది హోస్ట్ మీద 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"కంటైనర్ 1000 అని ప్రింట్ చేస్తుంది. హోస్ట్ లిస్టింగ్ 100999 అని యజమానిని చూపిస్తుంది, ఎందుకంటే 100000 ప్లస్ 1000 మైనస్ 1 అంటే 100999. ఏదీ పాడవ్వలేదు, మరియు సాధారణ chown కమాండ్ దీనిని సరిచేయదు, ఎందుకంటే మీ unprivileged యూజర్ namespace వెలుపల ఫైల్ యాజమాన్యాన్ని మార్చలేరు.
దీని నుండి బయటపడటానికి నాలుగు మార్గాలు ఉన్నాయి:
podman unshare chown 1000:1000 "$PWD/data"కమాండ్ chown ను అదే user namespace లో రన్ చేస్తుంది, అక్కడ సంఖ్యలు కంటైనర్ కు అర్థమయ్యే విధంగా ఉంటాయి.-v "$PWD/data:/data:U"కమాండ్ సోర్స్ డైరెక్టరీ యాజమాన్యాన్ని మీ కోసం సరిచేయమని Podman ను అడుగుతుంది. దీనిని కొత్త డైరెక్టరీలపై వాడండి, మీకు ముఖ్యమైన డేటాపై కాదు.--userns=keep-idకమాండ్ మీ హోస్ట్ UID ని కంటైనర్ లోపల అదే UID కి మ్యాప్ చేస్తుంది, తద్వారా కొత్త ఫైల్స్ మీకు చెందినవిగా ఉంటాయి.-v appdata:/dataవంటి named volume ఈ సమస్యను నివారిస్తుంది, ఎందుకంటే Podman దానిని మీ స్వంత స్టోరేజ్ లోపల సరైన యాజమాన్యంతో సృష్టిస్తుంది.
మీరు Docker లో దీనితో ఇబ్బంది పడి ఉంటే, ఇది ఒక మెట్టు పైన అదే సమస్య. అనేక ఇమేజ్లు అందించే PUID మరియు PGID వేరియబుల్స్ కంటైనర్ లోపల ప్రాసెస్ ఉపయోగించే UID ని సెట్ చేస్తాయి, మరియు rootless Podman కింద ఆ UID రెండవసారి మ్యాప్ చేయబడుతుంది. rootless కంటైనర్ లోపల PUID=1000 ఇప్పటికీ 100999 యాజమాన్యంతోనే హోస్ట్ ఫైల్స్ను రాస్తుంది. ఆ రెండవ మ్యాపింగ్ను దృష్టిలో ఉంచుకుని సంఖ్యలను ఎంచుకోండి, లేదా డేటాను named volume లోకి తరలించి ఈ సమస్య గురించి ఆలోచించడం మానేయండి.
మౌంట్ల గురించి మరో రెండు గమనికలు. Fedora మరియు RHEL ఉదాహరణలలో మీరు చూసే :z మరియు :Z ఫ్లాగ్లు SELinux relabel ఆప్షన్లు, కాబట్టి అవి Ubuntu లో ఏమీ చేయవు. Rootless Podman మీ యూజర్ చదవలేని హోస్ట్ డైరెక్టరీని మౌంట్ చేయలేదు, ఇది లోపం కాదు, భద్రతా పరమైన ఉద్దేశ్యం.
Rootless Podman ఎందుకు 80 పోర్ట్ను పబ్లిష్ చేయడానికి నిరాకరిస్తుంది?
1024 కంటే తక్కువ ఉన్న పోర్ట్ను బైండ్ చేయడానికి మీ యూజర్కు లేని ప్రత్యేక అనుమతి (privilege) అవసరం. ఈ ఎర్రర్ దాన్ని ఎలా సరిచేయాలో తెలియజేస్తుంది:
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దీనికి రెండు పరిష్కారాలు ఉన్నాయి. హోస్ట్ మొత్తానికి ఈ పరిమితిని తగ్గించడం మొదటిది:
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చివరి కమాండ్ అవుట్పుట్గా 80 అని చూపించాలి. ఈ సెట్టింగ్ ఏమి చేస్తుందో స్పష్టంగా తెలుసుకోండి: ఇప్పుడు మెషీన్లోని ప్రతి యూజర్ 80 మరియు 443 పోర్ట్లను బైండ్ చేయగలరు, కేవలం కంటైనర్లను రన్ చేసే యూజర్ మాత్రమే కాదు. ఒకే అడ్మిన్ ఉన్న VPSలో ఇది ఆమోదయోగ్యమైన మార్పు. కానీ ఇతరుల అకౌంట్లు కూడా ఉన్న సర్వర్లో ఇది సరైనది కాదు. మరొక పరిష్కారం ఏమిటంటే, 8080 పోర్ట్పై పబ్లిష్ చేసి, ముందు ఒక రివర్స్ ప్రాక్సీని ఉంచడం. మీరు certbot ద్వారా nginxలో సర్టిఫికెట్లు జారీ చేయడం మరియు రెన్యూ చేయడం వంటి పనులను అక్కడే చేయాలనుకుంటారు.
Rootless పబ్లిషింగ్ మీ అప్లికేషన్ చూసే విధానాన్ని కూడా మారుస్తుంది. Podman 4.x డిఫాల్ట్గా rootlesskit పోర్ట్ హ్యాండ్లర్తో slirp4netnsని ఉపయోగిస్తుంది. దీనివల్ల ఫార్వర్డ్ చేయబడిన కనెక్షన్లు సోర్స్ అడ్రస్ మార్చబడి వస్తాయి, కాబట్టి యాక్సెస్ లాగ్లో ప్రతి విజిటర్ 10.0.2.100గా కనిపిస్తారు. Podman 5.0 డిఫాల్ట్ను pastaకి మార్చింది, ఇది అసలైన క్లయింట్ అడ్రస్ను అలాగే ఉంచుతుంది. 4.x వెర్షన్లో, --network slirp4netns:port_handler=slirp4netnsని ఉపయోగించడం ద్వారా కొంత throughput తగ్గినప్పటికీ అసలైన సోర్స్ అడ్రస్ను తిరిగి పొందవచ్చు.
ఇక్కడ ఒక మంచి విషయం ఉంది. Rootless పబ్లిష్ చేసిన పోర్ట్ అనేది ఒక సాధారణ ప్రాసెస్ యాజమాన్యంలోని లిజనింగ్ సాకెట్, కాబట్టి మీ ఫైర్వాల్ ఇన్పుట్ రూల్స్ దీనికి వర్తిస్తాయి. Docker పోర్ట్లను NAT (network address translation) రూల్స్ మరియు దాని స్వంత ఫార్వర్డింగ్ యాక్సెప్ట్ల ద్వారా పబ్లిష్ చేస్తుంది, అందుకే పబ్లిష్ చేసిన Docker పోర్ట్ మీరు బ్లాక్ చేయాలనుకున్న ufw రూల్ను పట్టించుకోదు. Rootful Podman కూడా ఇలాంటి పద్ధతినే ఉపయోగిస్తుంది మరియు అదే సమస్యను కలిగి ఉంటుంది. కానీ Rootless అలా కాదు.
నా Docker Compose ఫైళ్లు Podman కింద పనిచేస్తాయా?
చాలా వరకు పనిచేస్తాయి, దీనికి రెండు మార్గాలు ఉన్నాయి. మొదటిది podman-compose, ఇది అదే ఫైల్ను చదివి Podman CLIని నడిపించే ఒక ప్రత్యేక అమలు:
sudo apt install -y podman-compose
podman-compose up -d
podman psరెండవది, అసలైన Docker Compose, ఇది ప్రతి వినియోగదారునికి ఉండే socket ద్వారా Podman యొక్క Docker-compatible APIతో మాట్లాడుతుంది:
systemctl --user enable --now podman.socket
export DOCKER_HOST="unix:///run/user/$(id -u)/podman/podman.sock"
docker compose up -d
podman psdocker compose ps మరియు podman ps రెండూ ఒకే కంటైనర్ల జాబితాను చూపాలి, ఎందుకంటే అక్కడ ఉండేవి ఒకే సెట్ కంటైనర్లు. Name resolution కూడా పనిచేస్తుంది: Podman యొక్క డిఫాల్ట్ నెట్వర్క్ బ్యాకెండ్ అయిన netavark, aardvark-dnsని నడుపుతుంది, కాబట్టి వినియోగదారు నిర్వచించిన నెట్వర్క్లోని కంటైనర్లు ఒకదానికొకటి పేరు ద్వారా కనుగొనగలవు.
కొన్ని పరిమితులు ఉన్నాయి. /var/run/docker.sockని మౌంట్ చేసే ఏదైనా సరే Podman socket వైపు మళ్లించాలి లేదా తొలగించాలి. network_mode: host అనేది user namespace కింద భిన్నంగా ప్రవర్తిస్తుంది. depends_on తో పాటు condition: service_healthy వాడకం podman-compose వెర్షన్లలో అస్థిరంగా ఉంటుంది. restart: always అనేది రీబూట్ తర్వాత స్వయంచాలకంగా కొనసాగదు, దీనిని తదుపరి విభాగంలో పరిష్కరిస్తాము. ఒకే ఫైల్లో మల్టీ-కంటైనర్ స్టాక్ను వివరించడానికి Compose ఇప్పటికీ మంచి మార్గం, మరియు Podman కింద ఇది ఒక అనువాద పొర (translation layer) వలె పనిచేస్తుంది. మీరు ఏళ్ల తరబడి ఉంచాలనుకునే స్టాక్ కోసం, దానిని quadlets గా మార్చుకుని, రెండు అబ్స్ట్రాక్షన్లకు బదులుగా ఒకదానినే నిర్వహించడం ఉత్తమం.
Pods: Docker వద్ద లేని ఒక ఆలోచన
Pod అనేది ఒకే network namespace ను పంచుకునే కంటైనర్ల సమూహం. ఆ namespace ను తెరిచి ఉంచడానికి Podman ఒక చిన్న infra కంటైనర్ను ప్రారంభిస్తుంది. ఆ తర్వాత, సభ్య కంటైనర్లు ఏ విధమైన 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 --podpodman pod ps కమాండ్, infra కంటైనర్తో కలిపి మొత్తం మూడు కంటైనర్లు ఉన్న pod Running ను చూపాలి. ఇప్పుడు web కంటైనర్ Redis ను app-cache:6379 లో కాకుండా 127.0.0.1:6379 లో చేరుకుంటుంది. ఈ shared namespace వల్ల రెండు నియమాలు వర్తిస్తాయి: పోర్ట్లను pod స్థాయిలోనే publish చేయాలి, సభ్య కంటైనర్ల స్థాయిలో కాదు; అలాగే, ఏ ఇద్దరు సభ్యులు ఒకే పోర్ట్పై వినకూడదు (listen).
ఇది Kubernetes మోడల్, Podman దీనినే అనుసరిస్తుంది. podman kube generate app > app.yaml కమాండ్ ప్రస్తుతం నడుస్తున్న వాటి నుండి Kubernetes manifest ను రూపొందిస్తుంది (పాత ప్యాకేజీలలో దీనిని podman generate kube అని పిలుస్తారు), మరియు podman kube play app.yaml దానిని మరొక హోస్ట్పై తిరిగి సృష్టిస్తుంది. Quadlet లో .kube అనే unit రకం ఉంది, ఇది అటువంటి ఫైల్ను systemd సర్వీస్గా నడుపుతుంది. ఇది సేవలను సమూహపరచడానికి ఒక విభిన్నమైన మార్గం. మీ భవిష్యత్తులో ఎక్కడైనా Kubernetes వాడాల్సి వస్తే, Podman ను ఎంచుకోవడానికి ఇదే అత్యంత బలమైన కారణం.
Daemon లేకుండా ఆటో-స్టార్ట్: quadlet యూనిట్లు
Quadlet అనేది ఒక systemd జనరేటర్. ఇది బూట్ సమయంలో కంటైనర్ను వివరించే ఒక చిన్న ఫైల్ను నిజమైన systemd సర్వీస్గా మారుస్తుంది. ఫైల్లను rootless యూజర్ కోసం ~/.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 దాదాపు ఖాళీగా ఉండవచ్చు, ఎందుకంటే సెక్షన్ హెడర్ వాల్యూమ్ను సృష్టిస్తుంది:
[Volume]systemctl --user daemon-reload
systemctl --user start caddy
systemctl --user status caddy
journalctl --user -u caddy -n 50సర్వీస్ పేరు ఫైల్ పేరు నుండి వస్తుంది: caddy.container అనేది caddy.service అవుతుంది. systemctl --user enable caddy ను రన్ చేయవద్దు. జనరేట్ అయిన యూనిట్లను enable చేయలేము, మరియు systemd Failed to enable unit: Unit /run/user/1000/systemd/generator/caddy.service is transient or generated. అని సమాధానం ఇస్తుంది. [Install] సెక్షన్ బూట్ సమయంలో కంటైనర్ను ప్రారంభిస్తుంది, మరియు మీరు ఫైల్ను ఎడిట్ చేసిన తర్వాత daemon-reload యూనిట్ను తిరిగి జనరేట్ చేస్తుంది.
ఇప్పుడు దాదాపు అందరినీ ఇబ్బంది పెట్టే సెట్టింగ్:
sudo loginctl enable-linger deploy
loginctl show-user deploy --property=LingerLinger=yes ఉండాలని ఆశించండి. Linger లేకపోతే, మీ చివరి SSH కనెక్షన్ ముగిసినప్పుడు systemd మొత్తం యూజర్ సెషన్ను తొలగిస్తుంది, కాబట్టి ప్రతి rootless కంటైనర్ దానితో పాటు ఆగిపోతుంది మరియు బూట్ సమయంలో ఏవీ తిరిగి రావు. మీరు లాగ్ అవుట్ అయినప్పుడు అదృశ్యమయ్యే కంటైనర్లు ఎల్లప్పుడూ దీని వల్లే జరుగుతాయి.
కంటైనర్ అనేది సాధారణ సర్వీస్ యూనిట్ యొక్క ప్రధాన ప్రాసెస్ కాబట్టి, systemd యొక్క స్వంత నియంత్రణలు నేరుగా వర్తిస్తాయి. [Service] సెక్షన్లోని MemoryMax= మరియు CPUQuota=, systemd తో మీరు పరిమితం చేసే ఇతర సర్వీసుల మాదిరిగానే పనిచేస్తాయి. దీనికి cgroup v2 (కంట్రోల్ గ్రూప్ వెర్షన్ 2) అవసరం, ఇది Ubuntu లో 22.04 నుండి డిఫాల్ట్గా ఉంది. podman info | grep -i cgroup తో దీనిని నిర్ధారించుకోండి.
అప్డేట్లకు సరిపోలే మెకానిజం ఉంది. AutoUpdate=registry మరియు systemctl --user enable --now podman-auto-update.timer కలిపి అదే ట్యాగ్పై కొత్త ఇమేజ్ కోసం రిజిస్ట్రీని తనిఖీ చేస్తాయి, యూనిట్ను రీస్టార్ట్ చేస్తాయి, మరియు కొత్త కంటైనర్ ప్రారంభం కాకపోతే మునుపటి ఇమేజ్కు రోల్ బ్యాక్ చేస్తాయి. ఇది ఏమి మారుస్తుందో చూడటానికి ముందుగా podman auto-update --dry-run ను రన్ చేయండి. పాత podman generate systemd కమాండ్ ఇప్పటికీ ఉంది కానీ అది deprecated చేయబడింది, కాబట్టి కొత్త వాటి కోసం quadlets రాయండి.
Docker alias ఎక్కడ పనిచేస్తుంది, ఎక్కడ పనిచేయదు
sudo apt install -y podman-docker
sudo touch /etc/containers/nodocker
docker pspodman-docker అనేది /usr/bin/docker wrapper ను ఇన్స్టాల్ చేస్తుంది, ఇది Podman ను పిలుస్తుంది. nodocker ఫైల్ లేకపోతే, ప్రతి కాల్ మొదట Emulate Docker CLI using podman. Create /etc/containers/nodocker to quiet msg. అని ప్రింట్ చేస్తుంది. ఈ wrapper మీరు రోజూ వాడే కమాండ్లను కవర్ చేస్తుంది: run, ps, logs, exec, build, pull, push, inspect, cp, volume, network.
ఏవి పనిచేయవో వాటి జాబితా చిన్నది మరియు స్పష్టమైనది. Swarm mode కు సమానమైనది ఏదీ లేదు, కాబట్టి Swarm stack కు ఎక్కడా చోటు ఉండదు. Docker socket తో మాట్లాడే టూల్స్ Podman socket ను ఎగుమతి (export) చేయాల్సి ఉంటుంది, కొన్ని టూల్స్ ఇప్పటికీ తేడాను గుర్తిస్తాయి; Traefik యొక్క Docker provider ను /run/user/<uid>/podman/podman.sock కి పాయింట్ చేసినప్పుడు అది పనిచేస్తుంది, కానీ Watchtower కు అసలు చోటు లేదు, ఎందుకంటే podman auto-update ఆ పనిని చేస్తుంది. స్టోరేజ్ వేరుగా ఉంటుంది, కాబట్టి మీరు ఇప్పటికే Docker తో డౌన్లోడ్ చేసిన images ను Podman చూడలేదు, మరియు బిజీగా ఉన్న Docker host పై podman images ఖాళీగా ప్రారంభమవుతుంది.
నడుస్తున్న stack ను దశలవారీగా తరలించడం
- కంటైనర్లను నిర్వహించే unprivileged యూజర్ను సృష్టించండి లేదా ఎంచుకోండి, మరియు ఆ యూజర్కు
/etc/subuidలో ఒక range ఉందని నిర్ధారించుకోండి. - Registry నుంచి వచ్చిన ప్రతిదాన్ని fully qualified names ఉపయోగించి మళ్ళీ pull చేయండి. Podman కు సొంత image store ఉంటుంది, అది Docker ఇమేజ్లను చదవదు.
- స్థానికంగా build చేసిన ఇమేజ్లను
docker save app:1.4 | podman loadఉపయోగించి తరలించండి. - Docker కంటైనర్ను ఆపి,
/var/lib/docker/volumes/<name>/_dataనుంచి ప్రతి volume లోని కంటెంట్ను కాపీ చేయండి, ఆపైpodman unshare chown -R 1000:1000 <path>తో ownership ను సరిచేయండి. - Port సమస్యను పరిష్కరించండి: reverse proxy వెనుక 1024 పైన port ను publish చేయండి, లేదా
net.ipv4.ip_unprivileged_port_startను సెట్ చేయండి. - ప్రతి కంటైనర్కు ఒక quadlet ఫైల్ను రాయండి,
systemctl --user daemon-reloadరన్ చేయండి, మరియు ప్రతి సేవను ప్రారంభించండి. sudo loginctl enable-linger <user>రన్ చేయండి, VPS ను reboot చేయండి, తిరిగి లాగిన్ అయ్యిpodman psలో ప్రతి సేవ కనిపిస్తుందో లేదో తనిఖీ చేయండి.
ఈ రెండు ఇంజన్లు వేటినీ పంచుకోవు: ఇమేజ్ స్టోరేజ్ మరియు నెట్వర్క్లు వేర్వేరుగా ఉంటాయి. కాబట్టి మీరు తరలింపు సమయంలో రెండింటినీ ఒకేసారి నడపవచ్చు, కేవలం host port నంబర్ విషయంలో మాత్రమే ఘర్షణ వచ్చే అవకాశం ఉంది. ఒక సేవను తరలించి, ఒక రోజు గమనించిన తర్వాత, తదుపరి సేవను తరలించండి.
Podman vs Docker: మీ VPSలో ఏది ఉండాలి?
మీ stack ఇతర వ్యక్తులు కూడా నిర్వహించే compose ఫైళ్లలో ఉంటే, లేదా Docker socket తో అనుసంధానమయ్యే సాధనాలపై మీరు ఆధారపడితే Docker నే వాడండి. ఇతరులు రాసే కోడ్తో అనుకూలత (compatibility) ఒక ముఖ్యమైన ఫీచర్, మరియు Docker లో ఇది ఎక్కువగా ఉంటుంది. టీమ్లోని అందరి ల్యాప్టాప్లలో Docker ఉన్నప్పుడు, ప్రొడక్షన్లో కూడా అదే ఇంజిన్ను వాడటం వల్ల స్పష్టమైన ప్రయోజనం ఉంటుంది.
మీరు పూర్తిగా నియంత్రించే కొన్ని సేవలు మాత్రమే VPSలో ఉంటే, లేదా ప్రతి అప్లికేషన్ను ఎటువంటి docker గ్రూప్ లేకుండా, ప్రత్యేకమైన unprivileged యూజర్ కింద నడపాలనుకుంటే Podman కు మారండి. డిస్ట్రిబ్యూషన్ అనుకూలత కూడా ముఖ్యమే: RHEL మరియు దాని ఆధారిత సిస్టమ్స్లో Podman అధికారికంగా మద్దతు ఇచ్చే ఇంజిన్, కాబట్టి ఆ సిస్టమ్స్లో Podman వాడటం వల్ల సమస్యలు తక్కువగా ఉంటాయి. మీరు ఇప్పటికే మిగిలిన వాటన్నింటినీ systemd units తో పర్యవేక్షిస్తుంటే, quadlets మీకు కొత్త సాధనంలా కాకుండా, లోపించిన ఒక భాగం దొరికినట్లు అనిపిస్తుంది.
మధ్యస్థంగా ఒక ఎంపిక ఉంది. Rootful Podman దాదాపు Docker లాగే పనిచేస్తుంది, wrapper ద్వారా docker కమాండ్ను అలాగే ఉంచుతుంది, మరియు నిరంతరం నడిచే daemon ను తొలగిస్తుంది. అయితే ఇది rootless సౌలభ్యాన్ని వదులుకుంటుంది, ఇది మీ భద్రతా స్థితిని మార్చే అంశం, కాబట్టి దీన్ని ఒక తాత్కాలిక మార్గంగా చూడండి.
మీరు ఇంకా మీ మొదటి కంటైనర్ హోస్ట్ను నిర్మిస్తుంటే, కొత్త VPSలో Docker సెటప్ మరియు హార్డెనింగ్ మార్గం సులభమైనది, మరియు ఆ పరిజ్ఞానం ఎప్పటికీ వృథా కాదు. రెండు ఇంజిన్లలోనూ images మరియు volumes ఒకేలా ఉంటాయి, కాబట్టి భవిష్యత్తులో మారినా మీ సేవల పర్యవేక్షణ విధానం మారుతుందే తప్ప, మిగిలినవి పెద్దగా మారవు.
FAQ
Podman అనేది Docker కు పూర్తి ప్రత్యామ్నాయమా?
మీరు టైప్ చేసే కమాండ్ల విషయానికి వస్తే, ఇది దాదాపు సమానంగా ఉంటుంది. podman-docker ఇన్స్టాల్ చేయడం ద్వారా మీకు /usr/bin/docker వ్రాపర్ లభిస్తుంది, మరియు run, ps, build, logs, మరియు exec అన్నీ ఒకే విధంగా పనిచేస్తాయి. ఇది daemon కు పూర్తి ప్రత్యామ్నాయం కాదు. Swarm కు దీనిలో సమానమైన ఫీచర్ లేదు, /var/run/docker.sock కు కనెక్ట్ అయ్యే టూల్స్ను ప్రతి యూజర్ యొక్క Podman సాకెట్కు మళ్లించాలి, మరియు Docker ద్వారా పుల్ చేసిన ఇమేజ్లు Podman కు కనిపించవు, ఎందుకంటే ఈ రెండూ వేర్వేరు స్టోరేజ్లను ఉపయోగిస్తాయి.
SSH నుండి లాగ్ అవుట్ అయినప్పుడు నా rootless Podman కంటైనర్లు ఎందుకు ఆగిపోతున్నాయి?
మీరు లాగ్ అవుట్ అయినప్పుడు, మీ చివరి సెషన్ ముగియడంతో పాటు systemd ఆ యూజర్ సెషన్ను మరియు ఆ సెషన్కు సంబంధించిన అన్ని సర్వీసులను ఆపివేస్తుంది. sudo loginctl enable-linger <user> రన్ చేయండి, ఆపై loginctl show-user <user> --property=Linger కమాండ్ Linger=yes అని చూపిస్తుందో లేదో తనిఖీ చేయండి. Linger ఫీచర్ యాక్టివ్ సెషన్ లేకపోయినా ఆ యూజర్ యొక్క systemd ఇన్స్టాన్స్ను రన్ అయ్యేలా చేస్తుంది, దీనివల్ల రీబూట్ తర్వాత కూడా కంటైనర్లు ఆటోమేటిక్గా ప్రారంభమవుతాయి.
నా వాల్యూమ్లోని ఫైల్స్ UID 100999 కి ఎందుకు చెందుతున్నాయి?
Rootless Podman కంటైనర్ UID 0 ను మీ హోస్ట్ యూజర్కు మ్యాప్ చేస్తుంది, ఆపై కంటైనర్ UID 1 మరియు ఆ పైన ఉన్నవాటిని మీ subuid పరిధిలోకి మ్యాప్ చేస్తుంది. 100000 తో ప్రారంభమయ్యే పరిధితో, కంటైనర్ UID 1000 అనేది హోస్ట్పై 100999 అవుతుంది. దీన్ని సరిచేయడానికి నేమ్స్పేస్ లోపల నుండి podman unshare chown 1000:1000 /path/to/data ఉపయోగించండి, మొదటిసారి రన్ చేసేటప్పుడు :U ఫ్లాగ్తో మౌంట్ చేయండి, లేదా కంటైనర్ UIDలు మీ యూజర్ UIDతో సరిపోలడానికి --userns=keep-id ఉపయోగించండి.
నేను Podman తో docker-compose.yml ఫైల్ను ఉపయోగించవచ్చా?
అవును, రెండు మార్గాల్లో చేయవచ్చు. podman-compose ఆ ఫైల్ను చదివి నేరుగా Podman CLIని నడుపుతుంది. లేదా systemctl --user enable --now podman.socket తో compatibility సాకెట్ను ఎనేబుల్ చేసి, DOCKER_HOST=unix:///run/user/$(id -u)/podman/podman.sock సెట్ చేసి, దానిపై అసలైన docker compose ను రన్ చేయవచ్చు. network_mode: host విషయంలో, Docker సాకెట్ను మౌంట్ చేసే సర్వీసుల విషయంలో, మరియు రీబూట్ తర్వాత కూడా రన్ అవ్వడానికి quadlet unit మరియు linger అవసరమయ్యే restart: always విషయంలో కొన్ని ఇబ్బందులు ఎదురుకావచ్చు.
Rootless విధానం కంటైనర్లను నిజంగా సురక్షితం చేస్తుందా?
ఇది ఒక నిర్దిష్ట ప్రమాదాన్ని తొలగిస్తుంది: rootless కంటైనర్ నుండి బయటపడిన ప్రాసెస్, root పర్మిషన్లకు బదులుగా మీ unprivileged యూజర్ పర్మిషన్లను మాత్రమే కలిగి ఉంటుంది. ఇది చాలా ముఖ్యమైనది, అందుకే root-equivalent అయిన docker గ్రూపుకు rootless Podman లో సమానమైనది ఏదీ లేదు. ఇది కెర్నల్ లోపాలను (kernel vulnerabilities) ఆపలేదు, మరియు మీ యూజర్ చదవగలిగే ఫైళ్లను రక్షించలేదు, కాబట్టి ఏదైనా సర్వర్లో మీరు చేసే ఇతర భద్రతా చర్యలను కొనసాగించండి.