second work

目录

一、实现并总结容器跨主机的通信过程

二、总结Dockerfile的常见指令

三、基于Dockerfile Nginx镜像并验证可以启动为容器

四、部署单机harbor并实现镜像的上传与下载

五、基于systemd实现容器的CPU及内存的使用限制

六、总结镜像的分层构建流程

七、总结基于lxcfs对容器的内存及CPU的资源限制

八、linux的安全模型

九、linux文件的权限属性,acl访问控制

十、vim几个常见操作

十一、总结学过的文本处理工具,文件查找工具,文本处理三剑客, 文本格式化命令(printf)的相关命令及选项,示例

十二、总结文本处理的grep命令相关的基本正则和扩展正则表达式

十三、 结合编程的for循环,条件测试,条件组合,完成批量创建100个用户,1)for遍历1..1002)先id判断是否存在3)用户存在则说明存在,用户不存在则添加用户并说明已添加。


一、实现并总结容器跨主机的通信过程

docker bridge网络模式 跨主机通信原理:

1、源容器产生请求报文发给网关docker0

2、docker0检查报文的目的ip,如果是本机就直接转发,如果不是本机就转发给宿主机

3、源宿主机收到报文后检查路由表,将源地址替换为本机ip并发送报文

4、目的宿主机收到请求报文,检查目的ip后将报文发给docker0

5、docker0检查目的ip后匹配MAC地址表,将报文发送给,目的MAC的容器

容器跨主机通信案例实现:

1、修改server1和server2的docker默认地址段

server1:

root@ubuntu2204:~# vim /lib/systemd/system/docker.service

ExecStart=/usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock --bip=10.100.10.1/24

root@ubuntu2204:~# systemctl daemon-reload

root@ubuntu2204:~# systemctl restart docker

root@ubuntu2204:~# ifconfig docker0 | grep -Eo "[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}"|head -1

10.100.10.1

修改成功

server2:

root@ubuntu2004:~# vim /lib/systemd/system/docker.service

ExecStart=/usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock --bip=10.200.10.1/24

root@ubuntu2004:~# systemctl daemon-reload

root@ubuntu2004:~# systemctl restart docker

root@ubuntu2004:~# ifconfig docker0 | grep -Eo "[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}"|head -1

10.200.10.1

修改成功

2、server1,server2添加路由

server1 IP地址:10.0.0.152

server2 IP地址:10.0.0.151

server1添加路由:将去往server2的容器的网关docker0,指向server2的eth0网卡

root@ubuntu2204:~# route add -net 10.200.10.0/24 gw 10.0.0.151

root@ubuntu2204:~# iptables -A FORWARD -s 10.0.0.0/24 -j ACCEPT #宿主机添加信任ip段

server2添加路由:将去往server1的容器的网关docker0,指向server1的eth0网卡

root@ubuntu2004:~# route add -net 10.100.10.0/24 gw 10.0.0.152

root@ubuntu2004:~# iptables -A FORWARD -s 10.0.0.0/24 -j ACCEPT #宿主机添加信任ip段

二、总结Dockerfile的常见指令

1、FROM:

整个文件除了注释的第一行,作用于指定当前镜像的父镜像

2、LABEL:

作用:设置镜像的属性标签

"key" = "value"

LABEL author="wang,wang@123.com"

LABEL version="1.1"

3、ADD

命令模式:

ADD [--chown=:] ...

作用:用于添加宿主机的本地的文件、目录,压缩文件资源到镜像里面去,会自动解压tar.gz格式的压缩包,但是不会自动解压zip文件

ADD --chown wang:wang test /opt/test #将宿主机的test目录拷贝到容器里并设置属主属组。

也可直接使用 ADD test /opt/test

4、COPY

命令模式:

COPY [--chown=:] ...

作用:用于添加宿主机的本地的文件、目录,压缩文件资源到镜像里面去,但是不会自动解压文件

COPY --chown wang:wang test /opt/test #将宿主机的test目录拷贝到容器里并设置属主属组。

也可直接使用 COPY test /opt/test

5、ENV

命令模式:

ENV MY_NAME="John Doe"

作用:

设置容器环境变量

6、USER

命令模式:

