[Perl5-syntax] Adding Moose type checking to Method::Signatures

Michael G Schwern schwern at pobox.com
Wed Feb 23 12:52:19 GMT 2011


Long story short:  I'll happily accept patches so Method::Signatures can parse
Perl 6 types.  What's done with that information is open to discussion, but it
sounds like once MS has done the parsing you've figured out how to add your
type check.


On 2011.2.23 8:08 PM, Buddy Burden wrote:
> I wish I was smart enough to be able to contribute a patch to MXMS
> that would fix all these things, but, alas, I am not. :)  But what I
> _have_ been able to do is to use MS instead, and just do the type
> checking separately.  First I did this with MooseX::Params::Validate
> (MXPV), which gives me the better performance, no bug with 5.12, and a
> much nicer error message.  Then I scrapped MXPV altogether (since it
> was checking a lot of things that MS was checking for me already), and
> rolled my own using Moose::Util::TypeConstraints (MUTC) directly,
> which gave me even _better_ performance, still no bug with 5.12, and I
> can make my own damn error message. :)

Cool!


> So now I want to take it to the next step and have all this rolled
> into one, instead of having type checking separately, which is a bit
> clumsy.  To do what I want, I basically have two problems:
> 
> *) I need to figure out a way to use MS with MooseX::Declare (MXD).
> *) I need to figure out a way to extend MS.

Something you should know: the MS code was written in the manner of a
prototype in that it's a bit of a mess and not very extensible and it was just
about getting it to work.  I've been meaning to rewrite it into something
extensible.  Something with better separation between the signature parser and
the code generator.  If you want to take that on, we can talk about that.


> Now, as to the first problem, I suppose as a last resort I could do
> this by telling MS to use a different keyword than "method", but I
> really don't want to do that if I can help it.  In a perfect world,
> I'd be using basically Perl6 syntax for classes and methods, and have
> as little work to do as possible when we decide to upgrade to P6 (one
> day).

I think this is a red herring.  Method declaration syntax is going to be the
least of your worries when upgrading Perl 5 code to Perl 6.


> Now, two issues that I wanted some help with.  First, I was
> considering using a syntax for the types in the signatures something
> like this:
> 
>     method doit ( :$foo is Foo, :$bar is Bar )
> 
> instead of the more traditional
> 
>     method doit ( Foo :$foo, Bar :$bar )
> 
> I was thinking of doing it this way because that would allow me to
> sneak by without having to change any of the parsing that MS is
> already doing--it already not only reads the "is whatever" syntax, but
> also reads multiples, so theoretically something like ":$foo is Foo is
> ro" would work as well.  I'm not sure this syntax would be legal in
> P6, but I _think_ it would be, and it seems like a reasonable
> compromise.  Does this seem reasonable to everyone else as well?
>
> If so, MS does _nearly_ all the work for me.  The parsing is all done
> for me, and the type would just end up being stored in MS's internal
> structs as a trait.  Then I could access that and build some extra
> lines of code to do the type checking.

I would prefer it was left in the MXMS/Perl 6 style for one concrete reason:
overloading traits makes the meaning of the trait ambiguous.  You'll never
know in "is Foo" if "Foo" refers to a class or a trait.  If somebody defines a
class with the same name as a trait, what do you do then?  I hit this problem
with Moose attributes, where types and classes share the same syntax.

If you were going to go down that road, I would prefer:

    method doit( :$foo is class("Foo") )

but that's unwieldy and will probably require changing the MS parser.  So you
might as well patch MS to handle Perl 6 type syntax.  Then it will share
syntax with MXMS.

The type *syntax* has never been in question.  What to use to resolve the type
is the issue.  I don't want to saddle MS with Moose.  Any::Moose might be
acceptable.

I'd be happy if you wanted to alter the MS parser to handle MXMS/Perl 6 type
syntax but with no default behavior.  Then you can use $sig->{type} to do your
thing and later we can resolve what to do by default.


> My second issue is that, as I mentioned, I would need to wrap
> inject_from_signature.  But it looks to me like I can't override it
> and just call SUPER because it's not actually a method (just a sub).

You could fix that.

> And it's not a Moose class, so I can't use "around".  So the only
> thing I've been able to think of is something like:
> 
>     *Method::Signatures::orig_ifs = \&Method::Signatures::inject_from_signature;
>     *Method::Signatures::inject_from_signature = \&_inject_from_signature;
> 
>     sub _inject_from_signature
>     {
>         my $code = Method::Signatures::orig_ifs(@_);
>         # add more stuff to $code
>         return $code;
>     }
> 
> Again, that's just rough.  But that seems sorta ... well, hacky. :D
> Is that approach kosher, or am I missing something obvious?

It is hacky, but that's how we did things before "around".

> If anyone wants to hear any more details about my situation, just let
> me know, but I figured I wouldn't drown anyone in details unless they
> asked for it. :)  Any thoughts that anyone has on how I should (or
> shouldn't) proceed would be much appreciated.  TIA.



-- 
54. "Napalm sticks to kids" is *not* a motivational phrase.
    -- The 213 Things Skippy Is No Longer Allowed To Do In The U.S. Army
           http://skippyslist.com/list/



More information about the Perl5-syntax mailing list