4
实现shell版的pv
source link: https://www.lujun9972.win/blog/2019/09/27/%E5%AE%9E%E7%8E%B0shell%E7%89%88%E7%9A%84pv/index.html
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
实现shell版的pv
从 https://blogs.oracle.com/linux/solving-problems-with-proc-v2 上看到的。
pv 能够显示数据处理的进度,非常神奇。而借助 /proc/$pid/fdinfo/$fd
我们能够用 shell 实现类似的功能。
我们都知道在 /proc/$pid/fd/
中可以察看各个进程打开的文件描述符实际指向的文件,
而今天我才知道,原来在 /proc/$pid/fdinfo/
目录下我们还能查看各个文件描述符的状态信息
for fdinfo in /proc/$(pgrep emacs)/fdinfo/* do echo ---------------${fdinfo}---------------- cat ${fdinfo} done |head -n 20
---------------/proc/1301/fdinfo/0---------------- pos: 0 flags: 0100000 mnt_id: 23 ---------------/proc/1301/fdinfo/1---------------- pos: 0 flags: 02 mnt_id: 9 ---------------/proc/1301/fdinfo/10---------------- pos: 184 flags: 0100001 mnt_id: 26 ---------------/proc/1301/fdinfo/11---------------- pos: 0 flags: 0100002 mnt_id: 26 lock: 1: POSIX ADVISORY WRITE 1301 00:17:2899622 0 EOF ---------------/proc/1301/fdinfo/12---------------- pos: 0 flags: 0100001
这些信息的意义可以通过 man 5 proc
来获得,其中 pos
表示的是文件的偏移位置。
因此我们可以实现一个简陋的pv
#!/usr/bin/env bash file="$1" cat <"${file}" & # 文件内容输出到stdout,这样方便通过管道传递出去. pid=$! fd=/proc/${pid}/fd/0 fdinfo=/proc/${pid}/fdinfo/0 size=$(stat --format=%s "${file}") # 获取文件的总大小 while [ -e ${fd} ]; do progress=$(cat ${fdinfo} | grep ^pos | awk '{print $2}') # 获取偏移量 echo $((100*${progress} / ${size})) # 计算百分比 sleep 0.1 done | dialog --gauge "Progress reading ${file}" 7 100 >&2 # 进度条输出到stdout
效果如下图所示:
Recommend
About Joyk
Aggregate valuable and interesting links.
Joyk means Joy of geeK