نصب داکر روی سرور مجازی یکی از مهم‌ترین گام‌ها برای مدرن‌سازی فرآیند توسعه و استقرار نرم‌افزار است. Docker با فراهم کردن مفهوم کانتینر (Container)، به شما اجازه می‌دهد اپلیکیشن‌ها را همراه با تمام وابستگی‌هایشان در یک بسته ایزوله و قابل حمل اجرا کنید. این یعنی دیگر با جمله معروف «روی سیستم من که کار می‌کرد!» روبه‌رو نخواهید شد، چون کانتینر در هر محیطی دقیقاً یکسان اجرا می‌شود. در این آموزش جامع از رپیدو سرور، یاد می‌گیرید که Docker را روی سرور مجازی لینوکسی خود نصب، پیکربندی و ایمن‌سازی کنید و اولین کانتینرهای خود را اجرا نمایید.

داکر چیست و چرا از آن استفاده کنیم؟

Docker یک پلتفرم متن‌باز برای ساخت، ارسال و اجرای اپلیکیشن‌ها درون کانتینرهاست. کانتینر یک واحد استاندارد نرم‌افزاری است که کد برنامه را به همراه کتابخانه‌ها، وابستگی‌ها و تنظیمات، در یک بسته سبک بندی می‌کند. برخلاف ماشین‌های مجازی که هرکدام یک سیستم‌عامل کامل را شبیه‌سازی می‌کنند، کانتینرها هسته سیستم‌عامل میزبان را به اشتراک می‌گذارند و به همین دلیل بسیار سبک‌تر و سریع‌تر هستند.

مهم‌ترین مزایای استفاده از Docker عبارت‌اند از:

  • قابلیت حمل: یک کانتینر روی لپ‌تاپ توسعه‌دهنده، سرور آزمایشی و محیط تولید دقیقاً یکسان اجرا می‌شود.
  • ایزولاسیون: هر اپلیکیشن در محیط مجزای خود اجرا می‌شود و با سایر اپلیکیشن‌ها تداخل ندارد.
  • مصرف کم منابع: کانتینرها در چند ثانیه بالا می‌آیند و حافظه بسیار کمتری نسبت به ماشین مجازی مصرف می‌کنند.
  • مقیاس‌پذیری: به‌راحتی می‌توانید چند نمونه از یک سرویس را اجرا و بار را میان آن‌ها توزیع کنید.
نکته: برای اجرای روان Docker حداقل به یک سرور با ۱ گیگابایت رم نیاز دارید، اما برای پروژه‌های واقعی ۲ گیگابایت یا بیشتر توصیه می‌شود. می‌توانید سرور مناسب را از صفحه خرید سرور مجازی تهیه کنید.

پیش‌نیازها و آماده‌سازی سرور

پیش از نصب داکر روی سرور مجازی، باید مطمئن شوید سیستم‌عامل به‌روز است. Docker از توزیع‌های محبوب لینوکس مانند Ubuntu، Debian، CentOS و AlmaLinux پشتیبانی می‌کند. ابتدا با دستور زیر بسته‌های سیستم را به‌روزرسانی کنید:

apt update && apt upgrade -y

سپس چند بسته پیش‌نیاز که برای افزودن مخزن رسمی Docker لازم است را نصب کنید:

apt install ca-certificates curl gnupg lsb-release -y

همچنین بررسی کنید که معماری و نسخه هسته سیستم شما با نیازمندی‌های Docker سازگار باشد. Docker به هسته لینوکس نسخه ۳.۱۰ یا بالاتر نیاز دارد که تقریباً تمام سرورهای امروزی این شرط را برآورده می‌کنند. برای مشاهده نسخه هسته:

uname -r

نصب داکر روی سرور مجازی از مخزن رسمی

بهترین روش برای نصب داکر روی سرور مجازی، استفاده از مخزن رسمی Docker است، زیرا همیشه آخرین نسخه پایدار را در اختیار شما می‌گذارد. ابتدا کلید GPG رسمی Docker را اضافه کنید:

install -m 0755 -d /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc
chmod a+r /etc/apt/keyrings/docker.asc

سپس مخزن Docker را به منابع apt اضافه کنید:

echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable" | tee /etc/apt/sources.list.d/docker.list

حالا فهرست بسته‌ها را دوباره به‌روز کنید و بسته‌های اصلی Docker را نصب نمایید:

apt update
apt install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin -y

