結構簡単なbashスクリプトを作っているが、細かい点を忘れがちでここに記す
もはやbashに関係ないものも書いているが..

cronでの多重起動防止 - pidof を使う

例えばrsyncの多重起動を防止したいとして下記のようにします.

[root@c ~]# cat backup_AtoB.bash
#!/bin/bash
 
/usr/bin/rsync -a /home root@destination:/backup/home/
 
[root@c ~]# crontab -e
 
MAILTO=""
 
0 23 * * * /usr/sbin/pidof -x backup_AtoB.bash >/dev/null ||  /root/backup_AtoB.bash  >> /root/backup_AtoB.bash.log
 
[root@c ~]#

説明としてはスクリプト「backup_AtoB.bash」プロセス番号を探して掲示します.
「||」で繋いでいるので、前段(/usr/sbin/pidof -x backup_AtoB.bash >/dev/null)が失敗したら、後段(/root/backup_AtoB.bash >> /root/backup_AtoB.bash.log)を実行します
前段の失敗とはそのようなプロセスがない. つまりは「backup_AtoB.bash」プロセスが存在しないことを意図します.

「backup_AtoB.bash」プロセスが存在していれば、「||」の後段には進みません

スクリプト名で判断するので同じ名前のスクリプトが走っていると誤作動するかも.

parallel

注意
CentOSにはパッケージ[moreutils-parallel.x86_64]と[parallel.noarch]があります
■[moreutils-parallel.x86_64]なら

parallel [option] [実行コマンド] -- [引数(変数かな?)]
 
例:
[saber@c Movies]$ parallel -j3 -i relion_convert_to_tiff --compression zip --deflate_level 9 --i {} -- *.mrc
 
-jはパラレル数
-iは引数の結果を{}で代用する

■[parallel.noarch](通称「GNU Parallel」)なら

(--dry-runで確認)
[saber@c Movies]$ ls *.mrc | parallel --dry-run relion_convert_to_tiff --compression zip --deflate_level 9 --i {}
(実行)
[saber@c Movies]$ ls *.mrc | parallel relion_convert_to_tiff --compression zip --deflate_level 9 --i {}

「-j」で同時実行数を決められるが、何も指定しないとthreads数で投げしてくれる

8には注意

a="0008"
echo $(($c))

を実行すると「行 2: 0008: 基底の値が大きすぎます (エラーのあるトークンは "0008")」と言われる。

