🎉✨ افتتاحیه ویژه! اولین سفارش شما = ۱۰٪ تخفیف 🎁 کد: NEW10 🛍️
راهنمای عملی OpenSSH

رفع خطای SSH سرور لینوکس
تشخیص شبکه، سرویس و کلید

یک پیام SSH می‌تواند دقیقاً نشان دهد خطا در کدام لایه رخ داده است. Timeout با Permission denied یک مشکل نیست و نباید با یک نسخه‌ی ثابت حل شود. در این راهنما ابتدا از سمت کلاینت شواهد جمع می‌کنیم، سپس از کنسول سرور شبکه و sshd را می‌سنجیم و فقط بعد از اعتبارسنجی تنظیمات سراغ تغییر می‌رویم. برای جلوگیری از قفل‌شدن، نشست فعلی و کنسول را تا پایان آزمون باز نگه دارید.

۱) خروجی کلاینت و نوع خطا را ثبت کنید

IP، پورت و نام کاربری را صریح وارد و حالت verbose را فعال کنید. این خروجی مرحله‌ی DNS، برقراری TCP، تبادل کلید میزبان و احراز هویت را جدا نشان می‌دهد؛ هنگام اشتراک‌گذاری لاگ، IP خصوصی، نام کاربری و مسیر فایل‌ها را در صورت حساس‌بودن حذف کنید و هرگز private key را نفرستید.

ssh -vvv -o ConnectTimeout=10 -p 22 USER@SERVER_IP
  • Connection timed out: مسیر، IP، پورت یا firewall بسته است یا پاسخی برنمی‌گردد.
  • Connection refused: مقصد پاسخ داده اما روی آن پورت listener ندارد یا فعالانه رد می‌کند.
  • No route to host: route، gateway، شبکه محلی یا فایروال میانی را بررسی کنید.
  • Permission denied: TCP و SSH برقرار شده‌اند؛ نام کاربر، روش احراز هویت یا مجوز کلید مشکل دارد.
  • Host key verification failed: هویت ثبت‌شده با کلید فعلی مقصد یکی نیست؛ قبل از حذف رکورد احتمال IP اشتباه یا حمله‌ی میانی را رد کنید.

اگر دامنه استفاده می‌کنید، اتصال مستقیم با IP را نیز بیازمایید. تفاوت نتیجه می‌تواند خطای DNS یا رکورد قدیمی را آشکار کند.

۲) از کنسول، شبکه و listener را بررسی کنید

اگر TCP برقرار نمی‌شود، از کنسول سرور شروع کنید. فرمان‌های زیر فقط وضعیت را می‌خوانند و نشان می‌دهند IP و route درست هستند، سرویس چه وضعی دارد و کدام پورت واقعاً گوش می‌دهد:

ip -br address
ip route
systemctl status ssh --no-pager
sudo ss -lntp | grep sshd
sudo journalctl -u ssh -n 100 --no-pager

در Ubuntu نام unit معمولاً ssh.service است. اگر بسته نصب نشده باشد، dpkg -l openssh-server را بررسی کنید. نبود listener همراه با سرویس failed معمولاً از خطای پیکربندی یا نبود host key می‌آید؛ لاگ همان زمان دلیل دقیق‌تری می‌دهد. وجود listener فقط روی 127.0.0.1 نیز اتصال بیرونی را نمی‌پذیرد و باید ListenAddress مؤثر بررسی شود.

اگر listener روی پورت دیگری است، کلاینت، UFW و firewall شبکه باید همان عدد را استفاده کنند. بازکردن 22 در حالی که sshd روی 2222 گوش می‌دهد کمکی نمی‌کند.

۳) پیکربندی مؤثر sshd را قبل از restart اعتبارسنجی کنید

