bash – 在shell脚本中通过s_client关闭连接
我试图在
shell脚本中建立与IMAP服务器的连接.虽然我可以连接并发出命令,但是合适地关闭连接似乎是不可能的.
这是我正在使用的测试命令: openssl s_client -crlf -connect server:993 <<EOF 01 login USERNAME PASSWORD 02 LIST "" "*" 03 logout EOF 因为一旦输入用完就连接关闭,这会在收到任何输出之前发生,因此我从未收到所需的数据. 如果我添加选项-ign_eof选项,以便它将忽略输入结束以保持连接打开,则根据需要返回输出.但是在连接关闭之后…… * BYE Logging out 03 OK Logout completed. … s_client保持活动状态,因此执行永远不会返回脚本. 是否有解决方案在服务器关闭连接时会导致s_client终止? 或者是否有使用标准工具的替代方法?该脚本将在Mac OS X,Debian和Redhat衍生物上运行,并且可能是Android终端模拟器,因此我想使用相当标准的工具来实现可移植性而不是专业包. 更新:我想出了一个我并不完全满意的答案,但它确实有效.它使用脚本将命令传递给openssl,然后进入无限循环以保持stdin打开,直到它收到一个信号告诉它退出.这是我的测试脚本: #!/bin/sh if [ "$1" = "doit" ]; then trap "echo "04 logout"; exit" SIGUSR1 echo "00 login USERNAME PASSWORD" echo "01 SELECT PID-$$" echo "02 SELECT FOLDER" echo "03 FETCH 1:* (BODY[HEADER.FIELDS (Subject)])" while :; do :; done fi MYFLAG= $0 doit | openssl s_client -crlf -connect server:993 2>/dev/null | while read LINE; do LINE=`echo "$LINE" | tr -d 'r'` [ "${LINE:0:4}" = "* OK" ] && MYFLAG=Y [ "${LINE:0:33}" = "01 NO Mailbox doesn't exist: PID-" ] && PID="${LINE##*PID-}" [ "$MYFLAG" ] && echo "$LINE" [ "$PID" -a "$LINE" = "03 OK Fetch completed." ] && kill -USR1 $PID done echo "Finished." 该脚本使用一个参数调用自身,以输出通过管道连接到openssl的IMAP命令,其输出通过管道传输到读取循环中,以便进行处理. MYFLAG变量仅用于隐藏openssl输出的信息,只是回显服务器连接的输出. 我选择一个虚拟文件夹名称,其中包含脚本第二个实例的PID作为一种传递回来的方法,显然临时文件会更好但是对于测试我想保持一切自包含并能够看到什么正在发生. 一旦显示获取信息并且服务器返回OK响应,它就会向脚本的第二个实例发送SIGUSR1信号,然后发送注销消息并退出,关闭stdin,导致s_client断开连接. 最初我在初始回声集中包含了04 logout命令,但是当我这样做时,读取循环只显示到获取输出然后停止,它甚至没有显示操作的OK状态,尽管收到了所有内容. 此外,我需要使用tr来去除尾随回车符,但是如果我从openssl输出管道,那么读取循环就不会收到任何内容. 解决方法
你可以通过计时输入openssl来解决这个问题.
我能想出的最简单的方法是使用一个回显stdout输入的函数: #!/bin/sh imapscript () { echo '01 login USER PASSWD' echo '02 LIST "" "*"' echo '03 logout' while sleep 1; do echo "04 logout" done } imapscript | openssl s_client -crlf -connect server:993 (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |