Abel'Blog

我干了什么?究竟拿了时间换了什么?

0%

bash

概述

记录一下Linux运维的时候常用的bash的知识。

目录相关

获取当前文件的绝对目录

1
2
3
4
5
6
if [ -L $0 ]
then
BASE_DIR=`dirname $(readlink $0)`
else
BASE_DIR=`dirname $0`
fi

$0 获取当前可执行程序的名称;

if [ -L $0 ] 用于检查一个名字是否为link;

$(readlink $0) 用于获取一个文件的正式的位置;

dirname 直接获取某个文件所在目录

本地IP地址抓取

1
LOCALIP=`ip addr|grep "eth0:" -A 3|grep "inet "|sed -r "s@.* (([0-9]{1,3}\.){3}[0-9]{1,3})/(32|24|16|8) .*@\1@"`

中间是使用了 s@正则@\1@ 来抓取了其中的IP地址;

if语句

指令 备注
–b 当file存在并且是块文件时返回真
-c 当file存在并且是字符文件时返回真
-d 当pathname存在并且是一个目录时返回真
-e 当pathname指定的文件或目录存在时返回真
-f 当file存在并且是正规文件时返回真
-g 当由pathname指定的文件或目录存在并且设置了SGID位时返回为真
-h 当file存在并且是符号链接文件时返回真,该选项在一些老系统上无效
-k 当由pathname指定的文件或目录存在并且设置了“粘滞”位时返回真
-p 当file存在并且是命令管道时返回为真
-r 当由pathname指定的文件或目录存在并且可读时返回为真
-s 当file存在文件大小大于0时返回真
-u 当由pathname指定的文件或目录存在并且设置了SUID位时返回真
-w 当由pathname指定的文件或目录存在并且可执行时返回真。一个目录为了它的内容被访问必然是可执行的。
-o 当由pathname指定的文件或目录存在并且被子当前进程的有效用户ID所指定的用户拥有时返回真。

字符串、数字比较

运算符 描述 示例
-e filename 如果 filename 存在,则为真 [ -e /var/log/syslog ]
-d filename 如果 filename 为目录,则为真 [ -d /tmp/mydir ]
-f filename 如果 filename 为常规文件,则为真 [ -f /usr/bin/grep ]
-L filename 如果 filename 为符号链接,则为真 [ -L /usr/bin/grep ]
-r filename 如果 filename 可读,则为真 [ -r /var/log/syslog ]
-w filename 如果 filename 可写,则为真 [ -w /var/mytmp.txt ]
-x filename 如果 filename 可执行,则为真 [ -L /usr/bin/grep ]
-z string 如果 string 长度为零,则为真 [ -z $myvar ]
-n string 如果 string 长度非零,则为真 [ -n $myvar ]
string1 = string2 如果 string1 与 string2 相同,则为真 [ $myvar = one two three ]
string1 != string2 如果 string1 与 string2 不同,则为真 [ $myvar != one two three ]
num1 -eq num2 等于 [ 3 -eq $mynum ]
num1 -ne num2 不等于 [ 3 -ne $mynum ]
num1 -lt num2 小于 [ 3 -lt $mynum ]
num1 -le num2 小于或等于 [ 3 -le $mynum ]
num1 -gt num2 大于 [ 3 -gt $mynum ]
num1 -ge num2 大于或等于 [ 3 -ge $mynum ]
1
2
  filename1 -nt filename2 如果 filename1 比 filename2 新,则为真 [ /tmp/install/etc/services -nt /etc/services ]
  filename1 -ot filename2 如果 filename1 比 filename2 旧,则为真 [ /boot/bzImage -ot arch/i386/boot/bzImage ]
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
killreg () {
if [ $# -lt 1 ]
then
echo "[Usage]"
echo "killreg <regexp> [killarg]"
return
fi
result=`ps ux | grep "$1" | grep -v grep`
if [ -z "$result" ]
then
echo "Can not find any process."
return
fi
echo $result
while true
do
vared -p 'kill process aboe?[Y/n]' -c input
case $input in
([yY][eE][sS] | [yY] | "") ps ux | grep --color=auto --exclude-dir={.bzr,CVS,.git,.hg,.svn,.idea,.tox} "$1" | grep --color=auto --exclude-dir={.bzr,CVS,.git,.hg,.svn,.idea,.tox} -v grep | awk '{print $2}' | xargs kill $2
return ;;
([nN][oO] | [nN]) echo "do nothing"
return ;;
(*) echo "Invalid input..." ;;
esac
done
}

-z 判断

a.sh

1
2
3
4
5
if [ -z $RPCPASS ]; then 
echo 'is true';
else
echo 'is false';
fi

如何让它输出 true, false.export RPCPASS=1设置一下,执行就会变成 is false。

grep 在目录中查找代码

1
grep -r --include="*.go" --text "PushBatch" .

2>&1

在Linux Bash中,2>&1是一种将标准错误输出重定向到标准输出的方法。其中,“2”是表示标准错误输出的文件描述符,而“1”则是表示标准输出的文件描述符。

具体来说,2>&1将标准错误输出重定向到与标准输出相同的地方,也就是说,它将标准错误输出发送到与标准输出相同的位置,这可以方便地将错误信息与正常输出一起处理。

例如,如果我们想要将一个命令的输出和错误信息都输出到一个文件中,可以使用如下的命令:

1
command > output.txt 2>&1

在这个例子中,>符号将命令的输出重定向到名为output.txt的文件中,而2>&1则将标准错误输出也发送到相同的位置。这样,我们就可以同时捕获正常输出和错误信息,并将它们保存到同一个文件中。

读取json地址,批量拷贝文件

1
2
3
4
5
6
7
8
9
10
11
12
#!/bin/bash  

# 从 JSON 文件中读取 remote_addr 数组
remote_addrs=$(cat /path/to/your/json_file.json | jq -r '.remote_addr[]')

# 遍历 remote_addr 数组并复制文件到远程机器
for addr in $remote_addrs; do
# 拼接 scp 命令
cmd="scp /root/tmp.log root@$addr:/path/to/remote/destination"
# 执行命令
$cmd
done

读取数据,转换

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
change_hex_str_int() {
local hexstr=`echo $1 |cut -c 3-`
echo $((16#${hexstr}))
}

get_bsc_info() {

local hexheight=`curl -s -H "Content-Type: application/json" \
-X POST --data '{"jsonrpc":"2.0","method":"eth_blockNumber","params":[],"id":1}' \
$1 | jq -r '.result'`

local height=`change_hex_str_int "${hexheight}"`

echo "height: ${height}"

local hextimestamp=`curl -s -H "Content-Type: application/json" \
-X POST --data '{"jsonrpc":"2.0","method":"eth_getBlockByNumber","params":["'${hexheight}'",false],"id":1}' \
$1 | jq -r '.result.timestamp'`

local timestamp=`change_hex_str_int "${hextimestamp}"`
echo `gdate -d @${timestamp}`
}

get_bsc_info "http://xxxxxx"

将秒数转换成人看得懂的事件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
#!/bin/bash

seconds_to_hms() {
local input=$1
local hours=$((input / 3600))
local minutes=$(( (input % 3600) / 60))
local seconds=$((input % 60))
printf "%02d:%02d:%02d\n" $hours $minutes $seconds
}

# 示例
seconds=3665
formatted_time=$(seconds_to_hms $seconds)
echo $formatted_time

参考资料