Ubuntu فایل اصلی /etc/ssh/sshd_config و snippetهای /etc/ssh/sshd_config.d/*.conf را می‌خواند. برای بسیاری از directiveها اولین مقدار مؤثر است؛ بنابراین دیدن یک خط در انتهای فایل لزوماً به معنی اعمال‌شدن آن نیست. تنظیم مؤثر و صحت نحو را بررسی کنید:

sudo sshd -t
sudo sshd -T | grep -E '^(port|listenaddress|passwordauthentication|pubkeyauthentication|permitrootlogin|allowusers|allowgroups) '
grep -RniE '^(Port|ListenAddress|PasswordAuthentication|PubkeyAuthentication|PermitRootLogin|AllowUsers|AllowGroups)' /etc/ssh/sshd_config /etc/ssh/sshd_config.d

sshd -t در صورت سالم‌بودن معمولاً خروجی ندارد. تا وقتی این آزمون موفق نشده، سرویس را restart نکنید؛ یک خطای نحوی می‌تواند دسترسی بعدی را ببندد. پیش از ویرایش، نسخه‌ی مرجع با مجوز فقط‌خواندنی نگه دارید و تغییر را در یک snippet واضح انجام دهید.

قانون جلوگیری از lockout: نشست فعلی را نبندید. ابتدا کلید را در یک پنجره‌ی دوم آزمایش کنید، سپس محدودکردن رمز یا root را اعمال کنید، دوباره sshd -t بگیرید و بعد سرویس را reload/restart کنید.

۴) Permission denied و مجوز کلید عمومی را رفع کنید

برای خطای Permission denied (publickey) ابتدا مطمئن شوید کاربر واقعاً وجود دارد، home درست است و کلید عمومی متناظر در فایل همان کاربر قرار گرفته است. private key روی کلاینت می‌ماند؛ متن فایل .pub است که در authorized_keys سرور قرار می‌گیرد.

getent passwd USER
sudo ls -ld /home/USER /home/USER/.ssh
sudo ls -l /home/USER/.ssh/authorized_keys
sudo ssh-keygen -lf /home/USER/.ssh/authorized_keys

OpenSSH فایل یا پوشه‌ای را که دیگران بتوانند در آن بنویسند ممکن است نپذیرد. پس از تأیید مسیر و مالک واقعی، مجوزهای متعارف را اعمال کنید:

sudo chown -R USER:USER /home/USER/.ssh
sudo chmod 700 /home/USER/.ssh
sudo chmod 600 /home/USER/.ssh/authorized_keys

USER را با نام دقیق حساب جایگزین کنید؛ این فرمان‌ها را روی مسیر حدسی یا home مشترک اجرا نکنید. برای تشخیص زنده، هم‌زمان با یک تلاش ورود، sudo journalctl -fu ssh.service را در کنسول ببینید. پیام‌هایی مثل bad ownership، user not allowed یا key type rejected علت را روشن می‌کنند.

۵) هشدار تغییر host key را کورکورانه حذف نکنید

پیام REMOTE HOST IDENTIFICATION HAS CHANGED می‌تواند پس از نصب مجدد همان سرور طبیعی باشد، اما همین پیام از شما در برابر اتصال به مقصد اشتباه یا حمله‌ی man-in-the-middle نیز محافظت می‌کند. ابتدا از کنسول اثرانگشت کلید میزبان را بخوانید و آن را از یک مسیر قابل‌اعتماد با مقدار کلاینت مقایسه کنید:

sudo ssh-keygen -lf /etc/ssh/ssh_host_ed25519_key.pub
ssh-keygen -F SERVER_IP

فقط پس از تأیید IP، نصب مجدد و fingerprint، رکورد قدیمی همان host را با ssh-keygen -R SERVER_IP از known_hosts حذف و اتصال تازه را تأیید کنید. پاک‌کردن کل فایل known_hosts یا استفاده دائمی از StrictHostKeyChecking=no حفاظت هویت همه‌ی مقصدها را از بین می‌برد.

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

۶) UFW، فایروال شبکه و ترتیب بازیابی امن

در سرور وضعیت UFW را بخوانید و در پنل شبکه نیز rule ورودی یا NAT را بررسی کنید:

sudo ufw status numbered
sudo ufw status verbose
sudo ss -lntp | grep sshd

پورت مجاز UFW باید با خروجی listener یکسان باشد. اگر دسترسی را به IP خاصی محدود کرده‌اید، تغییر IP اینترنت مدیر باعث timeout می‌شود. در محیطی با IPv6، ممکن است نام دامنه به AAAA resolve شود؛ هر دو مسیر IPv4 و IPv6 را جدا آزمایش و policy هر دو را هم‌راستا کنید.

  1. کنسول و نشست SSH فعلی را باز نگه دارید.
  2. یک تغییر انجام دهید و sshd -t بگیرید.
  3. از کلاینت دوم روی پورت واقعی تست کنید.
  4. لاگ همان تلاش را بخوانید و فقط بعد از ورود موفق نشست قبلی را ببندید.

خاموش‌کردن UFW، فعال‌کردن ورود مستقیم root یا بازکردن password authentication برای همه‌ی اینترنت، اصلاح پایدار نیست. اگر دسترسی کلیدی از بین رفته، از کنسول یک کلید معتبر برای کاربر مدیریتی بازیابی کنید و سپس policy قبلی را حفظ کنید.

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

پرسش‌های پرتکرار

فرق Connection timed out و Connection refused در SSH چیست؟

Timeout یعنی پاسخ TCP به کلاینت برنگشته و معمولاً مسیر یا firewall مطرح است. Refused یعنی مقصد پاسخ داده اما روی آن پورت listener وجود ندارد یا اتصال فعالانه رد شده است.

چرا با وجود روشن‌بودن ssh.service اتصال برقرار نمی‌شود؟

ممکن است sshd فقط روی آدرس محلی یا پورت دیگری گوش دهد، UFW یا firewall شبکه مسیر را ببندد، IP اشتباه باشد یا نام دامنه به IPv6 نامعتبر resolve شود. listener را با ss بررسی کنید.

برای خطای publickey چه چیزی را بررسی کنم؟

نام کاربر و home، وجود کلید عمومی درست در authorized_keys، مالکیت USER، مجوز 700 پوشه .ssh و 600 فایل، و directiveهای مؤثر PubkeyAuthentication و AllowUsers/AllowGroups را کنترل کنید.

آیا می‌توانم برای حل سریع، PasswordAuthentication را فعال کنم؟

بازکردن ورود رمزی روی اینترنت سطح حمله را بالا می‌برد و اغلب علت اصلی را پنهان می‌کند. از کنسول کلید درست را بازیابی و لاگ ssh را بررسی کنید؛ هر تغییر موقت باید محدود و قابل بازگشت باشد.

بعد از تغییر sshd_config باید چه کنم؟

ابتدا sudo sshd -t و سپس تنظیمات مؤثر را با sshd -T بررسی کنید. نشست فعلی را باز نگه دارید، سرویس را با احتیاط reload/restart کنید و ورود را در پنجره‌ای دوم بیازمایید.

آیا حذف known_hosts برای هشدار host key امن است؟

تنها حذف رکورد همان مقصد، آن هم پس از تطبیق fingerprint از کنسول، قابل قبول است. پاک‌کردن کل فایل یا غیرفعال‌کردن بررسی host key شما را در برابر مقصد جعلی بی‌دفاع می‌کند.

منابع

منابع رسمی و مطالعه بیشتر

برای مدیریت لینوکسی آماده می‌شوید؟

پیش از انتخاب سرور، روش اتصال با کلید SSH و مسئولیت نگهداری سیستم‌عامل را بشناسید.

صفحات مرتبط

شاید این‌ها هم به کارتان بیاید