🌐 Detecting your location…

كيفية إصلاح خطأ منفذ EADDRINUSE قيد الاستخدام بالفعل في Node.js

⏱️2 min read  ·  277 words

الخطأخطأ: استمع EADDRINUSE: العنوان قيد الاستخدام بالفعل :::3000 يعني أن هناك عملية أخرى تستخدم بالفعل المنفذ الذي يريده تطبيق Node.js. إنه أحد الأخطاء الأكثر شيوعًا أثناء التطوير. إليك كل الطرق لإصلاحها.

ما الذي يسبب هذا الخطأ

  • لم يتم إغلاق مثيل الخادم السابق بشكل نظيف ولا يزال يحتفظ بالمنفذ
  • يستخدم تطبيق آخر نفس المنفذ (خادم تطوير آخر، قاعدة بيانات)
  • أدت العملية المتعطلة إلى ترك زومبي ممسكًا بالمنفذ
  • لقد قمت بتشغيل الخادم الخاص بك مرتين

الإصلاح 1: البحث عن العملية وإيقافها (نظام التشغيل MacOS/Linux)

# Find the process using port 3000
lsof -i :3000
# COMMAND   PID  USER   FD   TYPE  DEVICE  NODE NAME
# node    12345  you   20u  IPv6  ...     TCP  *:3000 (LISTEN)

# Kill it by PID
kill -9 12345

# Or do it in one command
kill -9 $(lsof -ti :3000)

# Kill all node processes (nuclear option)
killall -9 node

الإصلاح 2: البحث عن العملية وإيقافها (Windows)

# Find the process using port 3000
netstat -ano | findstr :3000
# TCP    0.0.0.0:3000    0.0.0.0:0    LISTENING    12345

# Kill it by PID
taskkill /PID 12345 /F

# PowerShell one-liner
Stop-Process -Id (Get-NetTCPConnection -LocalPort 3000).OwningProcess -Force

الإصلاح 3: استخدام منفذ مختلف

// Make the port configurable via environment variable
const PORT = process.env.PORT || 3000;

app.listen(PORT, () => {
  console.log("Server running on port " + PORT);
});

// Then run with a different port:
// PORT=3001 node server.js

الإصلاح 4: التعامل مع الخطأ بلطف

const server = app.listen(PORT);

server.on('error', (err) => {
  if (err.code === 'EADDRINUSE') {
    console.error("Port " + PORT + " busy. Trying " + (PORT + 1));
    server.listen(PORT + 1);  // fall back to next port
  } else {
    throw err;
  }
});

الإصلاح 5: تنفيذ إيقاف التشغيل اللطيف (يمنع المشكلة)

غالبًا ما يكون السبب الجذري هو عدم قيام الخادم بتحرير المنفذ عند الخروج. إضافة معالجات إيقاف التشغيل الرشيقة:

const server = app.listen(PORT, () => {
  console.log("Server running on port " + PORT);
});

function shutdown(signal) {
  console.log(signal + " received. Closing server...");
  server.close(() => {
    console.log("Server closed. Port released.");
    process.exit(0);
  });
  setTimeout(() => {
    console.error("Forced shutdown");
    process.exit(1);
  }, 10000);
}

process.on('SIGTERM', () => shutdown('SIGTERM'));
process.on('SIGINT', () => shutdown('SIGINT'));  // Ctrl+C

الإصلاح 6: استخدم Nodemon لإعادة التشغيل النظيف

npm install --save-dev nodemon

# package.json
{
  "scripts": {
    "dev": "nodemon server.js"
  }
}

# nodemon cleanly restarts and releases ports between reloads
npm run dev

برنامج Kill-Port النصي القابل لإعادة الاستخدام

# kill-port.sh
#!/bin/bash
PORT=${1:-3000}
PID=$(lsof -ti :$PORT)
if [ -n "$PID" ]; then
  echo "Killing process $PID on port $PORT"
  kill -9 $PID
else
  echo "No process on port $PORT"
fi

# Usage: ./kill-port.sh 3000

الأسئلة المتداولة

س: لماذا يظل المنفذ قيد الاستخدام بعد أن أوقف تطبيقي؟
ج: عادة بسبب توقف العملية فجأة دون تحرير المقبس، أو أن العملية الفرعية لا تزال تحتفظ بها. تمنع معالجات إيقاف التشغيل الرشيقة ذلك.

س: ماذا يعني ::: في ‘:::3000’؟
ج: تدوين IPv6 لـ “جميع الواجهات” (مثل 0.0.0.0 في IPv4). يرتبط الخادم الخاص بك بجميع واجهات الشبكة على المنفذ 3000.

س: هل يمكن لتطبيقين مشاركة نفس المنفذ؟
ج: لا – يمكن ربط عملية واحدة فقط بمنفذ على الواجهة في المرة الواحدة. استخدم منافذ مختلفة أو وكيلًا عكسيًا (nginx) للتوجيه حسب المسار/المجال.

س: كيف يمكنني تجنب ذلك في Docker؟
ج: تحتوي كل حاوية على مساحة اسم الشبكة الخاصة بها، لذلك تحدث التعارضات فقط عند تعيين المضيف. تعيين منافذ مضيفة مختلفة:-p 3001:3000.

س: هل عقدة killall آمنة؟
ج: إنه يقتل جميع عمليات Node.js – جيد في التطوير، ولكن كن حذرًا إذا كان لديك تطبيقات Node أخرى لا تريد إيقافها.

الخلاصة

EADDRINUSE يعني أن المنفذ مأخوذ بالفعل. حل سريع:ابحث عن العملية باستخدامlsof -ti :PORT واقتله. الإصلاح الدائم:إضافة معالجات إيقاف التشغيل الرشيقة لذلك يقوم خادمك دائمًا بتحرير المنفذ عند الخروج واستخدامnodemon قيد التطوير لإعادة التشغيل النظيف. جعل المنفذ قابلاً للتكوين عبرprocess.env.PORT كما يتجنب الصراعات على الفور.

MD Rafikul Islam

Written by

MD Rafikul Islam is a software developer and the editor of TechPulse. He writes about developer tooling, hardware, and the practical decisions that come up in day-to-day engineering work — which laptop to buy, which framework to commit to, why a build broke at 2am. He tests the tools he writes about and says plainly when something is not worth the money. Corrections and corrections requests are welcome at rony.yf25@gmail.com.

✍️ Leave a Comment

Your email address will not be published. Required fields are marked *

🌐 Read in:🇬🇧 English🇩🇪 Deutsch🇧🇷 Português🇸🇦 العربية🇮🇳 हिन्दी🇧🇩 বাংলা