USER [:] or USER [:

作用:

指定运行操作的用户

7、RUN

命令模式:RUN yum install vim unzip -y && cd /etc/nginx

作用:

执行shell命令,但是一定要以非交互式的方式执行

8、VOLUME

命令模式:

VOLUME ["/data/data1","/data/data2"]

作用:

定义volume

9、EXPOSE

命令模式:

EXPOSE [/...]

作用:

声明要把容器的某些端口映射到宿主机

EXPOSE 80 443

10、CMD

CMD有以下三种方式定义容器启动时所默认执行的命令或脚本

CMD ["executable","param1","param2"] #推荐的可执行程序方式

CMD ["param1","param2"] #作为ENTRYPOINT默认参数

CMD command param1 param2 #基于shell命令的

如:基于CMD #镜像启动为一个容器时候的默认命令或脚本:CMD ["/bin/bash"]

11、ENTRYPOINT

ENTRYPOINT #也可以用于定义容器在启动时候默认执行的命令或者脚本,如果是和CMD命令混合使用的时候,会将CMD的命令当做参数传递给

ENTRYPOINT后面的脚本,可以在脚本中对参数做判断并相应的容器初始化操作。

案例1:

ENTRYPOINT ["top","-b"]

CMD ["-c"]

等价于:

ENTRYPOINT ["top","-b","-c"]

案例2:

ENTRYPOINT ["docker-entrypoint.sh"] #定义一个入口点脚本,并传递mysqld 参数

CMD ["mysqld"]

等价于:

ENTRYPOINT ["docker-entrypoint.sh","mysqld"]

三、基于Dockerfile Nginx镜像并验证可以启动为容器

1、在宿主机上创建Dockerfile的所在文件夹

mkdir -p /opt/build-nginx-iamges && cd /opt/build-nginx-iamges

2、创建 vim Dockerfile

FROM centos:7.9.2009

LABEL author="wang,wang@123.com"

RUN ln -snf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime

RUN yum install -y vim net-tools wget tree lrzsz gcc gcc-c++ automake pcre pcre-devel zlib zlib-devel openssl openssl-devel iproute net-tools iotop

RUN useradd -M -s /sbin/nologin nginx

ADD nginx-1.24.0.tar.gz /usr/local/src/

RUN cd /usr/local/src/nginx-1.24.0 && ./configure --prefix=/opt/nginx && make && make install && rm -rf /usr/local/src/nginx-1.24.0

ADD nginx.conf /opt/nginx/conf

ADD index.html /opt/nginx/html

RUN chown -R nginx:nginx /opt/nginx

#USER nginx

EXPOSE 80 443

CMD ["/opt/nginx/sbin/nginx"]

3、创建镜像创建脚本 vi build-nginx-image.sh

#/bin/bash

TAG=$1

docker build -t harbor.wang.com/centos-nginx:${TAG} .

4、执行build-nginx-image.sh 创建镜像

root@ubuntu2204:/opt/build-nginx-iamges# docker images

REPOSITORY TAG IMAGE ID CREATED SIZE

harbor.wang.com/centos-nginx v1 0b6d163e2bf7 16 minutes ago 604MB

测试:

root@ubuntu2204:/opt/build-nginx-iamges# docker run -it -d -p 80:80 harbor.wang.com/centos-nginx:v1

7e8bb50dea692eac4a9adf832701e3311488c1b7b0fa5d8fe80df3a952923557

四、部署单机harbor并实现镜像的上传与下载

1、在harborserver挂载数据盘:

fdisk /dev/sdb #分区

mkfs.xfs /dev/sdb1 #格式化

mkdir -p /data/harbordata && mount /dev/sdb1 /data/harbordata #挂载数据盘

在文件/etc/fstab 添加/dev/sdb1 /data/harbordata xfs defaults 0 0 设置开机自动挂载

2.安装docker和docker-compose

请参照:docker-ce镜像_docker-ce下载地址_docker-ce安装教程-阿里巴巴开源镜像站

3、安装harbor

解压二进制安装包

tar xvf harbor-offline-installer-v2.8.2.tgz

进入安装目录

cd harbor/

拷贝配置文件

cp harbor.yml.tmpl harbor.yml

编辑配置文件vim harbor.yml做如下修改:

注释点https段

hostname: harbor.wang.com

harbor_admin_password: 123456

data_volume: /data/harbordata

安装harbor:

./install.sh --with-trivy

4、登录harbor网页界面

新建项目:

5、在镜像制作服务器器中上传镜像

绑定host: 10.0.0.153 harbor.wang.com

编辑/etc/docker/daemon.json 文件,添加"insecure-registry": ["harbor.magedu.com"]

重启docker

systemctl daemon-reload

systemctl restart docker

登录harbor服务器:

docker login harbor.wang.com

修改镜像名称:

docker tag harbor.wang.com/centos-nginx:v1 harbor.wang.com/test/centos-nginx:v1

上传镜像:

docker push harbor.wang.com/test/centos-nginx:v1

拉取镜像

docker pull harbor.wang.com/test/centos-nginx:v1

五、基于systemd实现容器的CPU及内存的使用限制

对于Linux 主机,如果没有足够的内容来执行其他重要的系统任务,将会抛出 OOM (Out of Memory Exception,内存溢出、内存泄漏、内存异常), 随后系统会开始杀死进程以释放内存,凡是运行在宿主机的进程都有可能被 kill,包括Dockerd和其它的应用程序,如果重要的系统进程被Kill,会导致和该进程相关的服务全部宕机。

1、OOM机制的优先级:

linux会给每一个进程进行评分,当发生OOM时他会将评分最高的进程kill掉

/proc/PID/oom_score_adj #范围为-1000到1000,值越高越容易被宿主机kill掉,如果将该值设置为-1000,则进程永远不会被宿主机kernel kill。

/proc/PID/oom_adj #范围为-17到+15,取值越高越容易被干掉,如果是-17,则表示不能被kill,该设置参数的存在是为了和旧版本的Linux内核兼容。

/proc/PID/oom_score #这个值是系统综合进程的内存消耗量、CPU时间(utime + stime)、存活时间(uptime - start time)和oom_adj计算出的进程得分,消耗内存越多得分越高,越容易被宿主机kernel强制杀死。

2、docker容器的资源限制

默认情况下,容器没有资源限制,可以使用主机内核调度程序允许的尽可能多的给定资源,Docker提供了控制容器可以限制容器使用多少内存或CPU的方法,运行docker run命令创建容器的时候可以进行资源限制。

Docker早期使用cgroupfs进行容器的资源限制管理,然后再调用内核的cgroup进行资源限制,而kubernetes后来使用systemd直接调用cgroup对进程实现资源限制,等于绕过了docker的cgroupfs的管理,对资源限制更严格、性能更好,因此在kubernetes环境推荐使用systemd进行资源限制。

配置方法:

daemon.jsonz文件中添加:

"exec-opts": ["native.cgroupdriver=systemd"],

"exec-opts": ["native.cgroupdriver=cgroupfs"]

其中许多功能都要求宿主机的内核支持Linux功能,要检查支持,可以使用docker info命令,如果内核中禁用了某项功能,可能会在输出结尾处看到警告,如下所示:

WARNING: No swap limit support

解决办法:

修改 vim /etc/default/grub

GRUB_CMDLINE_LINUX="net.ifnames=0 biosdevname=0 cgroup_enable=memory swapaccount=1"

然后

sudo update-grub

reboot

(1)内存限制参数:

-m or --memory #限制容器可以使用的最大内存量,如果设置此选项,最小存值为4m(4兆字节)

--memory-swap #容器可以使用的交换分区大小,必须要在设置了物理内存限制的前提才能设置交换分区的限制

--memory-swappiness #设置容器使用交换分区的倾向性,值越高表示越倾向于使用swap分区,范围为0-100,0为能不用就不用,100为能用就用

--kernel-memory #容器可以使用的最大内核内存量,最小为4m,由于内核内存与用户空间内存隔离,因此无法与用户空间内存直接交换,因此内核内存不足的容器可能会阻塞宿主主机资源,这会对主机和其他容器或者其他服务进程产生影响,因此不要设置内核内存大小

--memory-reservation #允许指定小于--memory的软限制,当Docker检测到主机上的争用或内存不足时会激活该限制,如果使用-- memory-reservation,则必须将其设置为低于--memory才能使其优先。 因为它是软限制,所以不能保证容器不超过限制

--oom-kill-disable #默认情况下,发生OOM时,kernel会杀死容器内进程,但是可以使用--oom-kill-disable参数,可以禁止oom发生在指定的容器上,即 仅在已设置-m / --memory选项的容器上禁用OOM,如果-m 参数未配置,产生OOM时,主机为了释放内存还会杀死系统进程

docker run -it -d -p 81:80 -m 512m harbor.wang.com/test/centos-nginx:v1 #设置容器使用最大内存512m

(2)交换分区参数:

--memory-swap #只有在设置了 --memory 后才会有意义。使用Swap,可以让容器将超出限制部分的内存置换到磁盘上,WARNING:经常将内存交换到磁盘的应用程序会降低性能

--memory-swap #值为正数, 那么--memory和--memory-swap都必须要设置,--memory-swap表示你能使用的内存和swap分区大小的总和,例如: --memory=300m, --memory-swap=1g, 那么该容器能够使用 300m 内存和 700m swap,即--memory是实际物理内存大小值不变,而swap的实际大小计算方式为(--memory-swap)-(--memory)=容器可用swap

--memory-swap #如果设置为0,则忽略该设置,并将该值视为未设置,即未设置交换分区

--memory-swap #如果等于--memory-swap的值,并且--memory设置为正整数,容器无权访问swap即也没有设置交换分区

--memory-swap #如果设置为unset,如果宿主机开启了swap,则实际容器的swap值为2x( --memory),即两倍于物理内存大小,但是并不准确(在容器中使用free命令所看到的swap空间并不精确,毕竟每个容器都可以看到具体大小,但是宿主机的swap是有上限而且不是所有容器看到的累计大小)

--memory-swap #如果设置为-1,如果宿主机开启了swap,则容器可以使用主机上swap的最大空间

(3)cpu的资源限制:

同过--cpus 来设置

docker run -it --rm -p 80:80 --cpu 1.5 centos-nginx:v1 #给容器设置了最大只能使用1.5cpu。就是150%

注意:CPU资源限制是将分配给容器的1.5核心分配到了宿主机每一核心CPU上,也就是容器的总CPU值是在宿主机的每一个核心CPU分配了部分比例.

docker run -it --rm -p 80:80 --cpus 2 --cpuset-cpus 1,3 centos-nginx:v1 #给容器设置了最大能使用200%的cpu,并且只能运行在cpu1,和cpu3上

3、容器资源限制配置在宿主机的文件位置:

(1)cgroup限制的

docker run -it --rm --name test -m 128m --cpus 1.5 lorel/docker-stress-ng --vm 2

cat /sys/fs/cgroup/cpu,cpuacct/docker/d1e8a194178289d7fcd1bb59c9d245db1731d88cb3139c5c69cd7eb2c2271772/cpu.cfs_quota_us

150000

echo 200000 >/sys/fs/cgroup/cpu,cpuacct/docker/d1e8a194178289d7fcd1bb59c9d245db1731d88cb3139c5c69cd7eb2c2271772/cpu.cfs_quota_us #容器运行的时候也可以通过这种方式来修改

(2)systemd限制的

找出nginx的进程号

root@ubuntu2204:~# ps -ef | grep nginx

root 3357 3337 0 08:46 pts/0 00:00:00 nginx: master process /opt/nginx/sbin/nginx

wang 3380 3357 0 08:46 pts/0 00:00:00 nginx: worker process

root 3387 1516 0 08:52 pts/0 00:00:00 grep --color=auto nginx

root@ubuntu2204:~# cat /proc/3357/cpuset

/system.slice/docker-b161acfdc16aefa9acf3a572065159ed04b4e3416db9b179a3ebea58491fe65e.scope

root@ubuntu2204:~# cat /sys/fs/cgroup/system.slice/docker-b161acfdc16aefa9acf3a572065159ed04b4e3416db9b179a3ebea58491fe65e.scope/cpu.max

150000 100000

同样可以通过修改这些文件来修改运行中容器的资源限制

六、总结镜像的分层构建流程

镜像的分成构建:

可以大致划分成:

基础层:系统基础镜像

环境成:运行环境镜像

业务层:业务或服务运行镜像

1、基础成构建:

vim Dockerfile

FROM centos:7.9.2009
LABEL author="wang,wang@123.com"
RUN ln -snf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
RUN yum install -y vim net-tools wget tree  lrzsz gcc gcc-c++ automake pcre pcre-devel zlib zlib-devel openssl openssl-devel iproute net-tools iotop

vim build-centos-base-image.sh
#/bin/bash
TAG=$1
docker build -t harbor.wang.com/centos-base:${TAG} .

这一层主要是对操作系统进行简单的配置

2、环境层构建

vim Dockerfile

FROM harbor.wang.com/centos-base:v1

LABEL author="wang,wang@123.com"

RUN useradd -M -s /sbin/nologin nginx
ADD nginx-1.24.0.tar.gz /usr/local/src/
RUN cd /usr/local/src/nginx-1.24.0 && ./configure --prefix=/opt/nginx && make && make install && rm -rf /usr/local/src/nginx-1.24.0

vim build-centos-nginx-image.sh
#/bin/bash
TAG=$1
docker build -t harbor.wang.com/centos-nginx:${TAG} .

这一层主要是在系统基础层的基础上配置业务的运行环境

3、业务层构建

vim Dockerfile

FROM harbor.wang.com/centos-nginx:v1

LABEL author="wang,wang@123.com"

ADD nginx.conf /opt/nginx/conf
ADD index.html /opt/nginx/html
RUN chown -R nginx:nginx /opt/nginx
EXPOSE 80 443
CMD ["/opt/nginx/sbin/nginx"]

vim build-centos-nginx-web-image.sh
#/bin/bash
TAG=$1
docker build -t harbor.wang.com/centos-nginx-web:${TAG} .

这一层主要就是运行业务了。

七、总结基于lxcfs对容器的内存及CPU的资源限制

容器内⾥⾯是从/proc/cpuinfo中获取到 CPU 的核数,但是容器⾥⾯的/proc⽂件系统是物理机的,内存也是显示的宿主机的/proc/meminfo的信息,因此不准确,⽽lxcfs 则是通过⽂件挂载的⽅式,把 宿主机cgroup 中关于系统的相关信息读取出来,通过 docker 的 volume 挂载给容器内部的 proc 系统,然后让 docker 内的应⽤读取proc 中信息的时候以为就是读取的宿主机的真实的 proc

1、安装lxcfs: #对容器实现更加准确的限制,内存、⽹络、磁盘IO、读写速率、磁盘空间⼤⼩等

apt install lxcfs

2、修改docker的数据目录

vim /etc/docker/daemon.json

"data-root": "/data/docker"

3、挂载数据盘

mount /dev/sdb /data/docker/

设置开机自动挂载vim /etc/fstab

/dev/sdb /data/docker xfs defaults,prjquota 0 0

reboot

进入容器:

#限制内存大小

root@ubuntu2204:~# docker run -it -m 512m \

-v /var/lib/lxcfs/proc/cpuinfo:/proc/cpuinfo:rw \

-v /var/lib/lxcfs/proc/diskstats:/proc/diskstats:rw \

-v /var/lib/lxcfs/proc/meminfo:/proc/meminfo:rw \

-v /var/lib/lxcfs/proc/stat:/proc/stat:rw \

-v /var/lib/lxcfs/proc/swaps:/proc/swaps:rw \

-v /var/lib/lxcfs/proc/uptime:/proc/uptime:rw \

harbor.wang.com/test/centos-nginx:v1 /bin/bash

[root@06af55725c81 /]# cat /proc/m

mdstat meminfo misc modules mounts mpt/ mtrr

[root@06af55725c81 /]# cat /proc/meminfo

MemTotal: 524288 kB

MemFree: 522804 kB

限制cpu:

root@ubuntu2204:~# docker run -it --cpus 1 \

-v /var/lib/lxcfs/proc/cpuinfo:/proc/cpuinfo:rw \

-v /var/lib/lxcfs/proc/diskstats:/proc/diskstats:rw \

-v /var/lib/lxcfs/proc/meminfo:/proc/meminfo:rw \

-v /var/lib/lxcfs/proc/stat:/proc/stat:rw \

-v /var/lib/lxcfs/proc/swaps:/proc/swaps:rw \

-v /var/lib/lxcfs/proc/uptime:/proc/uptime:rw \

harbor.wang.com/test/centos-nginx:v1 /bin/bash

限制磁盘IO:

root@ubuntu2204:~# docker run -it --device-read-iops /dev/sdb:10 --device-write-iops /dev/sdb:10 \

-v /var/lib/lxcfs/proc/cpuinfo:/proc/cpuinfo:rw \

-v /var/lib/lxcfs/proc/diskstats:/proc/diskstats:rw \

-v /var/lib/lxcfs/proc/meminfo:/proc/meminfo:rw \

-v /var/lib/lxcfs/proc/stat:/proc/stat:rw \

-v /var/lib/lxcfs/proc/swaps:/proc/swaps:rw \

-v /var/lib/lxcfs/proc/uptime:/proc/uptime:rw \

harbor.wang.com/test/centos-nginx:v1 /bin/bash

限制磁盘速率:

root@ubuntu2204:~# docker run -it --device-read-bps /dev/sdb:10MB --device-write-bps /dev/sdb:10MB \

-v /var/lib/lxcfs/proc/cpuinfo:/proc/cpuinfo:rw \

-v /var/lib/lxcfs/proc/diskstats:/proc/diskstats:rw \

-v /var/lib/lxcfs/proc/meminfo:/proc/meminfo:rw \

-v /var/lib/lxcfs/proc/stat:/proc/stat:rw \

-v /var/lib/lxcfs/proc/swaps:/proc/swaps:rw \

-v /var/lib/lxcfs/proc/uptime:/proc/uptime:rw \

harbor.wang.com/test/centos-nginx:v1 /bin/bash

限制磁盘大小:

root@ubuntu2204:~# docker run -it --storage-opt size=10G \

-v /var/lib/lxcfs/proc/cpuinfo:/proc/cpuinfo:rw \

-v /var/lib/lxcfs/proc/diskstats:/proc/diskstats:rw \

-v /var/lib/lxcfs/proc/meminfo:/proc/meminfo:rw \

-v /var/lib/lxcfs/proc/stat:/proc/stat:rw \

-v /var/lib/lxcfs/proc/swaps:/proc/swaps:rw \

-v /var/lib/lxcfs/proc/uptime:/proc/uptime:rw \

harbor.wang.com/test/centos-nginx:v1 /bin/bash

[root@d74cce5b17c4 /]# df -h

Filesystem Size Used Avail Use% Mounted on

overlay 10G 8.0K 10G 1% /

tmpfs 64M 0 64M 0% /dev

八、linux的安全模型

linux的安全模型主要包括:

1、访问控制:linux系统中采用了DAC和MAC等多种访问控制策略,如基于用户和用户组的访问控制,基于文件系统权限的访问控制,selinux的强制访问控制等等,以限制用户对系统资源的访问和操作权限

2、身份验证和授权:linux系统中采用了多种身份验证和授权机制,如密码验证,秘钥验证等等,以确保用户和程序只能访问其授权的资源

3、安全审计:linux系统中有有强大的安全审计工具,记录了用户和程序的操作行为,以便分析和调查

4、加密和安全通信:linux支持多种加密方式和安全通信协议,如ssh ssl/tls ipsec等,以确保网络数据的机密性,完整性,可用性

5、漏洞管理和修补

资源分配:

Authentication:认证,验证用户身份

Authorzation: 授权,不同的用户设置不同的权限

Accouting|Autition:审计

当系统登录时,系统会自动分配一个令牌token,包括用户标识和组成员等信息

九、linux文件的权限属性,acl访问控制

r 100 4 读权限

w 010 2 写权限

x 001 1 执行权限

文件夹的读权限是:能够看到目录里面的文件列表

文件夹的写权限是:能够删除或者新建文件在目录里面

文件夹的执行权限是:能够进入目录

一个文件能不删除,看他所在目录的权限,账号是否有w权限

1、文件及目录权限修改:

chmod -R a+X /data #X 是对data目录下的文件夹添加执行权限

chmod u+x test.txt #增加执行权限

chmod u+w test.txt #增加写权限

chmod u+r test.txt #增加读权限

chmod u-x test.txt #去掉执行权限

chmod u-w test.txt #去掉写权限

chmod u-r test.txt #去掉读权限

ps:权限增加减少对象可以是:u:所属主,g:所属组,o:其他人,a:所有人

chmod 755 test.txt # 7表示4+2+1,所属主添加rwx权限;5表示4+1,所属组和附加组添加rx权限

2、umask

新建的文件夹默认权限是755

新建文件的默认权限是644

[root@Rocky9 ~]# umask #第一个0是八进制,主要看后面三个数字

0022

root默认umask是022

文件默认权限:666-umask #结果为奇数的就奇数加1;偶数不变

文件夹默认权限:777-umask

umask 123 #修改umask值为123

永久修改umask值:在用户自己的家目录里面有个.bashrc文件。在里面添加既可以

(umask 777;touch 3.txt) #临时创建权限为000的3.txt文件;不影响其他文件的默认权限,只针对3.txt

3、suid,sgid,sticky特殊权限

suid:

[root@Rocky9 ~]# ll $(which passwd)

-rwsr-xr-x. 1 root root 32656 May 15 2022 /usr/bin/passwd

rws里面的s是suid权限。suid的功能是:

作用于二进制可执行程序文件上,用户执行此程序时将继承此程序所有者权限

chmod 4755 /bin/cat #4就是suid的数字权限

chmod u+s /bin/cat

sgid:

root@ubuntu2004:~# chmod g+s /bin/cat #添加sigd权限

root@ubuntu2004:~# ll /bin/cat

-rwxr-sr-x 1 root root 43416 Sep 5 2019 /bin/cat*

r-s里面的s就是sgid;sgid的功能是:

作用于二进制可执行程序文件上,用户执行此程序是将继承此程序所有组权限

作用于目录上,此目录中新建文件的所属组将继承此目录的所属组

chmod 2755 /bin/cat #2就是sgid的数字权限号

sticky:

[root@Rocky9 ~]# ll -d /tmp/

drwxrwxrwt. 9 root root 4096 Jun 23 12:52 /tmp/

#rwt中的t就是sticky特殊权限

sticky粘滞位,作用于目录上,此目录中的文件只能有所有者来删除(root例外)

chmod o+t /tmp

chmod 1777 /tmp #1就是sticky权限

chmod 7777 /data #第一个7表示,suid,sgid,sticky特殊权限都有了

4、chattr命令

chattr +i a.txt #这个文件将不能被删除,不能被修改。包括root在内

chattr -i a.txt #这个文件将能被删除,能被修改了

chattr +a a.txt #只能追加内容,其他不能

lsattr a.txt #查看这个文件有哪些这些权限

[root@localhost data]# lsattr test.txt

----i---------e----- test.txt

5、acl访问控制

实现指定用户对指定目录或文件有指定权限

setfacl -m u:wang:rw 1.txt # 实现wang用户对1.txt的读写权限。-m是添加权限;u是所有者;rw是添加的权限,rw为0时,时什么权限都不加

[root@Rocky9 ~]# ll 1.txt

-rw-rw-r--+ 1 root root 8 Jun 21 15:01 1.txt #多了一个+号

[root@Rocky9 ~]# getfacl 1.txt #查看1.txt是不是有acl权限

#file: 1.txt

#owner: root

#group: root

user::rw-

user:wang:rw-

group::r--

mask::rw-

other::r--

setfacl -b 1.txt #删除acl权限;-b是删除所有策略,

setfacl -x u:wang 1.txt #删除某个用户的权限

总结:

1、getfacl [选项] 1.txt

#查看文件的acl策略

2、setfacl -m u:wang:rw 1.txt

#给予wang用户对1.txt文件的rw权限

3、setfacl -m g:liu:r 1.txt

#给予liu组对1.txt文件的r权限

4、setfacl -R -m g:liu:rwx /usr/local/nginx/

#递归级联给予liu组对nginx目录的rwx权限

5、setfacl -x u:wang 1.txt

#删除wang用户对1.txt文件的rw权限

6、setfacl -x g:liu 1.txt

#删除liu组对1.txt文件的权限

7、setfacl -b 1.txt

#全部删除1.txt文件的acl策略

十、vim几个常见操作

1、打开文件

vim 文件名

2、命令模式下退出vim

命令模式下输入:q!(不保存修改退出),输入:wq (保存修改退出)

3、打开文件(命令模式)之后,进入插入模式。并在插入模式中如何回到打开文件的状态(命令模式),并在命令模式之后如何退出文件。

打开文件(命令模式)之后,进入插入模式:

输入以下都可以

i 在光标所在处输入

I 在光标所在行的行首输入

a 在光标所在处后面输入

A 在光标所在行的行尾输入

o 在光标所在行的下方打开一个新行输入

O在光标所在行的上方打开一个新行输入

并在插入模式中如何回到打开文件的状态(命令模式):

按esc键

并在命令模式之后如何退出文件:

输入:q!(不保存修改退出),输入:wq (保存修改退出)

4、打开文件(命令模式)之后,进入插入模式,编写一段话,"马哥出品,必属精品", 之后从插入模式中如何回到打开文件的状态(命令模式),并在命令模式之后如何退出文件。

使用cat命令验证文件内容,是刚刚自己写的内容

[root@localhost data]# cat q
马哥出品,必属精品
 

 命令模式下,光标在单词,句子上进行前后,上下跳转。行复制粘贴。行删除。

w 下一个单词的词首

e 当前或下一个单词的词尾

b当前或前一个单词的词首

)下一句

