我在 Linux 中有一个脚本,它创建一个文件,一旦创建,它就会执行一个 Expect 脚本,将创建的文件上传到 SFTP 服务器。我在 cron 中运行它,无论出于何种原因,上传总是失败,但是当我在 shell 中执行脚本时,上传成功。我检查了日志,它们并没有真正告诉我过程哪里出了问题。
这是 shell 脚本
#!/bin/bash
cd /home/mysql/paradata/repoupload || exit
mv /mnt/restrictedreports/Restricted/Corporate/Accounting/GL2013/gldetail.csv /home/mysql/paradata/repoupload 2>/dev/null
mv /mnt/restrictedreports/Restricted/Corporate/Accounting/GL2013/vgldetail.csv /home/mysql/paradata/repoupload 2>/dev/null
test -f gldetail.csv && ./SAFCO.sh
test -f vgldetail.csv && ./SAFCO.sh
if [ -f vgldetail.csv ]; then filename=vgldetail.csv; fi
if [ -f gldetail.csv ]; then filename=gldetail.csv; fi
if [ $filename == gldetail.csv ];
then
./uploadsafco.exp REPOEX > lastftplogsafco.txt
else
./uploadvafco.exp REPOEX > lastftplogvafco.txt
fi
这是期望的脚本
#!/usr/bin/expect -f
set force_conservative 0 ;# set to 1 to force conservative mode even if
;# script wasn't run conservatively originally
if {$force_conservative} {
set send_slow {1 .1}
proc send {ignore arg} {
sleep .1
exp_send -s -- $arg
}
}
set arg1 [lindex $argv 0]
set timeout 30
expect_after {
timeout { puts "Timeout"; exit 1 }
}
spawn sftp not@this
match_max 100000
expect "password: "
send -- "notapassword\r"
expect -exact "\r
sftp> "
send -- "cd /usr/data/r1/ED\r"
expect "sftp> "
send -- "progress\r"
expect -exact "progress\r
Progress meter disabled\r
sftp> "
send -- "put REPOEX\r"
expect "sftp> "
send -- "chmod 777 REPOEX\r"
expect "sftp> "
send -- "bye\r"
expect eof
exit
答案1
“手动工作,在 cron 中失败”几乎总是由于以下原因之一:
- 环境变量的差异:
PATH
和其他; - 不同的当前工作目录;
- 缺少 TTY(可能不是 Expect 脚本的问题);
- 权限(与一个用户进行交互式测试,与另一用户进行 cron 作业);或者
- 不同的 shell:在 cron 命令行中执行的命令本身使用一个 shell,但您可以交互地使用另一个 shell。
答案2
我的 spawn telnet 脚本也遇到了类似的问题。脚本工作正常,直到添加 expect_after 来处理超时。尝试删除 expect_after { .. }。对我来说没问题。