User: sits    
  Date: 07/07/12 02:49:03

  Modified:    lib      Codestriker.pm
               lib/Codestriker/Repository Cvs.pm Subversion.pm
  Log:
  * Codestriker now behaves correctly under mod_perl when retrieving
    data externally from an SCM system, such as when the Parallel link
    is clicked, or when a topic is created directly from the SCM.
  
  * Creating Subversion topics directly from the SCM now works correctly
    in non-English locales.
  
  
  
  Index: Codestriker.pm
  ===================================================================
  RCS file: /cvsroot/codestriker/codestriker/lib/Codestriker.pm,v
  retrieving revision 1.100
  retrieving revision 1.101
  diff -u -r1.100 -r1.101
  --- Codestriker.pm    3 Jul 2007 10:00:24 -0000       1.100
  +++ Codestriker.pm    12 Jul 2007 09:49:02 -0000      1.101
  @@ -560,8 +560,10 @@
            my $stderr_filename = "$command_tmpdir/stderr.txt";
   
            # Thankfully this works under Windows.
  -         my $system_line = "$command_line > \"$stdout_filename\" 2> 
\"$stderr_filename\"";
  -         system($system_line) == 0 || croak "Failed to execute $system_line: 
$!\n";
  +         my $system_line =
  +             "$command_line > \"$stdout_filename\" 2> \"$stderr_filename\"";
  +         system($system_line) == 0 ||
  +             croak "Failed to execute $system_line: $!\n";
   
            open(TMP_STDOUT, $stdout_filename);
            binmode TMP_STDOUT;
  @@ -600,20 +602,19 @@
            waitpid($pid, 0);
        }
       };
  -    if ($@) {
  -     my $error_string = "Command failed: [EMAIL PROTECTED]";
  -     $error_string .= "$command " . join(' ', @args) . "\n";
  -     $error_string .= "Check your webserver error log for more 
information.\n";
  -     print $stderr_fh $error_string;
  -     print STDERR $error_string;
  -     flush STDERR;
  -    }
  +    my $exception = $@;
   
       # Make sure the temporary directory is removed if it was created.
       if (defined $command_tmpdir) {
        rmtree($command_tmpdir);
       }
   
  +    if ($exception) {
  +     croak("Command failed: [EMAIL PROTECTED]",
  +           "$command " . join(' ', @args) . "\n",
  +           "Check your webserver error log for more information.\n");
  +    }
  +
       # Flush the output file handles.
       $stdout_fh->flush;
       $stderr_fh->flush;
  
  
  
  
  
  Index: Cvs.pm
  ===================================================================
  RCS file: /cvsroot/codestriker/codestriker/lib/Codestriker/Repository/Cvs.pm,v
  retrieving revision 1.7
  retrieving revision 1.8
  diff -u -r1.7 -r1.8
  --- Cvs.pm    3 Jul 2007 06:29:38 -0000       1.7
  +++ Cvs.pm    12 Jul 2007 09:49:02 -0000      1.8
  @@ -11,6 +11,7 @@
   
   use strict;
   use FileHandle;
  +use Fatal qw / open close /;
   
   # Factory method for creating a local CVS repository object.
   sub build_local {
  @@ -64,7 +65,7 @@
   
       my $read_data;
       my $read_stdout_fh = new FileHandle;
  -    open($read_stdout_fh, '>', \$read_data) || die "Can't create in-memory 
fh: $!";
  +    open($read_stdout_fh, '>', \$read_data);
       my @args = ();
       push @args, '-q';
       push @args, '-d';
  @@ -78,7 +79,7 @@
                                 $Codestriker::cvs, @args);
   
       # Process the data for the topic.
  -    open($read_stdout_fh, '<', \$read_data) || die "Can't create in-memory 
