最近在开发过程中碰到一个问题,当我们在Linux环境下直接使用命令nohup Java -jar xxxxxx.jar & 来运行jar
包的时候,默认生成的log文件只会在启动时生成一次文件,nohup.out会越来越大。而由于我的linux运行环境是在一个硬件设备上,分配的内存有限,日志文件很容易就将磁盘空间占满了,如果直接删掉log文件的话,后续的操作不会输出,也没有日志文件生成。那么有没有什么办法来解决这个问题呢?下面是我梳理的三种不同的解决办法,如果更多的解决办法,大家评论区讨论

1.使用 Linux 自带的 logrotate 程序来控制日志文件尺寸

在linux环境中,一般在 /etc目录下有一个 logrotate.d 文件夹或者有一个logrotate.conf的文件。

  1. logrotate.d 文件夹内部有很多规则文件,例如:针对firewalld的
	/var/log/firewalld {
	    weekly
	    missingok
	    rotate 4
	    copytruncate
	    minsize 1M
	}

下面来一个日志大小控制的例子
编写配置文件,放在 /etc/logrotate.d/文件夹下新建一个文件 clearlogs,无需后缀,文件内容:

	/opt/volumn/nohup.out {
	    copytruncate
	    daily
	    dateext
	    rotate 3
	    compress
	    missingok
	    size 200M
	}

第一行是文件的全路径,大括号中的重要字段解释如下:
copytruncate 使用先拷贝文件再 truncate 原文件的方法来轮转,这种方法无需停应用,也不会有数据丢失。
daily 按天执行
dateext 轮转后的日志备份加上日期后缀
rotate 3 总共保留 3 份备份文件
compress 开启gzip压缩,能大幅减少日志备份的尺寸
missingok 日志文件不存在的时候不会报错(如果有多个配置,会继续执行)
size 200M 只有文件大于 200M 时才轮转
配置项的详细解释可以参考 man logrotate

2.在logrotate.conf文件的最后加入一下条目

# Rotate log files

	/opt/volumn/nohup.out {
		rotate 3
		size=50M
	}

Rotate的意思是当nohup.out的大小超过50mb以后,将创建一个新的空nohup.log文件,并且这个旧的文件将被重命名为nohup.out.1,如果旧的文件达到了3个,那么最旧的将被循环删除,类似于日志文件重用的概念。

为了使该命令生效,需要以root执行以下操作:
$ logrotate /etc/logrotate.conf
在/etc/logrotate.conf的顶端可以看见以下行:

# rotate log files weekly

weekly表示默认情况下,该命令每周执行一次。
通过’man logrotate’,可以查看各种命令选项。
需要特别注意的一个选项是copytruncate,在这个操作之间会有一段延迟,会造成数据的丢失,切忌不可在警告日志上使用

2.定时任务清除日志文件

我想的肯定是希望能写一个脚本把这些日志清除掉,但不是删除掉。那么现在需要实现3步:

     1.找到项目的log的位置
     2.清除log内容
     3.定时执行脚本

有了思路,查找了资料后,找到了几个相关的命令:

找到文件命令:
find /opt/volumn/ -name 'nohup.out’*

清除文件的命令:
truncate -s 0 nohup.out {} ;
切记,这里的“;”号不能省略, 意思是将nohup.out的大小变成0M,即把nohup.out的内容清空了

综上编写一个清除日志的脚本:
新建clearlogs.sh shell脚本

#!/bin/bash

status(){
  date 
  find /mnt/userdata/ulove/ -name 'nohup.out' -type f -print -exec truncate -s 0 {} \;
  echo "清空log成功"
  return
}

case "$1" in 
    status)
        status;;*)
            echo "清除失败"
esac

定时任务常用命令:
crontab -l :查看定时任务
crontab -e :添加任务
crontab -r :删除任务
cat /etc/crontab :查看crontab文件

现在我们来添加一条任务:
0 0 * * * ? /var/local/clearlog.sh status >>/var/local/clearresult.txt
每小时执行脚本并输出到clearresult.txt文件 ,定时任务的写法:*(分) *(时) *(日) *(月) *(周) command

 添加好后查看(crontab -l )

这里可能出现clear.txt生成了。但是没有内容,日志也没清除,这个原因可能是你没给这个脚本赋权限:
chmod 755 clearlogs.sh

3.docker运行环境

1.新建 /etc/docker/daemon.json,若有就不用新建了。添加log-dirver和log-opts参数,样例如下:

# vim /etc/docker/daemon.json

{
  "log-driver":"json-file",
  "log-opts": {"max-size":"200m", "max-file":"2"}
}

max-size=200m,意味着一个容器日志大小上限是200M,
max-file=2,意味着一个容器有两个日志,分别是id+.json、id+1.json

2.然后重启docker的守护线程

命令如下:

systemctl daemon-reload
systemctl restart docker

【需要注意的是:设置的日志大小规则,只对新建的容器有效,如果你是已经运行的docker容器,那么你需要重新再创建一遍才能生效】

Logo

华为开发者空间,是为全球开发者打造的专属开发空间,汇聚了华为优质开发资源及工具,致力于让每一位开发者拥有一台云主机,基于华为根生态开发、创新。

更多推荐