#!/usr/bin/perl
use strict;
use warnings;
use SVN::Dump;
use File::stat; # by-name access to mtime

my $rev;
my $date;
my $base;
my $file = shift;
my $dump = SVN::Dump->new( { file => $file } );

my %map  = @ARGV;

# compute some stats
my %type = (unknown=>0, revision=>0, node=>0);
my %kind;

REC: while ( my $record = $dump->next_record() ) 
{
    my $type = eval { $record->type() };
    ++$type{unknown} and next REC if not defined $type;

    ++$type{ $type };

    if ($type eq 'node')
    {
        my $action = eval { $record->get_header('Node-action')  };
        my $path   = eval { $record->get_header('Node-path') };

        ++$kind{ $action } if $action;

        if ($base and $action =~ /add|change/)
        {
            my $mtime  = svntime("$base/$path");
            $record->set_property("alt:mtime", $mtime ? $mtime : $date );
        }
    }

    if ($type eq 'revision')
    {
        $rev  = eval { $record->get_header('Revision-number') };
        $date = eval { $record->get_property('svn:date') };
        $base = $map{$rev};
    }
}
continue
{
    print $record->as_string();
}

# print the results
print STDERR "Statistics for dump $file:\n",
      "  version:   ", $dump->version(), "\n",
      "  uuid:      ", $dump->uuid(), "\n",
      "  unknown:   ", $type{unknown}, "\n",
      "  revisions: ", $type{revision}, "\n",
      "  nodes:     ", $type{node}, "\n";
print STDERR map { sprintf "  - %-7s: %d\n", $_, $kind{$_} } sort keys %kind;

# takes filename as input, returns mtime using the
# special format of svn time: 2005-07-11T09:17:35.000000Z
sub svntime 
{
    my $file = shift;
    my $mtime = eval { (stat($file))->mtime };
    warn $@ and return if $@;

    my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = gmtime($mtime);
    return sprintf "%4d-%02d-%02dT%02d:%02d:%02d.000000Z",
                 1900+$year,$mon+1,$mday,$hour,$min,$sec;
}

=head1 Name

mdump.pl - a script for adding alt:mtime properties to nodes of svn dump file

=head1 Synopsis

 mdump.pl inputdumpfile > outputdumpfile

=head1 Description

B<mdump.pl> is a perl script which adds alt:mtime to nodes of an svn dump 
file based on the actual mtime of files in the filesystem.

B<mdump.pl> uses L<SVN:Dump 0.03> to parse svn dump files.

=head1 See Also

SVN::Dump

=head1 Copyright

Copyright 2007 Aryeh Leib Taurog    www.aryehleib.com

This is free software.  It is available under the same license as Perl.

This software is provided AS IS with no warranty as to its usability or 
fitness for any purpose. I disclaim all responsibility for any damage 
whatsoever resulting from the download or use of this software.

=cut


