目次

Unixで最新のファイルがあるディレクトリ一覧を作る

2015/02/15
解説入れておけよ、と高飛車に言われたので小心者の私は従いました。

2015/02/12
awkコマンド使用でつっこみあったので対応

2015/02/11
自分の理解の整理も兼ねてのメモ。備忘録。

「最新のファイル」の定義

ここで言う「最新のファイル」は、「1日前からスクリプト実行日時まで」のタイムスタンプを持つファイルを指すものとする。

以降の例では、findコマンドの -mtime オプションを適用し、コマンド実行日時を「最新の日時」と定め、この日時を元にファイルのタイムスタンプの条件を設定している。

例1:最新のタイムスタンプを持つファイルを一覧させる

find /home/user/work -type f -size -1000c -mtime -1 | sort

findコマンドでファイル一覧を出力。条件は以下。

見た目を揃えたいので sortコマンドでソートをかけた一覧に変更。なくてもいい。

例2:最新のタイムスタンプを持つファイルが存在するディレクトリを一覧させる

find /home/user/work -type f -size -1000c -mtime -1 | sed -E "s/\/[^\/]+$//" | uniq | sort

findコマンドでファイル一覧を出力。条件は以下。

sedコマンドでファイル一覧のファイルの部分を削除。

uniqコマンドでディレクトリ名の重複を消す。

uniqコマンドの出力で問題なければsortコマンドは使わなくてもいい。

別に最短一致させなくても大丈夫じゃないか、の指摘があったのでawkコマンドからsedコマンドに置き換えした。

追記:各ディレクトリで一番新しいファイル一覧が欲しいんじゃ

newerlist.sh
for arg in `find /home/user/work -type d`
do
 filename=`ls -F1tr "${arg}"/ | grep -v "/$" | tail -1`
 if test -n "${filename}" ; then
   echo "${arg}/${filename}"
 fi
done

for文がfindコマンドの出力行数だけdo~doneの間の処理を繰り返す。10行出力されたなら10回ループ。変数$argに行の内容が入る。

findコマンドはディレクトリ /home/user/work 以降に配置されているサブディレクトリの一覧を出力。 -type d がその指定。

lsコマンドでfindコマンドの示すサブディレクトリ内の一覧を出力。タイムスタンプの昇順に出力される。

grepコマンドで最後が”/“の行をフィルタして出力しない。

tailコマンドはheadコマンドの逆。-1 の指定で入力した一覧の最終行を出力。最終行はそのディレクトリ内で一番新しいファイルを指す。

if文の行はファイルが存在しないディレクトリだった時の為のもの。test -n は指定の文字列が長さゼロではないか否かの判定。長さゼロでなければ真。

ワンライナーにする方法が思いつかなかったので、シェルスクリプトでfindコマンドの出力結果でループしながらディレクトリ毎に確認しています。
一番新しいファイル(タイムスタンプが同じファイル)が二つ以上ある場合、どれが採用されるのかはファイル名によって決まるんじゃないかな。