(  上一句

$跳到行尾

0跳到行首

^ 跳到行首第一个字符非空

十一、总结学过的文本处理工具,文件查找工具,文本处理三剑客, 文本格式化命令(printf)的相关命令及选项,示例

1、cat 查看文本内容

格式:

cat [参数]..[file]...

常见选项:

-E 显示行结束符$

-A 显示所有控制符

-n 对显示出的每一行进行编号

-b 非空行进行编号

-s 压缩连续的空行成一行

[root@localhost data]# cat ee

dadasa

sdadadsad

dsada

[root@localhost data]# cat -E ee

dadasa$

$

$

$

$

sdadadsad$

$

$

$

dsada$

$

[root@localhost data]# cat -A ee

dadasa$

$

$

$

$

sdadadsad$

$

$

$

dsada$

$

[root@localhost data]# cat -n ee

1 dadasa

2

3

4

5

6 sdadadsad

7

8

9

10 dsada

11

[root@localhost data]# cat -b ee

1 dadasa

2 sdadadsad

3 dsada

[root@localhost data]# cat -s ee

dadasa

sdadadsad

dsada

2、tac 逆向显示文本内容

[root@localhost data]# cat ee

1

2

3

[root@localhost data]# tac ee

3

2

1

3、rev 将同一行逆向显示

[root@localhost data]# cat ee

123

[root@localhost data]# rev ee

321

4、hexdump 查看二进制

[root@localhost data]# hexdump -C -n 512 /dev/nvme0n1p1

00000000 58 46 53 42 00 00 10 00 00 00 00 00 00 04 00 00 |XFSB............|

00000010 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................|

00000020 59 fc 66 e6 ac 4c 42 ee a7 6a 5e 2b 95 9e af d2 |Y.f..LB..j^+....|

00000030 00 00 00 00 00 02 00 06 00 00 00 00 00 00 00 80 |................|

00000040 00 00 00 00 00 00 00 81 00 00 00 00 00 00 00 82 |................|

00000050 00 00 00 01 00 01 00 00 00 00 00 04 00 00 00 00 |................|

00000060 00 00 0a 00 b4 b5 02 00 02 00 00 08 00 00 00 00 |................|

00000070 00 00 00 00 00 00 00 00 0c 09 09 03 10 00 00 19 |................|

00000080 00 00 00 00 00 00 02 00 00 00 00 00 00 00 00 ca |................|

00000090 00 00 00 00 00 03 49 65 00 00 00 00 00 00 00 00 |......Ie........|

000000a0 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff |................|

000000b0 00 00 00 00 00 00 00 08 00 00 00 00 00 00 00 00 |................|

000000c0 00 00 00 00 00 00 00 01 00 00 01 8a 00 00 01 8a |................|

000000d0 00 00 00 00 00 00 00 05 00 00 00 03 00 00 00 00 |................|

000000e0 9b 26 8c 92 00 00 00 04 ff ff ff ff ff ff ff ff |.&..............|

000000f0 00 00 00 01 00 00 0e b3 00 00 00 00 00 00 00 00 |................|

00000100 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................|

00000200

5、more 分页查看文件内容

less 分页查看文件内容

6、head 可以显示文件或标准输入的前面行

选项:

-c # 指定获取前面#字节

-n # 指定获取前面#行;#如果为负数,表示从文件头去到倒数#行

-# 同上

[root@localhost data]# head -n 3 ee

1

2

3

[root@localhost data]# head -n -3 ee

1

2

7、tail

和head相反,查看文件或标注输入的倒数行

常用选项:

-c # 指定获取后#字节

-n # 指定获取后面#行;#如果为+#,表示从#行开始到文件结束

-# 同上

-f 跟踪显示文件新加入的行

[root@localhost data]# tail -n 3 ee

5

6

7

[root@localhost data]# tail -n +3 ee

3

4

5

6

7

8、cut

可以提取文本文件或STDIN数据的指定列

常用选项:

-d 指定分割符

-f 指定字段

# 第#个字段

#,# 离散的多个字段

#-# 连续的多个字段

#,#-# 混合使用

-c 按字符切割

--output-delimiter=string 指定输出分割符

[root@localhost data]# cut -d: -f1,3-5 --output-delimiter="--" /etc/passwd

root--0--0--root

bin--1--1--bin

daemon--2--2--daemon

adm--3--4--adm

lp--4--7--lp

sync--5--0--sync

shutdown--6--0--shutdown

9、paste

合并多个文件同行号的列到一行

常用选项:

-d 指定分割符

-s 所有行合成一行显示

[root@localhost data]# paste -d: ee ff

1:a

2:b

3:c

4:d

[root@localhost data]# cat ee ff

1

2

3

4

a

b

c

d

[root@localhost data]# paste -d: -s ee ff

1:2:3:4

a:b:c:d

10、wc

统计行总数,单词数,字节数和字符数,可以对文件或stdin的数据统计

常用选项

-l 统计行数

-w 统计单词数

-c 统计字节数

-m统计字符数

-L 显示文件中最长行的长度

11、sort

把整理过的文本显示在stdout,不改变原始文本

常用选项

-r 执行反方向(由上至下)整理

-R随机排序

-n按数字大小整理

-h人类可读排序,如2k,1G,1M

-f 忽略字符串中的字符大小写

-u 合并重复的行,去重

-t c 使用c作为字段界定符

-k # 按照使用c字符分割的#列来整理,能够使用多次

[root@localhost data]# cut -d: -f1-5 /etc/passwd|sort -t: -k3 -nr|head -n 3

nobody:x:65534:65534:Kernel Overflow User

wang:x:1000:1000:

systemd-coredump:x:999:997:systemd Core Dumper

sort -t: -n -k3 /etc/passwd #-t指定分割符,-n按数字大小排序,-k指定几段

sort -t: -n -r -k3 /etc/passwd #-t指定分割符,-n按数字大小排序,-k指定几段;-r倒序

df|tail -n +2 |tr -s ' ' '%'|cut -d% -f5|sort -nr|head -3 #必须掌握

sort -u 合并重复的行。不管相邻不相邻

12、uniq

从输入中删除前后相接的重复行

常见选项:

-c 显示每行重复出现的次数

-d 仅显示重复过的行

-u 仅显示没有重复的行

cut -d' ' -f1 nginx.log |sort|uniq -c|sort -nr|head

cut -d' ' -f1 nginx.log #取出ip地址那一列

sort #排序,把相同的行排在一起(相邻起来)

uniq -c #合并重复相邻行并显示有多少重复的

sort -nr #从大到小排序

head #取前10行

cat a.txt b.txt | sort |uniq -d |sort -n #取相同的行

cat a.txt b.txt | sort |uniq -u |sort -n #取不同的行

13、locate

locate 查找文件(不是实时的)

[root@Rocky9 ~]# locate bashrc #查找文件,他不是在硬盘上面去找,而是在/var/lib/mlocate/mlocate.db这个文件里面去找。硬盘上面的文件信息都已经写在这个文件里面了。它不是实时的

/etc/bashrc

/etc/skel/.bashrc

/home/wang/.bashrc

/root/.bashrc

/usr/lib/python3.9/site-packages/pexpect/bashrc.sh

#查找文件,他不是在硬盘上面去找,而是在/var/lib/mlocate/mlocate.db这个文件里面去找。

硬盘上面的文件信息都已经写在这个文件里面了。它不是实时的,有可能新建的文件还没有写在这个文件里面去。

所以可以先更新这个文件再去查找。更新方法;updatedb。

locate -r #支持正在表达式

locate -i #不区分大小写

14、find

find 是实时查找工具,通过遍历指定路径完成文件查找

格式:

find [option] ...[查找路径] [查找条件] [处理动作]

查找路径:指定具体目标的路径;默认为当前目录

查找条件:指定查找标准,可以是文件名,大小,权限等标准。默认为找出路径下的所有文件

1)、指定搜索目录层级

