ARTICLE DETAIL

资讯详情

深耕网站视觉设计与运营推广的一线实战洞察。

Linux less 命令查找关键字:从 cat/grep 到高效日志排查

Linux less 命令查找关键字:从 cat/grep 到高效日志排查 1. 为什么我劝你把 less 用明白而不是只会 cat 和 grep刚入行那会儿我查日志的方式特别粗暴cat app.log | grep ERROR。文件小的时候没问题一旦日志涨到几百兆甚至几个G终端直接卡死滚动条疯狂往上翻想找上下文还得重新跑一遍命令。后来被一位老运维点了一句“你这是在用大炮打蚊子还打偏了。”他给我演示了一遍less我才意识到这个看起来不起眼的命令才是 Linux 下查文件关键字的正确姿势。less是什么简单说它是一个分页查看器但它比more强太多——支持向前向后翻页、支持关键字搜索、支持高亮匹配、支持实时跟踪文件变化。它能解决的核心问题是在不把整个文件加载进内存、不刷屏的前提下快速定位并浏览文件中的关键字及其上下文。这跟grep的定位完全不同grep是“过滤出匹配行”而less是“在文件里跳着看”。这篇文章适合谁如果你是刚接触 Linux 的开发、测试、运维或者你天天跟日志、配置文件、SQL 脚本打交道却还在用cat、vim硬扛大文件那这篇内容就是给你写的。我会从底层逻辑讲到实操细节把less查找关键字这件事彻底讲透包括那些文档里不会写、只有踩过坑才知道的技巧。先给个最基础的印象打开文件并搜索关键字两步less /var/log/nginx/access.log # 进入后输入 /关键字 回车按 n 跳下一个N 跳上一个就这么简单。但简单背后有一堆值得说道的东西往下看。2. less 查找关键字的整体思路与方案选型2.1 less 与 grep、vim、cat 的定位差异很多人搞不清这几个命令该在什么场景用我做个对比表你一看就明白。命令核心行为是否加载全文适合场景查找关键字能力cat一次性输出全部内容是小文件快速查看无grep过滤匹配行输出流式精确提取匹配行强但丢失上下文vim全功能编辑器是可配置编辑文件强但重less分页浏览否按需读取大文件浏览定位强且保留上下文关键点在于grep给你的是“结果”less给你的是“现场”。当你排查一个报错你不光想知道哪一行有 ERROR你还想知道这行前面发生了什么、后面触发了什么。grep默认只给你那一行你得加-A、-B、-C才能带上下文而less天然就在上下文里跳转。我个人的习惯是先用 grep 定位大致范围再用 less 进去精读。比如先grep -n Timeout app.log | head拿到行号然后less 行号 app.log直接跳到那一行附近看现场。这个组合拳后面会详细讲。2.2 为什么 less 能做到“不卡”这里涉及一个很多人忽略的原理。less并不会一次性把整个文件读进内存它是按需读取的。当你打开一个 5G 的日志文件less只读取当前屏幕需要显示的那部分内容翻页时再读下一块。这就是为什么cat大文件会卡死而less秒开。注意less默认对文件做的是“惰性加载”但如果你在 less 里用了某些会触发全文扫描的操作比如跳到文件末尾G它仍然需要读取到那里。不过相比 cat 全量输出开销小得多。这个特性决定了less在查找关键字时的一个行为搜索是从当前位置向文件末尾方向进行的。也就是说你打开文件时光标在开头输入/keyword是往下找如果你想往上找得用?keyword。这个方向性很多人第一次用会懵明明文件里有这个关键字怎么搜不到因为你当前位置已经在它后面了。2.3 查找关键字的两种模式正向与反向less的搜索分正向和反向这是理解查找逻辑的基础/pattern从当前位置向文件末尾方向搜索?pattern从当前位置向文件开头方向搜索n重复上一次搜索方向相同N重复上一次搜索方向相反举个例子你打开日志光标在开头想找最后一次出现的 shutdownless app.log # 先按 G 跳到文件末尾 # 再按 ?shutdown 回车从末尾往前找 # 按 n 继续往前找上一个这个“方向感”是新手最容易踩的坑。我见过太多人打开文件直接/keyword结果说“明明有怎么搜不到”其实是因为关键字在光标上方得用?。3. less 查找关键字的核心细节与实操要点3.1 基础搜索/ 和 ? 的正确打开方式先把最基本的操作过一遍但我会补充那些容易被忽略的细节。打开文件less filename进入 less 后界面底部会出现一个冒号提示符等待你输入命令。此时输入/底部变成/继续输入关键字回车开始向下搜索输入?底部变成?继续输入关键字回车开始向上搜索搜索到匹配项后匹配的文本会高亮显示默认反白或加粗取决于终端配色按n跳到下一个匹配按N跳到上一个匹配按Esc或CtrlC可以取消当前搜索输入这里有个细节搜索是大小写敏感的。默认情况下/error不会匹配Error或ERROR。如果你想让搜索忽略大小写有两个办法方法一进入 less 前加参数less -i filename-i表示 ignore case但它的行为有点特殊如果搜索模式里全是小写字母则忽略大小写如果模式里包含大写字母则大小写敏感。这个设计很聪明兼顾了灵活性和精确性。方法二在 less 内部临时切换# 进入 less 后输入 -I-I是强制忽略大小写不管模式里有没有大写。这个设置是当前会话生效的。我个人的习惯是查日志时用less -i因为日志里 ERROR、Error、error 混着写太常见了忽略大小写能少漏掉很多。但查代码或配置时我会保持大小写敏感避免误匹配。3.2 高亮匹配让关键字一眼可见默认情况下less搜索到的匹配项会高亮但有些终端配色下高亮不明显或者你希望所有匹配项都持续高亮而不只是当前那个。这里有几个技巧。第一确保高亮开启。有些环境默认关闭了高亮你可以用less -g filename-g表示只高亮当前匹配项其他匹配项不高亮。反过来如果你想让所有匹配项都高亮其实默认行为就是这样的取决于版本。如果发现不高亮检查一下环境变量LESS里有没有-G或-g。第二自定义高亮颜色。less的高亮颜色由终端的环境变量控制具体是LESS_TERMCAP_sostandout即反白模式。你可以在~/.bashrc里这样设置export LESS_TERMCAP_so$\E[30;43m # 黑字黄底 export LESS_TERMCAP_se$\E[0m # 重置这样搜索匹配项就会以黑字黄底显示非常醒目。我试过好几种配色黑字黄底在深色终端和浅色终端下都看得清推荐。提示修改~/.bashrc后记得source ~/.bashrc或重新打开终端。第三如果你用的是less的较新版本530 以上还支持--use-color参数做更细粒度的颜色控制不过这个属于进阶玩法日常用LESS_TERMCAP_so就够了。3.3 搜索方向与位置n、N、g、G 的配合搜索本身不难难的是在文件里“导航”。less提供了一组导航命令配合搜索使用效率翻倍。命令作用g跳到文件开头G跳到文件末尾n下一个匹配同方向N上一个匹配反方向CtrlF向下翻一页CtrlB向上翻一页CtrlD向下翻半页CtrlU向上翻半页行号g跳到指定行如100g跳到第100行一个典型场景你打开一个巨大的日志想找最后一次出现的 OutOfMemory。less -i app.log # 按 G 跳到末尾 # 按 ?outofmemory 回车从末尾往前找 # 按 n 继续往前找上一个反过来如果你想找第一次出现的less -i app.log # 按 g 回到开头 # 按 /outofmemory 回车从开头往后找 # 按 n 继续往后找这里有个经验先定位方向再搜索。很多人搜不到就是因为没搞清楚光标在哪、关键字在哪。养成习惯搜索前先g或G确定起点。3.4 正则表达式让查找更精准less的搜索支持正则表达式这是它比普通查找强大的地方。默认情况下less使用的是 POSIX 基本正则BRE但你可以切换到扩展正则ERE。基本用法举例# 查找以 ERROR 开头的行 /^ERROR # 查找以 timeout 结尾的行 /timeout$ # 查找包含数字的行 /[0-9] # 查找 ERROR 或 WARN /ERROR|WARN注意|在基本正则里需要转义为\|或者你切换到扩展正则模式。在 less 内部输入-E-E表示使用扩展正则ERE这样|、、?等元字符就不需要转义了。我一般会先按-E再搜索省得记哪些要转义。还有一个实用技巧搜索特殊字符。比如你想搜[ERROR]这种带方括号的方括号在正则里是字符类直接搜会出问题。你需要转义/\[ERROR\]或者用-F切换到“固定字符串”模式此时所有字符都按字面意思匹配-F这个模式在搜索包含大量特殊字符的字符串时特别有用比如搜 JSON 里的status: failed。3.5 从命令行直接带搜索进入每次打开文件再输入搜索效率低。less支持在命令行直接指定搜索模式打开就定位。less /keyword filename/表示打开文件后立即执行正向搜索keyword。同理less ?keyword filename表示打开后立即反向搜索。这个技巧在脚本里特别有用。比如你写一个排查脚本自动打开日志并定位到最新的错误less /ERROR /var/log/app/latest.log打开就直接跳到第一个 ERROR按n继续看下一个。省去了手动输入的步骤。还有一个更狠的用法结合 grep 拿到行号直接跳到那一行。# 先找到行号 grep -n NullPointerException app.log | head -1 # 假设输出 12345:xxx # 然后直接跳到那一行 less 12345g app.log12345g表示打开后执行12345g即跳到第 12345 行。这样你打开文件就精确落在目标行附近前后文一目了然。这个组合我在排查线上问题时用得最多比单纯 grep 高效太多。4. 实操过程与核心环节实现4.1 场景一在超大日志里定位报错上下文假设你有一个 2G 的app.log线上服务报错你要找到最近的NullPointerException并看上下文。第一步先确认文件大小和大致情况ls -lh app.log wc -l app.log第二步用 grep 快速定位匹配行号grep 是流式的不会卡grep -n NullPointerException app.log | tail -5tail -5取最后 5 个匹配因为你要找最近的。假设输出1234567:2024-01-15 10:23:45 ERROR NullPointerException at ... 1234890:2024-01-15 10:25:12 ERROR NullPointerException at ...第三步用 less 跳到目标行附近less 1234890g app.log打开后你就在第 1234890 行按k往上翻看前因按j往下翻看后果。如果想在这个位置继续搜索其他关键字直接/就行。第四步如果上下文里有多个相关关键字比如你想看这次报错前后的 requestId可以# 在 less 里 ?requestId从当前位置往前找 requestId找到后按n继续往前直到找到这次请求的起点。这个流程的关键在于grep 负责快速筛选less 负责精读现场。两者分工明确不要试图用 grep 解决所有问题也不要一上来就用 less 硬翻。4.2 场景二实时跟踪日志并搜索关键字less有一个-F参数注意和前面固定字符串的-F不同这里是 follow 的意思可以像tail -f一样实时跟踪文件变化。less F app.log进入后less会持续显示文件新增内容相当于tail -f。此时按CtrlC可以退出跟踪模式回到普通浏览模式然后你就可以用/搜索了。搜完想继续跟踪再按ShiftF回到跟踪模式。这个功能在排查实时问题时特别好用。比如你怀疑某个请求会触发错误可以less F app.log # 等待请求进来 # 看到异常输出后按 CtrlC # 按 ?Exception 往前找异常堆栈比开两个终端一个 tail 一个 grep 方便多了。注意F模式下如果文件被轮转logrotateless默认会继续跟踪旧的文件描述符。较新版本支持--follow-name参数按文件名跟踪轮转后自动切换到新文件。用法less --follow-name F app.log。4.3 场景三在多个文件中查找关键字less可以一次打开多个文件less file1.log file2.log file3.log进入后用:n切换到下一个文件:p切换到上一个文件:e filename打开新文件。搜索时/keyword只在当前文件内搜索不会跨文件。如果你需要跨多个文件搜索那还是得用 grepgrep -rn keyword /var/log/但如果你想逐个文件精读可以先用 grep 列出有匹配的文件grep -rl keyword /var/log/然后把这些文件传给 lessless $(grep -rl keyword /var/log/)这样你就能在 less 里逐个文件查看每个文件里再用/定位。这个组合适合“我知道大概在哪些文件里但需要逐个确认上下文”的场景。4.4 场景四搜索时排除干扰项有时候关键字太常见匹配一大堆你只想看特定的。比如日志里全是INFO你只想看ERROR级别的。方法一用更精确的正则/ERROR.*NullPointer方法二用命令过滤。less有一个命令可以只显示匹配的行相当于在 less 内部做 grepERROR输入后less只显示包含 ERROR 的行其他行隐藏。此时你再搜索就只在过滤后的内容里搜。想恢复全部内容再按一次回车空模式即可。这个功能太实用了。我经常用它来“聚焦”先ERROR过滤出所有错误行然后/NullPointer在错误里找空指针层层缩小范围。方法三用-p参数指定起始位置。这个和/类似但-p是“从第一个匹配处开始显示”而不是“搜索并高亮”less -p ERROR app.log区别在于/会高亮所有匹配并跳到第一个-p只是把视图定位到第一个匹配处。日常用/更多。4.5 参数配置让 less 更顺手less的行为可以通过环境变量LESS来配置。这个变量里的参数会在每次启动 less 时自动生效。我常用的配置export LESS-i -N -R -S -M逐个解释-i搜索时忽略大小写模式全小写时-N显示行号-R正确显示颜色转义码看带颜色的日志时必备-S超长行不换行左右滚动查看看宽表格或长 JSON 时有用-M在底部显示更详细的状态信息文件名、行号、百分比这个配置我用了好几年基本覆盖了日常查日志的所有需求。特别是-R如果你看的日志带 ANSI 颜色码不加这个参数会看到一堆^[[31m之类的乱码。提示-S会让长行不换行如果你习惯看换行的内容可以去掉。我个人的取舍是查日志时-S更好因为日志行通常很长换行后反而乱。另外-N显示行号后你可以直接看到匹配项在第几行方便后续用行号g跳转。5. 常见问题与排查技巧实录5.1 搜索不到明明存在的关键字这是最高频的问题。原因通常有三个原因一方向搞反了。光标在文件中间关键字在光标上方你用/往下搜自然搜不到。解决先按g回到开头再/或者用?往上搜。原因二大小写问题。文件里是Error你搜error默认大小写敏感就搜不到。解决用less -i或进入后按-I。原因三特殊字符未转义。关键字里有.、*、[、]等正则元字符被当成正则语法解释了。解决用-F切换固定字符串模式或者手动转义。排查顺序建议先g回开头再-I忽略大小写再-F固定字符串三板斧下去基本都能搜到。5.2 搜索高亮不明显或没有高亮有些终端默认配色下less的高亮几乎看不见。解决第一确认LESS变量里没有禁用高亮的参数如-g在某些版本下行为不同。第二设置LESS_TERMCAP_so自定义高亮颜色前面讲过黑字黄底最稳。第三如果用的是 tmux 或 screen检查终端的TERM变量是否正确xterm-256color通常没问题。5.3 大文件搜索卡顿理论上less是惰性加载不应该卡。但如果你搜索的关键字在文件很靠后的位置less需要从当前位置一直读到匹配处这个过程中会扫描大量数据可能感觉卡。优化方法先用 grep 定位行号再用行号g直接跳过去避免 less 从头扫描。grep -n keyword bigfile.log | head -1 # 拿到行号后 less 行号g bigfile.log这样 less 直接跳到目标位置不需要扫描前面的内容。5.4 搜索后想回到之前的位置less支持位置标记。按m后跟一个字母比如ma就在当前位置打了个标记a。之后按a单引号加字母就能跳回标记位置。这个功能在“搜索到一半想回去看看原文”时特别有用。比如你搜到第 10 个匹配想回到第 3 个匹配的位置可以提前在第三个匹配处按m3然后继续搜想回去时按3。5.5 常见问题速查表问题现象可能原因解决方法搜不到关键字方向反了按g回开头再/或用?搜不到关键字大小写不匹配less -i或按-I搜不到关键字特殊字符被当正则按-F或转义高亮看不见终端配色问题设置LESS_TERMCAP_so大文件搜索卡从头扫描先用 grep 拿行号行号g跳转想看匹配行上下文默认只显示当前屏用n/N跳转或过滤长行显示混乱自动换行加-S参数颜色码乱码未解析 ANSI加-R参数实时跟踪断掉文件轮转用--follow-name F5.6 几个我踩过的坑坑一-i和-I的区别。我一开始以为-i就是完全忽略大小写结果发现搜Error时它又区分大小写了。后来才明白-i的规则是“模式全小写才忽略”-I才是强制忽略。这个细节文档里写得含糊实际用的时候容易懵。坑二过滤后忘记恢复。有次我ERROR过滤后后面所有搜索都只在 ERROR 行里进行找了半天没找到 WARN还以为文件里没有。后来才想起过滤没取消。养成习惯过滤用完按回车恢复。坑三F模式下搜索。在F跟踪模式下你是没法直接搜索的必须先CtrlC退出跟踪。这个我当初也困惑过以为F下能直接搜。坑四LESS变量覆盖命令行参数。如果你在LESS里设了-i命令行又加了-I最终行为取决于版本和参数顺序容易混乱。建议LESS里只放通用配置特殊需求在命令行显式指定。6. 进阶技巧把 less 用出 grep 的效率6.1 用做二次过滤前面提过过滤这里展开讲。后面跟正则只显示匹配的行。这个功能相当于在 less 内部做了一次 grep但好处是你还能继续用 less 的导航和搜索。典型流程less app.log # 先过滤出所有 ERROR ERROR # 在 ERROR 里找 NullPointer /NullPointer # 找到后按 n 继续 # 想看看这个错误前后的 WARN取消过滤 # 然后 ?WARN 往前找这个“过滤-搜索-取消过滤-再搜索”的循环是我排查复杂问题的核心手法。6.2 结合-R看带颜色的日志很多应用的日志带 ANSI 颜色码比如 Spring Boot 的彩色日志、Python 的 coloredlogs。不加-R的话你会看到一堆转义字符。加上-R后颜色正常显示ERROR 是红的WARN 是黄的一眼就能分辨。less -R app.log配合LESS变量里的-R基本不用手动加。6.3 用-S看长行不换行JSON 日志、SQL 语句、长 URL这些内容一行可能几百个字符。默认 less 会换行显示导致一行占好几屏看起来乱。加-S后长行不换行用左右箭头滚动查看。less -S app.log此时按→和←可以水平滚动。这个在看结构化日志时特别舒服。6.4 用-N显示行号配合跳转-N显示行号后你可以直接看到匹配项的行号然后# 在 less 里看到行号 12345 # 按 q 退出 less 12345g app.log或者不退出直接按:进入命令行模式输入e 12345g app.log重新打开。不过更简单的是记住行号退出后重新进。6.5 搜索历史与重复less会记住你上次的搜索模式。按/后直接回车会重复上一次搜索。按n和N也是基于上次搜索。这个在反复查找同一关键字时很方便。另外less的搜索历史可以通过s命令保存到文件下次启动还能用。不过这个属于冷门功能日常用得少。7. 我的个人配置与日常习惯说了这么多最后分享一下我自己的配置和习惯你可以直接抄。~/.bashrc里的配置export LESS-i -N -R -S -M export LESS_TERMCAP_so$\E[30;43m export LESS_TERMCAP_se$\E[0m日常查日志的流程先ls -lh看文件大小超过 100M 就谨慎用 cat用grep -n 关键字 file | tail定位最近匹配的行号用less 行号g file跳过去精读在 less 里用/、?、n、N导航需要聚焦时用过滤需要实时跟踪时用F这套流程我用了好几年基本覆盖了 90% 的日志排查场景。less这个命令看起来简单但真正用透之后效率提升是肉眼可见的。尤其是那个行号g配合 grep 的用法我推荐给团队里好几个新人他们都说比原来cat | grep的方式快多了。最后一个小心得别怕在 less 里多按几个键。新手往往不敢操作怕弄乱。其实 less 里所有操作都是只读的不会修改文件随便按按错了q退出重来就行。多用几次肌肉记忆就形成了。
返回列表