三月驼雲 發表於 2024-8-14 14:52:00

线上问题排查——磁盘满

<h1 id="现象">现象</h1>
<p>群里反馈管理后台登录不上了,我一访问,整个界面空白,没有提示,打开 F12,发现控制台提示 js、css 等静态资源报 net::ERR_HTTP2_PROTOCOL_ERROR,客户端可以下载到服务端资源,第一次碰到这个,StackOverflow 走起</p>
<p>net::ERR_HTTP2_PROTOCOL_ERROR 是关于什么的?</p>
<p>可能出现的问题非常多,包括磁盘满、nginx 配置问题、请求头问题、浏览器问题、cdn 问题。因为这个服务没有更新过,也没人动过配置,所以不太可能是 nginx、服务的问题,另外每次下载 js 文件,似乎都不是完整的,虽然服务器都有做出响应。</p>
<p>所以初步判断是服务器出了问题,但是没有配置 ssh,登录阿里云后台的手机也在公司,没办法看到服务器监控。</p>
<p>此时发现多刷新几次,利用浏览器的本地缓存,首页还是能访问出来的,但是登录功能无法响应,如果填了错误的验证码,可以立马返回错误信息。说明 MySQL 写受到了影响,基本上可以是断定服务器的磁盘、内存问题。</p>
<p>第二天到了公司看控制台监控,好家伙磁盘占用 99%<br>
<img src="https://img2024.cnblogs.com/blog/2013206/202408/2013206-20240814141158751-1477891779.png"><br>
刷新了一下管理后台,响应非常非常的慢;先清理空间再验证是否这个问题</p>
<h1 id="解决">解决</h1>
<p>列出所有挂载的文件系统,并显示每个文件系统的总空间、已用空间、可用空间和使用率。</p>
<pre><code class="language-shell">df -h

