drop package_ from method names
[gitmo/Package-Stash-XS.git] / t / 01-basic.t
CommitLineData
f10f6217 1use strict;
2use warnings;
3
4use Test::More;
13f4d7c3 5use Test::Fatal;
f10f6217 6
e94260da 7use Package::Stash;
f10f6217 8
20336547 9like(exception { Package::Stash->name }, qr/Can't call name as a class method/,
10 q{... can't call name() as a class method});
f10f6217 11
12{
13 package Foo;
14
15 use constant SOME_CONSTANT => 1;
16}
17
18# ----------------------------------------------------------------------
19## tests adding a HASH
20
e94260da 21my $foo_stash = Package::Stash->new('Foo');
f10f6217 22ok(!defined($Foo::{foo}), '... the %foo slot has not been created yet');
15c104e2 23ok(!$foo_stash->has_symbol('%foo'), '... the object agrees');
f10f6217 24ok(!defined($Foo::{foo}), '... checking doesn\' vivify');
25
20336547 26is(exception {
15c104e2 27 $foo_stash->add_symbol('%foo' => { one => 1 });
20336547 28}, undef, '... created %Foo::foo successfully');
f10f6217 29
30# ... scalar should NOT be created here
31
15c104e2 32ok(!$foo_stash->has_symbol('$foo'), '... SCALAR shouldnt have been created too');
33ok(!$foo_stash->has_symbol('@foo'), '... ARRAY shouldnt have been created too');
34ok(!$foo_stash->has_symbol('&foo'), '... CODE shouldnt have been created too');
f10f6217 35
36ok(defined($Foo::{foo}), '... the %foo slot was created successfully');
15c104e2 37ok($foo_stash->has_symbol('%foo'), '... the meta agrees');
f10f6217 38
39# check the value ...
40
41{
42 no strict 'refs';
43 ok(exists ${'Foo::foo'}{one}, '... our %foo was initialized correctly');
44 is(${'Foo::foo'}{one}, 1, '... our %foo was initialized correctly');
45}
46
15c104e2 47my $foo = $foo_stash->get_symbol('%foo');
f10f6217 48is_deeply({ one => 1 }, $foo, '... got the right package variable back');
49
50# ... make sure changes propogate up
51
52$foo->{two} = 2;
53
54{
55 no strict 'refs';
15c104e2 56 is(\%{'Foo::foo'}, $foo_stash->get_symbol('%foo'), '... our %foo is the same as the metas');
f10f6217 57
58 ok(exists ${'Foo::foo'}{two}, '... our %foo was updated correctly');
59 is(${'Foo::foo'}{two}, 2, '... our %foo was updated correctly');
60}
61
62# ----------------------------------------------------------------------
63## test adding an ARRAY
64
65ok(!defined($Foo::{bar}), '... the @bar slot has not been created yet');
66
20336547 67is(exception {
15c104e2 68 $foo_stash->add_symbol('@bar' => [ 1, 2, 3 ]);
20336547 69}, undef, '... created @Foo::bar successfully');
f10f6217 70
71ok(defined($Foo::{bar}), '... the @bar slot was created successfully');
15c104e2 72ok($foo_stash->has_symbol('@bar'), '... the meta agrees');
f10f6217 73
74# ... why does this not work ...
75
15c104e2 76ok(!$foo_stash->has_symbol('$bar'), '... SCALAR shouldnt have been created too');
77ok(!$foo_stash->has_symbol('%bar'), '... HASH shouldnt have been created too');
78ok(!$foo_stash->has_symbol('&bar'), '... CODE shouldnt have been created too');
f10f6217 79
80# check the value itself
81
82{
83 no strict 'refs';
84 is(scalar @{'Foo::bar'}, 3, '... our @bar was initialized correctly');
85 is(${'Foo::bar'}[1], 2, '... our @bar was initialized correctly');
86}
87
88# ----------------------------------------------------------------------
89## test adding a SCALAR
90
91ok(!defined($Foo::{baz}), '... the $baz slot has not been created yet');
92
20336547 93is(exception {
15c104e2 94 $foo_stash->add_symbol('$baz' => 10);
20336547 95}, undef, '... created $Foo::baz successfully');
f10f6217 96
97ok(defined($Foo::{baz}), '... the $baz slot was created successfully');
15c104e2 98ok($foo_stash->has_symbol('$baz'), '... the meta agrees');
f10f6217 99
15c104e2 100ok(!$foo_stash->has_symbol('@baz'), '... ARRAY shouldnt have been created too');
101ok(!$foo_stash->has_symbol('%baz'), '... HASH shouldnt have been created too');
102ok(!$foo_stash->has_symbol('&baz'), '... CODE shouldnt have been created too');
f10f6217 103
15c104e2 104is(${$foo_stash->get_symbol('$baz')}, 10, '... got the right value back');
f10f6217 105
106{
107 no strict 'refs';
108 ${'Foo::baz'} = 1;
109
110 is(${'Foo::baz'}, 1, '... our $baz was assigned to correctly');
15c104e2 111 is(${$foo_stash->get_symbol('$baz')}, 1, '... the meta agrees');
f10f6217 112}
113
114# ----------------------------------------------------------------------
115## test adding a CODE
116
117ok(!defined($Foo::{funk}), '... the &funk slot has not been created yet');
118
20336547 119is(exception {
15c104e2 120 $foo_stash->add_symbol('&funk' => sub { "Foo::funk" });
20336547 121}, undef, '... created &Foo::funk successfully');
f10f6217 122
123ok(defined($Foo::{funk}), '... the &funk slot was created successfully');
15c104e2 124ok($foo_stash->has_symbol('&funk'), '... the meta agrees');
f10f6217 125
15c104e2 126ok(!$foo_stash->has_symbol('$funk'), '... SCALAR shouldnt have been created too');
127ok(!$foo_stash->has_symbol('@funk'), '... ARRAY shouldnt have been created too');
128ok(!$foo_stash->has_symbol('%funk'), '... HASH shouldnt have been created too');
f10f6217 129
130{
131 no strict 'refs';
132 ok(defined &{'Foo::funk'}, '... our &funk exists');
133}
134
135is(Foo->funk(), 'Foo::funk', '... got the right value from the function');
136
137# ----------------------------------------------------------------------
138## test multiple slots in the glob
139
140my $ARRAY = [ 1, 2, 3 ];
141my $CODE = sub { "Foo::foo" };
142
20336547 143is(exception {
15c104e2 144 $foo_stash->add_symbol('@foo' => $ARRAY);
20336547 145}, undef, '... created @Foo::foo successfully');
f10f6217 146
15c104e2 147ok($foo_stash->has_symbol('@foo'), '... the @foo slot was added successfully');
148is($foo_stash->get_symbol('@foo'), $ARRAY, '... got the right values for @Foo::foo');
f10f6217 149
20336547 150is(exception {
15c104e2 151 $foo_stash->add_symbol('&foo' => $CODE);
20336547 152}, undef, '... created &Foo::foo successfully');
f10f6217 153
15c104e2 154ok($foo_stash->has_symbol('&foo'), '... the meta agrees');
155is($foo_stash->get_symbol('&foo'), $CODE, '... got the right value for &Foo::foo');
f10f6217 156
20336547 157is(exception {
15c104e2 158 $foo_stash->add_symbol('$foo' => 'Foo::foo');
20336547 159}, undef, '... created $Foo::foo successfully');
f10f6217 160
15c104e2 161ok($foo_stash->has_symbol('$foo'), '... the meta agrees');
162my $SCALAR = $foo_stash->get_symbol('$foo');
f10f6217 163is($$SCALAR, 'Foo::foo', '... got the right scalar value back');
164
165{
166 no strict 'refs';
167 is(${'Foo::foo'}, 'Foo::foo', '... got the right value from the scalar');
168}
169
20336547 170is(exception {
15c104e2 171 $foo_stash->remove_symbol('%foo');
20336547 172}, undef, '... removed %Foo::foo successfully');
f10f6217 173
15c104e2 174ok(!$foo_stash->has_symbol('%foo'), '... the %foo slot was removed successfully');
175ok($foo_stash->has_symbol('@foo'), '... the @foo slot still exists');
176ok($foo_stash->has_symbol('&foo'), '... the &foo slot still exists');
177ok($foo_stash->has_symbol('$foo'), '... the $foo slot still exists');
f10f6217 178
15c104e2 179is($foo_stash->get_symbol('@foo'), $ARRAY, '... got the right values for @Foo::foo');
180is($foo_stash->get_symbol('&foo'), $CODE, '... got the right value for &Foo::foo');
181is($foo_stash->get_symbol('$foo'), $SCALAR, '... got the right value for $Foo::foo');
f10f6217 182
183{
184 no strict 'refs';
185 ok(!defined(*{"Foo::foo"}{HASH}), '... the %foo slot has been removed successfully');
186 ok(defined(*{"Foo::foo"}{ARRAY}), '... the @foo slot has NOT been removed');
187 ok(defined(*{"Foo::foo"}{CODE}), '... the &foo slot has NOT been removed');
188 ok(defined(${"Foo::foo"}), '... the $foo slot has NOT been removed');
189}
190
20336547 191is(exception {
15c104e2 192 $foo_stash->remove_symbol('&foo');
20336547 193}, undef, '... removed &Foo::foo successfully');
f10f6217 194
15c104e2 195ok(!$foo_stash->has_symbol('&foo'), '... the &foo slot no longer exists');
f10f6217 196
15c104e2 197ok($foo_stash->has_symbol('@foo'), '... the @foo slot still exists');
198ok($foo_stash->has_symbol('$foo'), '... the $foo slot still exists');
f10f6217 199
15c104e2 200is($foo_stash->get_symbol('@foo'), $ARRAY, '... got the right values for @Foo::foo');
201is($foo_stash->get_symbol('$foo'), $SCALAR, '... got the right value for $Foo::foo');
f10f6217 202
203{
204 no strict 'refs';
205 ok(!defined(*{"Foo::foo"}{HASH}), '... the %foo slot has been removed successfully');
206 ok(!defined(*{"Foo::foo"}{CODE}), '... the &foo slot has now been removed');
207 ok(defined(*{"Foo::foo"}{ARRAY}), '... the @foo slot has NOT been removed');
208 ok(defined(${"Foo::foo"}), '... the $foo slot has NOT been removed');
209}
210
20336547 211is(exception {
15c104e2 212 $foo_stash->remove_symbol('$foo');
20336547 213}, undef, '... removed $Foo::foo successfully');
f10f6217 214
15c104e2 215ok(!$foo_stash->has_symbol('$foo'), '... the $foo slot no longer exists');
f10f6217 216
15c104e2 217ok($foo_stash->has_symbol('@foo'), '... the @foo slot still exists');
f10f6217 218
15c104e2 219is($foo_stash->get_symbol('@foo'), $ARRAY, '... got the right values for @Foo::foo');
f10f6217 220
221{
222 no strict 'refs';
223 ok(!defined(*{"Foo::foo"}{HASH}), '... the %foo slot has been removed successfully');
224 ok(!defined(*{"Foo::foo"}{CODE}), '... the &foo slot has now been removed');
225 ok(!defined(${"Foo::foo"}), '... the $foo slot has now been removed');
226 ok(defined(*{"Foo::foo"}{ARRAY}), '... the @foo slot has NOT been removed');
227}
228
3634ce60 229# check some errors
230
20336547 231like(exception {
15c104e2 232 $foo_stash->add_symbol('@bar', {})
20336547 233}, qr/HASH.*is not of type ARRAY/, "can't initialize a slot with the wrong type of value");
3634ce60 234
20336547 235like(exception {
15c104e2 236 $foo_stash->add_symbol('bar', [])
20336547 237}, qr/ARRAY.*is not of type IO/, "can't initialize a slot with the wrong type of value");
3634ce60 238
20336547 239like(exception {
15c104e2 240 $foo_stash->add_symbol('$bar', sub { })
20336547 241}, qr/CODE.*is not of type SCALAR/, "can't initialize a slot with the wrong type of value");
3634ce60 242
243{
244 package Bar;
245 open *foo, '<', $0;
246}
247
20336547 248like(exception {
15c104e2 249 $foo_stash->add_symbol('$bar', *Bar::foo{IO})
20336547 250}, qr/IO.*is not of type SCALAR/, "can't initialize a slot with the wrong type of value");
3634ce60 251
6ee333b8 252# check compile time manipulation
253
254{
255 package Baz;
256
257 our $foo = 23;
258 our @foo = "bar";
259 our %foo = (baz => 1);
260 sub foo { }
261 open *foo, '<', $0;
15c104e2 262 BEGIN { Package::Stash->new(__PACKAGE__)->remove_symbol('&foo') }
6ee333b8 263}
264
265{
e94260da 266 my $stash = Package::Stash->new('Baz');
15c104e2 267 is(${ $stash->get_symbol('$foo') }, 23, "got \$foo");
268 is_deeply($stash->get_symbol('@foo'), ['bar'], "got \@foo");
269 is_deeply($stash->get_symbol('%foo'), {baz => 1}, "got \%foo");
270 ok(!$stash->has_symbol('&foo'), "got \&foo");
271 is($stash->get_symbol('foo'), *Baz::foo{IO}, "got foo");
6ee333b8 272}
273
0a5166af 274{
275 package Quux;
276
277 our $foo = 23;
278 our @foo = "bar";
279 our %foo = (baz => 1);
280 sub foo { }
281 open *foo, '<', $0;
282}
283
284{
285 my $stash = Package::Stash->new('Quux');
286
287 my %expect = (
288 '$foo' => \23,
289 '@foo' => ["bar"],
290 '%foo' => { baz => 1 },
291 '&foo' => \&Quux::foo,
292 'foo' => *Quux::foo{IO},
293 );
294
295 for my $sym ( sort keys %expect ) {
296 is_deeply(
15c104e2 297 $stash->get_symbol($sym),
0a5166af 298 $expect{$sym},
299 "got expected value for $sym"
300 );
301 }
302
15c104e2 303 $stash->add_symbol('%bar' => {x => 42});
0a5166af 304
305 $expect{'%bar'} = {x => 42};
306
307 for my $sym ( sort keys %expect ) {
308 is_deeply(
15c104e2 309 $stash->get_symbol($sym),
0a5166af 310 $expect{$sym},
311 "got expected value for $sym"
312 );
313 }
314
15c104e2 315 $stash->add_symbol('%bar' => {x => 43});
0a5166af 316
317 $expect{'%bar'} = {x => 43};
318
319 for my $sym ( sort keys %expect ) {
320 is_deeply(
15c104e2 321 $stash->get_symbol($sym),
0a5166af 322 $expect{$sym},
323 "got expected value for $sym"
324 );
325 }
326}
327
d1f721b3 328{
329 package Quuux;
164ea080 330 our $foo;
d1f721b3 331 our @foo;
332 our @bar;
333 our %baz;
334 sub baz { }
335 use constant quux => 1;
336 use constant quuux => [];
337 sub quuuux;
338}
339
340{
341 my $quuux = Package::Stash->new('Quuux');
342 is_deeply(
15c104e2 343 [sort $quuux->list_all_symbols],
d1f721b3 344 [qw(BEGIN bar baz foo quuuux quuux quux)],
15c104e2 345 "list_all_symbols",
d1f721b3 346 );
347 is_deeply(
15c104e2 348 [sort $quuux->list_all_symbols('SCALAR')],
d1f721b3 349 [qw(foo)],
15c104e2 350 "list_all_symbols SCALAR",
d1f721b3 351 );
352 is_deeply(
15c104e2 353 [sort $quuux->list_all_symbols('ARRAY')],
d1f721b3 354 [qw(bar foo)],
15c104e2 355 "list_all_symbols ARRAY",
d1f721b3 356 );
357 is_deeply(
15c104e2 358 [sort $quuux->list_all_symbols('HASH')],
d1f721b3 359 [qw(baz)],
15c104e2 360 "list_all_symbols HASH",
d1f721b3 361 );
362 is_deeply(
15c104e2 363 [sort $quuux->list_all_symbols('CODE')],
d1f721b3 364 [qw(baz quuuux quuux quux)],
15c104e2 365 "list_all_symbols CODE",
d1f721b3 366 );
367}
368
f10f6217 369done_testing;