我新安装了 Ubuntu 22.04 Desktop,想在上面运行公共服务(postgreSQL、redis 等)以便从其他主机访问。我将每项服务配置为绑定(侦听)到静态 IP 192.168.1.xxx 以及本地主机,启动它们,然后它们就可以正常工作了。
当我重新启动计算机时,这些服务不会在 192.168.1.xxx 上监听,而只会在 localhost/127.0.0.1 上监听。当我重新启动服务时,它会绑定到所有地址。没有变化。没有防火墙。SSH 确实通过 IP 地址连接。这是重启后立即在本地运行的 Redis 示例的粘贴。
% sudo ufw status
Status: inactive
% redis-cli -h 192.168.1.200
Could not connect to Redis at 192.168.1.200:6379: Connection refused
not connected>
% redis-cli -h 127.0.0.1
127.0.0.1:6379>
% redis-cli -h localhost
localhost:6379>
% sudo lsof -i :6379
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
redis-ser 3004 redis 6u IPv4 35436 0t0 TCP localhost:redis (LISTEN)
redis-ser 3004 redis 7u IPv6 35437 0t0 TCP ip6-localhost:redis (LISTEN)
% sudo service redis-server restart
% sudo lsof -i :6379
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
redis-ser 14396 redis 6u IPv4 67757 0t0 TCP localhost:redis (LISTEN)
redis-ser 14396 redis 7u IPv6 67758 0t0 TCP ip6-localhost:redis (LISTEN)
redis-ser 14396 redis 8u IPv4 67759 0t0 TCP server:redis (LISTEN)
% redis-cli -h 192.168.1.200
192.168.1.200:6379>
是什么阻止服务在启动期间绑定到公共 IP 地址?这与桌面安装有什么关系?提前感谢您的时间!
答案1
该服务可能会在网络接口完全准备好并配置之前启动,这使得服务仅与localhost
您想要的 IP 绑定。
您可以执行以下操作来检查服务启动前是否已完全准备就绪并配置完毕,首先通过将此行添加到部分来配置systemd
服务文件以依赖于网络。您还可以修改以包含您的静态 IP 地址,例如[Unit]
After=network-online.target
/etc/systemd/resolved.conf
DNS=192.168.1.1
Domains=example.com
您还可以使用传统的网络配置方法,编辑/etc/NetworkManager/NetworkManager.conf
并设置managed=false
,然后在 /etc/network/ 文件中配置您的网络接口interfaces
。此外,在systemd
服务文件中,您可以使用以下命令延迟服务的启动:
ExecStartPre=/bin/sleep 30
ExecStart=/usr/bin/postgresql
答案2
感谢所有提出建议的人。这支持了我的猜测,即服务启动时网络尚未准备好。我能够确认:
- Ubuntu 22.04 桌面虚拟机的超干净安装也存在同样的问题(服务在重启时没有绑定到公共 IP,只有环回地址)。
- 全新安装的 Ubuntu 22.04 Server 可以按预期运行(服务开始监听给定的 IP 地址)。
- 看来服务器和桌面的启动方式不同。也许网络是在 GUI 桌面之后/内部配置的?
- 关于 systemd 的这个链接有更深入的信息:https://unix.stackexchange.com/questions/126009/cause-a-script-to-execute-after-networking-has-started#126146
- 上面的链接提到使用通配符地址(* 或 0.0.0.0)进行绑定,而不是使用文字的公共静态 IP。这有效!但如果您有多个网络接口,这可能不是您想要的……但在这种情况下您可能不会使用桌面。
- 完整的解决方案将涉及学习 systemd 和调试启动。