Linux服务启动失败?别慌,journalctl排查技巧全解析

linux系统怎么查看服务启动失败的原因 journalctl排查技巧

服务启动失败,是运维工作中最常遇到的“老朋友”。一个核心技巧是:直接运行 journalctl -u 服务名 -n 50 -e,90%的问题根源就藏在最后那几行日志里。 这相当于直接翻到故障剧本的最后一页,往往答案就在那里。但有时候,剧本本身可能就出了问题,或者记录剧本的本子不见了。接下来,我们就顺着这条线索,把几种常见的“查不到”和“看不懂”的情况彻底理清。

journalctl -u 查不到日志?先确认服务名和 unit 文件是否加载成功

首先得明确一点:journalctl -u 只追踪那些已经被系统加载的 unit。所以,如果命令执行后一片空白,别急着怀疑日志系统,很可能第一步就踩了坑。

最常见的情况是服务名输错了。比如,完整的服务名通常是 nginx.service,但很多人会习惯性地只输入 nginx。更隐蔽的情况是,服务根本没安装,或者安装了但未被启用。这时候,可以先用 systemctl list-units --type=service | grep 服务名 看看它是否在运行的服务列表中。再用 systemctl status 服务名 仔细检查输出:重点看“Loaded”这一行,它显示了 unit 文件的路径以及是否启用(enabled)。如果这里显示的是 not-found(找不到文件)或者 masked(被屏蔽),那么 journalctl -u 自然就无迹可寻了。

为什么 journalctl -u 显示 “No entries”?检查 journal 是否持久化

遇到过这种情况吗?昨天服务明明崩溃过,今天用 journalctl -u 却什么也查不到。这很可能不是灵异事件,而是 journal 的存储方式在作祟。

默认情况下,systemd journal 的日志只保存在内存或 /run/log/journal/ 目录下,一旦重启,这些记录就烟消云散了。如果服务故障发生在上一次启动周期内,而你的系统又没有配置持久化日志,那么查询结果为空就再正常不过了。

此时,可以尝试使用 journalctl -b -u 服务名 来查询本次启动以来的所有相关日志。但治本之策,是检查并启用持久化。方法很简单:打开 /etc/systemd/journald.conf 配置文件,找到 Storage= 这一项。如果它是 volatile(易失的),就改为 persistent(持久的)。然后,手动创建存储目录并重启服务:mkdir -p /var/log/journal && systemctl restart systemd-journald。这样一来,日志就能在重启后幸存下来了。

日志里只看到 “Failed to start”,但没具体错误?加 --no-pager + grep -i

有时候,systemctl status 给出的那句“Failed to start”就像一份语焉不详的病情通知书,关键细节全被隐藏了。问题往往出在分页器上——重要的错误信息可能被截断,或者淹没在海量的 INFO 级别日志里。

这时候,需要更粗暴直接的过滤方式:journalctl -u 服务名 --no-pager | grep -i “fail\|error\|refused\|timeout\|denied”。这个命令能帮你把包含关键错误线索的行全部揪出来。特别要警惕以下几种高频“暗号”:

日志没报错,但服务就是不起来?试试 journalctl -b -p err

最让人头疼的情况莫过于此:服务的日志干干净净,但它就是启动失败。这说明,问题可能不在服务本身,而在它所依赖的“环境”上。

比如,服务配置了网络访问,但启动时网络尚未就绪(缺少 After=network-online.target 依赖);或者服务需要精确时间来进行 TLS 握手,但系统时间未同步(缺少 After=time-sync.target)。甚至,可能是根文件系统意外变成了只读状态(用 df -h / 检查一下)。

这时,应该把视野放宽。运行 journalctl -b -p err,查看本次系统启动以来所有错误级别(err)及以上的日志。真正的罪魁祸首,往往在你的服务尝试启动之前就已经出现了。这才是解决问题的关键线索。

说到底,真正卡住人的,往往是那些“沉默的失败”。环境变量缺失、工作目录不可写、EnvironmentFile= 指向的配置文件不存在,甚至只是 $PATH 环境变量里缺少了 /usr/local/bin 这样的路径。因此,别只死盯着 journalctl -u 的输出。一个更有效的思路是:通过 systemctl show 服务名 命令,仔细查看系统实际为服务设置的环境(Environment)、工作目录(WorkingDirectory)和运行用户(User),然后尝试手动在命令行复现 ExecStart 的命令。很多时候,手动执行一下,错误就会自己跳出来告诉你答案了。

本文转载于:https://www.php.cn/faq/2357344.html 如有侵犯,请联系zhengruancom@outlook.com删除。
免责声明:正软商城发布此文仅为传递信息,不代表正软商城认同其观点或证实其描述。