--maxdepth level 最大搜索深度

--mindepth level 最小搜索深度

例子:find /etc/ -maxdepth 3 -mindepth 2

-depth 对每个目录优先处理文件在处理目录本身

root@ubuntu2204:/opt# find containerd/ -depth

containerd/bin

containerd/lib

containerd/

2)、根据文件名和inode查找

-name “文件名” #支持通配符,通配符要加“”

-iname "文件名" #不区分大小写

-inum n #按文件iNode号查找

-samefile name #相同inode号的文件

-links n #链接数为n的文件

-regex "pattern" #以pattern匹配整个文件路径,而非文件名称

例子:

find -name 1.txt

find / -name ".txt"

root@ubuntu2204:/opt/sss# find -regex ".*\.txt$"

./1.txt

3)、根据属主属组查找

-user username #属主为username的文件

-group groupname #属组为groupname的文件

-uid

-gid

-nouser #查找没有属主的文件

-nogroup #查找没有属组的文件

4)、根据文件类型查找

-type TYPE

TYPE可是以下形式:

f 普通文件

d 目录文件

l 符号链接文件

s 套链接文件

b 块设备文件

c 字符设备文件

p 管道文件

例子:

root@ubuntu2204:/opt/sss# find /home -type d -ls #查找home下的目录文件并执行ls

