linux下shell编程中出现的一些问题(2)

2 篇文章 0 订阅

最近做shell脚本,出现了一些问题,在这里记录一下:

1、判断一个文件是否存在,最常用的方法还是file判别中的

if [ -e filename ]; then

  echo "exit!"

else

  echo "nonexit!"

fi

2、函数编写的格式:

function(){  //定义与编辑函数

...

...

}

function //引用函数,注意,引用函数的过程不需要加“()”。

3、想要实现scp自动上传,最便捷的方法是使用expect软件,如果在嵌入式上运行自动认证,则需要先移植该软件,移植expect软件链接不好找,这里献上链接(花很长时间才找到!)

http://blog.sina.com.cn/s/blog_43ffbf3e0101afir.html

expect指令想要简单使用的话比较简单,它是tcl指令体系中的东西,所以一般在bash下是无法执行的。

关于expect的学习可以参考经典:Exploring Expect

这个链接也可以考虑:

expect一共会产生两个进程,一个进程是执行命令的进程(spawn语句产生的进程);另一个是模拟用户(expect语句产生的进程)。

send就是模拟用户在console下输入字符串,我们输入命令都要回车的,相应的send的字符串要用\r结束。

expect使用最多的三个指令:

spawn+command:run the command

expect +“sentense”:check if the sentense come up

send   “command\n”:input the command as the last sentense‘s reply

此外,通常用来等待的语句

set timeout +n:waiting for n milliseconds

4、在执行expect语句时,由于上述语言都要在expect环境下执行,所以bash程序中的变量如何在expect程序中引用,请看下面的方法:

expect<<-END

...

...

expect eof

END

即可,将本条结合第二条就可以达到bash程序中的函数中引用expect指令的作用,同时还能达到expect引用程序中的变量的效果

5、linux中批量注释的方法:

<<MULTILINECOMMENT

...

...

MULTILINECOMMENT

6、expect在输出字符上,本应参考explore expect,但是还有一个笨办法:

send每个特殊字符前面都加上\就可以了,expect每个特殊字符前面加上\\\,此方法来自该链接:

http://www.newsmth.net/nForum/#!article/LinuxDev/20758

可以以下列语句做验证

send "\$ax\[sdf\]\@\#\r"
expect "\\\r\\\n"

但是,本人的测试场景是调用函数中的测试,和上面稍稍有一些区别,放上一点代码:

#!/bin/bash

test(){

expect<<-END

send $1

expect eof

END

}

filename=dmesg\\\[3\\\].txt

test $filename

本程序中传递的参数中含有特殊字符,需要“\\\”才能完成特殊字符显示,根据该链接的验证,我猜想应该是因为变量是被expect调用,所以尽管在send中被调用,仍然使用了\\\,读者若是知道原因,欢迎留言,本人若今后有时间一读explore expect,也会对此博客做更新。

7、脚本执行的命令必须在脚本开头的PATH=..中包含该命令的绝对路径,这一点在嵌入式实现中非常重要。

测试scp指令的嵌入式执行。

which scp,输出结果

/usr/local/bin/scp

添加到path中去,

PATH=...:...:/usr/local/bin

 下面就可以正常实现scp指令了。

8、使用cron来完成自动周期上传信息的功能。

crontab -e用来编辑需要自动完成的指令,通常的格式是

* * * * * command

前五个星号在其后分别添加分时日年等日期信息,如果想要周期执行则在其后添加“/intervel”,command部分可以填写需要执行的某条指令,也可以填写脚本的名称,如/home/upload.sh

具体可以详见如下链接:

http://www.cnblogs.com/youyou/archive/2007/01/20/625365.aspx

http://www.cnblogs.com/aix1314/archive/2013/03/20/2971004.html

编辑完成后使用crontab -l查看是否编辑正确,最后运行cron/crond start启动周期执行。在嵌入式linux和PC的linux中有些微的区别,具体可以输入cron 再敲tab键看看各自系统中是哪一个指令。

关闭cron的方式一般来说是cron/crond stop,但是一般都关闭不成功,所以需要将进程直接关闭,查看进程的方法是 pgrep cron,直接kill `pgrep cron`相应关闭即可。

此外,查看进程是否周期执行的方式可以到日志中查询,在嵌入式linux中可以查看/var/log/message中查看是否存在cron的指令执行,在PClinux中可以查看/var/log/system.log中是否存在和cron相关的执行日志。

另外:注意,嵌入式linux系统cron的执行需要目录:/var/spool/cron/crontabs,所需需要手动建立该目录。

9、前述提到expect的用法,由于如果是第一次scp,在过程中认证不能建立,会出现询问是否要继续连接,这是需要填写yes/no,之后再填密码,因此涉及到expect的case选择,在此,我们使用了expect的选择语句,建立例程如下:

server.sh

#!/bin/bash


echo "*******************************"

echo " ***************************"

echo "A:The authenticity of host '192.168.2.1 (192.168.2.1)' can't be established.

echo "Are you sure you want to continue connecting (yes/no)?"

read choice


echo "A:server@192.168.2.1's password:"

read password

if [ "$password" == "password" ];then

echo "A:passed"

read answ

else

echo "A:failed"

read fail

fi

echo " ***************************"

echo "*******************************"


host.sh

#!/bin/bash

function_test(){

expect<<-END

spawn ./talk.sh


expect {

"Are you sure you want to continue connecting (yes/no)?"{send "yes\r";exp_continue}

"server@192.168.2.1's password:"{send "password\r"}

}

expect {

"passed"{send "It worked!\r"}

"failed"       {send "It doesn't worked!\r"}

}

expect eof

exit

END

}

function_test

10、变量嵌套

为了使变量中嵌套变量,需要使用eval来完成嵌套,eval完成的功能是对命令的二次扫扫描,例如:

test_1=test

option=1

echo $option_$test #return $option,that is 1

eval echo \$test_$option #return $test_1

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值