line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
package Class::Meta::Class; |
2
|
|
|
|
|
|
|
|
3
|
|
|
|
|
|
|
=head1 NAME |
4
|
|
|
|
|
|
|
|
5
|
|
|
|
|
|
|
Class::Meta::Class - Class::Meta class introspection |
6
|
|
|
|
|
|
|
|
7
|
|
|
|
|
|
|
=head1 SYNOPSIS |
8
|
|
|
|
|
|
|
|
9
|
|
|
|
|
|
|
# Assuming MyApp::Thingy was generated by Class::Meta. |
10
|
|
|
|
|
|
|
my $class = MyApp::Thingy->my_class; |
11
|
|
|
|
|
|
|
my $thingy = MyApp::Thingy->new; |
12
|
|
|
|
|
|
|
|
13
|
|
|
|
|
|
|
print "Examining object of class ", $class->package, $/; |
14
|
|
|
|
|
|
|
|
15
|
|
|
|
|
|
|
print "\nConstructors:\n"; |
16
|
|
|
|
|
|
|
for my $ctor ($class->constructors) { |
17
|
|
|
|
|
|
|
print " o ", $ctor->name, $/; |
18
|
|
|
|
|
|
|
} |
19
|
|
|
|
|
|
|
|
20
|
|
|
|
|
|
|
print "\nAttributes:\n"; |
21
|
|
|
|
|
|
|
for my $attr ($class->attributes) { |
22
|
|
|
|
|
|
|
print " o ", $attr->name, " => ", $attr->get($thingy) $/; |
23
|
|
|
|
|
|
|
} |
24
|
|
|
|
|
|
|
|
25
|
|
|
|
|
|
|
print "\nMethods:\n"; |
26
|
|
|
|
|
|
|
for my $meth ($class->methods) { |
27
|
|
|
|
|
|
|
print " o ", $meth->name, $/; |
28
|
|
|
|
|
|
|
} |
29
|
|
|
|
|
|
|
|
30
|
|
|
|
|
|
|
=head1 DESCRIPTION |
31
|
|
|
|
|
|
|
|
32
|
|
|
|
|
|
|
Object of this class describe classes created by Class::Meta. They contain |
33
|
|
|
|
|
|
|
everything you need to know about a class to be able to put objects of that |
34
|
|
|
|
|
|
|
class to good use. In addition to retrieving meta data about the class itself, |
35
|
|
|
|
|
|
|
you can retrieve objects that describe the constructors, attributes, and |
36
|
|
|
|
|
|
|
methods of the class. See C for a fuller description |
37
|
|
|
|
|
|
|
of the utility of the Class::Meta suite of modules. |
38
|
|
|
|
|
|
|
|
39
|
|
|
|
|
|
|
Class::Meta::Class objects are created by Class::Meta; they are never |
40
|
|
|
|
|
|
|
instantiated directly in client code. To access the class object for a |
41
|
|
|
|
|
|
|
Class::Meta-generated class, simply call its C method. |
42
|
|
|
|
|
|
|
|
43
|
|
|
|
|
|
|
At this point, those attributes tend to be database-specific. Once other types |
44
|
|
|
|
|
|
|
of data stores are added (XML, LDAP, etc.), other attributes may be added to |
45
|
|
|
|
|
|
|
allow their schemas to be built, as well. |
46
|
|
|
|
|
|
|
|
47
|
|
|
|
|
|
|
=cut |
48
|
|
|
|
|
|
|
|
49
|
|
|
|
|
|
|
############################################################################## |
50
|
|
|
|
|
|
|
# Dependencies # |
51
|
|
|
|
|
|
|
############################################################################## |
52
|
21
|
|
|
21
|
|
28055
|
use strict; |
|
21
|
|
|
|
|
40
|
|
|
21
|
|
|
|
|
739
|
|
53
|
21
|
|
|
21
|
|
1016
|
use Class::ISA (); |
|
21
|
|
|
|
|
3343
|
|
|
21
|
|
|
|
|
404
|
|
54
|
21
|
|
|
21
|
|
916
|
use Class::Meta; |
|
21
|
|
|
|
|
79
|
|
|
21
|
|
|
|
|
502
|
|
55
|
21
|
|
|
21
|
|
33249
|
use Class::Meta::Attribute; |
|
21
|
|
|
|
|
63
|
|
|
21
|
|
|
|
|
806
|
|
56
|
21
|
|
|
21
|
|
13818
|
use Class::Meta::Method; |
|
21
|
|
|
|
|
56
|
|
|
21
|
|
|
|
|
12069
|
|
57
|
|
|
|
|
|
|
|
58
|
|
|
|
|
|
|
############################################################################## |
59
|
|
|
|
|
|
|
# Package Globals # |
60
|
|
|
|
|
|
|
############################################################################## |
61
|
|
|
|
|
|
|
our $VERSION = '0.66'; |
62
|
|
|
|
|
|
|
our @CARP_NOT = qw(Class::Meta); |
63
|
|
|
|
|
|
|
|
64
|
|
|
|
|
|
|
=head1 INTERFACE |
65
|
|
|
|
|
|
|
|
66
|
|
|
|
|
|
|
=head2 Constructors |
67
|
|
|
|
|
|
|
|
68
|
|
|
|
|
|
|
=head3 new |
69
|
|
|
|
|
|
|
|
70
|
|
|
|
|
|
|
A protected method for constructing a Class::Meta::Class object. Do not call |
71
|
|
|
|
|
|
|
this method directly; Call the L|Class::Meta/new"> constructor on a |
72
|
|
|
|
|
|
|
Class::Meta object, instead. A Class::Meta::Class object will be constructed |
73
|
|
|
|
|
|
|
by default, and can always be retrieved via the C method of the |
74
|
|
|
|
|
|
|
class for which it was constructed. |
75
|
|
|
|
|
|
|
|
76
|
|
|
|
|
|
|
=cut |
77
|
|
|
|
|
|
|
|
78
|
|
|
|
|
|
|
############################################################################## |
79
|
|
|
|
|
|
|
|
80
|
|
|
|
|
|
|
sub new { |
81
|
47
|
|
|
47
|
1
|
1870
|
my ($pkg, $spec) = @_; |
82
|
|
|
|
|
|
|
# Check to make sure that only Class::Meta or a subclass is |
83
|
|
|
|
|
|
|
# constructing a Class::Meta::Class object. |
84
|
47
|
|
|
|
|
129
|
my $caller = caller; |
85
|
47
|
100
|
100
|
|
|
446
|
Class::Meta->handle_error("Package '$caller' cannot create $pkg objects") |
86
|
|
|
|
|
|
|
unless UNIVERSAL::isa($caller, 'Class::Meta') |
87
|
|
|
|
|
|
|
|| UNIVERSAL::isa($caller, __PACKAGE__); |
88
|
|
|
|
|
|
|
|
89
|
|
|
|
|
|
|
# Set the name to be the same as the key by default. |
90
|
45
|
|
66
|
|
|
342
|
$spec->{name} ||= join ' ', map { ucfirst } split '_', $spec->{key}; |
|
33
|
|
|
|
|
215
|
|
91
|
|
|
|
|
|
|
|
92
|
|
|
|
|
|
|
# Set the abstract attribute. |
93
|
45
|
100
|
|
|
|
195
|
$spec->{abstract} = $spec->{abstract} ? 1 : 0; |
94
|
|
|
|
|
|
|
|
95
|
|
|
|
|
|
|
# Set the trusted attribute. |
96
|
45
|
50
|
|
|
|
242
|
$spec->{trusted} = exists $spec->{trust} |
|
|
100
|
|
|
|
|
|
97
|
|
|
|
|
|
|
? ref $spec->{trust} ? delete $spec->{trust} : [ delete $spec->{trust} ] |
98
|
|
|
|
|
|
|
: []; |
99
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
# Okay, create the class object. |
101
|
45
|
|
33
|
|
|
507
|
my $self = bless $spec, ref $pkg || $pkg; |
102
|
|
|
|
|
|
|
} |
103
|
|
|
|
|
|
|
|
104
|
|
|
|
|
|
|
############################################################################## |
105
|
|
|
|
|
|
|
# Instance Methods |
106
|
|
|
|
|
|
|
############################################################################## |
107
|
|
|
|
|
|
|
|
108
|
|
|
|
|
|
|
=head2 Instance Methods |
109
|
|
|
|
|
|
|
|
110
|
|
|
|
|
|
|
=head3 package |
111
|
|
|
|
|
|
|
|
112
|
|
|
|
|
|
|
my $pkg = $class->package; |
113
|
|
|
|
|
|
|
|
114
|
|
|
|
|
|
|
Returns the name of the package that the Class::Meta::Class object describes. |
115
|
|
|
|
|
|
|
|
116
|
|
|
|
|
|
|
=head3 key |
117
|
|
|
|
|
|
|
|
118
|
|
|
|
|
|
|
my $key = $class->key; |
119
|
|
|
|
|
|
|
|
120
|
|
|
|
|
|
|
Returns the key name that uniquely identifies the class across the |
121
|
|
|
|
|
|
|
application. The key name may simply be the same as the package name. |
122
|
|
|
|
|
|
|
|
123
|
|
|
|
|
|
|
=head3 name |
124
|
|
|
|
|
|
|
|
125
|
|
|
|
|
|
|
my $name = $class->name; |
126
|
|
|
|
|
|
|
|
127
|
|
|
|
|
|
|
Returns the name of the the class. This should generally be a descriptive |
128
|
|
|
|
|
|
|
name, rather than a package name. |
129
|
|
|
|
|
|
|
|
130
|
|
|
|
|
|
|
=head3 desc |
131
|
|
|
|
|
|
|
|
132
|
|
|
|
|
|
|
my $desc = $class->desc; |
133
|
|
|
|
|
|
|
|
134
|
|
|
|
|
|
|
Returns a description of the class. |
135
|
|
|
|
|
|
|
|
136
|
|
|
|
|
|
|
=head3 abstract |
137
|
|
|
|
|
|
|
|
138
|
|
|
|
|
|
|
my $abstract = $class->abstract; |
139
|
|
|
|
|
|
|
|
140
|
|
|
|
|
|
|
Returns true if the class is an abstract class, and false if it is not. |
141
|
|
|
|
|
|
|
|
142
|
|
|
|
|
|
|
=head3 default_type |
143
|
|
|
|
|
|
|
|
144
|
|
|
|
|
|
|
my $default_type = $class->default_type; |
145
|
|
|
|
|
|
|
|
146
|
|
|
|
|
|
|
The data type used for attributes of the class that were added with no |
147
|
|
|
|
|
|
|
explicit types. |
148
|
|
|
|
|
|
|
|
149
|
|
|
|
|
|
|
=head3 trusted |
150
|
|
|
|
|
|
|
|
151
|
|
|
|
|
|
|
my @trusted = $class->trusted; |
152
|
|
|
|
|
|
|
my $trusted = $class->trusted; |
153
|
|
|
|
|
|
|
|
154
|
|
|
|
|
|
|
In an array context, returns a list of class names that this class trusts. |
155
|
|
|
|
|
|
|
Returns the same list in an array reference in a scalar context. |
156
|
|
|
|
|
|
|
|
157
|
|
|
|
|
|
|
=cut |
158
|
|
|
|
|
|
|
|
159
|
82
|
|
|
82
|
1
|
379
|
sub package { $_[0]->{package} } |
160
|
6
|
|
|
6
|
1
|
49
|
sub key { $_[0]->{key} } |
161
|
5
|
|
|
5
|
1
|
36
|
sub name { $_[0]->{name} } |
162
|
5
|
|
|
5
|
1
|
37
|
sub desc { $_[0]->{desc} } |
163
|
121
|
|
|
121
|
1
|
643
|
sub abstract { $_[0]->{abstract} } |
164
|
7
|
|
|
7
|
1
|
469
|
sub default_type { $_[0]->{default_type} } |
165
|
6
|
100
|
|
6
|
1
|
23
|
sub trusted { wantarray ? @{ $_[0]->{trusted} } : [ @{ $_[0]->{trusted} } ] } |
|
1
|
|
|
|
|
8
|
|
|
5
|
|
|
|
|
29
|
|
166
|
|
|
|
|
|
|
|
167
|
|
|
|
|
|
|
############################################################################## |
168
|
|
|
|
|
|
|
|
169
|
|
|
|
|
|
|
=head3 is_a |
170
|
|
|
|
|
|
|
|
171
|
|
|
|
|
|
|
if ($class->is_a('MyApp::Base')) { |
172
|
|
|
|
|
|
|
print "All your base are belong to us\n"; |
173
|
|
|
|
|
|
|
} |
174
|
|
|
|
|
|
|
|
175
|
|
|
|
|
|
|
This method returns true if the object or package name passed as an argument |
176
|
|
|
|
|
|
|
is an instance of the class described by the Class::Meta::Class object or one |
177
|
|
|
|
|
|
|
of its subclasses. Functionally equivalent to |
178
|
|
|
|
|
|
|
C<< $class->package->isa($pkg) >>, but more efficient. |
179
|
|
|
|
|
|
|
|
180
|
|
|
|
|
|
|
=cut |
181
|
|
|
|
|
|
|
|
182
|
8
|
|
|
8
|
1
|
87
|
sub is_a { UNIVERSAL::isa($_[0]->{package}, $_[1]) } |
183
|
|
|
|
|
|
|
|
184
|
|
|
|
|
|
|
############################################################################## |
185
|
|
|
|
|
|
|
# Accessors to get at the constructor, attribute, and method objects. |
186
|
|
|
|
|
|
|
############################################################################## |
187
|
|
|
|
|
|
|
|
188
|
|
|
|
|
|
|
=head3 constructors |
189
|
|
|
|
|
|
|
|
190
|
|
|
|
|
|
|
my @constructors = $class->constructors; |
191
|
|
|
|
|
|
|
my $ctor = $class->constructors($ctor_name); |
192
|
|
|
|
|
|
|
@constructors = $class->constructors(@ctor_names); |
193
|
|
|
|
|
|
|
|
194
|
|
|
|
|
|
|
Provides access to the Class::Meta::Constructor objects that describe the |
195
|
|
|
|
|
|
|
constructors for the class. When called with no arguments, it returns all of |
196
|
|
|
|
|
|
|
the constructor objects. When called with a single argument, it returns the |
197
|
|
|
|
|
|
|
constructor object for the constructor with the specified name. When called |
198
|
|
|
|
|
|
|
with a list of arguments, returns all of the constructor objects with the |
199
|
|
|
|
|
|
|
specified names. |
200
|
|
|
|
|
|
|
|
201
|
|
|
|
|
|
|
=cut |
202
|
|
|
|
|
|
|
|
203
|
|
|
|
|
|
|
############################################################################## |
204
|
|
|
|
|
|
|
|
205
|
|
|
|
|
|
|
=head3 attributes |
206
|
|
|
|
|
|
|
|
207
|
|
|
|
|
|
|
my @attributes = $class->attributes; |
208
|
|
|
|
|
|
|
my $attr = $class->attributes($attr_name); |
209
|
|
|
|
|
|
|
@attributes = $class->attributes(@attr_names); |
210
|
|
|
|
|
|
|
|
211
|
|
|
|
|
|
|
Provides access to the Class::Meta::Attribute objects that describe the |
212
|
|
|
|
|
|
|
attributes for the class. When called with no arguments, it returns all of the |
213
|
|
|
|
|
|
|
attribute objects. When called with a single argument, it returns the |
214
|
|
|
|
|
|
|
attribute object for the attribute with the specified name. When called with a |
215
|
|
|
|
|
|
|
list of arguments, returns all of the attribute objects with the specified |
216
|
|
|
|
|
|
|
names. |
217
|
|
|
|
|
|
|
|
218
|
|
|
|
|
|
|
=cut |
219
|
|
|
|
|
|
|
|
220
|
|
|
|
|
|
|
############################################################################## |
221
|
|
|
|
|
|
|
|
222
|
|
|
|
|
|
|
=head3 methods |
223
|
|
|
|
|
|
|
|
224
|
|
|
|
|
|
|
my @methods = $class->methods; |
225
|
|
|
|
|
|
|
my $meth = $class->methods($meth_name); |
226
|
|
|
|
|
|
|
@methods = $class->methods(@meth_names); |
227
|
|
|
|
|
|
|
|
228
|
|
|
|
|
|
|
Provides access to the Class::Meta::Method objects that describe the methods |
229
|
|
|
|
|
|
|
for the class. When called with no arguments, it returns all of the method |
230
|
|
|
|
|
|
|
objects. When called with a single argument, it returns the method object for |
231
|
|
|
|
|
|
|
the method with the specified name. When called with a list of arguments, |
232
|
|
|
|
|
|
|
returns all of the method objects with the specified names. |
233
|
|
|
|
|
|
|
|
234
|
|
|
|
|
|
|
=cut |
235
|
|
|
|
|
|
|
|
236
|
|
|
|
|
|
|
for ([qw(attributes attr)], [qw(methods meth)], [qw(constructors ctor)]) { |
237
|
|
|
|
|
|
|
my ($meth, $key) = @$_; |
238
|
21
|
|
|
21
|
|
128
|
no strict 'refs'; |
|
21
|
|
|
|
|
46
|
|
|
21
|
|
|
|
|
29029
|
|
239
|
|
|
|
|
|
|
*{$meth} = sub { |
240
|
118
|
|
|
118
|
|
64763
|
my $self = shift; |
|
|
|
|
52
|
|
|
|
241
|
118
|
|
|
|
|
446
|
my $objs = $self->{"${key}s"}; |
242
|
|
|
|
|
|
|
# Who's talking to us? |
243
|
118
|
|
|
|
|
283
|
my $caller = caller; |
244
|
118
|
|
|
|
|
1425
|
for (my $i = 1; UNIVERSAL::isa($caller, __PACKAGE__); $i++) { |
245
|
0
|
|
|
|
|
0
|
$caller = caller($i); |
246
|
|
|
|
|
|
|
} |
247
|
|
|
|
|
|
|
# XXX Do we want to make these additive instead of discreet, so that |
248
|
|
|
|
|
|
|
# a class can get both protected and trusted attributes, for example? |
249
|
118
|
|
|
|
|
188
|
my $list = do { |
250
|
118
|
100
|
|
|
|
689
|
if (@_) { |
|
|
100
|
|
|
|
|
|
|
|
50
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
251
|
|
|
|
|
|
|
# Explicit list requested. |
252
|
98
|
|
|
|
|
456
|
\@_; |
253
|
|
|
|
|
|
|
} elsif ($caller eq $self->{package}) { |
254
|
|
|
|
|
|
|
# List of protected interface objects. |
255
|
8
|
50
|
|
|
|
53
|
$self->{"priv_$key\_ord"} || []; |
256
|
|
|
|
|
|
|
} elsif (UNIVERSAL::isa($caller, $self->{package})) { |
257
|
|
|
|
|
|
|
# List of protected interface objects. |
258
|
0
|
0
|
|
|
|
0
|
$self->{"prot_$key\_ord"} || []; |
259
|
|
|
|
|
|
|
} elsif (_trusted($self, $caller)) { |
260
|
|
|
|
|
|
|
# List of trusted interface objects. |
261
|
7
|
50
|
|
|
|
41
|
$self->{"trst_$key\_ord"} || []; |
262
|
|
|
|
|
|
|
} else { |
263
|
|
|
|
|
|
|
# List of public interface objects. |
264
|
5
|
50
|
|
|
|
35
|
$self->{"$key\_ord"} || []; |
265
|
|
|
|
|
|
|
} |
266
|
|
|
|
|
|
|
}; |
267
|
118
|
100
|
|
|
|
1045
|
return @$list == 1 ? $objs->{$list->[0]} : @{$objs}{@$list}; |
|
21
|
|
|
|
|
155
|
|
268
|
|
|
|
|
|
|
}; |
269
|
|
|
|
|
|
|
} |
270
|
|
|
|
|
|
|
|
271
|
|
|
|
|
|
|
############################################################################## |
272
|
|
|
|
|
|
|
|
273
|
|
|
|
|
|
|
=head3 parents |
274
|
|
|
|
|
|
|
|
275
|
|
|
|
|
|
|
my @parents = $class->parents; |
276
|
|
|
|
|
|
|
|
277
|
|
|
|
|
|
|
Returns a list of Class::Meta::Class objects representing all of the |
278
|
|
|
|
|
|
|
Class::Meta-built parent classes of a class. |
279
|
|
|
|
|
|
|
|
280
|
|
|
|
|
|
|
=cut |
281
|
|
|
|
|
|
|
|
282
|
|
|
|
|
|
|
sub parents { |
283
|
2
|
|
|
2
|
1
|
6
|
my $self = shift; |
284
|
2
|
|
|
|
|
11
|
return map { $_->my_class } grep { UNIVERSAL::can($_, 'my_class') } |
|
1
|
|
|
|
|
6
|
|
|
1
|
|
|
|
|
48
|
|
285
|
|
|
|
|
|
|
Class::ISA::super_path($self->package); |
286
|
|
|
|
|
|
|
} |
287
|
|
|
|
|
|
|
|
288
|
|
|
|
|
|
|
############################################################################## |
289
|
|
|
|
|
|
|
|
290
|
|
|
|
|
|
|
=head3 handle_error |
291
|
|
|
|
|
|
|
|
292
|
|
|
|
|
|
|
$class->handle_error($error) |
293
|
|
|
|
|
|
|
|
294
|
|
|
|
|
|
|
Handles Class::Meta-related errors using either the error handler specified |
295
|
|
|
|
|
|
|
when the Class::Meta::Class object was created or the default error handler at |
296
|
|
|
|
|
|
|
the time the Class::Meta::Class object was created. |
297
|
|
|
|
|
|
|
|
298
|
|
|
|
|
|
|
=cut |
299
|
|
|
|
|
|
|
|
300
|
|
|
|
|
|
|
sub handle_error { |
301
|
265
|
|
|
265
|
1
|
819
|
my $code = shift->{error_handler}; |
302
|
265
|
|
|
|
|
1362
|
$code->(join '', @_) |
303
|
|
|
|
|
|
|
} |
304
|
|
|
|
|
|
|
|
305
|
|
|
|
|
|
|
############################################################################## |
306
|
|
|
|
|
|
|
|
307
|
|
|
|
|
|
|
=head3 build |
308
|
|
|
|
|
|
|
|
309
|
|
|
|
|
|
|
$class->build($classes); |
310
|
|
|
|
|
|
|
|
311
|
|
|
|
|
|
|
This is a protected method, designed to be called only by the Class::Meta |
312
|
|
|
|
|
|
|
class or a subclass of Class::Meta. It copies the attribute, constructor, and |
313
|
|
|
|
|
|
|
method objects from all of the parent classes of the class object so that they |
314
|
|
|
|
|
|
|
will be readily available from the C, C, and |
315
|
|
|
|
|
|
|
C methods. Its sole argument is a reference to the hash of all |
316
|
|
|
|
|
|
|
Class::Meta::Class objects (keyed off their package names) stored by |
317
|
|
|
|
|
|
|
Class::Meta. |
318
|
|
|
|
|
|
|
|
319
|
|
|
|
|
|
|
Although you should never call this method directly, subclasses of |
320
|
|
|
|
|
|
|
Class::Meta::Class may need to override its behavior. |
321
|
|
|
|
|
|
|
|
322
|
|
|
|
|
|
|
=cut |
323
|
|
|
|
|
|
|
|
324
|
|
|
|
|
|
|
sub build { |
325
|
32
|
|
|
32
|
1
|
64
|
my ($self, $classes) = @_; |
326
|
|
|
|
|
|
|
|
327
|
|
|
|
|
|
|
# Check to make sure that only Class::Meta or a subclass is building |
328
|
|
|
|
|
|
|
# attribute accessors. |
329
|
32
|
|
|
|
|
86
|
my $caller = caller; |
330
|
32
|
100
|
66
|
|
|
1455
|
$self->handle_error("Package '$caller' cannot call " . ref($self) |
331
|
|
|
|
|
|
|
. "->build") |
332
|
|
|
|
|
|
|
unless UNIVERSAL::isa($caller, 'Class::Meta') |
333
|
|
|
|
|
|
|
|| UNIVERSAL::isa($caller, __PACKAGE__); |
334
|
|
|
|
|
|
|
|
335
|
|
|
|
|
|
|
# Copy attributes again to make sure that overridden attributes |
336
|
|
|
|
|
|
|
# truly override. |
337
|
30
|
|
|
|
|
120
|
$self->_inherit($classes, qw(ctor meth attr)); |
338
|
|
|
|
|
|
|
} |
339
|
|
|
|
|
|
|
|
340
|
|
|
|
|
|
|
############################################################################## |
341
|
|
|
|
|
|
|
# Private Methods. |
342
|
|
|
|
|
|
|
############################################################################## |
343
|
|
|
|
|
|
|
|
344
|
|
|
|
|
|
|
sub _inherit { |
345
|
74
|
|
|
74
|
|
191
|
my $self = shift; |
346
|
74
|
|
|
|
|
118
|
my $classes = shift; |
347
|
|
|
|
|
|
|
|
348
|
|
|
|
|
|
|
# Get a list of all of the parent classes. |
349
|
74
|
|
|
|
|
298
|
my $package = $self->package; |
350
|
74
|
|
|
|
|
296
|
my @classes = reverse Class::ISA::self_and_super_path($package); |
351
|
|
|
|
|
|
|
|
352
|
|
|
|
|
|
|
# Hrm, how can I avoid iterating over the classes a second time? |
353
|
74
|
|
|
|
|
1567
|
my @trusted; |
354
|
74
|
|
|
|
|
161
|
for my $super (@classes) { |
355
|
87
|
100
|
|
|
|
329
|
push @trusted, @{$classes->{$super}{trusted}} |
|
82
|
|
|
|
|
365
|
|
356
|
|
|
|
|
|
|
if $classes->{$super}{trusted}; |
357
|
|
|
|
|
|
|
} |
358
|
74
|
100
|
|
|
|
245
|
$self->{trusted} = \@trusted if @trusted; |
359
|
|
|
|
|
|
|
|
360
|
|
|
|
|
|
|
# For each metadata class, copy the parents' objects. |
361
|
74
|
|
|
|
|
172
|
for my $key (@_) { |
362
|
134
|
|
|
|
|
214
|
my (@lookup, @all, @ord, @prot, @trst, @priv, %sall, %sord, %sprot, %strst); |
363
|
134
|
|
|
|
|
222
|
for my $super (@classes) { |
364
|
155
|
|
|
|
|
256
|
my $class = $classes->{$super}; |
365
|
155
|
100
|
|
|
|
653
|
if (my $things = $class->{$key . 's'}) { |
366
|
88
|
|
|
|
|
108
|
push @lookup, %{ $things }; |
|
88
|
|
|
|
|
316
|
|
367
|
|
|
|
|
|
|
|
368
|
88
|
100
|
|
|
|
349
|
if (my $ord = $class->{"$key\_ord"}) { |
369
|
64
|
|
|
|
|
85
|
push @ord, grep { not $sord{$_}++ } @{ $ord} ; |
|
127
|
|
|
|
|
461
|
|
|
64
|
|
|
|
|
117
|
|
370
|
|
|
|
|
|
|
} |
371
|
|
|
|
|
|
|
|
372
|
88
|
100
|
|
|
|
327
|
if (my $prot = $class->{"prot_$key\_ord"}) { |
373
|
64
|
|
|
|
|
102
|
push @prot, grep { not $sprot{$_}++ } @{ $prot }; |
|
142
|
|
|
|
|
583
|
|
|
64
|
|
|
|
|
102
|
|
374
|
|
|
|
|
|
|
} |
375
|
|
|
|
|
|
|
|
376
|
88
|
100
|
|
|
|
302
|
if (my $trust = $class->{"trst_$key\_ord"}) { |
377
|
64
|
|
|
|
|
240
|
push @trst, grep { not $strst{$_}++ } @{ $trust }; |
|
142
|
|
|
|
|
379
|
|
|
64
|
|
|
|
|
111
|
|
378
|
|
|
|
|
|
|
} |
379
|
|
|
|
|
|
|
|
380
|
88
|
100
|
|
|
|
327
|
if (my $all = $class->{"all_$key\_ord"}) { |
381
|
64
|
|
|
|
|
77
|
for my $name (@{ $all }) { |
|
64
|
|
|
|
|
125
|
|
382
|
172
|
100
|
|
|
|
546
|
next if $sall{$name}++; |
383
|
155
|
|
|
|
|
221
|
push @all, $name; |
384
|
155
|
|
|
|
|
471
|
my $view = $things->{$name}->view; |
385
|
155
|
100
|
100
|
|
|
865
|
push @priv, $name if $super eq $package |
|
|
|
100
|
|
|
|
|
|
|
|
66
|
|
|
|
|
386
|
|
|
|
|
|
|
|| $view == Class::Meta::PUBLIC |
387
|
|
|
|
|
|
|
|| $view == Class::Meta::PROTECTED |
388
|
|
|
|
|
|
|
|| _trusted($class, $package); |
389
|
|
|
|
|
|
|
} |
390
|
|
|
|
|
|
|
} |
391
|
|
|
|
|
|
|
} |
392
|
|
|
|
|
|
|
} |
393
|
|
|
|
|
|
|
|
394
|
134
|
100
|
|
|
|
520
|
$self->{"${key}s"} = { @lookup } if @lookup; |
395
|
134
|
100
|
|
|
|
504
|
$self->{"$key\_ord"} = \@ord if @ord; |
396
|
134
|
100
|
|
|
|
399
|
$self->{"all_$key\_ord"} = \@all if @all; |
397
|
134
|
100
|
|
|
|
732
|
$self->{"prot_$key\_ord"} = \@prot if @prot; |
398
|
134
|
100
|
|
|
|
377
|
$self->{"trst_$key\_ord"} = \@trst if @trst; |
399
|
134
|
100
|
|
|
|
761
|
$self->{"priv_$key\_ord"} = \@priv if @priv; |
400
|
|
|
|
|
|
|
} |
401
|
|
|
|
|
|
|
|
402
|
|
|
|
|
|
|
|
403
|
74
|
|
|
|
|
249
|
return $self; |
404
|
|
|
|
|
|
|
} |
405
|
|
|
|
|
|
|
|
406
|
|
|
|
|
|
|
sub _trusted { |
407
|
26
|
|
|
26
|
|
52
|
my ($self, $caller) = @_; |
408
|
26
|
50
|
|
|
|
89
|
my $trusted = $self->{trusted} or return; |
409
|
26
|
|
|
|
|
40
|
for my $pkg (@{$trusted}) { |
|
26
|
|
|
|
|
61
|
|
410
|
21
|
100
|
|
|
|
187
|
return 1 if UNIVERSAL::isa($caller, $pkg); |
411
|
|
|
|
|
|
|
} |
412
|
19
|
|
|
|
|
94
|
return; |
413
|
|
|
|
|
|
|
} |
414
|
|
|
|
|
|
|
|
415
|
|
|
|
|
|
|
1; |
416
|
|
|
|
|
|
|
__END__ |