PR

COOLにバックアップ・ディレクトリを削除する

XWSS014758-s

とあるサーバーのバックアップを別のサーバーに送っている(画像はテキトー)。

送り方は単純で、指定したサーバにSSHでログインし、指定ディレクトリの配下に日付でディレクトリを作成し、その中にtar ballで固めたバックアップデータなどを流し込むという方法をとっている。

バックアップには補助する機能が付いているのだけれど、経過日数後に自動削除する機能が正しく動作していない。もしかしたら、日付でディレクトリを作成しているのかもしれないが(何かしら書かれているけれど英文なのであまり読んでない・・)。

ということで、やりたいことは「指定したディレクトリ(/backups)以下のディレクトリ(/YYY-MM-DD)」のうち、「n日経過したディレクトリ」を「削除」するということ。

スポンサードリンク

すでに作成された分もあるから、for文などでぐるぐる回すのもスマートではないし、日付計算が出てくるとややこしくなる。

何かよい方法はないかなーと探していると、「シェルスクリプトで古いファイルの自動削除をするには? | その他(プログラミング)のQ&A【OKWave】」という記事を見つけた。このベストアンサーがCOOLだと感じた。

find somedir -type f -mtime +3 -exec rm {} \;

このベストアンサーは、「指定したディレクトリ以下」かつ「3日以上前に作成された」「ファイル」を「削除」してくれる、というもの。単にfindの用意してくれている機能を使っているだけとも言えるけれど、知らなかった人間からすれば素晴らしいと素直に感心する。

「ディレクトリ」ではなく「ファイル」となっているけれど、タイプ指定を「d」とすればディレクトリが対象になるし、「rm {}」を「rm {} -rf」とでもすればディレクトリを削除してくれそうだ。

動作確認

ターゲット・ディレクトリに移動

$ cd vpsbackups/

今あるものを確認

$ ls
2013-03-30  2013-03-31  2013-04-01  2013-04-02  2013-04-04

ターゲットを確認

いきなり削除はアレなので、表示するだけにする。

$ find ./ -type f -mtime +3 -print
./2013-03-31/example.com.tar.gz.info
./2013-03-31/example.com.tar.gz
./2013-03-31/example.com.tar.gz.dom
./2013-03-30/example.com.tar.gz.info
./2013-03-30/example.com.tar.gz
./2013-03-30/example.com.tar.gz.dom

動作を確認

$ date
Thu Apr  4 22:52:04 JST 2013

today - 0 = 04/04
today - 1 = 04/03
today - 2 = 04/02
today - 3 = 04/01
today - 4 = 03/31

日付を見ると、確かに指定日を経過したものがリストされている。

結論

いろいろ試行錯誤した結果、以下のようになった。

$ find ./ -type d -mtime +3 -exec rm {} -rf \; >/dev/null

「>/dev/null」となっているのは、以下の表示が出るから:

find: `./2013-03-31': No such file or directory
find: `./2013-03-30': No such file or directory

ちなみに、「-exec」のほうに「>/dev/null」を付けても表示されたので、findに付けた。もし、シェルスクリプトで複数のディレクトリに対してループするなら、取り外してしまっても良いかもしれない。

備考

作業中に日付が変わったので、再度テストしたところ、正しく動作しているようだった。ただ、動作確認の途中でディレクトリなどの日時が更新されると対象から外れるようだった。まぁ通常触ることのないディレクトリだし、放置すれば自動的に削除してくれるだろう。

日付の指定方法は幾つかあるので以下を参考に。

参考

改めて確認すると、findには多くのオプションがあるんだな~

# 通常利用の場合はfind を多用してしまいがちだけどlocate のほうが・・

$ find --help
Usage: find [-H] [-L] [-P] [-Olevel] [-D help|tree|search|stat|rates|opt|exec] [path...] [expression]

default path is the current directory; default expression is -print
expression may consist of: operators, options, tests, and actions:

operators (decreasing precedence; -and is implicit where no others are given):
      ( EXPR )   ! EXPR   -not EXPR   EXPR1 -a EXPR2   EXPR1 -and EXPR2
      EXPR1 -o EXPR2   EXPR1 -or EXPR2   EXPR1 , EXPR2

positional options (always true): -daystart -follow -regextype

normal options (always true, specified before other expressions):
      -depth --help -maxdepth LEVELS -mindepth LEVELS -mount -noleaf
      --version -xdev -ignore_readdir_race -noignore_readdir_race

tests (N can be +N or -N or N): -amin N -anewer FILE -atime N -cmin N
      -cnewer FILE -ctime N -empty -false -fstype TYPE -gid N -group NAME
      -ilname PATTERN -iname PATTERN -inum N -iwholename PATTERN -iregex PATTERN
      -links N -lname PATTERN -mmin N -mtime N -name PATTERN -newer FILE
      -nouser -nogroup -path PATTERN -perm [+-]MODE -regex PATTERN
      -readable -writable -executable
      -wholename PATTERN -size N[bcwkMG] -true -type [bcdpflsD] -uid N
      -used N -user NAME -xtype [bcdpfls]

actions: -delete -print0 -printf FORMAT -fprintf FILE FORMAT -print
      -fprint0 FILE -fprint FILE -ls -fls FILE -prune -quit
      -exec COMMAND ; -exec COMMAND {} + -ok COMMAND ;
      -execdir COMMAND ; -execdir COMMAND {} + -okdir COMMAND ;

Report (and track progress on fixing) bugs via the findutils bug-reporting
page at http://savannah.gnu.org/ or, if you have no web access, by sending
email to <[email protected]>.

参考文献

コメント