Linux开机启动自定义脚本
一、Linux系统启动顺序
# 第一步:init /etc/inittab
# 第二步:启动相应的脚本,并且打开终端
rc.sysinit
rc.d(里面的脚本)
rc.local
# 第三步:启动login登录界面 login
# 第四步:在用户登录的时候执行sh脚本的顺序,每次登录的时候都会完全执行的
/etc/profile.d/file
/etc/profile(其中包含执行/etc/profile.d/目录下的脚本)
/etc/bashrc
/root/.bashrc
/root/.bash_profile
注意事项: Linux开机自启动程序无法读取环境变量问题,通常是因为启动脚本的环境和登录环境不一致。
如果你的环境变量定义在用户的.bashrc或.bash_profile中,而开机时使用的是systemd或init系统,它们可能不会加载用户的shell配置文件。
解决办法:
1.使用/etc/environment:这是全系统环境变量配置文件,对所有用户有效。编辑这个文件,添加你的环境变量。
2.使用systemd服务:如果你的程序是通过systemd服务启动的,可以在服务文件中手动设置环境变量。
3.使用/.profile或/.bashrc:如果你需要为特定用户设置环境变量,可以在该用户的home目录下的.profile或.bashrc文件中添加环境变量,并确保该用户登录时这些文件会被执行。
二、登录时被执行脚本目录
/etc/profile.d/
是一个在 Linux 系统中用于存放在登录时会被执行的脚本的目录。
将写好的脚本(.sh文件)放到目录 /etc/profile.d/
下,系统启动或登录时就会自动执行该目录下的所有shell脚本。
这些脚本通常用于设置环境变量,比如 PATH 环境变量,以便在用户登录时可以使用这些路径下的程序。
但请注意,由于不确定系统环境变量何时初始化完成,所以不推荐在此目录执行启动Java程序等需要特定环境变量的任务。
自定义脚本:/etc/profile.d/welcome.sh
echo 'welcome to myos!'
三、登录时被执行配置文件
/etc/profile
文件包含了设置全局环境变量、系统级别的初始化命令、以及系统wide shell配置的脚本。
/etc/profile
文件包含了>>执行/etc/profile.d/
目录下的脚本
当执行完当前文件,说明系统环境已经初始化完成,因此我们适合在此配置文件的最末尾添加启动Java程序脚本,如下:
pid=$(ps -ef | grep "check_and_start_jars.sh" | grep -v grep | awk '{print $2}')
if [ -z "${pid}" ]; then
nohup /data/script/check_and_start_jars.sh > /dev/null 2>&1 &
else
echo "check_and_start_jars.sh is running."
fi
因为每次登录时都会被执行,所以先判断脚本或程序是否已经在运行,防止重复运行。
四、周期性检查并自动拉起Jar包
编写脚本文件
/data/script/check_and_start_jars.sh
#!/bin/bash
# 定义jar文件列表
JAR_NAMES=("myapp1.jar" "myapp2.jar" "myapp3.jar")
# 定义拉起jar的命令
JAR_SH=("app1.sh" "app2.sh" "app3.sh")
# 获取数组的长度
length=${#JAR_NAMES[@]}
while :
do
# 循环检查每个jar文件是否正在运行
for ((i=0; i<$length; i++))
do
JAR_NAME=${JAR_NAMES[$i]}
pid=$(ps -ef | grep ${JAR_NAME} | grep -v grep | awk '{print $2}')
# 判断pid是否为空,即表示进程不存在
if [ -z "${pid}" ]; then
echo "${JAR_NAME} was shutdown."
sh /data/script/app/${JAR_SH[$i]} start
else
echo "${JAR_NAME} is running."
fi
done
# 每隔1分钟检查一次进程状态
sleep 1m
done
exit 0
exit 0 :正常运行程序并退出程序。
exit 1 :非正常运行导致退出程序,也可以是其他数字。
给予执行权限
chmod +x check_and_start_jars.sh
后台运行脚本
nohup ./check_and_start_jars.sh > /dev/null 2>&1 &
查杀运行脚本
ps -aux | grep check_and_start_jars.sh
五、修改/etc/rc.d/rc.local文件
无法读取环境变量
解释说明
注意:在CentOS7之后可能无法自启动,CentOS7之后采用systemd作为init,rc.local也是通过systemd的service启动的。
在这些新发行版中,使用 systemctl enable rc-local.service
命令可以启用 rc-local.service
服务,其作用如下:
-
启用 rc-local 功能:这将允许你在 /etc/rc.d/rc.local 文件中编写自定义命令或脚本,并在系统启动时自动执行。简而言之,它还是保留了以前 rc.local 的功能,但通过 systemd 初始化系统来实现。
-
设置 rc-local.service 的自启动:通过使用 systemctl enable 命令,你告诉系统在引导期间自动启动 rc-local.service 服务。这样,你就无需手动执行 rc-local.service,系统会在每次启动时自动启动。
总的来说,启用 rc-local.service 服务的作用是让你可以使用类似于以前 rc.local 的方式,在系统启动时执行自定义的命令或脚本。然而,这也取决于你的 Linux 发行版和版本,因为有些发行版可能已经移除了或不再默认安装 rc-local.service 服务。
说明:systemd 默认会读取 /etc/systemd/system 下的配置文件,该目录下的文件会链接 /lib/systemd/system/ 下的文件。一般系统安装完 /lib/systemd/system/ 下会有 rc-local.service 文件,即我们需要的配置文件。
1、配置rc-local.service软链接
将 /lib/systemd/system/rc-local.service 链接到 /etc/systemd/system/ 目录下面来
ln -s /lib/systemd/system/rc-local.service /etc/systemd/system/rc-local.service
2、修改rc-local.service配置
在 /etc/systemd/system/rc-local.service
文件添加如下一行(如不存在)
[Install]
WantedBy=multi-user.target
Alias=rc-local.service
3、配置/etc/rc.local软链接(若不存在)
注意:与linux发行版有关,有的系统rc.local就是在/etc/下的,我的是在/etc/rc.d/rc.local下
ln -s /etc/rc.d/rc.local /etc/rc.lcal
4、修改启动脚本执行内容
在 /etc/rc.d/rc.local
或者其链接文件 /etc/rc.local
文件中添加启动命令
# 启动基础服务
sudo /usr/local/nginx/sbin/nginx
sudo /opt/redis/bin/redis-server /opt/redis/redis.conf
# 加载java依赖,不建议在此配置Java程序,会出现各种奇怪的问题
export JAVA_HOME=/usr/local/jdk1.8
export CLASSPATH=.:$JAVA_HOME/lib
export PATH=$JAVA_HOME/bin:$PATH
nohup /data/script/start_jars.sh > /dev/null 2>&1 &
环境变量问题:rc.local不一定能成功启动脚本,rc.local运行在操作系统完全引导成功但是尚未启动login shell之前,所以我们配置在/etc/profiles或bashrc里的环境变量并未得到执行,因此在rc.local执行阶段看不到任何环境变量。
即使在启动java命令之前加上export设置环境变量值,还是可能会出现缺失系统初始化信息等问题。
5、添加可执行权限
chmod +x /etc/rc.local
chmod +x /etc/rc.d/rc.local
6、激活rc-local.service
systemctl enable rc-local.service
六、配置自定义服务
无法读取环境变量,不适用在使用过程需要使用环境变量的Java程序
将Java程序配置为系统服务(systemd服务)来实现开机自启动。使用systemd可以很方便地管理和控制后台服务,包括Java程序。与rc-local.service相同原理
。
以下是一个简单的步骤来配置Java程序为systemd服务:
1、编写启动脚本
vi /data/script/start_jar.sh
#!/bin/bash
# Java可执行文件路径
JAVA_EXECUTABLE=/usr/bin/java
# Java程序的jar包路径
JAR_PATH=/path/to/your/java/test.jar
# 启动Java程序
$JAVA_EXECUTABLE -jar $JAR_PATH
2、添加可执行权限
chmod +x /data/script/start_jar.sh
3、创建systemd服务单元文件
在/etc/systemd/system/
目录下创建一个以.service结尾的文件test.service
,用于定义您的Java程序作为systemd服务的配置。
[Unit]
Description=Your Java Program
After=network.target
[Service]
ExecStart=/data/sbin/check_and_start_jars.sh
Type=simple
Restart=on-failure
[Install]
WantedBy=multi-user.target
4、激活test.service服务
systemctl enable test.service
5、systemd常用命令
systemctl enable test.service //设置开机启动
systemctl disable test.service //取消开机启动
systemctl start test.service //启动service脚本
systemctl restart test.service //重启service脚本
systemctl stop test.service //停止service脚本
systemctl status test.service //查看service状态
journalctl -u test.service //查看service日志,journalctl用于查看系统日志,-u指定服务名称。
systemctl daemon-reload //重新加载systemd守护程序,以便它可以读取任何新的或更改的服务文件。
ps auxw --sort=-rss //查看内存占用情况,列出所有进程,并按内存使用量从高到低排序。
df -h //查看磁盘占用情况
du -sh * //查看当前目录文件大小
七、chkconfig命令
无法读取环境变量
1、首先编写好自启的脚本
/etc/init.d/test.sh
#!/bin/sh
# chkconfig: 2345 10 90
# 创建个文件
touch /opt/script/1.txt
2、添加可执行权限
chmod +x test.sh
3、将脚本添加到开机启动项
chkconfig --add test.sh
4、将脚本设置为自启动
chkconfig test.sh on
5、chkconfig命令的常用参数
chkconfig --list:列出所有系统服务的启动状态;
chkconfig --add:增加服务;
chkconfig --del:删除服务;
chkconfig 服务名 on:设定服务开机启动;
chkconfig 服务名 off:关闭服务开机启动;
chkconfig 服务名 --level 35 on:设定服务在等级3和等级5时启动;
chkconfig 服务名 --level 35 off:关闭服务在等级3和等级5时自动启动;
chkconfig --level 35 服务名 on:设定服务在等级3和等级5时启动;
chkconfig --level 35 服务名 off:关闭服务在等级3和等级5时自动启动;
八、配置计划任务
无法读取环境变量
可以周期性执行某些任务,如:清理日志、备份数据、检查服务运行状态...
安装crontabs
yum install contabs
编辑当前用户的crontab文件,添加计划任务
crontab -e
# 每分钟执行1次command
* * * * * /data/check_and_start_jars.sh > /dev/null 2>&1 &
点击查看代码
# 每分钟执行1次command
* * * * * command
# 每小时执行1次command
0 * * * * command
# 每天执行1次command
0 0 * * * command
# 每周执行1次command
0 0 * * 0 command
# 每月执行1次command
0 0 1 * * command
# 每月最后1天执行1次command
0 0 L * * command
# 每年1月1日执行1次command
0 0 1 1 * command
# 每2小时执行1次command
0 */2 * * * command
# 每天7:50执行1次command
50 7 * * * command
# 每月1号和15号执行1次command
0 0 1,15 * * command
# 每小时的第1分执行1次command
1 * * * * command
# 每小时的第3和第15分钟执行1次command
3,15 * * * * command
# 在上午8点到11点的第3和第15分钟执行1次command
3,15 8-11 * * * command
# 每隔2天的上午8点到11点的第3和第15分钟执行1次command
3,15 8-11 */2 * * command
# 每月1、10、22日的4 : 45执行1次command
45 4 1,10,22 * * command
# 每周六、周日的1:10执行1次command
10 1 * * 6,0 command
# 每天18 : 00至23 : 00之间每隔30分钟执行1次command
0,30 18-23 * * * command
查看当前用户的 crontab 文件
crontab -l
删除当前用户的 crontab 文件
crontab -r
查看crontab的日志信息
tail -f /var/log/cron
激活
systemctl enable crond
启动
systemctl start crond
状态
service crond status