fh: $!";
  +    open($read_stdout_fh, '<', \$read_data);
       for (my $i = 1; <$read_stdout_fh>; $i++) {
        $_ = Codestriker::decode_topic_text($_);
        chop;
  
  
  
  
  
  Index: Subversion.pm
  ===================================================================
  RCS file: 
/cvsroot/codestriker/codestriker/lib/Codestriker/Repository/Subversion.pm,v
  retrieving revision 1.17
  retrieving revision 1.18
  diff -u -r1.17 -r1.18
  --- Subversion.pm     3 Jul 2007 11:07:50 -0000       1.17
  +++ Subversion.pm     12 Jul 2007 09:49:02 -0000      1.18
  @@ -11,9 +11,10 @@
   use IPC::Open3;
   
   use strict;
  +use Fatal qw / open close /;
   
   # Constructor, which takes as a parameter the repository url.
  -sub new ($$) {
  +sub new {
       my ($type, $repository_url, $user, $password) = @_;
   
       # Determine if there are additional parameters required for user
  @@ -26,35 +27,45 @@
        push @userCmdLine, $password;
       }
   
  -    # Make sure the repo url does not end in a /, the 
  -    # rest of the module assumes that it does not.
  -    $repository_url =~ s/[\\\/]^//;
  -    
  -    # Replace any spaces with %20 uri friendly escapes.
  -    # Ditto with @ symbols, so Subversion doesn't interpret it as a peg.
  -    $repository_url =~ s/ /%20/g;
  -    $repository_url =~ s/\@/%40/g;
  +    # Sanitise the repository URL.
  +    $repository_url = sanitise_url_component($repository_url);
   
       my $self = {};
       $self->{repository_url} = $repository_url;
       $self->{userCmdLine} = [EMAIL PROTECTED];
  +    $self->{repository_string} = $repository_url;
  +    $self->{repository_string} .= ";$user" if defined $user;
  +    $self->{repository_string} .= ";$password" if defined $password;
  +    if ($self->{repository_string} !~ /^svn:/) {
  +     $self->{repository_string} = "svn:" . $self->{repository_string};
  +    }
   
       bless $self, $type;
   }
   
  +# Sanitise a Subversion URL component, by replacing spaces with %20 and @
  +# symbols with %40, so that there is no confused with pegged revisions.  Also
  +# remove any leading and trailing slashes.
  +sub sanitise_url_component {
  +    my $url = shift;
  +    $url =~ s/\/$//;
  +    $url =~ s/^\///;
  +    $url =~ s/ /%20/g;
  +    $url =~ s/\@/%40/g;
  +    return $url;
  +}
  +
   # Retrieve the data corresponding to $filename and $revision.  Store each 
line
   # into $content_array_ref.
   sub retrieve ($$$\$) {
       my ($self, $filename, $revision, $content_array_ref) = @_;
   
  -    # Replace any spaces with %20 uri friendly escapes.
  -    # Ditto with @ symbols, so Subversion doesn't interpret it as a peg.
  -    $filename =~ s/ /%20/g;
  -    $filename =~ s/\@/%40/g;
  +    # Sanitise the filename.
  +    $filename = sanitise_url_component($filename);
   
       my $read_data;
       my $read_stdout_fh = new FileHandle;
  -    open($read_stdout_fh, '>', \$read_data) || die "Can't create in-memory 
fh: $!";
  +    open($read_stdout_fh, '>', \$read_data);
       my @args = ();
       push @args, 'cat';
       push @args, '--non-interactive';
  @@ -67,7 +78,7 @@
                                 $Codestriker::svn, @args);
   
       # Process the data for the topic.
  -    open($read_stdout_fh, '<', \$read_data) || die "Can't create in-memory 
fh: $!";
  +    open($read_stdout_fh, '<', \$read_data);
       for (my $i = 1; <$read_stdout_fh>; $i++) {
        $_ = Codestriker::decode_topic_text($_);
        chop;
  @@ -87,6 +98,10 @@
   
       # Lookup the file viewer from the configuration.
       my $viewer = $Codestriker::file_viewer->{$self->toString()};
  +    if (! (defined $viewer)) {
  +     $viewer = $Codestriker::file_viewer->{$self->{repository_string}};
  +    }
  +
       return (defined $viewer) ? $viewer . "/" . $filename : "";
   }
   
  @@ -96,79 +111,90 @@
       return "svn:" . $self->getRoot();
   }
   
  +# Given a Subversion URL, determine if it refers to a directory or a file.
  +sub is_file_url {
  +    my ($self, $url) = @_;
  +    my $file_url;
  +
  +    eval {
  +     my @args = ();
  +     push @args, 'info';
  +     push @args, '--non-interactive';
  +     push @args, '--no-auth-cache';
  +     push @args, @{ $self->{userCmdLine} };
  +     push @args, '--xml';
  +     push @args, $self->{repository_url} . '/' . $url;
  +     my $read_data;
  +     my $read_stdout_fh = new FileHandle;
  +     open($read_stdout_fh, '>', \$read_data);
  +
  +     Codestriker::execute_command($read_stdout_fh, undef,
  +                                  $Codestriker::svn, @args);
  +     open($read_stdout_fh, '<', \$read_data);
  +     while (<$read_stdout_fh>) {
  +         if (/kind\s*\=\s*\"(\w+)\"/) {
  +             $file_url = $1 eq "File";
  +             last;
  +         }
  +     }
  +    };
  +    if ($@ || !(defined $file_url)) {
  +     # The above command failed, try using the older method which only works
  +     # in an English locale.  This supports Subversion 1.2 or earlier
  +     # releases, which don't support the --xml flag for the info command.
  +     my @args = ();
  +     push @args, 'cat';
  +     push @args, '--non-interactive';
  +     push @args, '--no-auth-cache';
  +     push @args, @{ $self->{userCmdLine} };
  +     push @args, '--revision';
  +     push @args, 'HEAD';
  +     push @args, $self->{repository_url} . '/' . $url;
  +
  +     my $read_stdout_data;
  +     my $read_stdout_fh = new FileHandle;
  +     open($read_stdout_fh, '>', \$read_stdout_data);
  +
  +     my $read_stderr_data;
  +     my $read_stderr_fh = new FileHandle;
  +     open($read_stderr_fh, '>', \$read_stderr_data);
  +
  +     Codestriker::execute_command($read_stdout_fh, $read_stderr_fh,
  +                                  $Codestriker::svn, @args);
  +     $file_url = 1;
  +     open($read_stderr_fh, '<', \$read_stderr_data);
  +     while(<$read_stderr_fh>) {
  +         if (/^svn:.* refers to a directory/) {
  +             $file_url = 0;
  +             last;
  +         }
  +     }
  +    }
  +    
  +    return $file_url;
  +}
  +
   # The getDiff operation, pull out a change set based on the start and end 
   # revision number, confined to the specified moduled_name.
  -sub getDiff ($$$$$) {
  +sub getDiff {
       my ($self, $start_tag, $end_tag, $module_name, $stdout_fh, $stderr_fh) = 
@_;
   
  -    # Make sure the module does not end or start with a /
  -    $module_name =~ s/\/$//;
  -    $module_name =~ s/^\///;
  -
  -    # Replace any spaces with %20 uri friendly escapes.
  -    # Ditto with @ symbols, so Subversion doesn't interpret it as a peg.
  -    my $filename = $module_name;
  -    $filename =~ s/ /%20/g;
  -    $filename =~ s/\@/%40/g;
  +    # Sanitise the URL, and determine if it refers to a directory or 
filename.
  +    $module_name = sanitise_url_component($module_name);
  +    my $directory;
  +    if ($self->is_file_url($module_name)) {
  +     $module_name =~ /(.*)\/[^\/]+/;
  +     $directory = $1;
  +    } else {
  +     $directory = $module_name;
  +    }
   
  -    my $write_stdin_fh = new FileHandle;
  +    # Execute the diff command.
  +    my $read_stdout_data;
       my $read_stdout_fh = new FileHandle;
  -    my $read_stderr_fh = new FileHandle;
  +    open($read_stdout_fh, '>', \$read_stdout_data);
   
       my @args = ();
  -    push @args, 'cat';
  -    push @args, '--non-interactive';
  -    push @args, '--no-auth-cache';
  -    push @args, @{ $self->{userCmdLine} };
  -    push @args, '--revision';
  -    push @args, 'HEAD';
  -    push @args, $self->{repository_url} . '/' . $filename;
  -
  -    my $pid = open3($write_stdin_fh, $read_stdout_fh, $read_stderr_fh,
  -                 $Codestriker::svn, @args);
  -
  -    while(<$read_stdout_fh>) {}
  -
  -    my $directory;
  -
  -    # TODO: need a better way of detecting this, since Chinese users
  -    # receive a different output string.  Kind is either a file or
  -    # directory from what I have seen.
  -    # C:\Program Files\svn-win32-1.4.4\bin>svn info --xml 
http://svn.collab.net/repos/svn/trunk/tools/README
  -# <?xml version="1.0"?>
  -# <info>
  -# <entry
  -#   kind="file"
  -#    path="README"
  -#   revision="25631">
  -# <url>http://svn.collab.net/repos/svn/trunk/tools/README</url>
  -
  -    # If there is an error about it being a directory, then use the
  -    # module name as a directory.
  -    while(<$read_stderr_fh>) {
  -        my $line = $_;
  -
  -        if ($line =~ /^svn:.*URL '.*' refers to a directory/) {
  -            $directory = $module_name;
  -        }
  -    }
  -
  -    # if there was no error, then the module name is a file, so get the
  -    # directory before the file name.
  -    if (! defined $directory) {
  -        $module_name =~ /(.*)\/[^\/]+/;
  -        $directory = $1;
  -    }
  -
  -    $write_stdin_fh->close();
  -    $read_stdout_fh->close();
  -    $read_stderr_fh->close();
  -
  -    $write_stdin_fh = new FileHandle;
  -    $read_stdout_fh = new FileHandle;
  -    $read_stderr_fh = new FileHandle;
  -
  -    @args = ();
       push @args, 'diff';
       push @args, '--non-interactive';
       push @args, '--no-auth-cache';
  @@ -178,47 +204,35 @@
       push @args, '--old';
       push @args, $self->{repository_url};
       push @args, $module_name;
  +    Codestriker::execute_command($read_stdout_fh, $stderr_fh,
  +                              $Codestriker::svn, @args);
   
  -    $pid = open3($write_stdin_fh, $read_stdout_fh, $read_stderr_fh,
  -              $Codestriker::svn, @args);
  -
  +    open($read_stdout_fh, '<', \$read_stdout_data);
       while(<$read_stdout_fh>) {
  -        my $line = $_;
  +     my $line = $_;
  +     
  +     # If the user specifies a path (a branch in Subversion), the
  +     # diff file does not come back with a path rooted from the
  +     # repository base making it impossible to pull the entire file
  +     # back out. This code attempts to change the diff file on the
  +     # fly to ensure that the full path is present. This is a bug
  +     # against Subversion, so eventually it will be fixed, so this
  +     # code can't break when the diff command starts returning the
  +     # full path.
  +     if ($line =~ /^--- / || $line =~ /^\+\+\+ / ||
  +         $line =~ /^Index: /) {
  +         # Check if the bug has been fixed.
  +         if ($line =~ /^\+\+\+ $module_name/ == 0 && 
  +             $line =~ /^--- $module_name/ == 0 &&
  +             $line =~ /^Index: $module_name/ == 0) {
  +                 $line =~ s/^--- /--- $directory\// or
  +                 $line =~ s/^Index: /Index: $directory\// or
  +                 $line =~ s/^\+\+\+ /\+\+\+ $directory\//;
  +         }
  +     }
   
  -        # If the user specifies a path (a branch in Subversion), the
  -        # diff file does not come back with a path rooted from the
  -        # repository base making it impossible to pull the entire file
  -        # back out. This code attempts to change the diff file on the
  -        # fly to ensure that the full path is present. This is a bug
  -        # against Subversion, so eventually it will be fixed, so this
  -        # code can't break when the diff command starts returning the
  -        # full path.
  -        if ($line =~ /^--- / || $line =~ /^\+\+\+ / || $line =~ /^Index: /) {
  -            # Check if the bug has been fixed.
  -            if ($line =~ /^\+\+\+ $module_name/ == 0 && 
  -                $line =~ /^--- $module_name/ == 0 &&
  -                $line =~ /^Index: $module_name/ == 0) {
  -
  -                $line =~ s/^--- /--- $directory\// or
  -                $line =~ s/^Index: /Index: $directory\// or
  -                $line =~ s/^\+\+\+ /\+\+\+ $directory\//;
  -            }
  -        }
  -
  -        print $stdout_fh $line;
  -    }
  -
  -    my $buf;
  -    while (read($read_stderr_fh, $buf, 16384)) {
  -     print $stderr_fh $buf;
  -    }
  -
  -    # Wait for the process to terminate.
  -    waitpid($pid, 0);
  -
  -    # Flush the output file handles.
  -    $stdout_fh->flush;
  -    $stderr_fh->flush;
  +     print $stdout_fh $line;
  +    }
   
       return $Codestriker::OK;
   }
  
  
  

-------------------------------------------------------------------------
This SF.net email is sponsored by DB2 Express
Download DB2 Express C - the FREE version of DB2 express and take
control of your XML. No limits. Just data. Click to get it now.
http://sourceforge.net/powerbar/db2/
_______________________________________________
Codestriker-commits mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/codestriker-commits

Reply via email to