a="0008"
echo $((10#$c))

と修正すればok

ファイルの存在が確認できたら実行する

前段での処理が完了して、その出力ファイルの存在を確認したら次のステップへ進ませる

until [ -r Micrographs/$seqfile ] ; do sleep 1; done

findで見つけたファイルをtarで固める

tar . -name \( '*.html' -o -name '*.htm' \) -print0 |  tar czf find.tar.gz --null -T -

繰り返して実行する

while true ;do echo `date '+%y%m%d %H%M%S'` $(sensors | head -n +3 | tail -n 1 ); sleep 10; done;
 
while true; do echo `date '+%y%m%d %H:%M:%S'`  $(smartctl -d scsi -a /dev/nvme0n1 -T permissive | grep "Current Drive"|awk '{print $4}'); sleep 10 ;done;

pidに関係するファイルをみる

lsof -p <pid>
 
watch -n 2 lsof -p <pid>     <-- 2秒ごとにlsofの内容を表示する

○行目以降を表示

qstatの表示で上二行を省いて表示

qstat | tail -n +3

ヒアドキュメント

cat << _EOF_  > README.1st
どうして
こうなった?
_EOF_

変数に収めるなら

l=$(cat <<_EOF_
どうしても
こうなる
_EOF_ 
)             #改行して「)」を入れる

awk

awkをbashで使ったので
unixユーザで、uidが1000以上のユーザリストを取得する

[foo@c ~]$ getent passwd |awk -F: '$3>1000{print $1}'

「-F」はデミリタ、「$3」でUIDの部分を示してそれが1000より大きいのを持って来て、「{print $1}」でアカウント名を表示

標準出力

標準出力、標準エラー共に一つのファイルに入れる. 「2>1&」を使う

[foo@c ~]$ ./bash.cmd  > log  2>&1

他にも「./bash.cmd >& log」、「./bash.cmd &> log」

共に出力しないなら「2>1&」と「/dev/null」を使って

[foo@c ~]$ ./bash.cmd  > /dev/null 2>&1

どちらとも別々のファイルに入れたい. log1(標準出力)、log2(標準エラー)

[foo@c ~]$ ./bash.cmd  1> log1  2> log2

標準エラーは画面に出しつつファイルにも書いて欲しい。標準出力はいらね.
teeコマンドは標準出力をファイルに落としてくれるが、標準エラーは見ない。
なので一旦エラーの識別子(2)を(1)に変更して、パイプ(|)で渡す

[foo@c ~]$ { ./bash.cmd   3>&2  2>&1  1>&3 | tee log1; }  2> /dev/null

留意 先頭の「{」の後は空白が必要
「3>&2 2>&1 1>&3」の考え方だけど、1と2を入れ替えただけ。イメージは下記のような感じ
2017y08m23d_190145715.png 最終的に1と2が入れ替わった

for文

よく使います. フォルダ内のファイルを処理したい場合

#!/bin/bash
IFS=$'\n'               # IFS="$'\n'$'\t' " デフォルト値だと改行、タブ、スペースが区切りと見做される
for f in `ls /tmp`; do
  echo $f
done

そのフォルダが複数ある場合

#!/bin/bash
etc=`ls -d /etc/*`       #/etc直下のファイルをフルパスで表記
tmp=`ls -d /tmp/*`       #同/tmp直下も
for f in $etc $tmp; do   # 2つの変数を同時に扱う
  echo $f
done

特定のファイルで

#!/bin/bash
mrcs=$(find /data4 -type f -name "*.mrcs" | grep -e "[0-9]\{4\}_[0-9]\{2\}") # "2012_06"とかを含むmrcsファイル
for f in $mrcs; do
  echo $f
done

連番のファイルにしたい

#!/bin/bash
mrcs=$(find /data4 -type f -name "*.mrcs")
i=1
for f in $mrcs; do
  cmd="ln -s $f $(printf "%04d" $i).mrcs"   #一旦コマンドラインに整形して、次の行で実行
  $cmd
  i=$(expr $i + 1)
done

既に連番を持ったファイルで偶数番号のファイルだけを拾いたい

#!/bin/bash
tif=$(find . -name "*.tif")
i=1
for f in $tif; do  #aaaa
   num=$(echo $f | cut -c6-9|bc)   # ファイル名の連番部分を切り出して(cut)、数字にします(bc)
   if [ $(($num%2)) == 0 ]; then   # 2で割った余りで偶数/奇数を見る
     echo $f
   fi
done

for文 一行で

for i in `ls *.tif`; do echo $i ;done

一分ごとにコマンドを実行

for i in `ls *.tif`;do echo $i; cp $i /xxx/xxx/Micrographs/ ;sleep 60; done

超簡易並列

多数のディレクトリに対して処理を施したいが、どうせなら複数のジョブを流して対処したい
っで作ってみた

#!/bin/bash

cat <<'_EOF_'>run.$$.sh            # 個々のディレクトリで動くスクリプト
#!/bin/bash
echo start:`date '+%y%m%d %H:%M:%S'`
expr `cat max |bc` - 1 > max

<目的の処理>

expr `cat max |bc` + 1 > max
echo end:`date '+%y%m%d %H:%M:%S'`
_EOF_
chmod +x run.$$.sh

echo 8 > max.                  # 同時実行数

for d in `find . -maxdepth 2  -mindepth 2 -type d`; do   # ターゲットのディレクトリを取得
  ./run.$$.sh $d &             # 「&」でバックグラウンド処理へ回す
  sync                         # 「max」ファイルの同期に必須
  if [ $(expr `cat max`) -eq 0 ]; then
     while :
     do
       sleep 10
       echo "break:" `cat max`
       if [ $(expr `cat max`) -gt 0 ]; then
         break
       fi
     done
  fi
done
rm -f run.$$.sh max

文字列操作

pid=12345.chaperone.jp
 
echo ${pid%%.*} ---> 12345
 
echo ${pid%.*}  ---> 12345.chaperone
 
echo ${pid#*.}  ---> chaperone.jp
 
echo ${pid##*.} ---> jp
 
#-------------------------------#
 
dir="/var/lib/pbs"
 
echo ${dir##*/} ---> pbs                  *注意 dir="/var/lib/pbs/"なら ""(なし)になる
 
echo ${dir#*/}  ---> var/torque/pbs
 
echo ${dir%/*}  ---> /var/torque          *注意 dir="/var/lib/pbs/"なら "/var/torque/pbs"となる
 
echo ${dir%%/*} ---> "" (なし)
 
#-------------------------------#
tif="Micrographs/s1_100001_movie.tif"
 
echo ${tif/_movie.tif}.mrc --> Micrographs/s1_100001.mrc

空行とコメント行(#)を取り除くには

[root@c ~]# sed '/^#/d' /etc/chrony.conf | sed '/^$/d'
server ntp.nict.jp iburst
driftfile /var/lib/chrony/drift
makestep 1.0 3
rtcsync
keyfile /etc/chrony.keys
leapsectz right/UTC
logdir /var/log/chrony
[root@c ~]#

マシン同士のバックアップ

方法はたくさんある。
rsync, rsnapshot, lsync,,
簡単に

#!/bin/bash
#
log=backup.log
#
d=$(date +%y%m%d_%H%M%S)
#
if [ -f runfile ];then
   echo "This backup script is already running ($d)"
   exit
else
 
/bin/cat <<_EOF_>runfile
start: $d
_EOF_
 
cmd="rsync -avz -delete --log-file=/var/log/rsync-`date +"%Y%m%d-%H%M"`.log \
--log-file-format=\"%o %f (%U %B) %l %b\"  /home/ root@backup:/backup/home/"
 
$cmd
/bin/rm -f runfile
 
fi

容量確認

みかんせい

d=$(/usr/bin/df -l -t xfs -h | /usr/bin/grep data| /usr/bin/awk '{print $6}'| /usr/bin/sort -n)
for i in $d ;do
 
  find $i -mindepth 1  -maxdepth 1 -type d -exec du -hs {} \;
 
don
最新の60件
2024-09-16 2024-09-14 2024-09-12 2024-09-09 2024-09-08 2024-09-06 2024-09-05 2024-09-04 2024-09-02 2024-09-01 2024-08-31 2024-08-28 2024-08-21 2024-08-18 2024-08-17 2024-08-16 2024-08-15 2024-08-14 2024-08-11 2024-08-09 2024-08-01 2024-07-27 2024-07-26 2024-07-16 2024-07-15 2024-07-12 2024-07-07 2024-06-22 2024-06-21 2024-06-17 2024-06-14 2024-06-11 2024-06-10 2024-06-08 2024-06-07 2024-06-02 2024-06-01 2024-05-30 2024-05-16 2024-04-26 2024-04-15 2024-04-11

edit


トップ   編集 差分 履歴 添付 複製 名前変更 リロード   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS
Last-modified: 2020-06-22 (月) 06:51:21