Ubuntu设置开机自启动项,支持需要sudo的命令
对于Ubuntu桌面版及各种发行版,例如Zorin OS,可以使用“启动应用程序”图形界面工具添加开机启动项:
使用这个工具添加开机启动项实际上是在以下目录创建了启动器:
$HOME/.config/autostart
启动器的内容如下:
[Desktop Entry]
Type=Application
Exec=命令
Hidden=false
NoDisplay=false
X-GNOME-Autostart-enabled=true
Name[zh_CN]=名称
Name=名称
Comment[zh_CN]=描述
Comment=描述
事实上直接将.desktop文件拷贝到这个目录中也是等效的。
使用这种方式创建的开机启动项不能执行需要sudo的命令,尽管可以给要执行的脚本赋予可执行权限:
sudo chmod a+x path
相比之下,我更倾向于添加自启动服务。
Systemd的.service服务文件配置
.service文件的基本结构如下:
[Unit]
...
[Service]
...
[Install]
...
[Unit]块:
配置服务的启动顺序和依赖关系,示例:
[Unit]
Description=/etc/rc.local Compatibility
Documentation=man:systemd-rc-local-generator(8)
ConditionFileIsExecutable=/etc/rc.local
After=network.target
常用参数:
- Description:对该服务的描述;
- Documention:该服务的说明文档;
- ConditionFileIsExecutable:指定执行文件,需要可执行权限;
- Before:在其他服务启动前启动本服务;
- After:在其他服务启动后再启动本服务;
- Wants:弱依赖,即使被依赖服务启动失败或停止,本服务仍然运行;
- Requires:强依赖,如果被依赖服务启动失败或停止,本服务也会停止。
[Service]块:
配置服务运行的方式,示例:
[Service]
Type=forking
ExecStart=/etc/rc.local start
TimeoutSec=0
常用参数:
- EnvironmentFile:服务的参数文件;
- ExecStart:服务启动时执行的命令;
- ExecStop:服务停止时执行的命令;
- Type:服务的启动类型;
- TimeoutStartSec:服务允许的最大启动时长。如果守护进程未能在限定的时长内发出"启动完毕"的信号,那么该服务将被视为启动失败,并会被关闭。单位默认为s,可以指定其他时间单位;
- TimeoutStopSec:服务允许的最大停止时长;
- TimeoutSec:同时设置服务的最大启动和停止时长;
- KillMode:服务停止类型;
- Restart:服务重启类型;
- RestartSec:间隔多久重启服务。
[Install]块:
配置服务所属服务组,示例:
[Install]
WantedBy=multi-user.target
Alias=rc-local.service
常用参数:
- WantedBy:指定服务所在服务组;
- Alias:服务别名。不指定的情况下,服务名为文件名称;
Systemd服务管理
Systemd默认从以下目录读取配置文件:
/etc/systemd/system/
但实际的.service文件都是放置在以下目录:
/usr/lib/systemd/system
建立符号链接:
sudo systemctl enable my.service
以上命令效果等同于:
sudo ln -s /usr/lib/systemd/system/my.service /etc/systemd/system/my.service
systemctl命令:
重新加载服务的配置文件:
sudo systemctl daemon-reload my.service
启动服务:
sudo systemctl start my.service
停止服务:
sudo systemctl stop my.service
重启服务:
sudo systemctl restart my.service
设置开机启动:
sudo systemctl enable my.service
禁用开机启动:
sudo systemctl disable my.service
一劳永逸开机自启动法
利用rc.local来实现开机自启动,编辑rc-local.service文件:
sudo gedit /usr/lib/systemd/system/rc-local.service
可以看到该配置文件缺少[Install]块,在末尾添加即可:
[Install]
WantedBy=multi-user.target
设置开机启动:
sudo systemctl enable rc-local.service
此时可以看到以下目录中添加了rc-local.service的符号链接:
/etc/systemd/system/multi-user.target.wants
创建rc.local文件:
sudo gedit /etc/rc.local
文件内容如下:
#!/bin/sh -e
# 要执行的命令
/opt/lampp/lampp startapache
exit 0
文件开头的内容必须是:
#!/bin/sh -e
这里简单说下#!/bin/sh与#!/bin/bash的区别:
- #!/bin/sh相当于带有–posix标志的#!/bin/bash,即POSIX标准的bash;
- #!/bin/sh如果某行代码出错,就不再继续往下执行。
#!/bin/sh -e 的作用:
- 正常的shell脚本里,执行完一条命令会用$?去判断上一条命令的返回值。如果为0代表执行成功,则可以继续往下执行;如果非0则代表执行失败,此时应该退出脚本。
- -e 的作用是脚本运行时,只要命令返回值为非0就会自动退出,而不再需要自己去加判断。
注意:在/etc/rc.local文件中执行的命令不再需要加sudo,另外如果是执行sh,需要在命令末尾加&符号
最后,必须给/etc/rc.local可执行权限:
sudo chmod a+x /etc/rc.local