131073 4 drwxr-xr-x 3 root root 4096 Jul 7 05:22 /home

393218 4 drwxr-x--- 4 wang wang 4096 Jul 7 09:30 /home/wang

393224 4 drwx------ 2 wang wang 4096 Jul 7 05:25 /home/wang/.cache

393222 4 drwx------ 2 wang wang 4096 Jul 7 05:22 /home/wang/.ssh

5)、空文件或目录

-empty

例子:

root@ubuntu2204:/opt/sss# find ./ -type f -empty #查找当前目录的空文件

./wwtxt

./wtxt

./1.txt

6)、组合条件

与:-a 。默认多个条件与关系,所以可以省略-a

或:-o

非:-not !

例子:

root@ubuntu2204:/opt/sss# find /etc/ -type d -o -type l | wc -l #查找目录和文件

854

摩尔定律:

(非A)且(非B)=非(A或B)

(非A)或(非B)=非(A且B)

示例:!A -a !B = !(A -o B) !A -o !B = !(A -a B)

7)、排除目录

# 在当前目录下排除abc目录和def/h.txt文件和jk目录,查找所有以.txt结尾的文件

find . \( -path ./abc -o -path ./def/h.txt -o -path ./jk \) -prune -o -name "*.txt"

# 在当前目录下排除abc目录和def/h.txt文件,查找所有以.txt结尾的文件

