0%

端口已被占用时,用 ss 找出监听的进程

服务日志里出现 Address already in use,就是要绑的端口上已经有套接字。先找出谁在监听,再决定停掉哪一个。不要按端口号去猜进程名。

把 80 换成报错里的端口。不加 sudo 时,ss 经常只能看到端口,看不到进程:

1
sudo ss -ltnp 'sport = :80'

-l 只看监听,-t 是 TCP,-n 不解析服务名,-p 打印进程。一行里 users:(("nginx",pid=1234,fd=6)) 就是进程名和 pid。sport = :80 只匹配本机这个端口,避免把连出去的连接也列出来。

UDP 同样报地址占用时,把 -t 换成 -u:

1
sudo ss -lunp 'sport = :53'

没有 ss 的系统上可以用:

1
sudo lsof -nP -iTCP:80 -sTCP:LISTEN

停掉之前

pid 对应的是这个监听套接字的进程。它可能是:

  • 上一次没退出的同一个服务
  • 另一个程序占了你要的端口
  • 父进程还在,显示出来的是 worker

先看命令行,再停:

1
2
ps -fp 1234
systemctl status 1234 --no-pager

systemctl status 后面跟 pid 时,如果这个进程属于某个单元,会把单元名打出来。用单元停,而不是直接 kill:

1
sudo systemctl stop 那个单元.service

不属于 systemd、确认可以结束时,再对 pid 发信号。停完用同一条 ss 看这个端口是否还在监听,然后再启动你的服务。