Beefy Boxes and Bandwidth Generously Provided by pair Networks
Do you know where your variables are?
 
PerlMonks  

Trash temporary files

by bruno (Friar)
on Aug 22, 2008 at 00:27 UTC ( [id://706028]=sourcecode: print w/replies, xml ) Need Help??
Category: Utility Scripts
Author/Contact Info Bruno Vecchi

brunovecchi@yahoo.com.ar

Description:
BACKGROUND
I am a little obsessive with the tidiness of my home folder. I cannot stand seeing loose, uncategorized files scattered everywhere (let alone in the Desktop -- the horror!). But more often than not, i run across files that do not really fit into any particular category, and I also do not know if I'll want to store them permanently or not.
So I have a ~/tmp folder in which I toss "the garbage" there, and every month or so I take a look at it and see what gets deleted and what gets "saved" and categorized.

THE SOLUTION
So I wrote this little script (I think of it as one of those robot-housewives from The Jetsons) that looks into my ~/tmp folder every hour and sends those files that are N days or older (measured as days upon arrival to the ~/tmp folder) to the trash. This gives you a certain time window in which you can re-evaluate the usefulness of that file and rescue it from oblivion or not.

It uses Schedule::Cron, so is cron-independent (and possibly cross-platform). It also uses Config::Tiny to write an editable configuration file. More information in the POD documentation within the script.

DISCLAIMER
Probably this program won't be of much use to anyone, specially the sysadmins around here. But I wrote it to solve a very peculiar need of mine, and seemed like a good idea to post it here in case that someone else happens to make a good use of it.

#!/usr/bin/perl
use strict;
use warnings;
use Schedule::Cron;
use File::HomeDir;
use Config::Tiny;
use DirHandle;
use File::Copy;
use File::stat;

# Variable initialization.
my ( $time_limit, $tmp_folder, $trash_folder );
my $home = File::HomeDir->my_home or die 'Couldn\'t get $HOME: $!';
my $conf_file = $home . "/.trashtmprc";

if ( -e $conf_file ) {
    # Read configuration file if it's there.

    warn "$conf_file found. Reading...\n";

    ( $time_limit, $tmp_folder, $trash_folder )
        = read_conf_file( \$conf_file );

} else {
    # Write configuration file to disk if doesn't
    # exist yet.

    warn "$conf_file not found. Writing default parameters...\n";

    $time_limit   = 30;
    $tmp_folder   = $home . "/tmp/";
    $trash_folder = $home . "/.local/share/Trash/files";

    my $config = Config::Tiny->new();

    $config->{_}->{time_limit}   = $time_limit;
    $config->{_}->{tmp_folder}   = $tmp_folder;
    $config->{_}->{trash_folder} = $trash_folder;
    $config->write($conf_file)
       or die "Couldn't write default configuration file to disk!: $!"
+;
}

# Check that the directories exist.
die "Trash directory $trash_folder doesn't seem to exist!"
    unless -e $trash_folder;

unless ( -e $tmp_folder ) {
    warn "Folder $tmp_folder doesn't exist, creating it...\n";
    mkdir $tmp_folder or die "Coudln't create $tmp_folder: $!";
}

warn "    Time Limit: $time_limit days
    tmp directory: $tmp_folder
    Trash: $trash_folder\n";

# Create the cron object with the trash subroutine as default
my $cron = new Schedule::Cron( \&trash );

# Set the cron job to run every hour.
$cron->add_entry("0 * * * * ");

warn "Running...\n";

# Run cron job.
$cron->run();

sub trash {
    # Using get_file_age(), calculates how old each file in the
    # temp directory is, and trashes the old ones.
    
    warn "Looking for garbage...\n";
    my $dirhandle = DirHandle->new($tmp_folder);

    # Get a list of file elements in the folder, not counting
    # "." or ".."
    my @files = grep { $_ !~ /^\.+$/ } $dirhandle->read();

    # Get the files that are older than wanted.
    my @old_files
       = grep { get_file_age( $tmp_folder.$_, "days" ) > $time_limit }
        @files;

    if (@old_files) {
        warn "Garbage found!\n";

        # Move this files to the trash.
        map {
            move( $tmp_folder . $_, $trash_folder . $_ )
                or warn "Couldn't remove $_: :!"
        } @old_files;

        warn @old_files, " files deleted\n";
    } else {
        warn "No garbage found\n";
    }
}

sub get_file_age {
    my ( $filename, $unit ) = @_;
    my %convertion_to = (
        'seconds' => 1,
        'minutes' => 60,
        'hours'   => 3600,
        'days'    => 86400,
        'weeks'   => 604800,
    );
    die "Not a valid unit!" unless defined $convertion_to{$unit};

    my $file_stat = stat($filename);

    my $time = ( time - $file_stat->ctime ) / $convertion_to{$unit};

    return $time;
}


sub read_conf_file {

    my $conf_file = shift;

    # Create configuration object
    my $config = Config::Tiny->new();

    # Obtain parameters' values from configuration file
    my ( $time_limit, $tmp_folder, $trash_folder );

    # Read the configuration parameters
    $config       = Config::Tiny->read($$conf_file);
    $time_limit   = $config->{_}->{time_limit};
    $tmp_folder   = $config->{_}->{tmp_folder};
    $trash_folder = $config->{_}->{trash_folder};

    # Check for success in getting the variables in their
    # correct format
    unless (
        $time_limit      =~ /^\d+|\d+\.\d+$/    # Number
        or $tmp_folder   =~ /\w+/               # Words
        or $trash_folder =~ /\w+/
        )                                       # Words
    {
        die "Configuration file has errors!";
    }

    # Append the backslash if it isn't there...
    foreach ( $tmp_folder, $trash_folder ) {
        $_ =~ s|(.+\w)/?$|$1/|
            or die "$_ doesn't look like a directory";
    }
    return ( $time_limit, $tmp_folder, $trash_folder );
}
__END__

=head1 trash-temp-files

=head1 SYNOPSIS

trash-temp-files

Runs in the background, so don't launch from a terminal emulator that
you'll later close.
If you shut down your computer often, it would be better to add this
script to the list of programs launched at startup.

=head1 DESCRIPTION

trash-temp-files watches an user-defined directory and sends old files
(measured as days upon arrival to the folder) to the trash. 
The spirit of this is to have a special folder in your home directory
for you to put those files that don't really belong anywhere but that 
you are not ready to delete yet. So you move them there, and after a
given number of days, they are sent to the trashcan. This gives you
a certain time window in which you can re-evaluate the usefulness of
that file and rescue it from oblivion or not.

The program uses the module Schedule::Cron, so it is cron-independent.
+ It scans the status of the temporary folder every hour.

=head1 CONFIGURATION 

There are only three configuration parameters:

=over

=item * trash_folder: the location of the trashcan. Defaults to Gnome 
+2.22.3's default.

=item * tmp_folder: the folder whose files are going to be watched. De
+fault is $HOME/tmp

=item * time_limit: the amount of time upon arrival to tmp_folder afte
+r which the file is going to be sent to trash_folder. The default tim
+e is 30 days.

=back

All three of them can be changed by editing the .trashtmprc file, 
which lives in your home directory and is created after running
the application for the first time.

=head1 AUTHOR

bruno, E<lt>brunovecchi@yahoo.com.arE<gt>

=head1 COPYRIGHT AND LICENSE

Copyright (C) 2008 by bruno

This program is free software; you can redistribute it and/or modify
it under the same terms as Perl itself, either Perl version 5.8.8 or,
at your option, any later version of Perl 5 you may have available.

=cut

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: sourcecode [id://706028]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others about the Monastery: (5)
As of 2024-03-29 13:38 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found