برای کاربرانی که عجله دارند یا محیط ساده‌تری می‌خواهند، اسکریپت رسمی نصب سریع نیز وجود دارد که همه این مراحل را یکجا انجام می‌دهد:

curl -fsSL https://get.docker.com | sh

بررسی نصب و اجرای اولین کانتینر

پس از پایان نصب، سرویس Docker را فعال کنید تا با هر بار روشن شدن سرور به‌طور خودکار اجرا شود:

systemctl start docker
systemctl enable docker

برای اطمینان از صحت نصب، نسخه Docker را بررسی کنید:

docker --version

حالا وقت آن رسیده که اولین کانتینر خود را اجرا کنید. تصویر آزمایشی hello-world دقیقاً برای همین منظور طراحی شده است:

docker run hello-world

اگر پیام خوش‌آمدگویی Docker را دیدید، همه چیز به‌درستی کار می‌کند. برای تجربه‌ای واقعی‌تر، می‌توانید یک وب‌سرور Nginx را در کانتینر اجرا کنید و آن را روی پورت ۸۰ سرور در دسترس قرار دهید:

docker run -d -p 80:80 --name webserver nginx

در این دستور، سوییچ -d کانتینر را در پس‌زمینه اجرا می‌کند، -p 80:80 پورت سرور را به پورت کانتینر متصل می‌کند و --name نامی خوانا برای کانتینر تعیین می‌کند. حالا اگر آدرس IP سرور را در مرورگر باز کنید، صفحه پیش‌فرض Nginx را خواهید دید که در حال اجرا از داخل یک کانتینر است. نکته جالب اینجاست که هیچ نرم‌افزاری روی خود سرور نصب نکردید؛ همه چیز درون کانتینر ایزوله باقی مانده و با یک دستور حذف، هیچ ردی از آن روی سیستم نمی‌ماند. همین ویژگی تمیز و بازگشت‌پذیر بودن، یکی از بزرگ‌ترین دلایل محبوبیت Docker در میان توسعه‌دهندگان و مدیران سرور است.

مدیریت کانتینرها و ایمیج‌ها

پس از اجرای کانتینرها، باید بتوانید آن‌ها را مدیریت کنید. جدول زیر پرکاربردترین دستورهای Docker را خلاصه می‌کند:

دستورکاربرد
docker psنمایش کانتینرهای در حال اجرا
docker ps -aنمایش همه کانتینرها شامل متوقف‌شده‌ها
docker imagesنمایش لیست ایمیج‌های دانلودشده
docker stop <name>توقف یک کانتینر
docker rm <name>حذف یک کانتینر
docker logs <name>مشاهده لاگ‌های کانتینر

برای ورود به داخل یک کانتینر در حال اجرا و اجرای دستور در آن، از exec استفاده کنید:

docker exec -it webserver bash

برای پاک‌سازی منابع بلااستفاده مانند کانتینرهای متوقف‌شده، شبکه‌های بدون استفاده و ایمیج‌های آویزان، دستور بسیار مفید prune وجود دارد که فضای دیسک را آزاد می‌کند:

docker system prune -a

استفاده از Docker Compose برای پروژه‌های چند سرویسی

وقتی پروژه شما از چند سرویس تشکیل شده باشد — مثلاً یک وب اپلیکیشن، یک پایگاه داده و یک کش Redis — مدیریت آن‌ها به‌صورت جداگانه دشوار می‌شود. اینجاست که Docker Compose به کمک می‌آید. با یک فایل docker-compose.yml می‌توانید کل معماری اپلیکیشن را تعریف کنید. نمونه ساده‌ای از این فایل:

services:
  web:
    image: nginx
    ports:
      - "80:80"
  db:
    image: postgres:16
    environment:
      POSTGRES_PASSWORD: secret
    volumes:
      - db_data:/var/lib/postgresql/data

volumes:
  db_data:

پس از ساخت این فایل، با یک دستور کل استک را بالا می‌آورید:

docker compose up -d

و برای متوقف کردن و پاک کردن همه سرویس‌ها:

docker compose down

استفاده از volume در این مثال تضمین می‌کند که داده‌های پایگاه داده حتی پس از حذف و ساخت مجدد کانتینر حفظ شوند. این موضوع یکی از مفاهیم کلیدی در کار با Docker است که به آن پایداری داده (Data Persistence) می‌گویند.

ساخت ایمیج سفارشی با Dockerfile

