file-monitor 2.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596
  1. #!/usr/bin/perl
  2. # Daniel "Trizen" Șuteu
  3. # License: GPLv3
  4. # Date: 10 April 2012
  5. # https://github.com/trizen
  6. # Monitor a path for updated files, new files and deleted files.
  7. use 5.010;
  8. use strict;
  9. use warnings;
  10. use File::Find qw(find);
  11. use Time::HiRes qw(sleep);
  12. use Getopt::Std qw(getopts);
  13. use File::Spec::Functions qw(rel2abs);
  14. sub usage {
  15. print <<"USAGE";
  16. usage: $0 [options] [files] [dirs]
  17. options:
  18. -c [i] : monitor for changes interval (in sec)
  19. -n [i] : monitor for new files interval (in sec)
  20. -v : verbose mode
  21. USAGE
  22. exit 1;
  23. }
  24. # Arguments
  25. my %opts;
  26. getopts('c:n:v', \%opts);
  27. my %files;
  28. my @files = grep { -f } @ARGV;
  29. my @directories = grep { -d } @ARGV;
  30. if (!@files and !@directories) {
  31. usage();
  32. }
  33. else {
  34. if (@directories) {
  35. populate_files(1);
  36. }
  37. foreach my $file (map { rel2abs($_) } @files) {
  38. $files{$file} = [-M $file, 0];
  39. }
  40. }
  41. my $monitor_for_changes_interval = $opts{c} // 8;
  42. my $monitor_for_new_files_interval = $opts{n} // $monitor_for_changes_interval**2;
  43. sub populate_files {
  44. my ($first_time) = @_;
  45. find {
  46. no_chdir => 1,
  47. wanted => sub {
  48. -f or return;
  49. -M _ // return;
  50. $files{$_} =
  51. exists $files{$_}
  52. ? [$files{$_}[0] => 0]
  53. : [-M _ => $first_time ? 0 : 1];
  54. }
  55. } => @directories;
  56. }
  57. my $track = 0;
  58. while (1) {
  59. while (my ($file, $info) = each %files) {
  60. if (not -f $file) {
  61. printf "[DELETED]: %s\n", $file;
  62. delete $files{$file};
  63. }
  64. elsif ($info->[1]) {
  65. printf "[CREATED]: %s\n", $file;
  66. $files{$file}[1] = 0;
  67. }
  68. elsif (-M _ != $info->[0]) {
  69. printf "[UPDATED]: %s\n", $file;
  70. $files{$file}[0] = -M _;
  71. }
  72. }
  73. sleep $monitor_for_changes_interval;
  74. printf STDERR "[TOTAL_F]: %d\n", scalar keys %files if $opts{v};
  75. if (($track += $monitor_for_changes_interval) >= $monitor_for_new_files_interval) {
  76. warn "[$track] Looking for new files...\n" if $opts{v};
  77. populate_files(0) if @directories;
  78. $track = 0;
  79. }
  80. }