export实现命令交互式脚本
一、说明
ssh、passwd、mysql等命令经常会有输入密码或选项的交互场景,本篇介绍如何通过shell自动化实现该类功能。
二、expect命令
提示:man expect查看更加详细说明
1.简单Case, 实现与mysql数据库交互脚本
代码如下(mysql_interact.exp):
#!/usr/bin/expect -f
# 注意expect中的注释不能与命令同行
# 设置超时时间, 默认10秒,这里改成20秒
set timeout 20
# expect脚本的参数列表存于数组argv中,argv0是脚本名称
# 第一个参数访问方式是[lindex $argv 0], 网上说的$argv1是错的
set user "[lindex $argv 0]"
# 打印user参数到控制台, 类似bash中的echo
puts "The param user is $user"
set password "[lindex $argv 1]"
set host "[lindex $argv 2]"
set port "[lindex $argv 3]"
# 启动 MySQL 客户端
spawn mysql -h $host -P $port -u $user -p
# 匹配密码提示
expect "password:"
# 发送密码
send "$password\r"
#expect的其他用法:
#expect {
# "password" {
# send "$password\r"
# #如果没有exp_continue命令,则整个expect结束,如果有exp_continue,此次输入密码后会继续向下交互
# exp_continue
# }
# "mysql" {
# # 调用bash的方式
# exec bash -c {echo 2 >> 123.log}
# send "show databases;\r"
# }
#}
# 匹配登录成功的提示,这里以 MySQL 的提示为例
expect "mysql>"
# 在这里执行你的 SQL 命令
send "SHOW DATABASES;\r"
# 匹配命令执行后的提示
expect "mysql>"
# 退出 MySQL 客户端
send "exit\r"
# 等待退出, 如果想继续留在mysql中交互可以使用interact替换expect eof
expect eof
运行方式如下:
/usr/bin/expect mysql_interact.exp root pwd 192.168.0.1 3306
三、使用自定义密码便捷连接数据库
AES对称加密算法脚本(aes_enc.sh):
#!/bin/bash
iv="1234567890ABCDEF" # 这是测试使用的16进制,使用的时候建议随机生成
function enc {
data="$1"
slat="$2"
ciphertext=$(echo "$data" | openssl enc -aes-256-cbc -a -K $(echo "$slat" | xxd -r -p | openssl dgst -sha256 | cut -c1-32) -iv "$iv")
echo $ciphertext
}
function dec {
ciphertext="$1"
slat="$2"
data=$(echo "$ciphertext" | openssl enc -aes-256-cbc -d -a -K $(echo "$slat" | xxd -r -p | openssl dgst -sha256 | cut -c1-32) -iv "$iv")
echo $data
}
使用此脚本将数据库密码进行加密
连接数据库脚本(go_to_db.sh):
#!/bin/bash
set -e
SCRIPT_PATH=$(dirname "$0")
source $SCRIPT_PATH/aes_enc.sh
envName="$1"
user=
password=
pwdEnc=
host=
port=
case "$envName" in
"dev")
user="root"
host="192.168.1.1"
pwdEnc="" # 写入AES加密的数据库密码
port="3306"
;;
"beta")
user="beta"
host="192.168.1.1"
pwdEnc="" # 写入AES加密的数据库密码
port="3307"
;;
*) echo "未知数据库"
exit 100;
;;
esac
# 关闭终端回显功能,这样输入的密码就不会显示在屏幕上
stty -echo
echo -n "Enter secret key:"
read slat
# 重新启用终端回显功能
stty echo
echo
password=`dec "$pwdEnc" "$slat"`
expect $SCRIPT_PATH/db_interact.exp "$user" "$password" "$host" "$port"
数据库命令交互脚本(db_interact.exp):
#!/usr/bin/expect -f
# 设置超时时间
#set timeout 20
set user "[lindex $argv 0]"
set password "[lindex $argv 1]"
set host "[lindex $argv 2]"
set port "[lindex $argv 3]"
# 启动 MySQL 客户端
spawn mysql -h $host -P $port -u $user -p
# 匹配密码提示
expect "password:"
# 发送密码
send "$password\r"
# 匹配登录成功的提示,这里以 MySQL 的提示为例
expect "mysql>"
# 在这里执行你的 SQL 命令
send "SHOW DATABASES;\r"
# 匹配命令执行后的提示
expect "mysql>"
# 切换到use_db
send "use user_db\r"
# 交互
interact