从
kubectl get pods -o wide
输出看起来类似于
some-pod-name-with-numbers-123 1/1 Running 0 6d4h 192.168.0.23 node-name-abcdeft-host.domain <none> <none>
some-pod-name-with-numbers-1234 1/1 Running 0 4h38m 192.168.0.24 node-name-abcdeft-host.domain <none> <none>
some-pod-name-with-numbers-1235 1/1 Running 0 2m38s 192.168.0.25 node-name-abcdeft-host.domain <none> <none>
我得到 Pod 的经过时间,格式如下:4d3h15m3s(看起来最多是两个连续的单位,天和小时,小时分钟,分钟和秒,但我不能保证这一点。
我需要检查 pod 的存在时间是否超过某个阈值 X。
我试图找到某种方法通过 kubectl 将该字段提取为秒,但没有运气。我在互联网上搜索了一种预装解决方案,但找不到。
我想我可以使用 awk 将字符串转换为数字秒,这样我就可以比较它是否 > $X,这个值是可配置的。
答案1
您不需要仅仅为了获取 kubernetes 运行时间(以秒为单位)而派生外部进程。下面的 GNU awk 代码有一个用户定义的函数fx()
,该函数将执行该转换,从那里您可以将其用于比较目的。
kubectl get pods -o wide |
awk '
BEGIN {
a["d"] = 24*(\
a["h"] = 60*(\
a["m"] = 60*(\
a["s"] = 1)));
}
{
print fx($5); # kubernetes time elapsed in seconds
}
function fx(ktym, f,u,n,t,i) {
n = split(ktym, f, /[dhms]/, u)
t = 0
for (i=1; i<n; i++) {
t += f[i] * a[u[i]]
}
return t
}
'
如果你想使用 bash 中的用户定义函数,那么我们可以执行以下操作。我们有一个函数 fx(),它需要一个参数,即以 kubernetes 格式表示的经过时间,它将以秒为单位输出时间。
fx() {
echo "$1" |
sed -Ee '
s/[1-9][0-9]*[dhms]/&+ /g
:a;s/[+]([^+].*)/\1+/;ta
s/.$//
:loop
s/d/ 24h*/
s/h/ 60m*/
s/m/ 60s*/
s/s//
t loop
s/.*/echo "&" | dc -e "?p"/e
'
}
我们正在为名为的 Linux 实用程序动态生成代码直流电或桌面计算器RPN(逆波兰表示法)。
答案2
如果有人像我一样在寻找 python 函数,这里是:
def kubctle_dur_to_secs(kubectl_time:str) -> int:
total_time = 0
for t_char, sec_in_t in zip( ('d', 'h', 'm', 's'), (86400, 3600, 60, 1) ):
if t_char in kubectl_time:
t_index = kubectl_time.find(t_char)
total_time += int(kubectl_time[:t_index])*sec_in_t
kubectl_time = kubectl_time[t_index+1:]
return total_time
答案3
花了一些时间,发现最快的方法是用 sed 替换来标记时间。
sed -e 's/\([smhd]\)/\1 /g' | awk '{ b=0; for(i=1; i<=NF; ++i) { s=substr($i,1,length($i)-1); u=substr($i,length($i)); if (u=="s") b+=s; else if (u=="m") b+=s*60; else if (u=="h") b+=s*60*60; else if (u=="d") b+=s*60*60*24; else u=""; } if (b>1) printf "%d", b}'
到目前为止,我只观察到该领域使用了 d、h、m、s 单位,即使对于超过 100 天的 pod 也是如此。
sed 命令基本上用空格分隔每个单元。
然后 awk 循环遍历字段并将字符串拆分为单位 (u) 和数字字符串 (s)。
链接的 if-elseif-else 语句只是根据单位将值转换为秒,并将其添加到保留的总时间(以秒为单位)中。
我已将此命令放在脚本“kube_elapsed_to_seconds”中,并计划在外部使用另一个 awk 和系统命令在此字段上运行此脚本。
kubectl get pods -o wide | awk '{ system("echo " $5 " | kube_elapased_to_seconds"); print $0 }'
我愿意接受有关如何使此命令更易于阅读或与其他非时间相关字段(例如可能存在的 podname 和状态)更好地交互的建议。
答案4
对于理解这些的命令4d3h15m3s
,请参阅 dateutils 的dadd
:
$ TZ=UTC0 dateutils.dadd -f%s 1970-01-01T00:00:00 4d3h15m3s
357303
这里将该持续时间添加到 Unix 纪元时间的开头,并将结果输出为 Unix 纪元时间(在与 UTC 偏移量为 0 的时区中)。