find . \( -path ./abc -o -path ./def/h.txt \) -prune -o -name "*.txt"

# 在当前目录下排除abc和def目录,查找所有以.txt结尾的文件

find . \( -path ./abc -o -path ./def \) -prune -o -name "*.txt"

# 在当前目录下排除abc目录,查找所有以.txt结尾的文件【方式一】

find . -path "./abc" -prune -o -name "*.txt" -print

8)、根据文件大小来查找

-size [+|-]#UNIT #常用单位:k,G,M,c,注意大小写敏感

#UNIT :#表示(#-1,#]

-#UNIT:#表示[0,#-1]

+#UNIT: #表示(#,无穷)

find -size 1024k #(1023,1024]

find -size 3M #(2,3]

find -size -5M #[0,4]

find -size +5M #(5,无穷)

9)、根据时间戳查找

以天为单位

-atime [+|-]#

# 表示[#,#+1)

+# 表示 [#+1,无穷]

-# 表示 [0,#)

-mtime -ctime

以分钟为单位

-amin -mmin -cmin

10)、

根据权限查找

-perm [/|-]MODE

MODE #精确匹配

/MODE #任何一类(u,g,o)对象的权限中只要有一位匹配即可

-MODE #每一类对象都必须同事拥有指定权限

11)、处理动作

-print :默认的处理动作,显示在屏幕

-ls:类似于对查找到的文件执行“ls -dils”命令格式输出

-fls file 查找到的所有文件的长格式信息保存到指定文件中

-delete:删除查找到的文件

-ok COMMAND {} \; 对查找到的每个文件执行COMMAND指定命令,对于每个文件执行前,都会交互式要求用户确认

-exec command {} \; 对查找到的每个文件执行COMMAND指定命令

{} 用于引用查找到的文件名称自身

例子:

find -name "*.txt" -exec cp {} {}.bak ; #备份配置文件,添加.bak扩展名

12)、参数替换xargs

由于很多命令不支持管道来传递参数,xargs用于产生某个的参数,xargs可以读入stdin的数据,并且以空格符或回车符将stdin的数据分隔成为参数

另外,许多命令不能接收过多的参数,xargs可以解决

注意:文件名或者其他意义的名词内含有空格符的情况

find经常和xargs 命令进行组合,形式如下

find | xargs command

例子:

root@ubuntu2204:/opt/sss# seq 10 | xargs

1 2 3 4 5 6 7 8 9 10

ls | xargs rm #删除大量文件

root@ubuntu2204:/opt/sss# find -name "*.txt" | xargs ls -Sl

-rw-r--r-- 1 root root 0 Jul 11 06:36 ./1.txt

root@ubuntu2204:/opt/sss# echo {1..3} | xargs -n1

1

2

3

root@ubuntu2204:/opt/sss# echo {1..4} | xargs -n2

1 2

3 4

15、grep

作用:文本搜索工具,根据用户指定的”模式“对目标文本进行逐行的匹配检查,打印匹配到的行。

--color=auto 对匹配到的文本着色显示

-m # 匹配#次后停止

-v 显示不被“模式”匹配到的行,即取反

-i 忽略大小写字符

-n 显示匹配的行号

-c 统计匹配的行数

-o 仅显示匹配到的字符串

-q 静默模式,不输出任何信息

-A # after 后#行 匹配到的字符串的行和它后面的3行也显示出来

-B before 前#行 匹配到的字符串的行和它前面的3行也显示出来

-C context 前后各#行 匹配到的字符串的行和它前后的3行也显示出来

-e 实现多个选项间逻辑或的关系。例如:grep -e "cat" -e "dog" file

-w 匹配整个单词

-E 使用扩展正则表达式 相当于 egrep

-F 不支持正则表达式,相当于fgrep

-P 支持perl格式的正则表达式

-f file 根据file文件的模式处理

-r 递归目录,但不处理软连接

-R 递归目录,但处理软连接

-----------------------------------------------------------------------------------------

grep hello #不跟目录或者文件名,就是让你输入内容,然后在你输入的里面去查找

grep -m 3 nologin /etc/passwd #-m指定查看几个nologin

grep -v -m 3 nologin /etc/passwd #取不包含nologin的前3行 -v取反

grep -v "#" /etc/fstab #显示不包含#(注释)的行

grep -i 忽略大小写

grep -n 显示行号

grep -c 统计次数

grep -c processor /proc/cpuinfo #取cpu核数

grep -o 取匹配到的字符串本身

grep -q 匹配到,匹配不到都不输出

grep -A3 #匹配到的字符串的行和它后面的3行也显示出来

grep -B3 #匹配到的字符串的行和它前面的3行也显示出来

grep -C3 #匹配到的字符串的行和它前后的3行也显示出来

grep -e bash -e false /etc/passwd #查找包含bash或者包含false的行

grep bash /etc/passwd | grep wang #查找包含bash并且包含wang的行

grep -w wang /etc/passwd #查找wang必须是一个完整的单词。-w匹配单词

grep -f a.txt b.txt #把a文件里面的内容作为匹配条件,来查找b文件 (可以用来查找两个文件的相同行)

grep -r 递归目录,不处理软连接

grep -R 递归目录,处理软连接

root@ubuntu2204:~# grep -c processor /proc/cpuinfo #查看有几个cpu

2

root@ubuntu2204:~# df | grep "^/dev"|tr -s " " "%"|cut -d% -f5|sort -n|tail -n 1

39

#sort -n 按数字大小排序,从小到大; sort -nr 从大到小

cut -d: -f1,3,6,7 /etc/passwd #以:为分隔符,去取这个文件的1,3,6,7列

cut -d: -f1,3,6-7 /etc/passwd #以:为分隔符,去取这个文件的1,3,6,7列

cut -c44-46 /etc/passwd #-c以字符分割,取44到46的字符

48.sort:排序

sort -t: -n -k3 /etc/passwd #-t指定分割符,-n按数字大小排序,-k指定几段

sort -t: -n -r -k3 /etc/passwd #-t指定分割符,-n按数字大小排序,-k指定几段;-r倒序

df|tail -n +2 |tr -s ' ' '%'|cut -d% -f5|sort -nr|head -3 #必须掌握

sort -u 合并重复的行。不管相邻不相邻

49.uniq #相邻的重复的行重合起来

uniq -d #只显示相邻且重复的行

uniq -u #只显示相邻且不重复的行

cut -d' ' -f1 nginx.log |sort|uniq -c|sort -nr|head

cut -d' ' -f1 nginx.log #取出ip地址那一列

sort #排序,把相同的行排在一起(相邻起来)

uniq -c #合并重复相邻行并显示有多少重复的

sort -nr #从大到小排序

head #取前10行

取出两个文件相同和不相同的行

cat a.txt b.txt | sort |uniq -d |sort -n #取相同的行

cat a.txt b.txt | sort |uniq -u |sort -n #取不同的行

例子:

cat 1.txt

wang=10

dwewq=34

sfewf=45

dsd=14

grep -Eo '[0-9]{1,3}' 1.txt | tr '\n' '+'| grep -o -E '.*[0-9]'|bc

