deepimport.pl #1

  • //
  • guest/
  • sam_stafford/
  • scripts/
  • deepimport.pl
  • View
  • Commits
  • Open Download .zip Download (4 KB)
# deepimport.pl -- import history from a remote depot.
#
# Usage:
#       deepimport.pl srcPath... tgtPath...
# 
# The srcPath should be in a remote depot that maps to a Perforce
# server that you can access directly.  You will only need "list"
# access on the remote server, but you will need "admin" access on
# the local server to copy the changelists over.
#
# If you don't set the configuration variables, they'll be read from your
# environment.  If you don't specify authentication info
# for the remote server, the local user/password will be used.

$p4 = "p4";
$P4PORT = "";
$P4USER = "";
$P4PASSWD = "";
$P4CLIENT = "";

$P4USER_remote = "";
$P4PASSWD_remote = "";

#####end configuration section###########

if ( !$P4USER_remote )   { $P4USER_remote   = $P4USER;   }
if ( !$P4PASSWD_remote ) { $P4PASSWD_remote = $P4PASSWD; }

$p4_local  = $p4;
$p4_remote = $p4;

if ( $P4PORT )   { $p4_local .= " -p $P4PORT"; }
if ( $P4USER )   { $p4_local .= " -u $P4USER"; }
if ( $P4PASSWD ) { $p4_local .= " -P $P4PASSWD"; }
if ( $P4CLIENT ) { $p4_local .= " -c $P4CLIENT"; }

$source_local = $ARGV[0];
$target_local = $ARGV[1];

if ( !$source_local or !$target_local )
{
    die "Please provide a source and target path.";
}

# Resolve $source_local to a depot path.
open WHERE, "$p4_local -Ztag where \"$source_local\" 2>&1|" or die "$!";
while (<WHERE>)
{
    chomp;
    if ( /\.\.\. depotFile (.*)/ ) { $source_local = $1; last; }
}
close WHERE;

$_ = $source_local;
if ( /^\/\/([^\/]+)/ ) { $depot = $1; }
else { die "Unable to resolve $_ to a depot path." }

# Get remote server information.
$P4PORT_remote = $P4PORT;
$map_remote = "//$depot/...";
open DEPOT, "$p4_local -Ztag depot -o \"$depot\"|" or die "$!";
while (<DEPOT>)
{
    chomp;
    if ( /\.\.\. Type (.*)/ and $1 ne "remote" ) { last; }
    # I was going to throw an error here if Type wasn't remote,
    # but maybe somebody will really want to do an import from
    # a local depot?  Not too hard to allow that; we just bail
    # out here and use the local connection settings instead.

    if ( /\.\.\. Address (.*)/ ) { $P4PORT_remote = $1; }
    if ( /\.\.\. Map (.*)/ ) { $map_remote = $1; }
}
close DEPOT;

if ( $P4PORT_remote )   { $p4_remote .= " -p $P4PORT_remote"; }
if ( $P4USER_remote )   { $p4_remote .= " -u $P4USER_remote"; }
if ( $P4PASSWD_remote ) { $p4_remote .= " -P $P4PASSWD_remote"; }

#Use Map to translate $source_local into $source_remote.
$_ = $map_remote;
if ( !/\.\.\.$/ ) { die "Map field doesn't end in ..."; }
s/\.\.\.$//;
$map_remote = $_;
$map_local = "//$depot/";
$_ = $source_local;
s/$map_local/$map_remote/;
$source_remote = $_;

# Now the fun begins!  We're going to connect to the remote server, get
# the list of changes for this path, and start importing.
@changes = ();
open CHANGES, "$p4_remote changes \"$source_remote\"|" or die "$!";
while (<CHANGES>)
{
    if ( !/^Change (\d+)/ ) { last; }
    # Changes come in reverse order.
    unshift @changes, $1;
}
close CHANGES;

$count = 0;

foreach $change ( @changes )
{
    #Import the change.
    print "Importing change $change...";
    `$p4_local integ "$source_local\@$change" "$target_local"`;
    `$p4_local resolve -as "$target_local" 2>&1`;
    $_ = `$p4_local submit -d "Import $change from $source_local."`;
    if ( !/Change (\d+) submitted.$/ ) { last; }
    $import = $1;
    print " local change $import submitted.\n";

    #Try to copy the change description over.
    open REMOTE, "$p4_remote change -o $change|" or die "$!";
    open LOCAL,  "$p4_local  change -o $import|" or die "$!";
    open EDIT,   "|$p4_local  change -if" or die "$!";
    # Everything before the User: field should remain unchanged.
    # Everything after that is either identical or can be
    # overwritten.  (Note that there is no Files: field.)
    while ( <LOCAL> )
    {
        print EDIT $_;
        if ( /^Client:/ ) { last; }
    }
    while ( <REMOTE> )
    {
        if ( /^Client:/ ) { last; }
    }
    while ( <REMOTE> )
    {
        print EDIT $_;
    }
    close REMOTE;
    close LOCAL;
    close EDIT;
    $count++;
}

print "$count changes imported.\n";
# Change User Description Committed
#2 6324 Sam Stafford Update deepimport to not require "admin" access; the description
is now copied in on submit rather than set after the fact, and
the user/client/date info is also copied into the description.
#1 6323 Sam Stafford A little script to import history from a remote depot.