Shell grep
1. grep 概述
1.1 grep 是什么
在我们日常 Linux 运维过程中,最多的就是对 Linux 文件进行处理,grep(global search regular expression (RE) and print out the line)作为一款非常方便且强大的文本搜索工具,其能使用正则表达式搜索文本,并把匹配的行打印出来,其使用对象为 Linux 系统的所有用户,使得我们日常操作更加方便简单。
1.2 为什么要用 grep
在 Linux 系统中一切皆文件,我们日常的工作就是与文件打交道,能够运用 grep 这款文件搜索工具,可以大大提高我们的工作效率,我们上节课学习了正则表达式,grep 配合正则表达式能够作出 1+1 大于 2 的效果,灵活使用使得我们的工作更加高效快捷。
2. grep 详解
2.1 grep 分类
Unix 的 grep 家族包括 grep、egrep 和 fgrep。egrep 和 fgrep 的命令跟 grep 只有很小不同。
egrep 是 grep 的扩展,其支持更多 re 元字符,和扩展正则表达式等。
fgrep 就是 fixed grep 或 fast grep,它们把所有的字母都看作单词,也就是说,正则表达式中的元字符表示其自身的字面意义,不再特殊。
linux 使用 GNU 版本的 grep。它功能更强,可以通过 - G、-E、-F 命令行选项来使用 egrep 和 fgrep 的功能。
2.2 grep 工作方式
grep 的工作方式为将一个或多个文件中搜索字符串模版。如果模版包括空格,则必须被引用,模板后的所有字符串被看作文件名。搜索的结果被送到屏幕,不影响原文件内容。
grep 命令结束后通过一个状态值来说明搜索状态,如果为 0 则意味着搜索成功,反之则为失败,我们可以利用其对文件自动化处理。
2.3 grep 语法
grep [OPTION]... PATTERN [FILE]
其中 OPTION
有很多方式,例如 - A3 表示显示符合范本样式的那一行之外,并显示该行之后的 3 行内容。
PATTERN
表示:匹配的模式,通常为一个表达式。
FilE
为具体的需要处理的问题,当然也可以为标准输入。
2.3 参数详解
在上一节中我们详细讲解了正则表达式,它就可以用在 grep 命令的 PATTERN
字段中,使得 grep 更加强大,本章节我们着重来讲解 grep 命令的 OPTION
。
不加参数,匹配 /etc/passwd 文件中的 root 行,例如:
[root@master grep]# grep root /etc/passwdroot:x:::root:/root:/bin/bash operator:x:::operator:/root:/sbin/nologin
-A:显示模式匹配后的几行
查找 /etc/passwd 文件中以 root 开头的后两行,例如:
[root@master grep]# grep -A2 ^root /etc/passwdroot:x:::root:/root:/bin/bash bin:x:::bin:/bin:/sbin/nologin daemon:x:::daemon:/sbin:/sbin/nologin
-B:显示模式匹配行的前几行
查找 /etc/passwd 文件中以 bin 开头的前一行,例如:
[root@master grep]# grep -B1 ^bin /etc/passwdroot:x:::root:/root:/bin/bash bin:x:::bin:/bin:/sbin/nologin
-C:显示模式匹配的前后各几行
查找 /etc/passwd 文件中以 ftp 开头的前后各 2 行,例如:
[root@master grep]# grep -C2 ^ftp /etc/passwd operator:x:::operator:/root:/sbin/nologin games:x:::games:/usr/games:/sbin/nologin ftp:x:::FTP User:/var/ftp:/sbin/nologin nobody:x:::Nobody:/:/sbin/nologin systemd-network:x:::systemd Network Management:/:/sbin/nologin
-i:忽略大小写匹配
匹配 /etc/passwd 包含 Nobody 的行,例如:
[root@master grep]# grep -i Nobody /etc/passwdnobody:x:::Nobody:/:/sbin/nologin nfsnobody:x:::Anonymous NFS User:/var/lib/nfs:/sbin/nologin
-o :只显示匹配到的字符串
匹配出 /etc/passwd 文件中字符串长度最少 10 位的字符 ,例如:
[root@master grep]# grep -o [[:alnum:]]\{10,\} /etc/passwd Management Kubernetes
-n:输出匹配到的行的行号
匹配出 /etc/passwd 文件中包含 root 的字符串的行,例如:
[root@master grep]# grep -n root /etc/passwd:root:x:::root:/root:/bin/bash :operator:x:::operator:/root:/sbin/nologin
-v:反向选择,即显示除过 匹配’搜寻字符串’ 内容的那一行
匹配出 /etc/passwd 中不包含 bash 的行,例如:
[root@master grep]# grep -v nologin /etc/passwd root:x:::root:/root:/bin/bash sync:x:::sync:/sbin:/bin/syncshutdown:x:::shutdown:/sbin:/sbin/shutdownhalt:x:::halt:/sbin:/sbin/halt
-c : 计算找到 ‘搜寻字符串’ 的次数
计算 /etc/passwd 文件中 root 字符串出现的次数,例如:
[root@master grep]# grep -c root /etc/passwd
-E: 开启正则表达式,相当于使用命令
egrep
查找 /etc/passwd 文件中包含三位数字的行,例如:
[root@master grep]# grep -E [[:digit:]]{3} /etc/passwdgames:x:::games:/usr/games:/sbin/nologin systemd-network:x:::systemd Network Management:/:/sbin/nologin polkitd:x:::User for polkitd:/:/sbin/nologin ceph:x:::Ceph daemons:/var/lib/ceph:/sbin/nologin kube:x:::Kubernetes user:/home/kube:/sbin/nologin etcd:x:::Etcd user:/var/lib/etcd:/bin/nologin gluster:x:::GlusterFS daemons:/run/gluster:/sbin/nologin nfsnobody:x:::Anonymous NFS User:/var/lib/nfs:/sbin/nologin chrony:x::::/var/lib/chrony:/sbin/nologin redis:x:::Redis Database Server:/var/lib/redis:/sbin/nologin
3. 实例
3.1 需求
编写一个脚本,获取 Linux 系统的服务信息,将结果保存到文件中。
3.2 思路
可以利用函数来编写获取 Linux 服务相关信息,最后利用重定向将信息输出到文件中。
3.3 实现
#!/bin/bash# Description: service check# Auth: kaliarch# Email: kaliarch@163.com# function: sys check# Date: 2020-04-11 14:00# Version: 1.0[ $(id -u) -gt ] && echo 请用root用户执行此脚本! && exit sysversion=$(rpm -q centos-release|cut -- -)line=-------------------------------------------------[ - logs ] || mkdir logs service_check_file=logs/service-`date +%Y%m%d`.txt# 获取服务信息function get_service_info() { port_listen=$(netstat -lntup|grep -v Active Internet)kernel_config=$(sysctl -p >/dev/null)if [ ${sysversion} -gt ];thenservice_config=$(systemctl list-unit-files --type=service --state=enabled|grep enabled)run_service=$(systemctl list-units --type=service --state=running |grep .service)elseservice_config=$(/sbin/chkconfig | grep -E :on|:启用 |column -t)run_service=$(/sbin/service --status-all|grep -E running)fi cat <<EOF 服务启动配置: ${service_config} ${line} 运行的服务: ${run_service} ${line} 监听端口: ${port_listen} ${line} 内核参考配置: ${kernel_config} EOF }function sys_check() { get_service_info echo ${line} }# 执行主函数将输出重定向到文件中sys_check > ${sys_check_file}# 执行测试[root@xuel-terraform-cvm ~]# bash sys_check.sh[root@xuel-terraform-cvm ~]# cat logs/10.0.1.15-20200329.txt[root@master grep]# cat logs/service-20200411.txt 服务启动配置: auditd.service enabled autovt@.service enabled ceph-mon@.service enabled ceph-osd@.service enabled chronyd.service enabled crond.service enabled dbus-org.freedesktop.NetworkManager.service enabled dbus-org.freedesktop.nm-dispatcher.service enabled docker.service enabled etcd.service enabled gapd.service enabled getty@.service enabled irqbalance.service enabled kdump.service enabled kubelet.service enabled microcode.service enabled NetworkManager-dispatcher.service enabled NetworkManager.service enabled postfix.service enabled rpcbind.service enabled rsyslog.service enabled smarteye-server-agent.service enabled sshd.service enabled systemd-readahead-collect.service enabled systemd-readahead-drop.service enabled systemd-readahead-replay.service enabled tuned.service enabled-------------------------------------------------运行的服务: auditd.service loaded active running Security Auditing Service ceph-mon@master.service loaded active running Ceph cluster monitor daemon ceph-osd@0.service loaded active running Ceph object storage daemon chronyd.service loaded active running NTP client/server crond.service loaded active running Command Scheduler dbus.service loaded active running D-Bus System Message Bus docker.service loaded active running Docker Application Container Engineetcd.service loaded active running etcd docker wrapper gapd.service loaded active running guest agent for pitrix getty@tty1.service loaded active running Getty on tty1 gssproxy.service loaded active running GSSAPI Proxy Daemon irqbalance.service loaded active running irqbalance daemon kubelet.service loaded active running Kubernetes Kubelet Server NetworkManager.service loaded active running Network Manager polkit.service loaded active running Authorization Manager postfix.service loaded active running Postfix Mail Transport Agent rpcbind.service loaded active running RPC bind service rsyslog.service loaded active running System Logging Service smarteye-server-agent.service loaded active running The Smarteye Monitoring of server sshd.service loaded active running OpenSSH server daemon systemd-journald.service loaded active running Journal Service systemd-logind.service loaded active running Login Service systemd-udevd.service loaded active running udev Kernel Device Manager tuned.service loaded active running Dynamic System Tuning Daemon-------------------------------------------------监听端口: Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name tcp .: .:* LISTEN /calico-node tcp .: .:* LISTEN /etcd tcp6 ::: :::* LISTEN /node-cache udp .: .:* /dhclient udp .: .:* /node-cache udp .: .:* /dhclient udp .: .:* /systemd udp .: .:* /chronyd udp .: .:* /chronyd udp .: .:* /rpcbind udp6 ::: :::* /dhclient udp6 ::: :::* /systemd udp6 ::: :::* /chronyd udp6 ::: :::* /rpcbind -------------------------------------------------内核参考配置: net.ipv4.ip_forward = net.bridge.bridge-nf-call-ip6tables = net.bridge.bridge-nf-call-iptables = net.ipv4.ip_local_reserved_ports = -net.bridge.bridge-nf-call-arptables = -------------------------------------------------
可以看到利用了一个函数来获取系统的信息,主函数将输出利用重定向方式保存到文件中。
4. 注意事项
grep 对于文件搜索效率非常高,其不会对源文件作出修改;
默认 Linux 系统 grep 可以使用参数 - E,-F 来使用 egrep/fgrep;
对于复杂的条件可以利用 grep 配合管道多匹配来达到目的。
5. 小结
grep 命令是 Linux 系统非常强大的文本搜索工具,可以配合正则表达式及其丰富的选项来灵活处理,同时对于复杂的文件搜索,可以配合管道多次匹配来达到搜索的目的,特殊情况下可以利用选项 - E,开启正则表达式来提供强大的模式匹配处理。