تا اینجا از ایمیج‌های آماده استفاده کردیم، اما قدرت واقعی Docker زمانی آشکار می‌شود که ایمیج اختصاصی اپلیکیشن خود را بسازید. برای این کار از فایلی به نام Dockerfile استفاده می‌شود که مجموعه‌ای از دستورالعمل‌ها برای ساخت ایمیج است. فرض کنید یک اپلیکیشن Node.js دارید؛ یک نمونه Dockerfile برای آن به این شکل است:

FROM node:20-alpine
WORKDIR /app
COPY package*.json ./
RUN npm install --production
COPY . .
EXPOSE 3000
CMD ["node", "server.js"]

هر خط این فایل یک لایه (layer) در ایمیج می‌سازد. دستور FROM ایمیج پایه را مشخص می‌کند، WORKDIR پوشه کاری را تعیین می‌کند، COPY فایل‌ها را وارد ایمیج می‌کند، RUN دستورها را در زمان ساخت اجرا می‌کند و CMD فرمان اجرای اصلی کانتینر را مشخص می‌کند. توجه کنید که ابتدا فایل package را کپی و وابستگی‌ها را نصب کردیم و سپس بقیه کد را کپی نمودیم؛ این ترتیب باعث می‌شود Docker از کش لایه‌ها بهتر استفاده کند و ساخت‌های بعدی سریع‌تر باشند. برای ساخت ایمیج از این فایل:

docker build -t myapp:1.0 .

پس از ساخت، می‌توانید کانتینری از این ایمیج اجرا کنید:

docker run -d -p 3000:3000 --name myapp myapp:1.0
نکته: استفاده از ایمیج‌های پایه سبک مانند نسخه‌های alpine حجم نهایی ایمیج را به‌شدت کاهش می‌دهد و امنیت را بالا می‌برد، زیرا سطح حمله کوچک‌تری دارند.

مدیریت شبکه در Docker

کانتینرها برای ارتباط با یکدیگر به شبکه نیاز دارند. Docker به‌صورت پیش‌فرض چند شبکه می‌سازد، اما بهترین روش برای پروژه‌ها، ساخت یک شبکه اختصاصی است. مزیت شبکه سفارشی این است که کانتینرها می‌توانند یکدیگر را با نام به‌جای آدرس IP پیدا کنند. برای ساخت یک شبکه:

docker network create app-network

سپس کانتینرها را به این شبکه متصل کنید:

docker run -d --name db --network app-network postgres:16
docker run -d --name web --network app-network myapp:1.0

حالا کانتینر web می‌تواند به‌سادگی با نام db به پایگاه داده متصل شود، بدون اینکه نیازی به دانستن آدرس IP آن باشد. این قابلیت کشف سرویس (Service Discovery) داخلی، مدیریت اپلیکیشن‌های چند بخشی را بسیار ساده می‌کند و یکی از دلایل محبوبیت Docker در معماری‌های میکروسرویس است.

انتشار ایمیج در رجیستری

پس از ساخت ایمیج، اغلب می‌خواهید آن را در سرورهای دیگر نیز استفاده کنید. برای این کار ایمیج را در یک رجیستری مانند Docker Hub منتشر می‌کنید. ابتدا وارد حساب خود شوید:

docker login

سپس ایمیج را با نام کاربری خود برچسب‌گذاری و آن را ارسال کنید:

docker tag myapp:1.0 username/myapp:1.0
docker push username/myapp:1.0

از این پس روی هر سرور دیگری می‌توانید همان ایمیج را با یک دستور دریافت و اجرا کنید. برای پروژه‌های خصوصی، می‌توانید از رجیستری‌های خصوصی یا سرویس‌های ابری استفاده کنید تا ایمیج‌های شما در دسترس عموم قرار نگیرند. این جریان کاری ساخت، انتشار و اجرا، ستون فقرات فرآیندهای مدرن استقرار مداوم (CI/CD) را تشکیل می‌دهد.

نکات امنیتی مهم در کار با Docker

