Я пишу маленький сценарий для загрузки файлов на удаленный ssh сервер, и на удаленном ssh сервере я буду иметь почти 2 TB
из доступного Пространства.
Я должен проверить в рамках сценария оболочки, если Пространство вокруг 1.5 TB
полный, чем sleep the script
и **start the script again**
однажды его движения назад это возвращается к 1TB
вот моя часть кода, который должен выполнить логику для проверки размера каталога и затем поместить ее в if else statements
SIZE="$(ssh archiveupload@REMOTESERVER-IP "du -s")"
LIMIT="1.5TB"
if [ $SIZE -gt $LIMIT ];
then
sleep 4h
elif
continue ;
fi
СЦЕНАРИЙ ОБНОВЛЕНИЯ:
if [ ! -f /home/user/Tupload/upload-lock ]; then
touch /home/user/Tupload/upload-lock
###Define the File in unix style#############
filename="/home/user/Tupload/20186.txt"
####starting of the while loop.###########
LIMIT='1500000000'
while read line;
do
name="${line%$'\r'}"
SIZE="$(ssh -n USER@REMOTEIP"df /var/www/Upload/" | awk 'NR > 1 {print $4; exit}')"
if [[ $SIZE -gt $LIMIT ]]
then
YEAR=$(echo $name | cut -c 1-4) #####define the Year from the read line ####
MONTH=$(echo $name | cut -c 5-6) #####Define the Month from the read line####
DAY=$(echo $name | cut -c 7-8) #####Define the DAY from the read line####
YM=${YEAR}-${MONTH} ####define the Year and Month######
april="2017-04"
may="2017-05"
june="2017-06"
march="2017-03"
######if else statement ######
if [ "$april" = "$YM" ]; then
cd /mnt/smxfxml/$YEAR/April/
elif [ "$may" = "$YM" ]; then
cd /mnt/smxfxml/$YEAR/May/
elif [ "$june" = "$YM" ]; then
cd /mnt/smxfxml/$YEAR/June/
elif [ "$march" = "$YM" ]; then
cd /mnt/smxfxml/$YEAR/March/
else
cd /mnt/smxfxml/$YEAR/$YM/
fi
ssh USER@REMOTEIP"mkdir $YEAR/$MONTH/$DAY/$name/" < /dev/null
scp $name.mxf USER@REMOTEIP:$YEAR/$MONTH/$DAY/$name/
cd /mnt/smxfxml/XML/$YEAR/$YM/
scp $name.xml USER@REMOTEIP:$YEAR/$MONTH/$DAY/$name/
else
echo 'Not enough space.'; sleep 4h
fi
done <"$filename"
rm -rf /home/user/Tupload/upload-lock
exit 0
else
sleep 0
fi
exit 0
Благодаря pa4080 для "свободного пространства" один лайнер.
Теперь, когда Вы совместно использовали свой сценарий:
Это будет трудным, потому что мы не можем использовать continue
в while read line
цикл, не пропуская строки.
Вы хотите приостановить сценарий, когда существует не больше, чем свободные 0.5 ТБ, и резюме, когда существует свободный по крайней мере 1 ТБ.
Для хранения сценария коротким и человекочитаемым определите функцию, которая говорит Вам, если существует достаточно пространства на сервере и берет минимальный размер в качестве параметра:
enough_space () {
local limit=$1
free_space="$(ssh -n user@host "df /" | awk 'NR > 1 {print $4; exit}')"
[ $free_space -ge $limit ]
}
... и любой сон, в то время как недостаточно пространства:
while ! enough_space $limit; do
sleep 4h
done
... или сон до достаточного количества пространства:
until enough_space $limit; do
sleep 4h
done
Поместите это в начале своего сценария:
pause_limit='500000000' # 0.5TB free space
resume_limit='1000000000' # 1.0TB free space
enough_space () {
local limit=$1
free_space="$(ssh -n user@host "df /" | awk 'NR > 1 {print $4; exit}')"
[ $free_space -ge $limit ]
}
Мы представим "большое количество" while
цикл в существующем while
цикл. Это позволяет нам повторить тот же файл снова, когда не было достаточного свободного пространства первый раз. Кроме того, присвоение переменных не зависит от свободного пространства сервера, таким образом, это должно быть сохранено за пределами if
оператор (и внутреннее while
цикл).
####starting of the while loop.###########
while read line; do
#### this can all be done before checking the server's free space
# name="${line%$'\r'}"
# YEAR=$(echo $name | cut -c 1-4)
# .
# .
######if else statements ######
# if [ "$april" = "$YM" ]; then
# .
# .
# fi
while true; do
if enough_space $pause_limit;
then
ssh USER@REMOTEIP"mkdir $YEAR/$MONTH/$DAY/$name/" < /dev/null
scp $name.mxf USER@REMOTEIP:$YEAR/$MONTH/$DAY/$name/
cd /mnt/smxfxml/XML/$YEAR/$YM/
scp $name.xml USER@REMOTEIP:$YEAR/$MONTH/$DAY/$name/
break
else
until enough_space $resume_limit; do
sleep 4h
done
fi
done
done <"$filename"
"Бесконечный" цикл с условием продолжения будет или работать однажды (если будет достаточно свободного пространства на сервере), или дважды (если существует достаточно свободного пространства снова).
Если Вы хотите выполнить свою стандартную программу копии много раз неограниченно долго, используйте бесконечный цикл с условием продолжения (while true; do...
). Не делайте рекурсивных вызовов (называющий сценарий в рамках сценария или функцию в функции), потому что это увеличит размер стека вызовов, и Ваш сценарий откажет рано или поздно.
Это - конечно, только один из многих способов достигнуть того же самого. Одна оборотная сторона этого подхода - то, что каждый раз, когда свободное пространство падает ниже 0.5 ТБ или превышает 1.0 ТБ, будет один ненужный вызов к enough_space
.
Если я неправильно истолковал Ваш вопрос, скажите мне так, что я могу адаптировать свой ответ.
Сначала я пустошь предлагаю, чтобы Вы использовали команду df
получить свободное пространство. Также необходимо обеспечить системный путь (например, /
) или имя устройства (например, /dev/sda1
) сделать вещи простыми. Вывод команды df /
выполняемый на моем VPS похож:
$ ssh -n user@host "df /"
Filesystem 1K-blocks Used Available Use% Mounted on
/dev/vda1 25671932 8335064 16009768 35% /
Нам нужно только свободное место, таким образом, мы можем отфильтровать вывод справкой awk
(например):
$ ssh -n user@host "df /" | awk 'NR > 1 {print $4; exit}'
16009768
Второе использование те же единицы как вывод вышеупомянутой команды (1K-блоки) для значения переменной $LIMIT
: 1,5 ТБ = 1 500 000 000 КБ.
Треть поместила основную логику в функцию, которая назовет себя рекурсивно снова и снова после sleep
команда. Кроме того, места sleep
и continue
должен быть инвертирован, я думаю :)
Согласно выше сценария могло быть что-то как это:
#!/bin/bash -e
LIMIT='1500000000'
# define the function
main() {
SIZE="$(ssh -n user@host "df /" | awk 'NR > 1 {print $4; exit}')"
if [[ $SIZE -gt $LIMIT ]]
then
echo 'continue'
else
echo 'Not enough space.'; sleep 4h
# call the function
main
fi
}
# initial call of the function
main
Согласно комментарию @danzel вместо рекурсии мы можем использовать бесконечный while
цикл:
#!/bin/bash -e
LIMIT='1500000000'
while true
do
SIZE="$(ssh -n user@host "df /" | awk 'NR > 1 {print $4; exit}')"
if [[ $SIZE -gt $LIMIT ]]
then
# remove the exit command if you do not want to interupt the loop
echo 'continue'; exit
else
echo 'Not enough space.'; sleep 4h
fi
done