16、sed

sed :

命令格式:sed [option]...'script;script;...' [inputfile...]

-n 不输出模式空间内容到屏幕,即不自动打印

-e 多点编辑

-f file 从指定文件中读取编辑脚本

-r,-E 使用正则表达式

-i.bak 备份原文件并原处编辑

-s 将多个文件视为独立文件,而不是单个连续的长文件流

说明:

-ir 不支持

-i -r 支持

-ri 支持

-ni 危险选项,会清空文件

script的格式:

'地址命令'“:

1、不给地址:对全文进行处理

2、单地址:

#:指定的行,$:最后一行

/pattern/:被此模式所能匹配到的每一行

3、地址范围

#,# 从好多行到好多行 例如3,6 就是3到6行

#,+# 从好多航到+好多航,例如3,+4 就是3到7行

/pat1/,/pat2/

#,/pat/

/pat/,#

4、步进

1~2 奇数行

2~2 偶数行

命令:

p 打印当前模式空间的内容,追加到默认输出之后

Ip 忽略大小写输出

d 删除模式空间匹配的行,并立即启用下一轮循环

a [\n]test 在指定行后面追加文本。支持使用\n实现多行追加

i [\n]test 在行前面插入文本。支持使用\n实现多行插入

c [\n]test 替换行为单行或多行

w file 保存模式匹配的行到文件

r file 读取指定文件的文本到模式空间中匹配的行后

= 为模式空间中的行打印行号

!模式空间中匹配的行取反处理

q 结束或退出sed

查找替代:

s/pattern/string/修饰符 查找替换,支持使用其他分割符。可以是:s@@@ s###

修饰符:

g 行内全局替换

p 显示替换成功的行

w /path/file 将替换成功的行保存至文件中

I,i 忽略大小写

例子:

root@ubuntu2204:~# sed "" #默认sed会将输入的信息直接输出

hel

hel

root@ubuntu2204:~# sed '' /etc/issue

Ubuntu 22.04.2 LTS \n \l

root@ubuntu2204:~# sed 'p' /etc/issue #p打印当前模式空间内容,追加到默认输出之后

Ubuntu 22.04.2 LTS \n \l

Ubuntu 22.04.2 LTS \n \l

root@ubuntu2204:~# sed -n '' /etc/issue #-n不输出模式空间内容到屏幕,即不自动打印

root@ubuntu2204:~# sed -n 'p' /etc/issue #打印当前模式空间内容,追加到默认输出之后

Ubuntu 22.04.2 LTS \n \l

root@ubuntu2204:~# sed -n '1p' /etc/passwd #输出第一行

root:x:0:0:root:/root:/bin/bash

root@ubuntu2204:~# ifconfig ens33 | sed -n '2p' #输出第二行

inet 10.0.0.152 netmask 255.255.255.0 broadcast 10.0.0.255

root@ubuntu2204:~# sed -n '$p' /etc/passwd #输出最后一行

lxd:x:999:100::/var/snap/lxd/common/lxd:/bin/false

root@ubuntu2204:~# ifconfig ens33 | sed -n '/netmask/p'

inet 10.0.0.152 netmask 255.255.255.0 broadcast 10.0.0.255

root@ubuntu2204:~# df | sed -n '/^/dev/sd/p' #匹配以/dev/sd 开头的行

/dev/sda2 1992552 132940 1738372 8% /boot

/dev/sdb 52403200 1038348 51364852 2% /data/docker

root@ubuntu2204:~# seq 10 | sed -n '3,6p' #打印3到6行

3

4

5

6

root@ubuntu2204:~# seq 10 | sed -n '1~2p' #打印奇数行

1

3

5

7

9

root@ubuntu2204:~# seq 10 | sed -n '2~2p' #打印偶数行

2

4

6

8

10

root@ubuntu2204:~# seq 10 | sed '1~2d' #将奇数行删除,并且去掉-n

2

4

6

8

10

sed -e '2d' -e '2d' 1.txt #删除第二行和第四行

sed '2d;4d' 1.txt #删除第二行和第四行

root@ubuntu2204:~# sed -n -r 's/r..t/&er/gp' /etc/passwd # &表示前面的模式

rooter:x:0:0:rooter:/rooter:/bin/bash

root@ubuntu2204:~# ifconfig ens33 | sed -n -r '2s/[^0-9]+([0-9.]+).*/\1/p'

10.0.0.152 #取ip地址

sed 的高级用法

sed中除了模式空间,还另外支持保持空间,可以将模式空间的数据,临时保存在保持空间,从而后续接着处理,实现更强大的功能

p 打印模式空间开端至\n内容,并追加到默认输出之前

h 把模式空间中的内容覆盖至保持空间

H 把模式空间的内容追加至保持空间

g 从保持空间取出数据覆盖至模式空间

G 从保持空间取出数据追加至模式空间

x 把模式空间中的内容与保持空间中的内容进行互换

n 读取匹配到的行的下一行覆盖至模式空间

N 读取匹配到的行的下一行追加至模式空间

d 删除模式空间中的行

D 如果模式空间包含换行符,则删除直到第一个换行符的模式空间中的文本,并不会读取新的输入行,而使用合成的模式空间重新启动循环。如果模式空间不包含换行符,则会像发出d命令那样启动正常的新的循环

例子:

sed -n 'n;p' file #输出下一行,即偶数行

root@ubuntu2204:~# seq 10 | sed 'N;s/\n//'

12

34

56

78

910

17、printf

格式化输出printf

相当于增强的echo。

格式:printf "指定的格式" 文本1 文本2 ...

1、常用格式替换符:

%s 字符串

%d,%i 十进制整数

%f 浮点格式

%c ASCII字符 ,即显示对应参数的第一个字符

%b 相对应的参数中包含转义字符时,可以使用次替换符进行替换,对应的转义字符会被转义

%o 八进制值

%u 不带正负号的十进制值

%x 十六进制(a-f)

%X 十六进制(A-F)

%% %号本身

注意:

%#s 中的数字代表次替换符中输出字符宽度,默认是右对齐。%-10s表示10个字符宽度,-表示左对齐

%03d 表示3位宽度,不足前面用0补全,超出位数原样输出

%.2f 中的2表示小数点后显示的小数位数

2、常用转义字符:

\a 警告字符,通常为ASCII的BEL字符

\b 后退

\f 换页

\n 换行

\r 回车

\t 水平制表符

\v 垂直制表符

\ 表示 \ 本身

范例:

root@ubuntu2204:~# printf "%s" 1 2 3 4

1234root@ubuntu2204:~#

1234root@ubuntu2204:~# printf "%s\n" 1 2

1

2

root@ubuntu2204:~# printf "%f\n" 1 2

1.000000

2.000000

root@ubuntu2204:~# printf "%.2f\n" 1 2

1.00

2.00

root@ubuntu2204:~# printf "(%s)" 1 2;echo

(1)(2)

root@ubuntu2204:~# printf " (%s) " 1 2;echo

(1) (2)

root@ubuntu2204:~# printf "(%s)\n" 1 2

(1)

(2)

root@ubuntu2204:~# printf "%s %s\n" 1 2 3 4

1 2

3 4

root@ubuntu2204:~# printf "%-10s %-4s %-2s\n" 姓名 升高 年龄 wang 1.8 23 liu 1.68 23

姓名 升高 年龄

wang 1.8 23

liu 1.68 23

11root@ubuntu2204:~# printf "%x" 17;echo #十进制转换成16进制

11

root@ubuntu2204:~# printf "%d\n" 0xc #十六进制转换成10进制

12

root@ubuntu2204:~# VAR="1 2 3";printf "%s" ${VAR};echo

123

十二、总结文本处理的grep命令相关的基本正则和扩展正则表达式

用正则表达式的时候用''或者""扩起来

字符匹配

. 表示任意单个字符,\n除外,可以是一个汉字或其他国家的文字

[] 匹配范围内的任意单个字符,例如:[wang] [0-9] [a-z] [A-Z]

