1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154
|
package VCP::Filter::csv_trace ;
=head1 NAME
VCP::Filter::csv_trace - developement logging filter
=head1 DESCRIPTION
Dumps fields of revisions in CSV format.
Not a supported module, API and behavior may change without warning.
=cut
$VERSION = 0.1 ;
@ISA = qw( VCP::Filter );
use strict ;
#use base qw( VCP::Filter );
use VCP::Filter;
use VCP::Logger qw( pr lg );
use VCP::Utils qw( empty start_dir_rel2abs );
use Getopt::Long;
#use fields (
# 'FIELDS', ## Which fields to print
# 'FILE', ## Where to write output
# 'FH', ## The filehandle of the output file
#);
sub new {
my $self = shift->SUPER::new;
## Parse the options
my ( $spec, $options ) = @_ ;
## Cheesy. TODO: factor parse_options up to plugin?
if ( $options && @$options ) {
local *ARGV = $options;
GetOptions(
"fields=s" => \$self->{FIELDS},
"file=s" => \$self->{FILE},
) or $self->usage_and_exit ;
}
die "vcp: output filename required for csv_trace filter\n"
if empty $self->{FILE};
return $self ;
}
sub csv_escape {
local $_ = @_ ? shift : $_;
return "" unless defined;
return '""' unless length;
## crude but effective.
s/\r/\\r/g;
s/\n/\\n/g;
s/"/""/g;
$_ = qq{"$_"} if /[",]/;
$_;
}
sub init {
my $self = shift ;
$self->SUPER::init;
$self->{FIELDS} = [
!empty( $self->{FIELDS} )
? do {
my @names = split /,/, $self->{FIELDS};
my %fields = map {
my $name = $_;
$name =~ s/\@//;
( $name => $_ );
} VCP::Rev->fields;
for ( @names ) {
if ( ! exists $fields{$_} && !VCP::Rev->can($_) ) {
pr "vcp: '$_' not a name, skipping";
next;
}
$_ = $fields{$_} if exists $fields{$_};
}
@names;
}
: VCP::Rev->fields
];
}
sub handle_header {
my $self = shift ;
local *F;
my $fn = start_dir_rel2abs( $self->{FILE} );
open F, "> $fn" or die "$! opening $fn\n";
$self->{FH} = *F{IO};
my $fh = $self->{FH};
print $fh join( ",", map {
my $name = $_;
$name =~ s/\@//;
csv_escape( $name );
} @{$self->{FIELDS}} ),
"\n";
$self->SUPER::handle_header( @_ );
}
sub handle_rev {
my $self = shift ;
my ( $r ) = @_;
my $fh = $self->{FH};
print $fh join( ",", map {
my $name = $_;
my $is_list = $name =~ s/\@//;
csv_escape(
$name eq "time"
? VCP::Rev::iso8601format( $r->$name )
: $is_list
? join ";", $r->$name
: $r->$name
);
} @{$self->{FIELDS}}
),
"\n";
$self->SUPER::handle_rev( $r );
}
=head1 AUTHOR
Barrie Slaymaker <barries@slaysys.com>
=head1 COPYRIGHT
Copyright (c) 2000, 2001, 2002 Perforce Software, Inc.
All rights reserved.
See L<VCP::License|VCP::License> (C<vcp help license>) for the terms of use.
=cut
1
|