“我的网站很慢!”
-- Erik Ljungstrom(作者)
我通常会严格保持此博客的技术性,将观察、意见等内容保持在最低限度。但是,这篇和接下来的几篇文章将介绍刚进入系统管理/SRE/系统工程师/sysops/devops-ops(无论你想称自己是什么)角色的常见的基础知识。
请跟我来!
“我的网站很慢!”
我只是随机选择了本文的问题类型,这也可以应用于任何与系统管理员相关的故障排除。我并不是要炫耀那些可以发现最多的信息的最聪明的“金句”。它也不是一个详尽的、一步步指导的、并在最后一个方框中导向“利润”一词的“流程图”。
我会通过一些例子展示常规的方法。
示例场景仅用于说明本文目的。它们有时会做一些不适用于所有情况的假设,而且肯定会有很多读者在某些时候说“哦,但我觉得你会发现……”。
但那可能会让我们错失重点。
十多年来,我一直在从事于支持工作,或在支持机构工作,有一件事让我一次又一次地感到震惊,这促使我写下了这篇文章。
有许多技术人员在遇到问题时的本能反应,就是不管三七二十一去尝试可能的解决方案。
“我的网站很慢,所以”,
“我曾经看过这个问题,它是因为某种原因造成的 —— 所以我估计还是这个原因,它应该能解决这个问题。”
这浪费了很多时间,并会让你在黑暗中盲目乱撞,胡乱鼓捣。
你的 InnoDB 的缓冲池也许达到 100% 的利用率,但这可能只是因为有人运行了一段时间的一次性大型报告导致的。如果没有排除这种情况,那你就是在浪费时间。
在这里,我应该说明一下,虽然这些建议同样适用于许多角色,但我是从一般的支持系统管理员的角度来撰写的。在一个成熟的内部组织中,或与规模较大的、规范管理的或“企业级”客户合作时,你通常会对一切都进行检测、测量、绘制、整理(甚至不是文字),并发出警报。那么你的方法也往往会有所不同。让我们在这里先忽略这种情况。
如果你没有这种东西,那就随意了。
首先确定实际上是什么问题。“慢”可以是多种形式的。是收到第一个字节的时间吗?从糟糕的 JAVAscript 加载和每页加载要拉取 15 MB 的静态内容,这是一个完全不同类型的问题。是慢,还是比通常慢?这是两个非常不同的解决方案!
在你着手做某事之前,确保你知道实际报告和遇到的问题。找到问题的根源通常很困难,但即便找不到也必须找到问题本身。
否则,这相当于系统管理员带着一把刀去参加枪战。
首次登录可疑服务器时,你可以查找一些常见的嫌疑对象。事实上,你应该这样做!每当我登录到服务器时,我都会发出一些命令来快速检查一些事情:我们是否发生了页交换(free / vmstat),磁盘是否繁忙(top / IOStat / iotop),是否有丢包(netstat / proc/net/dev),是否处于连接数过多的状态(netstat),有什么东西占用了 CPU(top),谁在这个服务器上(w / who),syslog 和 dmesg 中是否有引人注目的消息?
如果你从 RAID 控制器得到 2000 条抱怨直写式缓存没有生效的消息,那么继续进行是没有意义的。
这用不了半分钟。如果什么都没有引起你的注意 —— 那么继续。
如果某处确实存在问题,并且找不到唾手可得的信息。
那么采取所有步骤来尝试重现问题。当你可以重现该问题时,你就可以观察它。当你能观察到时,你就可以解决。如果在第一步中尚未显现出或覆盖了问题所在,询问报告问题的人需要采取哪些确切步骤来重现问题。
对于由太阳耀斑或只能运行在 OS/2 上的客户端引起的问题,重现并不总是可行的。但你的第一个停靠港应该是至少尝试一下!在一开始,你所知道的是“某人认为他们的网站很慢”。对于那些人,他们可能还在用他们的 GPRS 手机,也可能正在安装 windows 更新。你在这里挖掘得再深也是浪费时间。
尝试重现!
我对于有必要包括这一点感到很难过。但是我曾经看到有人在运行 tail /var/log/... 之后几分钟就不看了。大多数 *NIX 工具都特别喜欢记录日志。任何明显的错误都会在大多数应用程序日志中显得非常突出。检查一下。
如果没有明显的问题,但你可以重现所报告的问题,那也很棒。所以,你现在知道网站是慢的。现在你已经把范围缩小到:浏览器的渲染/错误、应用程序代码、DNS 基础设施、路由器、防火墙、网卡(所有的)、以太网电缆、负载均衡器、数据库、缓存层、会话存储、Web 服务器软件、应用程序服务器、内存、CPU、RAID 卡、磁盘等等。
根据设置添加一些其他可能的罪魁祸首。它们也可能是 SAN,也不要忘记硬件 WAF!以及…… 你明白我的意思。
如果问题是接收到第一个字节的时间,你当然会开始对 Web 服务器去应用上已知的修复程序,就是它响应缓慢,你也觉得几乎就是它,对吧?但是你错了!
你要回去尝试重现这个问题。只是这一次,你要试图消除尽可能多的潜在问题来源。
你可以非常轻松地消除绝大多数可能的罪魁祸首:你能从服务器本地重现问题吗?恭喜,你刚刚节省了自己必须尝试修复 BGP 路由的时间。
如果不能,请尝试使用同一网络上的其他计算机。如果可以的话,至少你可以将防火墙移到你的嫌疑人名单上,(但是要注意一下那个交换机!)
是所有的连接都很慢吗?虽然服务器是 Web 服务器,但并不意味着你不应该尝试使用其他类型的服务进行重现问题。 netcat 在这些场景中非常有用(但是你的 SSH 连接可能会一直有延迟,这可以作为线索)! 如果这也很慢,你至少知道你很可能遇到了网络问题,可以忽略掉整个 Web 软件及其所有组件的问题。用这个知识(我不收 200 美元)再次从顶部开始,按你的方式由内到外地进行!
即使你可以在本地复现 —— 仍然有很多“因素”留下。让我们排除一些变量。你能用普通文件重现它吗? 如果 i_am_a_1kb_file.html 很慢,你就知道它不是数据库、缓存层或 OS 以外的任何东西和 Web 服务器本身的问题。
你能用一个需要解释或执行的 hello_world.(py|php|js|rb..) 文件重现问题吗?如果可以的话,你已经大大缩小了范围,你可以专注于少数事情。如果 hello_world 可以马上工作,你仍然学到了很多东西!你知道了没有任何明显的资源限制、任何满的队列或在任何地方卡住的 IPC 调用,所以这是应用程序正在做的事情或它正在与之通信的事情。
所有页面都慢吗?或者只是从第三方加载“实时分数数据”的页面慢?
这可以归结为:你仍然可以重现这个问题所涉及的最少量的“因素”是什么?
我们的示例是一个缓慢的网站,但这同样适用于几乎所有问题。邮件投递?你能在本地投递吗?能发给自己吗?能发给<常见的服务提供者>吗?使用小的、纯文本的消息进行测试。尝试直到遇到 2MB 拥堵时。使用 STARTTLS 和不使用 STARTTLS 呢?按你的方式由内到外地进行!
这些步骤中的每一步都只需要几秒钟,远远快于实施大多数“可能的”修复方案。
到目前为止,当你去除特定组件时无法重现问题时,你可能已经偶然发现了问题所在。
但如果你还没有,或者你仍然不知道为什么:一旦你找到了一种方法来重现问题,你和问题之间的“东西”(某个技术术语)最少,那么就该开始隔离和观察了。
请记住,许多服务可以在前台运行和/或启用调试。对于某些类别的问题,执行此操作通常非常有帮助。
这也是你的传统武器库发挥作用的地方。strace、lsof、netstat、GDB、iotop、valgrind、语言分析器(cProfile、xdebug、ruby-prof ……)那些类型的工具。
一旦你走到这一步,你就很少能摆脱剖析器或调试器了。
strace 通常是一个非常好的起点。
你可能会注意到应用程序停留在某个连接到端口 3306 的套接字文件描述符上的特定 read() 调用上。你会知道该怎么做。
转到 MySQL 并再次从顶部开始。显而易见:“等待某某锁”、死锁、max_connections ……进而:是所有查询?还是只写请求?只有某些表?还是只有某些存储引擎?等等……
你可能会注意到调用外部 API 资源的 connect() 需要五秒钟才能完成,甚至超时。你会知道该怎么做。
你可能会注意到,在同一对文件中有 1000 个调用 fstat() 和 open() 作为循环依赖的一部分。你会知道该怎么做。
它可能不是那些特别的东西,但我保证,你会发现一些东西。
如果你只是从这一部分学到一点,那也不错;学习使用 strace 吧!真的学习它,阅读整个手册页。甚至不要跳过历史部分。man 每个你还不知道它做了什么的系统调用。98% 的故障排除会话以 strace 而终结。
via: http://northernmost.org/blog/troubleshooting-101/index.html
作者: Erik Ljungstrom 译者: wxy 校对: wxy
本文由 LCTT 原创编译, linux中国 荣誉推出