Mac how-to

How to fix “port 3000 is already in use” on a Mac

Updated · Tested commands for macOS Terminal (zsh or bash)

You run npm run dev and get EADDRINUSE: address already in use :::3000. Something on your Mac is still holding the port, often a dev server from an earlier session or one an AI agent started. Here's how to find it and stop it safely in about a minute, with nothing to install.

Quick answer

Run lsof -nP -iTCP:3000 -sTCP:LISTEN, then kill followed by the PID it shows. Use kill -9 only if it refuses to stop.

Or as one line (stops everything listening on 3000):

kill $(lsof -t -iTCP:3000 -sTCP:LISTEN)

Step by step

  1. Find what is listening on port 3000

    Open Terminal and run:

    lsof -nP -iTCP:3000 -sTCP:LISTEN

    -nP keeps addresses and ports as numbers (faster), and -sTCP:LISTEN shows only the process that is listening, not every connection to it. Note the number in the PID column.

    Example output (example data)
    COMMAND   PID USER   FD   TYPE  DEVICE SIZE/OFF NODE NAME
    node    46210 you    21u  IPv6  0x1a2b      0t0  TCP *:3000 (LISTEN)

    No output? Nothing you own is listening. Try again with sudo in front in case another user or root owns it, and check Docker with docker ps, since a container can publish port 3000 too.

  2. Check what it is before you stop it

    Replace 46210 with your PID to see the full command and how long it has been running:

    ps -o pid,ppid,etime,command -p 46210

    If it's a server you still have open in another Terminal tab, just go there and press Control + C. That's the cleanest stop. To see which project folder it was started from, run lsof -a -p 46210 -d cwd.

  3. Ask it to stop

    A plain kill sends SIGTERM, which lets the server shut down cleanly:

    kill 46210

    Give it a couple of seconds, then run the lsof command from step 1 again. Empty output means port 3000 is free.

  4. Force it only if it won't quit

    If the process is still there after a few seconds, force it:

    kill -9 46210

    kill -9 (SIGKILL) can't be ignored, but it also skips cleanup. Child processes the server started may keep running, so check for them with pgrep -P 46210 before you force the parent, and stop those first.

  5. Confirm the port is free and restart

    lsof -nP -iTCP:3000 -sTCP:LISTEN

    No output means you're clear. Start your dev server again with npm run dev (or your usual command).

Can't stop it? Use another port

If the thing on 3000 is something you need, run your server somewhere else. Both Next.js and Vite accept a --port flag, and the extra -- passes it through npm:

npm run dev -- --port 3001

Seeing this error every day? The cause is usually a dev server that outlived the terminal or AI agent session that started it. Our guide to killing orphaned node processes shows how to find all of them at once.

Questions

Why does it say port 3000 is in use when nothing is running?

Something usually is, just not in a window you can see: a server from a closed terminal, an AI agent session or a crashed editor. lsof -nP -iTCP:3000 -sTCP:LISTEN will find it. If that shows nothing, try it with sudo and check docker ps.

Is kill -9 bad?

Not bad, just blunt. It stops the process instantly with no chance to clean up, so files may be left half written and child processes can keep running. Use plain kill first.

I killed it and the port got taken again straight away. Why?

Something is restarting it: a file watcher like nodemon, a process manager like pm2, a Docker container with a restart policy, or a parent process that respawns its worker. Find the parent with ps -o ppid= -p PID and stop that instead.

Does this work for other ports like 5173 or 8080?

Yes. Swap 3000 for any port number in the commands. For 5000 or 7000, check whether it's macOS AirPlay Receiver first (see find what's using a port).

Related guides

Coming soon

Rather not do this by hand?

Spookle will show which project and branch own :3000 and stop the whole process tree safely in one click, gently first. It isn't out yet. Join the waitlist and we'll email you once, when it launches.