Some errors for auto_deref
[gitmo/Mouse.git] / lib / Mouse.pm
CommitLineData
c3398f5b 1#!perl
2package Mouse;
3use strict;
4use warnings;
5
6our $VERSION = '0.01';
7
8use Sub::Exporter;
9use Carp 'confess';
10use Scalar::Util 'blessed';
11
306290e8 12use Mouse::Meta::Attribute;
13use Mouse::Meta::Class;
c3398f5b 14use Mouse::Object;
d60c78b9 15use Mouse::TypeRegistry;
c3398f5b 16
17do {
18 my $CALLER;
19
20 my %exports = (
21 meta => sub {
306290e8 22 my $meta = Mouse::Meta::Class->initialize($CALLER);
c3398f5b 23 return sub { $meta };
24 },
25
26 extends => sub {
27 my $caller = $CALLER;
28 return sub {
29 $caller->meta->superclasses(@_);
30 };
31 },
32
33 has => sub {
34 return sub {
35 my $package = caller;
36 my $names = shift;
37 $names = [$names] if !ref($names);
38
39 for my $name (@$names) {
306290e8 40 Mouse::Meta::Attribute->create($package, $name, @_);
c3398f5b 41 }
42 };
43 },
44
45 confess => sub {
b17094ce 46 return \&confess;
c3398f5b 47 },
48
49 blessed => sub {
b17094ce 50 return \&blessed;
c3398f5b 51 },
52 );
53
54 my $exporter = Sub::Exporter::build_exporter({
55 exports => \%exports,
56 groups => { default => [':all'] },
57 });
58
59 sub import {
60 $CALLER = caller;
61
62 strict->import;
63 warnings->import;
64
306290e8 65 my $meta = Mouse::Meta::Class->initialize($CALLER);
ca73a208 66 $meta->superclasses('Mouse::Object')
67 unless $meta->superclasses;
c3398f5b 68
69 goto $exporter;
70 }
71
72 sub unimport {
73 my $caller = caller;
74
75 no strict 'refs';
76 for my $keyword (keys %exports) {
77 next if $keyword eq 'meta'; # we don't delete this one
78 delete ${ $caller . '::' }{$keyword};
79 }
80 }
81};
82
83sub load_class {
84 my $class = shift;
262801ef 85
9694b71b 86 if (ref($class) || !defined($class) || !length($class)) {
87 my $display = defined($class) ? $class : 'undef';
88 confess "Invalid class name ($display)";
89 }
c3398f5b 90
2a674d23 91 return 1 if is_class_loaded($class);
92
c3398f5b 93 (my $file = "$class.pm") =~ s{::}{/}g;
94
95 eval { CORE::require($file) };
2a674d23 96 confess "Could not load class ($class) because : $@" if $@;
c3398f5b 97
98 return 1;
99}
100
2a674d23 101sub is_class_loaded {
102 my $class = shift;
103
7ecc2123 104 return 0 if ref($class) || !defined($class) || !length($class);
105
bf134049 106 # walk the symbol table tree to avoid autovififying
107 # \*{${main::}{"Foo::"}} == \*main::Foo::
108
109 my $pack = \*::;
110 foreach my $part (split('::', $class)) {
111 return 0 unless exists ${$$pack}{"${part}::"};
112 $pack = \*{${$$pack}{"${part}::"}};
2a674d23 113 }
bf134049 114
115 # check for $VERSION or @ISA
116 return 1 if exists ${$$pack}{VERSION}
117 && defined *{${$$pack}{VERSION}}{SCALAR};
118 return 1 if exists ${$$pack}{ISA}
119 && defined *{${$$pack}{ISA}}{ARRAY};
120
121 # check for any method
122 foreach ( keys %{$$pack} ) {
123 next if substr($_, -2, 2) eq '::';
124 return 1 if defined *{${$$pack}{$_}}{CODE};
125 }
126
127 # fail
2a674d23 128 return 0;
129}
130
c3398f5b 1311;
132
133__END__
134
135=head1 NAME
136
6caea456 137Mouse - Moose minus antlers
c3398f5b 138
139=head1 VERSION
140
141Version 0.01 released ???
142
143=head1 SYNOPSIS
144
145 package Point;
6caea456 146 use Mouse; # automatically turns on strict and warnings
147
148 has 'x' => (is => 'rw', isa => 'Int');
149 has 'y' => (is => 'rw', isa => 'Int');
150
151 sub clear {
152 my $self = shift;
153 $self->x(0);
154 $self->y(0);
155 }
156
157 package Point3D;
c3398f5b 158 use Mouse;
159
6caea456 160 extends 'Point';
c3398f5b 161
6caea456 162 has 'z' => (is => 'rw', isa => 'Int');
163
164 #after 'clear' => sub {
165 # my $self = shift;
166 # $self->z(0);
167 #};
c3398f5b 168
169=head1 DESCRIPTION
170
171Moose.
172
173=head1 INTERFACE
174
306290e8 175=head2 meta -> Mouse::Meta::Class
c3398f5b 176
177Returns this class' metaclass instance.
178
179=head2 extends superclasses
180
181Sets this class' superclasses.
182
183=head2 has (name|names) => parameters
184
185Adds an attribute (or if passed an arrayref of names, multiple attributes) to
186this class.
187
188=head2 confess error -> BOOM
189
190L<Carp/confess> for your convenience.
191
192=head2 blessed value -> ClassName | undef
193
194L<Scalar::Util/blessed> for your convenience.
195
196=head1 MISC
197
198=head2 import
199
6caea456 200Importing Mouse will default your class' superclass list to L<Mouse::Object>.
c3398f5b 201You may use L</extends> to replace the superclass list.
202
203=head2 unimport
204
205Please unimport Mouse so that if someone calls one of the keywords (such as
206L</extends>) it will break loudly instead breaking subtly.
207
208=head1 FUNCTIONS
209
210=head2 load_class Class::Name
211
6caea456 212This will load a given C<Class::Name> (or die if it's not loadable).
c3398f5b 213This function can be used in place of tricks like
214C<eval "use $module"> or using C<require>.
215
262801ef 216=head2 is_class_loaded Class::Name -> Bool
217
218Returns whether this class is actually loaded or not. It uses a heuristic which
219involves checking for the existence of C<$VERSION>, C<@ISA>, and any
220locally-defined method.
221
c3398f5b 222=head1 AUTHOR
223
224Shawn M Moore, C<< <sartak at gmail.com> >>
225
226=head1 BUGS
227
228No known bugs.
229
230Please report any bugs through RT: email
231C<bug-mouse at rt.cpan.org>, or browse
232L<http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Mouse>.
233
234=head1 COPYRIGHT AND LICENSE
235
236Copyright 2008 Shawn M Moore.
237
238This program is free software; you can redistribute it and/or modify it
239under the same terms as Perl itself.
240
241=cut
242