vi split_log.sh
#!/bin/sh
count=$#
if [ $count -le 0 ]
then
echo “please input date”
exit
fi
filename=”access.log”
cd ~weblog/
if [ ! -d ./$1 ]
then
mkdir ./$1
fi
cd ./$1
rm * -f
zcat ../$filename.$1.gz | gawk -F ‘[ /]‘ ‘ {dom=$11;print $0 >> dom}’
for file in ./*
do
if [ -s $file ]
then
gzip $file
else
rm $file -f
fi
done
参数使用的是长格式日期
例如:
./split_log.sh 20080909
在产生的日志中会出现一些莫名其妙的域名日志,这是由于有人非法使用squid做代理造成的。这样的情况在配置禁止非法代理也一样会发生。
由于最近刚接手一批oracle数据库服务器,只能使用指定用户oracle进行相关操作。而且ssh没有做public key,并且也没有权限做ssh的public key,使用shell脚本居然问我一次又一次的要密码,怎么脚本自动化?没办法,只能使用expect来实现了。
一般使用ssh的public key的ssh脚本如下:
#!/bin/sh
servers=`cat /etc/hosts | grep -v ^# | grep ^192.168.1 | cut -f1`
username="oracle"
echo exec cmd all...
for server in $servers; do
echo "##########################################"
echo $server
ssh $username@$server $1
echo "##########################################"
done
wait
echo complete!
上面是shell脚本,这里就不多解释了,相信大家都能看明白。$1可以是运行命令也可以执行脚本,随便你,只要你喜欢!
如果不允许或者没有权限使用ssh的public key,那么只能使用expect进行ssh自动交互了
#!/usr/bin/expect
set username "oracle"
#ssh的用户名
set passwd "oracle11"
#ssh的密码
set servers [exec cat /etc/hosts | grep -v ^# | grep ^192.168.1 | cut -f1]
#读取hosts中要访问的主机
foreach server $servers {
#循环
spawn ssh $username@$server "[lindex $argv 0]";
#执行ssh,注意expect中输入的第一个变量用$argv 0表示。
expect "*password: ";
sleep .1;
send "$passwd\r";
#当出现提示输入密码时,自动输入密码
interact;
}
ok,这样指定的一般用户在ssh且不能使用key时就不用一次次输入密码了。
Expect 是一个控制交互式程序的工具。你可以用它来编写一段脚本来处理一些交互式的操作,比如执行passwd、su 远程登录 ssh,远程命令操作等 ,如果你有多台服务器需要执行相同的操作命令,用Expect就比较适合。
下面这段文字描述了expect的一些概念。
* Expect 是一种特定的、高级的和通用的编程语言,其语法与 Tcl 相同,并增加了 Tcl 中所没有的一些特殊用途的命令。
* Expect 是一种可执行程序,从它正确地处理用 Expect 语言编写的输入的角度来看,它实现了这种语言。
* expect 命令是其中的一个命令,Expect 以此对 Tcl 进行了扩展。
* Expect 是一个 Tcl 包。一般说来,这意味着任何 Tcl 应用程序都可以在运行时加载 Expect 功能。
* Expect 是一个基于 C 源代码的库,而这些 C 源代码则深入到 Expect 可加载的包和 Expect 可执行程序。
* Expect 是某种工具的抽象概念,该工具:
o 实现终端交互的自动化,甚至在涉及到密码或者其他特殊项目的情况下
o 实现了一种“对话”模型,通过它对消息和响应的简单规律进行编码
下面两篇文章详细介绍了Expect的使用
http://fanqiang.chinaunix.net/a4/b8/20010912/1000001278.html
http://www.ibm.com/developerworks/cn/aix/library/au-expect/index.html
当然,在学习Expect 之前你应当先学习一些Tcl编程的内容,请看这里 TclTk中文网,另外expect 的安装需要依赖Tcl,你必须首先安装 Tcl。
下面是我写的一段演示脚本,主要操作是从一个文本中批量读取ip地址,普通用户用户名和密码,超级用户密码,执行ssh登录,su root 操作 然后退出
pwd.txt
127.0.0.1 mars 1234 root 123456
192.168.0.3 mars 1234 root 123456
run.exp
#!/usr/bin/expect
set timeout 5
proc do_ssh_login {host username pass susername spass} {
set timeout_case 0
set done 1
send_user "\n"
spawn ssh $username@$host
send_user "正在连接主机 $host\n"
while {$done} {
expect {
timeout {
switch -- $timeout_case {
0 { send "\n" }
1 {
send_user "重试...\n"
send "\n"
}
2 {
puts stderr "登录超时...\n"
close
set done 0
break
}
}
incr timeout_case
}
"*(yes/no)?" {send "yes\n"}
"?assword:" {send "$pass\n"}
"*Permission denied*" { send_user "登录受限\n"
close
set done 0
break
}
"*Connection refused*" { send_user "主机不可访问\n"
close
set done 0
break
}
"*$*" {send_user "\n登录成功...\n"
if {[string equal $susername "NULL"] !=1} {
send "export LC_ALL=en_US\r"
send "su - $susername\r"
expect "*Password:*"
sleep 1
send "$spass\n"
expect {
"*Authentication failure*" {send_user "密码错误\n"
close
break
}
"*Permission denied*" {send_user "登录受限\n"
close
break
}
}
}
}
"*#*" {
send_user "超级用户登录成功\n"
send_user "\n*************************$host********************************\n"
send "cat /proc/cpuinfo |grep model\\ name\n"
expect "#"
send "df -T\n"
expect "#"
send "fdisk -l\n"
expect "#"
send "free\n"
expect "#"
send "lspci\n"
expect "#"
expect {
"#" {set done 0
send_user "\n***************************************************************\n"
send_user "\n"
send "exit\n"
}
}
}
}
}
}
set f [open "pwd.txt" r]
while { [gets $f line] >= 0 } {
set su [lindex $line 3]
set sp [lindex $line 4]
if { [string length $su] <=0 } {
set sp "NULL"
set su "NULL"
}
do_ssh_login [lindex $line 0] [lindex $line 1] [lindex $line 2] $su $sp
}
close $f
以前写的一个脚本,因为有一个项目要求让普通用户修改一些配置文件,而不能让他们有root权限。首先想到的是给这个用户sudo 权限用来执行一个脚本调用vi编辑器,而在vi中是可以直接调用系统命令的,因此这样做并不可靠。我想到了在脚本控制下给vi编辑器一个chroot环境,当vi修改完配置文件后,通过脚本控制复制到实际路径中替换掉旧文件并且可以备份每次修改的diff。下面是我写的一个脚本。介绍一下:
首先设置一个vi的chroot环境,主要程序文件,实际vim依赖哪些so可以用命令 ldd vim 来获取到,可以从相应实际目录中拷贝过来。
./
./bin
./bin/vim
./tmp
./etc
./etc/vimrc
./lib
./lib/ld-linux.so.2
./lib/libdl.so.2
./lib/libselinux.so.1
./lib/libgpm.so.1
./lib/libattr.so.1
./lib/libnsl.so.1
./lib/libc.so.6
./lib/libpthread.so.0
./lib/libncurses.so.5
./lib/libresolv.so.2
./lib/libacl.so.1
./lib/libcrypt.so.1
./lib/libperl.so
./lib/libtermcap.so.2
./lib/libm.so.6
./lib/libutil.so.1
./root
./root/.viminfo
下面是脚本,主要功能:自动搜索特定目录下的文件,修改后自动备份和随时回滚的功能,脚本写的很简单,没什么可说的。当然,你肯定又会说了,何必这么麻烦呢,直接把那些配置文件的修改权给这个用户不就好了吗?如果你非要这样也我也没有办法,这里只是提供这样一种方法,到底要怎么实现怎么做要看具体情况。
#!/bin/sh
#################################################
# File edit&backup&restore tools for sudo user #
# martian <martian2008@gmail.com> #
#################################################
if [ "$UID" != 0 ];then
echo access denied
exit 1
fi
chroot="/usr/local/chroot_vim" # chroot环境路径
backup="/usr/local/configfile_back" # 备份文件保存目录
path=(/usr/local/tomcat6/conf /usr/local/httpd/conf /usr/local/php/etc)
# 有权限修改配置文件的目录
USAGE="Usage: `basename $0` [OPTION]... {FileName} \n -e Edit File \n \
-r Restore File \n"
if [ "$#" -eq 0 ] ;then
echo -e "${USAGE}"
exit 1
fi
get_char()
{
SAVEDSTTY=`stty -g`
stty -echo
stty raw
dd if=/dev/tty bs=1 count=1 2> /dev/null
stty -raw
stty echo
stty $SAVEDSTTY
}
answer()
{
ANSWER=""
while [[ "$ANSWER" != "y" ]] && [[ "$ANSWER" != "Y" ]]
do
echo -en "Do you want to "
echo -en "\\033[0;35m"
echo -en "$info"
echo -en "\\033[0;38m"
echo " this File? (y/n)"
read ANSWER
case $ANSWER in
(y|Y) return 0 ;;
(n|N) return 1 ;;
*)continue;
esac
done
}
select_diff()
{
N=""
read N
until [[ $N =~ ^[0-9]+$ ]] # bash 3.0
do
echo -n "Please type one number:"
read N
done
}
while getopts e:r: OPTION;
do
case "$OPTION" in
e) info="Edit"
F="$OPTARG";;
r) info="Restore"
F="$OPTARG";;
\?) echo -e $USEAGE
exit 1
esac
done
if [ -n "$F" ];then
for filedir in ${path[*]}
do
for f in `/usr/bin/find "$filedir" -type f -name "$F"`
do
echo
echo -en "\\033[0;35m"
echo -en "$info"
echo -en "\\033[0;38m"
echo -en " File "
echo -en "\\033[0;36m"
echo "$f ..."
echo -en "\\033[0;38m"
answer
if [ "$?" == 0 ];then
filename="`echo "$f" |sed 's#/#\|#g'`"
if [ "$info" == "Restore" ];then
f1=(`/usr/bin/find "$backup"/"$filename".diff.* -xdev 2>/dev/null `)
echo -ne "Found "
echo -ne "\\033[0;35m"
echo -ne ${#f1[*]}
echo -ne "\\033[0;38m"
echo " Diff File"
if [ "${#f1[*]}" == 0 ];then
echo "Skip..."
else
i=${#f1[*]}
for f4 in ${f1[*]}
do
echo -ne "`/bin/basename $f4` "
echo `ls -l "$f4" |awk '{print $6, $7, $8}'`
done
echo -n "Please type one number to Restore [ ${#f1[*]}-1 ]:"
select_diff
echo -ne "Your Select "
echo -ne "\\033[0;35m"
echo -ne "$N"
echo -ne "\\033[0;38m"
echo " to Restore"
pushd "`/usr/bin/dirname $f`" >/dev/null
until [ $N -gt $i ]
do
i=$((i-1))
echo "Process File ${f1[$i]}......"
/usr/bin/patch <${f1[$i]}
if [ "$?" == 0 ];then
/bin/rm ${f1[$i]}
fi
done
popd >/dev/null 2>&1
fi
else
/bin/cp -a "$f" "$chroot"/tmp/"$filename"
/usr/sbin/chroot "$chroot" /bin/vim /tmp/"$filename"
/usr/bin/diff -Nu "$chroot"/tmp/"$filename" "$f" \
>"$chroot"/tmp/"$filename".diff
if [ "$?" != 0 ];then
echo -n "Backup Confilg File..."
f2="$backup"/"$filename".diff
f1=(`/usr/bin/find $f2.* -xdev 2>/dev/null `)
i=${#f1[*]}
i=$((i+1))
echo $i
/bin/mv "$chroot"/tmp/"$filename".diff "$f2".$i
echo done
echo -n "Saveing... Press any key to continue..."
/bin/cp -a "$chroot"/tmp/"$filename" "$f"
echo done
char=`get_char`
fi
fi
fi
done
done
fi
制作软件:FreeMind 0.9.0
源文件下载
刚做好的思维导图,新鲜出炉!不过相对于awk软件来说,那它可是历史悠久了,希望这张图能对学习awk的朋友有所帮助吧,如有不对或者遗漏的地方望请指正,当然不可能这个图能包含awk的一切,但已经是相当丰富了。如果你实在是记不住这张图上的内容,可以把它打印出来贴在墙上,前提是你家有足够大的墙壁来贴。

Flash plugin or Javascript are turned off. Activate both and reload to view the mindmap

近期评论