Shell通配符与正则:*?[]{} 通配,基础正则匹配(grep 入门)

Shell通配符与正则:*?[]{} 通配,基础正则匹配(grep 入门)

------ 当你的脚本需要"精准定位"文件或文本
"通配符是文件系统的模糊搜索,正则是文本世界的精确制导。搞混它们,就像用渔网捞针。"

------ 一个被误删日志文件逼出模式匹配洁癖的DBA


上个月,我们的一位同事想清理 电科金仓 KES 的旧归档日志。

他写了这样一条命令:

bash 复制代码
rm /opt/Kingbase/archives/*2023*.wal

本意是删 2023 年的日志,结果把 archive_2023_backup.wal 也删了------那是人工保留的灾备副本。

问题在哪?

他以为 *2023* 是"包含 2023 的文件",但没意识到通配符在 Shell 层展开,不理解语义,只匹配字符

更糟的是,他没用 -i 确认,也没先 ls 预览。

那一刻我意识到:不懂通配符和正则边界的运维,是在雷区跳舞

今天,我们就把这两套模式系统彻底分开讲清------什么场景用什么,怎么用才安全。


一、通配符(Globbing):Shell 的文件名匹配

通配符由 Shell 自身 在命令执行前展开,用于匹配文件路径

常见通配符:

符号 含义 示例
* 匹配任意长度字符(不含 / *.log → 所有 .log 文件
? 匹配单个字符 file?.txtfile1.txt, fileA.txt
[abc] 匹配括号内任一字符 log_[123].wallog_1.wal, log_2.wal
[a-z] 匹配范围 backup_2024[01-12].sql
{a,b,c} 大括号扩展(非通配符,但常混淆) cp file.{txt,log} /backup/

关键特性:

  • 只用于文件路径
  • 由 Shell 展开,命令本身看不到 *
  • 不支持正则语法 (如 \d, +, ()

安全实践:先 echols 预览

bash 复制代码
# 危险!直接删除
rm /opt/Kingbase/archives/*2023*.wal

# 安全!先看匹配了哪些
ls -l /opt/Kingbase/archives/*2023*.wal

# 或用 echo 查看展开结果
echo rm /opt/Kingbase/archives/*2023*.wal

二、正则表达式(Regex):文本内容的模式匹配

正则由命令内部引擎 处理(如 grepsed),用于匹配文件内容或字符串

grep 基础用法:

bash 复制代码
# 默认使用基本正则(BRE)
grep "pattern" file

# 启用扩展正则(ERE),支持 + ? | () 
grep -E "pattern" file

常见正则元字符(ERE):

模式 含义 示例
. 任意单字符 a.cabc, a2c
* 前一字符重复0次或多次 ab*cac, abbc
+ 前一字符重复1次或多次(需 -E ab+cabc, abbbc(不含 ac
? 前一字符出现0次或1次(需 -E colou?rcolor, colour
^ 行首 ^ERROR → 以 ERROR 开头的行
$ 行尾 timeout$ → 以 timeout 结尾的行
[0-9] 数字 [0-9]{4} → 四位数(需 -E
\d 不支持! Shell 正则不用 \d

⚠️ 注意:Shell 通配符的 * 和正则的 * 完全不是一回事


三、真实场景:KES 日志分析中的正确用法

场景1:找出所有 2024 年 6 月的慢查询日志文件

bash 复制代码
# 用通配符(匹配文件名)
ls /opt/Kingbase/log/kes_slowlog_202406*.log

场景2:从日志中提取执行时间 > 2000ms 的 SQL

bash 复制代码
# 用正则(匹配文件内容)
grep -E "duration: [2-9][0-9]{3,}" /opt/Kingbase/log/kes.log

解释:

  • [2-9]:首位是 2-9(确保 ≥2000)
  • [0-9]{3,}:后面至少3位数字(总长≥4)

场景3:统计各小时的错误日志量

bash 复制代码
# 提取时间戳中的小时部分(如 14:30:22 → 14)
grep "FATAL\|PANIC" /opt/Kingbase/log/kes.log \
  | grep -oE "[0-9]{2}:[0-9]{2}:[0-9]{2}" \
  | cut -d: -f1 \
  | sort \
  | uniq -c

这里:

  • grep -oE:只输出匹配部分
  • cut -d: -f1:取冒号分隔的第一段(小时)
  • 整个流程依赖正则精准提取

四、常见混淆点与避坑指南

混淆1:以为 *.log 是正则

bash 复制代码
# 错误!这是通配符,只能用于文件路径
grep "*.log" file   # 实际匹配字面量 "*." 后跟 "log"

✅ 正确写法(匹配任意 .log 结尾的行):

bash 复制代码
grep "\.log$" file      # BRE
grep -E "\.log$" file   # ERE(推荐)

混淆2:在通配符中用正则语法

bash 复制代码
# 错误!Shell 不认识 \d
ls /opt/Kingbase/archives/*\d{8}*.wal  # 不会匹配任何文件

✅ 正确写法(用 [0-9]):

bash 复制代码
ls /opt/Kingbase/archives/*[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]*.wal
# 或用 brace expansion(如果日期连续)
ls /opt/Kingbase/archives/*2024{01..12}{01..31}*.wal

混淆3:大括号 {} 是通配符?

bash 复制代码
# 这不是通配符,是 Shell 的大括号扩展
echo file{1,2,3}.txt  # 展开为 file1.txt file2.txt file3.txt

它在命令执行前由 Shell 处理,和 * 无关。


五、运维建议:安全第一

  1. 通配符操作前必预览

    bash 复制代码
    echo rm /path/to/*.wal  # 先看展开结果
  2. 正则测试用小样本

    bash 复制代码
    head -100 kes.log | grep -E "your_pattern"
  3. 区分上下文

    • 路径 → 通配符
    • 内容 → 正则
  4. 默认用 grep -E

    扩展正则更接近现代正则习惯,避免 \{n,m\} 这类繁琐转义。


结语:模式匹配是运维的"显微镜"

在管理像 电科金仓 KES 这类产生结构化日志与多实例文件的数据库系统时(技术背景参考),你每天都在和海量文本与文件打交道。

通配符帮你快速定位目标文件

正则帮你精准提取关键信息

用对工具,事半功倍;用错工具,灾难现场。

今日实践

  1. 用通配符列出 /opt/Kingbase/log/ 下所有 2024 年的日志文件
  2. grep -E 从这些文件中找出包含 "deadlock" 的行

做完这个,你就真正"看清"了数据。


注:文中涉及的 KES(Kingbase Enterprise Server)是由电科金仓开发的企业级关系型数据库,其日志与归档文件管理常需结合通配符与正则实现高效运维。技术细节可参考 产品页面

相关推荐
ulias21218 小时前
Linux系统中的权限问题
linux·运维·服务器
沃尔威武19 小时前
数据库 Sinks(.net8)
数据库·.net·webview
青花瓷19 小时前
Ubuntu下OpenClaw的安装(豆包火山API版)
运维·服务器·ubuntu
问简20 小时前
docker 镜像相关
运维·docker·容器
Dreamboat¿20 小时前
SQL 注入漏洞
数据库·sql
Dream of maid20 小时前
Linux(下)
linux·运维·服务器
齐鲁大虾20 小时前
统信系统UOS常用命令集
linux·运维·服务器
Benszen21 小时前
Docker容器化技术实战指南
运维·docker·容器
ZzzZZzzzZZZzzzz…21 小时前
Nginx 平滑升级:从 1.26.3 到 1.28.0,用户无感知
linux·运维·nginx·平滑升级·nginx1.26.3·nginx1.28.0
曹牧21 小时前
Oracle数据库中,将JSON字符串转换为多行数据
数据库·oracle·json