![メモリ使用量テスト用スクリプト[閉じる]](https://linux33.com/image/50273/%E3%83%A1%E3%83%A2%E3%83%AA%E4%BD%BF%E7%94%A8%E9%87%8F%E3%83%86%E3%82%B9%E3%83%88%E7%94%A8%E3%82%B9%E3%82%AF%E3%83%AA%E3%83%97%E3%83%88%5B%E9%96%89%E3%81%98%E3%82%8B%5D.png)
アプリケーションメモリリークの解決策を探している間に一時的な倉庫を貼り付けようとしています。私が書いたのは、小さなbash
スクリプトでサーバーのルートディレクトリにあります。スクリプトが実行する必要がある作業は次のとおりです。
- 実行中の場所を取得します。
- スクリプトがcrontabであることを確認する
- crontabにない場合は、crontabに追加して5分ごとに実行します。
- メモリをテストし、%がPercentage_allowedより高いことを確認してください。
- 上記のテストが完了したら、nginxとphp-fmpサービスを再起動してください。
memory_protect.sh
:
#!/bin/sh
cronfile=memory_protect.sh #NOTE THIS SHOULD DETECT IT'S SELF
path=pwd #this is the path to the file
percent_allowed=80 #this should be max memory before action
has_cron(){
#is the file in the cron?
return [[ crontab -l | egrep -v '^$|^#' | grep -q $cronfile ]] && return 1 || return 0
}
test_memory(){
memusage=`top -n 1 -b | grep "Mem"`
MAXMEM=`echo $memusage | cut -d" " -f2 | awk '{print substr($0,1,length($0)-1)}'`
USEDMEM=`echo $memusage | cut -d" " -f4 | awk '{print substr($0,1,length($0)-1)}'`
USEDMEM1=`expr $USEDMEM \* 100`
PERCENTAGE=`expr $USEDMEM1 / $MAXMEM`
#if it's above 80% alert
return [[ $PERCENTAG>$percent_allowed ]] && return 1 || return 0
}
if [[ has_cron -eq 0 ]]
then
#was not here so add
#run this script every 5 mins
*/5 * * * $path/$cronfile
fi
if [[ test_memory ]]
then
#clear some memory
/etc/init.d/nginx restart
/etc/init.d/php-fpm restart
fi
メモリテストを独自に実行してみるとうまくいくようですが、これはできないようです。
修正するdos2unix
ファイルで実行する必要がありますが、最終的には各関数の条件に対する戻りが発生することに気づきました。したがって、この方法は機能しません。今、そのドアが見つからないようです[[
。if
アップデート2 詳しく見ると、サービスを再起動していますが、cronジョブを入れていないため、実行中のものは見えません。
#!/bin/bash
cronfile=memory_protect.sh #NOTE THIS SHOULD DETECT IT'S SELF
path=pwd #this is the path to the file
percent_allowed=80 #this should be max memory before action
has_cron(){
#is the file in the cron?
#return 0 #returning this just to test should
#be the next line but it's not working
return 0
[[ crontab -l | egrep -v '^$|^#' | grep -q $cronfile ]] && return 1 || return 0
}
test_memory(){
memusage=`top -n 1 -b | grep "Mem"`
MAXMEM=`echo $memusage | cut -d" " -f2 | awk '{print substr($0,1,length($0)-1)}'`
USEDMEM=`echo $memusage | cut -d" " -f4 | awk '{print substr($0,1,length($0)-1)}'`
USEDMEM1=`expr $USEDMEM \* 100`
PERCENTAGE=`expr $USEDMEM1 / $MAXMEM`
#if it's above 80% alert
[[ $PERCENTAG -gt $percent_allowed ]] && return 1 || return 0
}
if [[ has_cron -eq 0 ]]
then
#was not here so add
#run this script every 5 mins
#crontab -e */5 * * * $path/$cronfile
cat <(crontab -l) <(echo "*/5 * * * $path/$cronfile") | crontab -
else
echo "cron present"
fi
if [ test_memory ]
then
#clear some memory
sudo /etc/init.d/nginx restart
sudo /etc/init.d/php-fpm restart
fi
今はほとんど修正されたと思います。
答え1
Bashスクリプトを介してcrontabエントリを生成するには、次の行を変更する必要があります。
*/5 * * * * $path/$cronfile
次の場合:
# Write out current crontab
crontab -l > mycron
# Echo new cron into cron file
echo "*/5 * * * * $path/$cronfile" >> mycron
# Install new cron file
crontab mycron
rm mycron
このライナーを使用してすべての操作を実行することもできます。
cat <(crontab -l) <(echo "*/5 * * * $path/$cronfile") | crontab -
あなたのスクリプト
これは私のために働いた修正されたスクリプトバージョンです。
#!/bin/sh
cronfile=memory_protect.sh #NOTE THIS SHOULD DETECT IT'S SELF
path=$(pwd) #this is the path to the file
percent_allowed=80 #this should be max memory before action
has_cron(){
#is the file in the cron?
#return 0 #returning this just to test should
#be the next line but it's not working
if crontab -l | egrep -v '^$|^#' | grep -q $cronfile; then
return 1
else
return 0
fi
}
test_memory(){
memusage=$(top -n 1 -b | grep "Mem")
MAXMEM=$(echo $memusage | cut -d" " -f2 | awk '{print substr($0,1,length($0)-1)}')
USEDMEM=$(echo $memusage | cut -d" " -f4 | awk '{print substr($0,1,length($0)-1)}')
USEDMEM1=$(expr $USEDMEM \* 100)
PERCENTAGE=$(expr $USEDMEM1 / $MAXMEM)
#if it's above 80% alert
[[ $PERCENTAG>$percent_allowed ]] && return 1 || return 0
}
if has_cron;
then
#was not here so add
#run this script every 5 mins
#crontab -e */5 * * * $path/$cronfile
#cat <(crontab -l) <(echo "*/5 * * * $path/$cronfile") | crontab -
crontab -l > mycron
# Echo new cron into cron file
echo "*/5 * * * * $path/$cronfile" >> mycron
# Install new cron file
crontab mycron
rm mycron
else
echo "cron present"
fi
if test_memory;
then
#clear some memory
echo "/etc/init.d/nginx restart"
echo "/etc/init.d/php-fpm restart"
fi
はい
$ ./memory_protect.sh
/etc/init.d/nginx restart
/etc/init.d/php-fpm restart
$ crontab -l
*/5 * * * * /home/saml/tst/91789/memory_protect.sh
nginx
スクリプトを実際に再起動してサービスできるようにするには、これら2行を変更する必要がありますphp-fpm
。
次の行を変更してください: echo "/etc/init.d/nginx restart" echo "/etc/init.d/php-fpm restart"
これらのために:
/etc/init.d/nginx restart
/etc/init.d/php-fpm restart
スクリプトが正しく実行されていることを確認するためにこれを行います。注:sudo
このスクリプトをroot以外のユーザーとして実行している場合は、これらの再起動行の前に!
sudo /etc/init.d/nginx 再起動 sudo /etc/init.d/php-fpm 再起動
これを使用するには、NOPASSWD
両方のスクリプトに対する最小限の権限が必要な場合があります。それ以外の場合は、cronを所有しているユーザーがパスワードを入力するのを待ちます。
crontabエントリが存在しませんか?
crontabがディレクトリに作成されていない場合、この問題が発生します/var/sppol/cron
。次のように実行すると、この問題が発生しますcrontab -l
。
$ crontab -l
no crontab for saml
もう一度確認してください:
$ sudo ls -l /var/spool/cron/
total 0
-rw------- 1 root root 0 Sep 16 23:47 root
したがって、単に編集し、空のファイルを保存して作成するとします。
$ crontab -e
# now you're in the vim editor, add a empty line
# type "i", hit return, hit Escape,
# and do a Shift + Z + Z to save!
これで以下が表示されます。
$ crontab -l
$
これ:
$ sudo ls -l /var/spool/cron/
total 0
-rw------- 1 root root 0 Sep 16 23:47 root
-rw------- 1 saml root 0 Sep 21 16:20 saml
サービスの再起動
直面するもう1つの問題は、このcrontabエントリがuser1ユーザーとして実行されている場合、user1がsudo
それを再起動するには権限が必要であることです。
答え2
私は使用します監視装置そのために
あなたの要件のためのmonitスクリプトの例は次のとおりです。
check process nginx with pidfile /var/run/nginx.pid
start program = "/etc/init.d/nginx start"
stop program = "/etc/init.d/nginx stop"
if memory usage > 95% then restart
group www-data
if 5 restarts within 5 cycles then timeout
5回再起動しようとしました。モニターが失敗した場合、競合状態を避けるためにWebサーバーを5回再起動しました。