File: 05notifier-loop.t

package info (click to toggle)
libio-async-perl 0.64-1
  • links: PTS, VCS
  • area: main
  • in suites: jessie, jessie-kfreebsd
  • size: 1,068 kB
  • ctags: 491
  • sloc: perl: 12,530; makefile: 8
file content (129 lines) | stat: -rw-r--r-- 3,262 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
#!/usr/bin/perl

use strict;
use warnings;

use Test::More;
use Test::Fatal;
use Test::Refcount;

use IO::Async::Notifier;

use IO::Async::Loop;

my $loop = IO::Async::Loop->new;
is_refcount( $loop, 2, '$loop has refcount 2 initially' );

{
   package TestNotifier;
   use base qw( IO::Async::Notifier );

   sub new
   {
      my $self = shift->SUPER::new;
      ( $self->{varref} ) = @_;
      return $self;
   }

   sub _add_to_loop
   {
      my $self = shift;
      ${ $self->{varref} } = 1;
   }

   sub _remove_from_loop
   {
      my $self = shift;
      ${ $self->{varref} } = 0;
   }
}

# $loop->add
{
   my $notifier = TestNotifier->new( \my $in_loop );

   is_deeply( [ $loop->notifiers ],
              [],
              '$loop->notifiers empty' );
   is( $notifier->loop, undef, 'loop undef' );

   $loop->add( $notifier );

   is_refcount( $loop, 2, '$loop has refcount 2 adding Notifier' );
   is_refcount( $notifier, 2, '$notifier has refcount 2 after adding to Loop' );

   is( $notifier->loop, $loop, 'loop $loop' );

   is_deeply( [ $loop->notifiers ],
              [ $notifier ],
              '$loop->notifiers contains new Notifier' );

   ok( $in_loop, '_add_to_loop called' );

   ok( exception { $loop->add( $notifier ) }, 'adding again produces error' );

   $loop->remove( $notifier );

   is( $notifier->loop, undef, '$notifier->loop is undef' );

   is_deeply( [ $loop->notifiers ],
              [],
              '$loop->notifiers empty once more' );

   ok( !$in_loop, '_remove_from_loop called' );

   is_oneref( $notifier, '$notifier has refcount 1 finally' );
}

# parent/child in Loop
{
   my $parent = TestNotifier->new( \my $parent_in_loop );
   my $child = TestNotifier->new( \my $child_in_loop );

   $loop->add( $parent );

   $parent->add_child( $child );

   is_refcount( $child, 3, '$child has refcount 3 after add_child within loop' );

   is( $parent->loop, $loop, '$parent->loop is $loop' );
   is( $child->loop,  $loop, '$child->loop is $loop' );

   ok( $parent_in_loop, '$parent now in loop' );
   ok( $child_in_loop,  '$child now in loop' );

   ok( exception { $loop->remove( $child ) }, 'Directly removing a child from the loop fails' );

   $loop->remove( $parent );

   is_deeply( [ $parent->children ], [ $child ], '$parent->children after $loop->remove' );

   is_oneref( $parent, '$parent has refcount 1 after removal from loop' );
   is_refcount( $child, 2, '$child has refcount 2 after removal of parent from loop' );

   is( $parent->loop, undef, '$parent->loop is undef' );
   is( $child->loop,  undef, '$child->loop is undef' );

   ok( !$parent_in_loop, '$parent no longer in loop' );
   ok( !$child_in_loop,  '$child no longer in loop' );

   ok( exception { $loop->add( $child ) }, 'Directly adding a child to the loop fails' );

   $loop->add( $parent );

   is( $child->loop, $loop, '$child->loop is $loop after remove/add parent' );

   ok( $parent_in_loop, '$parent now in loop' );
   ok( $child_in_loop,  '$child now in loop' );

   $loop->remove( $parent );

   $parent->remove_child( $child );

   is_oneref( $parent, '$parent has refcount 1 finally' );
   is_oneref( $child,  '$child has refcount 1 finally' );
}

is_refcount( $loop, 2, '$loop has refcount 2 finally' );

done_testing;