Zydeco
view release on metacpan or search on metacpan
lib/Zydeco.pm view on Meta::CPAN
if ($sig =~ /^((?&PerlBlock)) $GRAMMAR/xso) {
my $type = $1;
$parsed[-1]{type} = $type;
$parsed[-1]{type_is_block} = 1;
$sig =~ s/^\Q$type//xs;
$sig =~ s/^((?&PerlOWS)) $GRAMMAR//xso;
}
elsif ($sig =~ /^((?&MxpTypeSpec)) $GRAMMAR/xso) {
my $type = $1;
$parsed[-1]{type} = ($type =~ /#/) ? $type->$decomment : $type;
$parsed[-1]{type_is_block} = 0;
$sig =~ s/^\Q$type//xs;
$sig =~ s/^((?&PerlOWS)) $GRAMMAR//xso;
}
else {
$parsed[-1]{type} = 'Any';
$parsed[-1]{type_is_block} = 0;
}
if ($sig =~ /^\*((?&PerlIdentifier)) $GRAMMAR/xso) {
my $name = $1;
$parsed[-1]{name} = $name;
$parsed[-1]{named} = 1;
$parsed[-1]{positional} = 0;
++$seen_named;
$sig =~ s/^\*\Q$name//xs;
$sig =~ s/^((?&PerlOWS)) $GRAMMAR//xso;
}
elsif ($sig =~ /^ ( [\$\@\%] ) (?: [=),?] | (?&PerlNWS) | $ ) $GRAMMAR/xso) {
state $dummy = 0;
my $name = substr($sig,0,1) . '____ZYDECO_DUMMY_VAR_' . ++$dummy;
$parsed[-1]{name} = $name;
$parsed[-1]{named} = 0;
$parsed[-1]{positional} = 1;
$sig = substr($sig, 1);
$sig =~ s/^((?&PerlOWS)) $GRAMMAR//xs;
}
elsif ($sig =~ /^((?&MxpSignatureVariable)) $GRAMMAR/xso) {
my $name = $1;
$parsed[-1]{name} = $name;
$parsed[-1]{named} = 0;
$parsed[-1]{positional} = 1;
++$seen_pos;
$sig =~ s/^\Q$name//xs;
$sig =~ s/^((?&PerlOWS)) $GRAMMAR//xs;
}
if ($sig =~ /^\?/) {
$parsed[-1]{optional} = 1;
$sig =~ s/^\?((?&PerlOWS)) $GRAMMAR//xso;
}
elsif ($sig =~ /^=((?&PerlOWS))((?&PerlScalarExpression)) $GRAMMAR/xso) {
my ($ws, $default) = ($1, $2);
$parsed[-1]{default} = $default;
$sig =~ s/^=\Q$ws$default//xs;
$sig =~ s/^((?&PerlOWS)) $GRAMMAR//xso;
if ($default =~ / \$ (?: class|self) /xso) {
require PadWalker;
$default = sprintf('do { my $invocants = PadWalker::peek_my(2)->{q[@invocants]}||PadWalker::peek_my(1)->{q[@invocants]}; my $self=$invocants->[-1]; my $class=ref($self)||$self; %s }', $default);
$parsed[-1]{default} = $default;
}
}
if ($sig) {
if ($sig =~ /^,/) {
$sig =~ s/^,//;
}
else {
require Carp;
Carp::croak(sprintf "Could not parse signature (%s), remaining: %s", $_[0], $sig);
}
}
}
my @signature_var_list;
my $type_params_stuff = '[';
my (@head, @tail);
if ($seen_named and $seen_pos) {
while (@parsed and $parsed[0]{positional}) {
push @head, shift @parsed;
}
while (@parsed and $parsed[-1]{positional}) {
unshift @tail, pop @parsed;
}
if (grep $_->{positional}, @parsed) {
require Carp;
Carp::croak("Signature contains an unexpected mixture of positional and named parameters");
}
for my $p (@head, @tail) {
my $is_optional = $p->{optional};
$is_optional ||= ($p->{type} =~ /^Optional/s);
if ($is_optional) {
require Carp;
Carp::croak("Cannot have optional positional parameter $p->{name} in signature with named parameters");
}
elsif ($p->{default}) {
require Carp;
Carp::croak("Cannot have positional parameter $p->{name} with default in signature with named parameters");
}
elsif ($p->{name} =~ /^[\@\%]/) {
require Carp;
Carp::croak("Cannot have slurpy parameter $p->{name} in signature with named parameters");
}
}
}
require B;
my $extra = '';
my $count = @parsed;
while (my $p = shift @parsed) {
$type_params_stuff .= B::perlstring($p->{name}) . ',' if $seen_named;
if ($p->{name} =~ /^[\@\%]/) {
if (@parsed) {
require Carp;
Carp::croak("Cannot have slurpy parameter $p->{name} in non-final position");
}
$extra .= sprintf(
( run in 0.871 second using v1.01-cache-2.11-cpan-97f6503c9c8 )