#Filesystem      SizeUsed Avail Use% Mounted on
#udev             16G   0   16G   0% /dev
#tmpfs         3.1G724K3.1G   1% /run
#/dev/vda1      99G   94G343M 100% /
#tmpfs            16G   0   16G   0% /dev/shm
#tmpfs         5.0M   05.0M   0% /run/lock
#tmpfs            16G   0   16G   0% /sys/fs/cgroup
#tmpfs         3.1G   03.1G   0% /run/user/0
</code></pre>
<p>这时候要注意了,如果直接从根目录递归查找,会消耗大量的 CPU 和 IO 资源,可能会导致服务器变得非常慢,甚至暂时无法响应,所以要一层一层来</p>
<pre><code class="language-shell"># /* 换成对应的目录即可
du -sh /* | sort -rh | head -n 10
</code></pre>
<p><img src="https://img2024.cnblogs.com/blog/2013206/202408/2013206-20240814142248250-1581011801.png"></p>
<p>最终找出了两个目录,nacos 的 access 日志 和 MySQL binlog 日志,总计 80G 空间,其中大部分都是七天前的,可处理<br>
<img src="https://img2024.cnblogs.com/blog/2013206/202408/2013206-20240814142443083-1478447991.png"><br>
对于 nacos 的日志,直接删了之前的就好。而 MySQL 的 binlog 文件,建议从控制台执行命令</p>
<pre><code class="language-mysql"># 删除 七天前的 binlog
PURGE BINARY LOGS BEFORE NOW() - INTERVAL 7 DAY;
</code></pre>
<p>最终,处理了 40% 的空间<br>
<img src="https://img2024.cnblogs.com/blog/2013206/202408/2013206-20240814143026534-27780763.png"></p>
<h1 id="验证">验证</h1>
<p>多次强制刷新前端页面,静态资源和接口的响应速度也变快了。</p>
<p>接下来看一下昨天的日志,MySQL 除了写数据时获取不到锁,没有其他报错</p>
<p><img src="https://img2024.cnblogs.com/blog/2013206/202408/2013206-20240814143605608-1313533300.png"></p>
<p>包括 nginx 日志, /var/log/syslog 系统日志,/var/log/mysql/error.log 提示空间不足</p>
<pre><code class="language-log">2024-08-13T02:27:02.537301Z 1256492 Disk is full writing './binlog.000556' (OS errno 28 - No space left on device). Waiting for someone to free space... Retry in 60 secs. Message reprinted in 600 secs.
2024-08-13T02:37:02.571302Z 1256492 Disk is full writing './binlog.000556' (OS errno 28 - No space left on device). Waiting for someone to free space... Retry in 60 secs. Message reprinted in 600 secs.
2024-08-13T02:47:02.605275Z 1256492 Disk is full writing './binlog.000556' (OS errno 28 - No space left on device). Waiting for someone to free space... Retry in 60 secs. Message reprinted in 600 secs.
2024-08-13T02:57:02.640862Z 1256492 Disk is full writing './binlog.000556' (OS errno 28 - No space left on device). Waiting for someone to free space... Retry in 60 secs. Message reprinted in 600 secs.
2024-08-13T03:07:02.674508Z 1256492 Disk is full writing './binlog.000556' (OS errno 28 - No space left on device). Waiting for someone to free space... Retry in 60 secs. Message reprinted in 600 secs.
2024-08-13T03:17:02.710238Z 1256492 Disk is full writing './binlog.000556' (OS errno 28 - No space left on device). Waiting for someone to free space... Retry in 60 secs. Message reprinted in 600 secs.
</code></pre>
<p>除了页面实际上变快了,没有其他日志信息进一步确认</p>
<h1 id="后续工作">后续工作</h1>
<p>由于日志问题导致磁盘空间不足,需要启用定时器或者自带工具进行定时清理</p>
<h2 id="nacos-access-日志">nacos access 日志</h2>
<p>对于 nacos 没有提供对 access log 没有提供大小、分割配置,只有开关,而线上不建议关闭,所以需要编写 shell 脚本,加入定时器中</p>
<p>生产环境编写定时任务Crontab, 将脚本放到/etc/cron.daily 目录,赋予可执行权限</p>
<pre><code class="language-shell">#!/bin/bash

logFile="/data/nacos/bin/logs/nacos_del_access.log"
# 保留14天日志
date=`date -d "$date -14 day" +"%Y-%m-%d"`
# 具体位置可调整
delFilePath="/data/nacos/bin/logs/access_log.${date}.log"

if [ ! -f "${logFile}" ];then
        echo 'access log文件打印日志频繁. /etc/cron.daily/nacosDelAccessLogs.sh 会定时删除access日志文件' &gt;&gt;${logFile}
fi
# 日志文件存在, 则删除
if [-f "${delFilePath}" ];then
        rm -rf ${delFilePath}
        curDate=`date --date='0 days ago' "+%Y-%m-%d %H:%M:%S"`
        echo '['${curDate}'] 删除文件'${delFilePath} &gt;&gt;${logFile}
fi

</code></pre>
<h2 id="mysql-binlog">MySQL binlog</h2>
<p>建议保留七天或十四天,使用 MySQL 自带配置即可</p>
<pre><code class="language-mysql"># 我的默认配置三十天
# -- binlog_expire_logs_seconds        2592000
# SHOW VARIABLES LIKE 'binlog_expire_logs_seconds';
SET GLOBAL binlog_expire_logs_seconds = 604800;
</code></pre>
<blockquote>
<p>show VARIABLES like 'expire_logs_days';<br>
set global expire_logs_days = 7;<br>
之前是使用这两个命令,新版 MySQL 被废弃了</p>
</blockquote>
<p>永久生效,my.conf,需要重启</p>
<pre><code class="language-conf">
binlog_expire_logs_seconds = 604800
</code></pre>
<p>后面添加日志,需要进行管理和轮换日志文件,可以考虑使用 logrotate</p>
<p>参考:</p>
<ol>
<li>https://stackoverflow.com/questions/58215104/whats-the-neterr-http2-protocol-error-about</li>
<li>https://blog.csdn.net/wtzvae/article/details/107212870</li>
<li>https://blog.51cto.com/haibo0668/5486115</li>
<li>https://blog.csdn.net/mr_wanter/article/details/112515814</li>
</ol>
<pre><code class="language-js">这是一段防爬代码块,我不介意文章被爬取,但请注明出处
console.log("作者主页:https://www.cnblogs.com/Go-Solo");
console.log("原文地址:https://www.cnblogs.com/Go-Solo/p/18358836");
</code></pre><br><br>
来源:https://www.cnblogs.com/Go-Solo/p/18358836
頁: [1]
查看完整版本: 线上问题排查——磁盘满