fix union with string types
[gitmo/MooseX-Types.git] / lib / MooseX / Types / TypeDecorator.pm
CommitLineData
4c2125a4 1package MooseX::Types::TypeDecorator;
2
a706b0f2 3use strict;
4use warnings;
4c2125a4 5
c1260541 6
bb5b7b28 7use Carp::Clan qw( ^MooseX::Types );
475bbd1d 8use Moose::Util::TypeConstraints ();
bb5b7b28 9use Moose::Meta::TypeConstraint::Union;
371efa05 10use Scalar::Util qw(blessed);
bb5b7b28 11
4c2125a4 12use overload(
13 '""' => sub {
c1260541 14 my $self = shift @_;
15 if(blessed $self) {
16 return $self->__type_constraint->name;
17 } else {
18 return "$self";
19 }
4c2125a4 20 },
cf1a8bfa 21 '|' => sub {
686e5888 22
23 ## It's kind of ugly that we need to know about Union Types, but this
24 ## is needed for syntax compatibility. Maybe someday we'll all just do
25 ## Or[Str,Str,Int]
442e42ba 26
27 my @tc = map {
28 blessed $_ ? $_ :
29 Moose::Util::TypeConstraints::find_or_parse_type_constraint($_)
30 } @_;
31
bb5b7b28 32 my $union = Moose::Meta::TypeConstraint::Union->new(type_constraints=>\@tc);
33 return Moose::Util::TypeConstraints::register_type_constraint($union);
cf1a8bfa 34 },
1d9a68a6 35 fallback => 1,
36
4c2125a4 37);
38
39=head1 NAME
40
41MooseX::Types::TypeDecorator - More flexible access to a Type Constraint
42
43=head1 DESCRIPTION
44
45This is a decorator object that contains an underlying type constraint. We use
46this to control access to the type constraint and to add some features.
47
a706b0f2 48=head1 METHODS
4c2125a4 49
a706b0f2 50This class defines the following methods.
4c2125a4 51
a706b0f2 52=head2 new
4c2125a4 53
a706b0f2 54Old school instantiation
4c2125a4 55
56=cut
57
a706b0f2 58sub new {
475bbd1d 59 my $class = shift @_;
60 if(my $arg = shift @_) {
371efa05 61 if(blessed $arg && $arg->isa('Moose::Meta::TypeConstraint')) {
475bbd1d 62 return bless {'__type_constraint'=>$arg}, $class;
e7d06577 63 } elsif(
64 blessed $arg &&
65 $arg->isa('MooseX::Types::UndefinedType')
66 ) {
475bbd1d 67 ## stub in case we'll need to handle these types differently
68 return bless {'__type_constraint'=>$arg}, $class;
371efa05 69 } elsif(blessed $arg) {
70 croak "Argument must be ->isa('Moose::Meta::TypeConstraint') or ->isa('MooseX::Types::UndefinedType'), not ". blessed $arg;
475bbd1d 71 } else {
d8f30dd4 72 croak "Argument cannot be '$arg'";
475bbd1d 73 }
bb5b7b28 74 } else {
e7d06577 75 croak "This method [new] requires a single argument.";
bb5b7b28 76 }
a706b0f2 77}
4c2125a4 78
5a9b6d38 79=head2 __type_constraint ($type_constraint)
4c2125a4 80
e088dd03 81Set/Get the type_constraint.
4c2125a4 82
83=cut
84
475bbd1d 85sub __type_constraint {
c1260541 86 my $self = shift @_;
371efa05 87 if(blessed $self) {
88 if(defined(my $tc = shift @_)) {
89 $self->{__type_constraint} = $tc;
90 }
91 return $self->{__type_constraint};
92 } else {
93 croak 'cannot call __type_constraint as a class method';
a706b0f2 94 }
a706b0f2 95}
4c2125a4 96
bb5b7b28 97=head2 isa
98
99handle $self->isa since AUTOLOAD can't.
100
101=cut
102
103sub isa {
371efa05 104 my ($self, $target) = @_;
bb5b7b28 105 if(defined $target) {
c1260541 106 if(blessed $self) {
107 return $self->__type_constraint->isa($target);
108 } else {
109 return;
110 }
bb5b7b28 111 } else {
112 return;
113 }
114}
115
116=head2 can
117
118handle $self->can since AUTOLOAD can't.
119
120=cut
121
122sub can {
123 my ($self, $target) = @_;
124 if(defined $target) {
c1260541 125 if(blessed $self) {
126 return $self->__type_constraint->can($target);
127 } else {
128 return;
129 }
bb5b7b28 130 } else {
131 return;
132 }
133}
134
c1260541 135=head2 meta
136
137have meta examine the underlying type constraints
138
139=cut
140
141sub meta {
142 my $self = shift @_;
143 if(blessed $self) {
144 return $self->__type_constraint->meta;
145 }
146}
147
148
a706b0f2 149=head2 DESTROY
4c2125a4 150
a706b0f2 151We might need it later
4c2125a4 152
a706b0f2 153=cut
4c2125a4 154
a706b0f2 155sub DESTROY {
156 return;
157}
4c2125a4 158
a706b0f2 159=head2 AUTOLOAD
4c2125a4 160
a706b0f2 161Delegate to the decorator targe
4c2125a4 162
a706b0f2 163=cut
4c2125a4 164
e088dd03 165sub AUTOLOAD {
077ac262 166
475bbd1d 167 my ($self, @args) = @_;
a706b0f2 168 my ($method) = (our $AUTOLOAD =~ /([^:]+)$/);
077ac262 169
170 ## We delegate with this method in an attempt to support a value of
171 ## __type_constraint which is also AUTOLOADing, in particular the class
172 ## MooseX::Types::UndefinedType which AUTOLOADs during autovivication.
173
174 my $return;
175
176 eval {
177 $return = $self->__type_constraint->$method(@args);
178 }; if($@) {
179 croak $@;
475bbd1d 180 } else {
077ac262 181 return $return;
475bbd1d 182 }
a706b0f2 183}
4c2125a4 184
185=head1 AUTHOR AND COPYRIGHT
186
187John Napiorkowski (jnapiorkowski) <jjnapiork@cpan.org>
188
189=head1 LICENSE
190
191This program is free software; you can redistribute it and/or modify
192it under the same terms as perl itself.
193
194=cut
195
1961;