use strict;
use warnings;
use POSIX qw(strftime); # 日付をフォーマットするために使用
use File::Basename qw(basename); # ファイルパスからファイル名部分のみを取得するために使用
# --- 設定 (ここを編集してください) ---
# 処理対象のフォルダを指定してください。
my $target_directory = "."; # ★★★ 対象フォルダを実際のパスに書き換えてください ★★★
# 対象とするファイルの拡張子を指定してください (ドットなし、例: "txt", "log")
my $file_extension = "txt"; # ★★★ 対象の拡張子を書き換えてください ★★★
# 何日以上前のファイルを古いと判断するかの日数を指定してください
my $days_threshold = 8; # ★★★ 日数を書き換えてください ★★★
# リネーム情報が記載されたバッチファイル名を指定してください (スクリプトと同じフォルダにある前提)
my $rename_batch_filename = "xxx.bat"; # ★★★ バッチファイル名を書き換えてください ★★★
# --- グローバル変数 ---
my %latest_files_in_group; # 各グループの最新ファイル情報
my %rename_map; # リネーム情報 (キー: 新しいファイル名(数値なし), 値: 元のファイル名)
# --- メイン処理 ---
# 0. リネーム情報バッチファイルの読み込み
if (-f $rename_batch_filename) {
open(my $fh_batch, "<", $rename_batch_filename)
or warn "警告: バッチファイル '$rename_batch_filename' を開けませんでした: $!. リネーム前の名前は表示されません。\n";
if ($fh_batch) {
print "リネーム情報ファイル '$rename_batch_filename' を読み込んでいます...\n";
while (my $line = <$fh_batch>) {
chomp $line;
# rename "元のファイル名" "新しいファイル名(数値なし)"
if ($line =~ /^\s*rename\s+"([^"]+)"\s+"([^"]+)"\s*$/i) {
my $original_name_from_bat = basename($1); # 元のファイル名もbasenameで
my $renamed_to_name_base = basename($2); # 新しいファイル名(数値なし)
# 新しいファイル名(数値なし)をキーとして、元のファイル名を保存
$rename_map{$renamed_to_name_base} = $original_name_from_bat;
}
}
close $fh_batch;
print "リネーム情報の読み込み完了。\n";
}
} else {
warn "警告: 指定されたリネーム情報バッチファイル '$rename_batch_filename' が見つかりません。リネーム前の名前は表示されません。\n";
}
# 1. ファイル一覧の取得と解析
my $glob_pattern = "$target_directory/*.$file_extension";
my @filepaths = glob $glob_pattern;
unless (@filepaths) {
print "対象となる *.$file_extension ファイルがディレクトリ '$target_directory' に見つかりませんでした。\n";
print "指定したパスや拡張子が正しいか、そのフォルダに該当ファイルが存在するか確認してください。\n";
exit;
}
my $escaped_extension = quotemeta($file_extension);
foreach my $filepath (@filepaths) {
my $filename = basename($filepath);
# グループ名(スペース含む可能性あり) <スペース1つ> 数値 .拡張子
if ($filename =~ /^(.*?) (\d+)\.$escaped_extension$/) {
my $group_name_from_file = $1; # ファイルから抽出したグループ名部分
my $number = int($2);
my $timestamp = (stat $filepath)[9];
unless (defined $timestamp) {
warn "警告: ファイル '$filepath' の日時情報を取得できませんでした。スキップします。\n";
next;
}
if ( (not exists $latest_files_in_group{$group_name_from_file}) or
($number > $latest_files_in_group{$group_name_from_file}{number}) ) {
$latest_files_in_group{$group_name_from_file} = {
name => $filename,
number => $number,
timestamp => $timestamp,
path => $filepath
# group_name_key は後で @all_latest_file_details に追加する際に設定
};
}
}
}
unless (keys %latest_files_in_group) {
print "指定された命名パターン(グループ名<半角スペース1つ>数値.$file_extension)にマッチするファイルが\n";
print "ディレクトリ '$target_directory' に見つかりませんでした。\n";
exit;
}
# 2. 各グループで数値が一番高いファイルの一覧を表示
print "\n";
print "------------------------------------------------------------------------------\n";
print "各グループで数値が一番高いファイルの一覧 (対象: $target_directory/*.$file_extension):\n";
print "------------------------------------------------------------------------------\n";
printf "%-30s %-15s\n", "ファイル名", "最終更新日時";
print "-" x (30+1+15), "\n";
my @sorted_group_names = sort keys %latest_files_in_group;
my @all_latest_file_details;
foreach my $group_name_key (@sorted_group_names) { # ループ変数を変更
my $file_info = $latest_files_in_group{$group_name_key};
my $formatted_date = strftime "%Y-%m-%d", localtime($file_info->{timestamp});
printf "%-30s %-15s\n", $file_info->{name}, $formatted_date;
# グループ名も一緒に保存しておく
push @all_latest_file_details, { %$file_info, group_name_for_lookup => $group_name_key };
}
print "------------------------------------------------------------------------------\n";
# 3. 指定された日数以上昔に更新されたファイルのみの一覧を表示 (リネーム前の名前も表示)
print "\n";
print "-------------------------------------------------------------------------------------------------\n"; # 幅調整
print "上記一覧のうち、最終更新日が$days_threshold日以上前のファイルの一覧 (リネーム前情報付き):\n";
print "-------------------------------------------------------------------------------------------------\n"; # 幅調整
printf "%-30s %-15s %-30s\n", "ファイル名", "最終更新日時", "リネーム前";
print "-" x (30+1+15+1+30+2), "\n"; # 幅調整 (リネーム前ファイル名が長くなる可能性を考慮)
my $current_time = time();
my $age_threshold_seconds = $days_threshold * 24 * 60 * 60;
my $cutoff_timestamp = $current_time - $age_threshold_seconds;
my $found_old_files_count = 0;
foreach my $file_detail_item (@all_latest_file_details) { # ループ変数を変更
if ($file_detail_item->{timestamp} < $cutoff_timestamp) {
my $current_filename = $file_detail_item->{name};
my $formatted_date = strftime "%Y-%m-%d", localtime($file_detail_item->{timestamp});
# リネームマップ検索用のキーを作成
# (ファイルから抽出したグループ名 + "." + 設定された拡張子)
my $group_for_lookup = $file_detail_item->{group_name_for_lookup};
my $lookup_key_for_rename_map = $group_for_lookup . '.' . $file_extension;
my $original_name_display = (exists $rename_map{$lookup_key_for_rename_map})
? $rename_map{$lookup_key_for_rename_map}
: "-";
printf "%-30s %-15s %-30s\n", $current_filename, $formatted_date, $original_name_display;
$found_old_files_count++;
}
}
if ($found_old_files_count == 0) {
print "最終更新日が$days_threshold日以上前のファイルはありませんでした。\n";
}
print "-------------------------------------------------------------------------------------------------\n"; # 幅調整
print "\nスクリプトの実行が完了しました。\n";
$a=<>;