App-Codeowners
view release on metacpan or search on metacpan
lib/App/Codeowners.pm view on Meta::CPAN
package App::Codeowners;
# ABSTRACT: A tool for managing CODEOWNERS files
use v5.10.1; # defined-or
use utf8;
use warnings;
use strict;
use App::Codeowners::Formatter;
use App::Codeowners::Options;
use App::Codeowners::Util qw(find_codeowners_in_directory run_git git_ls_files git_toplevel);
use Color::ANSI::Util 0.03 qw(ansifg);
use File::Codeowners 0.54;
use Path::Tiny;
our $VERSION = '0.51'; # VERSION
sub main {
my $class = shift;
my $self = bless {}, $class;
my $opts = App::Codeowners::Options->new(@_);
my $color = $opts->{color};
local $ENV{NO_COLOR} = 1 if defined $color && !$color;
my $command = $opts->command;
my $handler = $self->can("_command_$command")
or die "Unknown command: $command\n";
binmode(STDOUT, ':encoding(UTF-8)');
$self->$handler($opts);
exit 0;
}
sub _command_show {
my $self = shift;
my $opts = shift;
my $toplevel = git_toplevel('.') or die "Not a git repo\n";
my $codeowners_path = find_codeowners_in_directory($toplevel)
or die "No CODEOWNERS file in $toplevel\n";
local $ENV{GIT_CODEOWNERS_ALIASES} = 1 if $opts->{expand_aliases};
my $codeowners = $self->_parse_codeowners($codeowners_path);
my ($proc, $cdup) = run_git(qw{rev-parse --show-cdup});
$proc->wait and exit 1;
my $show_projects = $opts->{projects} // scalar @{$codeowners->projects};
my $formatter = App::Codeowners::Formatter->new(
format => $opts->{format} || ' * %-50F %O',
handle => *STDOUT,
columns => [
'File',
$opts->{patterns} ? 'Pattern' : (),
'Owner',
$show_projects ? 'Project' : (),
],
);
my %filter_owners = map { $_ => 1 } @{$opts->{owner}};
my %filter_projects = map { $_ => 1 } @{$opts->{project}};
my %filter_patterns = map { $_ => 1 } @{$opts->{pattern}};
$proc = git_ls_files('.', $opts->args);
while (my $filepath = $proc->next) {
my $match = $codeowners->match(path($filepath)->relative($cdup),
expand => $opts->{expand_aliases});
if (%filter_owners) {
for my $owner (@{$match->{owners}}) {
goto ADD_RESULT if $filter_owners{$owner};
}
next;
}
if (%filter_patterns) {
goto ADD_RESULT if $filter_patterns{$match->{pattern} || ''};
next;
}
if (%filter_projects) {
goto ADD_RESULT if $filter_projects{$match->{project} || ''};
next;
}
ADD_RESULT:
$formatter->add_result([
$filepath,
$opts->{patterns} ? $match->{pattern} : (),
$match->{owners},
$show_projects ? $match->{project} : (),
]);
}
$proc->wait and exit 1;
}
sub _command_owners {
my $self = shift;
my $opts = shift;
my $toplevel = git_toplevel('.') or die "Not a git repo\n";
my $codeowners_path = find_codeowners_in_directory($toplevel)
or die "No CODEOWNERS file in $toplevel\n";
my $codeowners = $self->_parse_codeowners($codeowners_path);
my $results = $codeowners->owners($opts->{pattern});
my $formatter = App::Codeowners::Formatter->new(
format => $opts->{format} || '%O',
handle => *STDOUT,
columns => [qw(Owner)],
);
$formatter->add_result(map { [$_] } @$results);
}
sub _command_patterns {
my $self = shift;
my $opts = shift;
my $toplevel = git_toplevel('.') or die "Not a git repo\n";
my $codeowners_path = find_codeowners_in_directory($toplevel)
or die "No CODEOWNERS file in $toplevel\n";
my $codeowners = $self->_parse_codeowners($codeowners_path);
my $results = $codeowners->patterns($opts->{owner});
my $formatter = App::Codeowners::Formatter->new(
format => $opts->{format} || '%T',
handle => *STDOUT,
( run in 2.370 seconds using v1.01-cache-2.11-cpan-97f6503c9c8 )