最标准做法是编写包含unit[install]三段的.service文件放入/etc/systemd/system/并执行systemctl daemon-reload。最小示例含description、after、type、user、workingdirectory、execstart、restart及wantedby,部署需确保权限、路径正确,启用后支持status、journalctl、restart等命令管理,并通过日志、权限、路径三方面排错。

直接写一个 .service 文件,放进 /etc/systemd/system/,再用 systemctl daemon-reload 加载,就能像原生服务一样管理——这是最标准、最可靠的做法。
自定义 service 文件怎么写
一个最小可用的 .service 文件包含三部分:[Unit]、[Service]、[Install]。下面是一个典型示例:
/etc/systemd/system/myapp.service
[Unit] Description=My Custom Application After=network.target [Service] Type=simple User=myuser WorkingDirectory=/opt/myapp ExecStart=/usr/bin/python3 /opt/myapp/app.py Restart=on-failure RestartSec=5 [Install] WantedBy=multi-user.target
-
Description是服务描述,systemctl status时会显示 -
After=network.target表示该服务在网络就绪后启动,避免因网络未通导致失败 -
Type=simple适用于前台运行的进程(如 Python 脚本);若程序自己 fork 到后台,应改用Type=forking -
User和WorkingDirectory强烈建议显式指定,避免权限或路径问题 -
Restart=on-failure让 systemd 在进程异常退出时自动拉起,比手动守护更稳定
部署和启用服务的完整流程
写完文件后不能直接 start,必须走标准加载流程:
- 保存文件到
/etc/systemd/system/myapp.service(注意权限:root 所有,644 权限) - 确保
ExecStart指向的程序有执行权限(如chmod +x /opt/myapp/app.py) - 运行
sudo systemctl daemon-reload—— 这步必不可少,否则 systemd 不知道新服务存在 - 测试启动:
sudo systemctl start myapp,然后用sudo systemctl status myapp查看是否成功 - 确认无误后,设置开机自启:
sudo systemctl enable myapp
启用后,会在 /etc/systemd/system/multi-user.target.wants/ 下生成软链接,系统启动时自动触发。
日常管理常用命令
服务上线后,这些命令就是你每天打交道的对象:
-
sudo systemctl status myapp—— 查看实时状态、最近日志、退出原因 -
sudo journalctl -u myapp -f—— 实时跟踪服务输出(-f 表示 follow) -
sudo systemctl restart myapp—— 修改配置或代码后重新加载 -
sudo systemctl stop myapp—— 临时停用 -
sudo systemctl disable myapp—— 取消开机自启(不删除文件,只删软链接)
如果修改了 .service 文件内容,必须先 daemon-reload,再 restart,否则更改不会生效。
排错关键点
服务启动失败很常见,核心排查思路是“看日志 + 看权限 + 看路径”:
- 失败时第一时间运行
sudo systemctl status myapp,它会高亮显示最后一行错误(比如 “Permission denied” 或 “No such file”) - 用
sudo journalctl -u myapp --since "2 minutes ago"查看精确时间窗口内的完整输出 - 检查
ExecStart中的路径是否为绝对路径;相对路径在 systemd 下无效 - 确认
User指定的用户对WorkingDirectory和脚本本身有读+执行权限 - 如果程序依赖环境变量(如
PYTHONPATH),在[Service]段添加Environment="KEY=VALUE"