[^] 匹配指定范围以外的任意单个字符。例如[^wascas]

[:alnum:] 字母和数字

[:alpha:] 任何英文大小写字符。即A-Z,a-z

[:lower:] 小写字母

[:upper:] 大写字母

[:blank:] 空白字符(空格和制表符)

[:space:] 空白字符,包括空格,制表符(水平和垂直),换行符,回车等各种各类的,比[:blank:]广

[:cntrl:] 不可以打印的控制符(退格,删除,警铃。。)

[:digit:] 十进制数字

[:xdigit:] 十六进制数字

[:graph:] 可打印的非空空白字符

[:print:] 可打印字符

[:punct:] 标点符号

------------------------------------------------------------------------------------------------

\s 匹配任何空白字符,包括空格,制表符,换页等。等价于于[\f\r\t\v]

\S 匹配任何非空白字符,等价于[^\f\r\t\v]

\w 匹配一个字母,数字,下划线,汉子,其他国家文字字符,等价于[_[:alnum:]字]

\W 匹配一个非字母,数字,下划线,汉子,其他国家文字字符,等价于[^_[:alnum:]字]

------------------------------------------------------------------------------------------------

经典案例:

root@ubuntu2204:/etc/ssh/sshd_config.d# ll /etc/ | grep 'rc[.0-6]'

drwxr-xr-x 2 root root 4096 Jul 7 05:29 rc0.d/

drwxr-xr-x 2 root root 4096 Jul 7 05:29 rc1.d/

drwxr-xr-x 2 root root 4096 Jul 7 05:29 rc2.d/

drwxr-xr-x 2 root root 4096 Jul 7 05:29 rc3.d/

drwxr-xr-x 2 root root 4096 Jul 7 05:29 rc4.d/

drwxr-xr-x 2 root root 4096 Jul 7 05:29 rc5.d/

drwxr-xr-x 2 root root 4096 Jul 7 05:29 rc6.d/

drwxr-xr-x 2 root root 4096 Jul 7 05:29 rc.d/

匹配包含.和0到6数字的行

ll /etc/ | grep 'rc[.0-6].' #最后一个点表示任意单个字符

ll /etc/ | grep 'rc[.0-6]\.' #最后一个点就是表示一个点,\.转义

次数匹配

* 匹配前面的字符任意次,包括0次,贪婪模式;尽可能长的匹配

.* 任意长度的任意字符

\?匹配前面的字符0次或1次

\+ 匹配前面的字符最少一次,肯定有

\{n\} 匹配前面的字符n次

\{m,n\} 匹配前面的字符m到n次

\{,n\} 匹配前面的字符最多n次

\{n,\} 匹配前面的字符最少n次

例子:

[root@Rocky9 ~]# grep "gooo*gle" test.txt #表示:匹配前面的单个字符0次或者无数次

google

goooogle

goooooooooooogle

用正则表达式的时候用''或者""扩起来。

[root@Rocky9 ~]# grep "g.*gle" test.txt #.*表示任意长度的字符串

google

gsdwqfgle

goooogle

goooooooooooogle

g0000gle

gogle

ggle

[root@Rocky9 ~]# grep "go?gle" test.txt #?表示匹配前面单个字符0次或1次

gogle

ggle

[root@Rocky9 ~]# grep "go+gle" test.txt #+表示匹配前面单个字符1次或1次以上

google

goooogle

goooooooooooogle

gogle

[root@Rocky9 ~]# grep "go{4}gle" test.txt #{m}表示匹配前面单个字符m次

goooogle

经典案例:

[root@localhost ~]# ifconfig ens160 | grep -E -o "[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}"|head -n 1

10.0.0.131

位置锚定

^ 行首锚定,用于模式最左侧

$ 行尾锚定,用于模式的最右侧

^pattarn$ 用于模式匹配整行

^$ 匹配空行

^[[:space:]]*$ 空白行

\

\> 或\b 词尾锚定,用于单词右侧

\bPATTERN\b;\ 匹配整个单词

注意:单词是由字母,数字,下划线组成

金典案例“:

grep "^[^#]" /etc/ssh/sshd_config #去掉由注释的行

grep -v "^$" /etc/profile | grep -v "^#" #去掉空行和#开头的行

grep -v "^$\|^#" /etc/profile #去掉空行和注释行

grep -v -E "^($|#)" /etc/profile #去掉空行和注释行

分组

() 将多个字符捆绑在一起,当做一个整体;如\(root\)\+

后项引用:分组括号中的模式匹配到的内容会被正则表达式引擎记录于内部的变量中,这些变量的命名方式是:\1,\2,\3,...

\1 表示从左侧第一个左括号以及与之匹配右括号之间的模式所匹配到的字符

注意:\0表示正则表达式匹配的所有字符

示例\(wang1\(wang2\)\)

\1就是wang1\(wang2\)

\2就是wang2

或者

或者:\|

示例:

a\|b #a或者b

c\|cat #c或者cat

\(c\|b\)at # cat或者bat

grep -v "^\($\|#\)" /etc/profile #去掉空行和以#开头的行

扩展正则表达式

字符匹配

. 表示任意单个字符,\n除外,可以是一个汉字或其他国家的文字

[] 匹配范围内的任意单个字符,例如:[wang] [0-9] [a-z] [A-Z]

[^] 匹配指定范围以外的任意单个字符。例如[^wascas]

[:alnum:] 字母和数字

[:alpha:] 任何英文大小写字符。即A-Z,a-z

[:lower:] 小写字母

[:upper:] 大写字母

[:blank:] 空白字符(空格和制表符)

[:space:] 空白字符,包括空格,制表符(水平和垂直),换行符,回车等各种各类的,比[:blank:]广

[:cntrl:] 不可以打印的控制符(退格,删除,警铃。。)

[:digit:] 十进制数字

[:xdigit:] 十六进制数字

[:graph:] 可打印的非空空白字符

[:print:] 可打印字符

[:punct:] 标点符号

次数匹配

* 匹配前面的字符任意次,包括0次,贪婪模式;尽可能长的匹配

.* 任意长度的任意字符

?匹配前面的字符0次或1次

+ 匹配前面的字符最少一次,肯定有

{n} 匹配前面的字符n次

{m,n} 匹配前面的字符m到n次

{,n} 匹配前面的字符最多n次

{n,} 匹配前面的字符最少n次

位置锚定

^ 行首锚定,用于模式最左侧

$ 行尾锚定,用于模式的最右侧

^pattarn$ 用于模式匹配整行

^$ 匹配空行

^[[:space:]]*$ 空白行

\

\> 或\b 词尾锚定,用于单词右侧

\bPATTERN\b;\ 匹配整个单词

注意:单词是由字母,数字,下划线组成

分组

() 将多个字符捆绑在一起,当做一个整体;如(root)+

后项引用:分组括号中的模式匹配到的内容会被正则表达式引擎记录于内部的变量中,这些变量的命名方式是:\1,\2,\3,...

\1 表示从左侧第一个左括号以及与之匹配右括号之间的模式所匹配到的字符

注意:\0表示正则表达式匹配的所有字符

示例(wang1(wang2))

\1就是wang1(wang2)

\2就是wang2

或者

或者:|

示例:

a|b #a或者b

c|cat #c或者cat

(c|b)at # cat或者bat

十三、 结合编程的for循环,条件测试,条件组合,完成批量创建100个用户,
1)for遍历1..100
2)先id判断是否存在
3)用户存在则说明存在,用户不存在则添加用户并说明已添加。

#!/bin/bash
set -u -e
if [ $# -eq 0 ];then
        echo "qing shu ru xu yao chuang jian de yong hu!"
else

        for i in {1..100};do
                for user ;do
                        id ${user}${i} &> /dev/null && echo "${user}${i} yi jing chun zai !" || { useradd ${user}${i};echo "${user}${i} chuang jian cheng gong!"; }
                done
        done
fi


本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!

相关文章

立即
投稿

微信公众账号

微信扫一扫加关注

返回
顶部