امنیت در محیط‌های کانتینری اهمیت ویژه‌ای دارد. چند توصیه کلیدی که هر مدیر سرور باید رعایت کند:

  1. اجرای کانتینر با کاربر غیر root: تا حد امکان از دستور USER در Dockerfile برای اجرای اپلیکیشن با کاربر معمولی استفاده کنید.
  2. استفاده از ایمیج‌های رسمی و معتبر: همیشه ایمیج‌ها را از منابع معتبر و ترجیحاً نسخه‌های تگ‌دار مشخص دریافت کنید، نه latest.
  3. به‌روزرسانی منظم: ایمیج‌ها و خود Docker را به‌طور مرتب به‌روزرسانی کنید تا آسیب‌پذیری‌های امنیتی برطرف شوند.
  4. محدود کردن منابع: با سوییچ‌های --memory و --cpus مصرف منابع هر کانتینر را محدود کنید تا یک کانتینر کل سرور را اشغال نکند.
هشدار: هرگز اطلاعات حساس مانند رمزها و کلیدهای API را مستقیماً درون Dockerfile قرار ندهید. به‌جای آن از متغیرهای محیطی یا ابزارهای مدیریت راز (Secrets) استفاده کنید.

برای یادگیری بیشتر درباره مدیریت سرور و ابزارهای DevOps، پیشنهاد می‌کنیم مجموعه مقالات رپیدو سرور را دنبال کنید که به‌طور منظم به‌روز می‌شود.

نظارت بر منابع و نگهداری کانتینرها

پس از راه‌اندازی کانتینرها روی سرور تولید، نظارت مستمر بر مصرف منابع اهمیت زیادی دارد. Docker یک دستور داخلی برای مشاهده زنده مصرف CPU، حافظه و شبکه هر کانتینر دارد:

docker stats

این دستور جدولی زنده نمایش می‌دهد که به شما کمک می‌کند کانتینرهای پرمصرف را شناسایی کنید. اگر متوجه شدید یک کانتینر بیش از حد منابع مصرف می‌کند، می‌توانید هنگام اجرا محدودیت تعیین کنید تا از فشار روی سرور جلوگیری شود:

docker run -d --memory="512m" --cpus="1.0" --name limited-app myapp:1.0

برای نگهداری بلندمدت، سیاست ری‌استارت مناسب را نیز تعیین کنید تا در صورت خرابی یا ری‌استارت سرور، کانتینرها به‌طور خودکار دوباره اجرا شوند. گزینه --restart unless-stopped برای بیشتر سرویس‌های تولید انتخاب خوبی است:

docker run -d --restart unless-stopped --name web -p 80:80 nginx

همچنین توصیه می‌شود لاگ‌های Docker را مدیریت کنید، زیرا در صورت عدم کنترل می‌توانند فضای دیسک را پر کنند. می‌توانید در فایل پیکربندی daemon، محدودیت اندازه و تعداد فایل‌های لاگ را تعیین کنید تا سرور شما همیشه فضای کافی داشته باشد. ترکیب این عادت‌های نظارتی و نگهداری، پایداری بلندمدت زیرساخت کانتینری شما را تضمین می‌کند.

سوالات متداول

برای نصب داکر روی سرور مجازی چه میزان منابع لازم است؟

Docker خودش سبک است و منابع کمی مصرف می‌کند، اما میزان رم و CPU مورد نیاز به اپلیکیشن‌هایی بستگی دارد که در کانتینرها اجرا می‌کنید. برای شروع و پروژه‌های سبک، سروری با ۱ تا ۲ گیگابایت رم کافی است.

تفاوت کانتینر و ماشین مجازی چیست؟

ماشین مجازی یک سیستم‌عامل کامل را شبیه‌سازی می‌کند و منابع زیادی مصرف می‌کند، در حالی که کانتینر هسته سیستم‌عامل میزبان را به اشتراک می‌گذارد و بسیار سبک‌تر و سریع‌تر است. کانتینرها در چند ثانیه اجرا می‌شوند اما ماشین مجازی به دقیقه‌ها زمان نیاز دارد.

آیا Docker Compose جداگانه نصب می‌شود؟

در نسخه‌های جدید Docker، افزونه Compose به‌صورت داخلی همراه با بسته اصلی نصب می‌شود و با دستور docker compose در دسترس است. بنابراین اگر Docker را از مخزن رسمی نصب کرده باشید، Compose نیز آماده استفاده است.

چگونه از پاک شدن داده‌های کانتینر جلوگیری کنم؟

با استفاده از volume می‌توانید داده‌ها را خارج از لایه قابل نوشتن کانتینر ذخیره کنید. به این ترتیب حتی اگر کانتینر حذف و دوباره ساخته شود، داده‌ها باقی می‌مانند. این روش برای پایگاه‌های داده و فایل‌های مهم ضروری است.