From: Lukas Mai Date: Tue, 5 Feb 2013 01:07:47 +0000 (+0100) Subject: Merge branch 'metadata' into mooseish-types X-Git-Tag: v1.0101~3 X-Git-Url: http://git.shadowcat.co.uk/gitweb/gitweb.cgi?a=commitdiff_plain;h=bd79c063bca2e01fddac72c931aed9c37c4535b3;hp=-c;p=p5sagit%2FFunction-Parameters.git Merge branch 'metadata' into mooseish-types --- bd79c063bca2e01fddac72c931aed9c37c4535b3 diff --combined lib/Function/Parameters.pm index dc6a79f,a3afc55..47107f1 --- a/lib/Function/Parameters.pm +++ b/lib/Function/Parameters.pm @@@ -8,7 -8,7 +8,7 @@@ use Carp qw(confess) use XSLoader; BEGIN { - our $VERSION = '1.0003'; + our $VERSION = '1.0004'; XSLoader::load; } @@@ -32,14 -32,12 +32,14 @@@ my %type_map = default_arguments => 1, check_argument_count => 0, named_parameters => 1, + types => 1, }, method => { name => 'optional', default_arguments => 1, check_argument_count => 0, named_parameters => 1, + types => 1, attrs => ':method', shift => '$self', invocant => 1, @@@ -49,7 -47,6 +49,7 @@@ default_arguments => 1, check_argument_count => 0, named_parameters => 1, + types => 1, attributes => ':method', shift => '$class', invocant => 1, @@@ -119,7 -116,6 +119,7 @@@ sub import $clean{check_argument_count} = !!delete $type{check_argument_count}; $clean{invocant} = !!delete $type{invocant}; $clean{named_parameters} = !!delete $type{named_parameters}; + $clean{types} = !!delete $type{types}; %type and confess "Invalid keyword property: @{[keys %type]}"; @@@ -135,10 -131,9 +135,10 @@@ FLAG_ANON_OK | FLAG_NAME_OK ; $flags |= FLAG_DEFAULT_ARGS if $type->{default_arguments}; - $flags |= FLAG_CHECK_NARGS if $type->{check_argument_count}; + $flags |= FLAG_CHECK_NARGS | FLAG_CHECK_TARGS if $type->{check_argument_count}; $flags |= FLAG_INVOCANT if $type->{invocant}; $flags |= FLAG_NAMED_PARAMS if $type->{named_parameters}; + $flags |= FLAG_TYPES_OK if $type->{types}; $^H{HINTK_FLAGS_ . $kw} = $flags; $^H{HINTK_SHIFT_ . $kw} = $type->{shift}; $^H{HINTK_ATTRS_ . $kw} = $type->{attrs}; @@@ -167,58 -162,40 +167,58 @@@ sub _register_info $key, $declarator, $invocant, + $invocant_type, $positional_required, $positional_optional, $named_required, $named_optional, $slurpy, + $slurpy_type, ) = @_; - my $blob = pack '(Z*)*', - $declarator, - $invocant // '', - join(' ', @$positional_required), - join(' ', @$positional_optional), - join(' ', @$named_required), - join(' ', @$named_optional), - $slurpy // '', - ; - - $metadata{$key} = $blob; + my $info = { + declarator => $declarator, + invocant => defined $invocant ? [$invocant, $invocant_type] : undef, + slurpy => defined $slurpy ? [$slurpy , $slurpy_type ] : undef, + positional_required => $positional_required, + positional_optional => $positional_optional, + named_required => $named_required, + named_optional => $named_optional, + }; + + $metadata{$key} = $info; +} + +sub _mkparam1 { + my ($pair) = @_; + my ($v, $t) = @{$pair || []} or return undef; + Function::Parameters::Param->new( + name => $v, + type => $t, + ) +} + +sub _mkparams { + my @r; + while (my ($v, $t) = splice @_, 0, 2) { + push @r, Function::Parameters::Param->new( + name => $v, + type => $t, + ); + } + \@r } sub info { my ($func) = @_; my $key = _cv_root $func or return undef; - my $blob = $metadata{$key} or return undef; - my @info = unpack '(Z*)*', $blob; + my $info = $metadata{$key} or return undef; require Function::Parameters::Info; Function::Parameters::Info->new( - keyword => $info[0], - invocant => $info[1] || undef, - _positional_required => [split ' ', $info[2]], - _positional_optional => [split ' ', $info[3]], - _named_required => [split ' ', $info[4]], - _named_optional => [split ' ', $info[5]], - slurpy => $info[6] || undef, + keyword => $info->{declarator}, + invocant => _mkparam1($info->{invocant}), + slurpy => _mkparam1($info->{slurpy}), + (map +("_$_" => _mkparams @{$info->{$_}}), glob '{positional,named}_{required,optional}') ) } @@@ -662,44 -639,6 +662,44 @@@ affects the file that is currently bein # or Function::Parameters->import(@custom_import_args); } +=head2 Experimental feature: Types + +An experimental feature is now available: You can annotate parameters with +L. That is, before each parameter you can put +a type specification consisting of identifiers (C), unions (C<... | ...>), +and parametric types (C<...[...]>). Example: + + fun foo(Int $n, ArrayRef[String | CodeRef] $cb) { ... } + +If you do this, L will be loaded automatically (if that hasn't happened +yet). These specifications are parsed and validated using +L|Moose::Util::TypeConstraints/find_or_parse_type_constraint>. + +If you are in "lax" mode, nothing further happens and the types are ignored. If +you are in "strict" mode, C generates code to make sure +any values passed in conform to the type (via +L<< C<< $constraint->check($value) >>|Moose::Meta::TypeConstraint/$constraint->check($value) >>). + +In addition, these type constraints are inspectable through the +L object returned by +L|/Introspection>. + +=head2 Experimental experimental feature: Type expressions + +An even more experimental feature is the ability to specify arbitrary +expressions as types. The syntax for this is like the literal types described +above, but with an expression wrapped in parentheses (C<( EXPR )>). Example: + + fun foo(('Int') $n, ($othertype) $x) { ... } + +Every type expression must return either a string (which is resolved as for +literal types), or a L +(providing C and C methods). + +Note that these expressions are evaluated (once) at parse time (similar to +C blocks), so make sure that any variables you use are set and any +functions you call are defined at parse time. + =head2 How it works The module is actually written in L and uses @@@ -717,39 -656,6 +717,39 @@@ generated code corresponds to # ... turns into ... sub bar :method { my $self = shift; my ($x, $y, @z) = @_; sub bar; ... } +=head1 SUPPORT AND DOCUMENTATION + +After installing, you can find documentation for this module with the +perldoc command. + + perldoc Function::Parameters + +You can also look for information at: + +=over + +=item MetaCPAN + +L + +=item RT, CPAN's request tracker + +L + +=item AnnoCPAN, Annotated CPAN documentation + +L + +=item CPAN Ratings + +L + +=item Search CPAN + +L + +=back + =head1 SEE ALSO L