Bash 스크립트에서 루프를 만드는 방법

Bash 스크립트에서 루프를 만드는 방법

나는 다음 스크립트를 작성했습니다. udev에 의해 호출됩니다. 외부 USB 하드 드라이브를 연결하면 스크립트는 볼륨이 truecrypt로 마운트되었는지 확인하고, 그렇지 않은 경우 마운트하고, 마운트된 경우 폴더의 모든 파일을 외부 하드 드라이브에 복사합니다. 복사가 완료된 후 볼륨이 여전히 truecrypt에 의해 마운트되어 있는지 확인합니다. 그렇다면 제거를 시도하고, 그렇지 않으면 나에게 이메일을 보냅니다.

제가 구현하고 싶은 것은 볼륨이 마운트되었는지 재귀적으로 확인하는 방법입니다. 즉, 볼륨이 여전히 마운트되어 있으면 볼륨이 마운트되지 않았음을 확인하고 이메일을 보낼 때까지 마운트 해제를 시도해야 한다는 의미입니다.

더 명확하게 말하면 Windows cmd에서는 GOTO 태그를 사용하지만 Linux bash에는 GOTO가 없습니다.

#!/bin/sh
# 
############ Parameters ############
from="from"
dest="dest"
smtp="smtp"
username="username"
pass="pass"
message="Sync to hard disk 1TB completed. You shall now remove the external hard drive."
subject="Sync to hard disk 1TB completed."
file="/media/truecrypt2/sync/dummy.file"
sendanemail="sendEmail -f $from -t $dest -u $subject -s $smtp -xu $username -xp $pass -m $message"
############ End Parameters ############

sleep 4
touch $file

if [ -f $file ];
then
   cp /storage/sdf1/folder/*.txt /media/truecrypt2/sync/ -n -r
   cp /storage/sdf1/folder/*.jpg /media/truecrypt2/sync/ -n -r
else
   echo "truecryptpassword" | truecrypt /dev/sdj1 /media/truecrypt2 -t -k="" --protect-hidden=no -p=""
   cp /storage/sdf1/folder/*.txt /media/truecrypt2/sync/ -n -r
   cp /storage/sdf1/folder/*.jpg /media/truecrypt2/sync/ -n -r
fi

sleep 4

if [ -f $file ]
then
   truecrypt -d /dev/sdj1
   if [ -f $file ]
   then
     truecrypt -d /dev/sdj1
   else
     $sendanemail
   fi
else
   $sendanemail
fi

답변1

while true; do
   if [ -f $file ]; then
       truecrypt -d /dev/sdj1
       break
   fi
       $sendanemail
       sleep n # change n to number of seconds to pause 
done

루프는 명령문 실행이 완료될 while때까지 영원히 계속 실행됩니다 . true로 평가 break되면 [ -f $file ]해당 코드 블록이 실행되고 break루프가 종료됩니다. 그렇지 않으면 $sendemail실행되고 sleep n루프가 다시 시작됩니다.

답변2

while [[ -f $file ]]; do
    truecrypt -d /dev/sdj1
    sleep 10    # pause for 10 seconds
done
$sendanemail

귀하의 $subject메시지가 "완료"인 것을 고려하면 귀하는 이메일만 보내기를 원한다고 가정합니다.

이 버전은 성공할 때까지 반복적으로 truecrypt 드라이브 분리를 시도한 다음 이메일을 보냅니다.

USB 드라이브를 마운트 해제할 수 없으면 무한 루프가 발생합니다. 또 다른 접근 방식은 스크립트에 시간 초과를 추가하는 것입니다.

attempts=5
while [[ -f $file ]]; do
    truecrypt -d /dev/sdj1
    sleep 10

    attempts=$(($attempts - 1))
    if [[ $attempts -eq 0 ]]; then
        subject="Failed to unmount /dev/sdj1"
        message="Cannot umount external hard disk.  Please verify sync to hard disk 1TB completed and manually unmount the external hard disk before removal."
        sendanemail="sendEmail -f $from -t $dest -u $subject -s $smtp -xu $username -xp $pass -m $message"
        break
    fi

    # attempts=$(($attempts - 1))  # this adds an extra attempt
done
$sendanmail

답변3

글쎄, 필요한 사람을 위해 여기에 내 최종 스크립트가 있습니다. 매력처럼 작동하는 것 같습니다.

#!/bin/sh
#
# Comments....

############ Parameters ############
attempts="3"
from="[email protected]"
to="[email protected]"
smtp="smtp.example.com:25"
username="[email protected]"
pass="emailpass"
message="Sync to hard disk 1TB completed. You shall now remove the external hard drive."
subject="SRVR: Sync to hard disk 1TB completed."
file="/media/truecrypt2/sync/dummy.file"
sendanemail="sendemail -f $from -t $to -u $subject -s $smtp -xu $username -xp $pass -m $message"
subjectfail="Unable to umount external hard disk."
messagefail="Unable to dismount external hard disk after $attempts attempts. Please check it."
sendanemailfail="sendemail -f $from -t $to -u $subjectfail -s $smtp -xu $username -xp $pass -m $messagefail"
############ End Parameters ############

sleep 4

touch $file

if [ -f $file ];
then
   cp /storage/sdf1/folder/*.txt /media/truecrypt2/sync/ -n -r
   cp /storage/sdf1/folder/*.jpg /media/truecrypt2/sync/ -n -r
else
   echo "my truecrypt password" | truecrypt /dev/sdj1 /media/truecrypt2 -t -k="" --protect-hidden=no -p=""
   cp /storage/sdf1/folder/*.txt /media/truecrypt2/sync/ -n -r
   cp /storage/sdf1/folder/*.jpg /media/truecrypt2/sync/ -n -r
fi

sleep 0

while [ -f $file ]; do
    truecrypt -d /dev/sdj1
    sleep 5

    attempts=$(($attempts - 1))         # decrement timeout counter.
    if [ $attempts -eq 0 ]; then
      $sendanemailfail
      break
    fi

    [[ ! -f $file ]] && $sendanemail    # only send email once when `truecrypt -d` succeeds.
done

관련 정보