local copy of DBIC ordered_handle_updates branch
[dbsrgits/DBIx-Class.git] / t / 87ordered.t
1 # vim: filetype=perl
2 use strict;
3 use warnings;  
4
5 use Test::More;
6 use lib qw(t/lib);
7 use DBICTest;
8
9 my $schema = DBICTest->init_schema();
10
11 plan tests => 417;
12
13 my $employees = $schema->resultset('Employee');
14 $employees->delete();
15
16 foreach (1..5) {
17     $employees->create({ name=>'temp' });
18 }
19 $employees = $employees->search(undef,{order_by=>'position'});
20 ok( check_rs($employees), "intial positions" );
21
22 hammer_rs( $employees );
23
24 DBICTest::Employee->grouping_column('group_id');
25 $employees->delete();
26 foreach my $group_id (1..4) {
27     foreach (1..6) {
28         $employees->create({ name=>'temp', group_id=>$group_id });
29     }
30 }
31 $employees = $employees->search(undef,{order_by=>'group_id,position'});
32
33 foreach my $group_id (1..4) {
34     my $group_employees = $employees->search({group_id=>$group_id});
35     $group_employees->all();
36     ok( check_rs($group_employees), "group intial positions" );
37     hammer_rs( $group_employees );
38 }
39
40 my $group_3 = $employees->search({group_id=>3});
41 my $to_group = 1;
42 my $to_pos = undef;
43 while (my $employee = $group_3->next) {
44         $employee->move_to_group($to_group, $to_pos);
45         $to_pos++;
46         $to_group = $to_group==1 ? 2 : 1;
47 }
48 foreach my $group_id (1..4) {
49     my $group_employees = $employees->search({group_id=>$group_id});
50     $group_employees->all();
51     ok( check_rs($group_employees), "group positions after move_to_group" );
52 }
53
54 my $employee = $employees->search({group_id=>4})->first;
55 $employee->position(2);
56 $employee->update;
57 ok( check_rs($employees->search_rs({group_id=>4})), "overloaded update 1" );
58 $employee = $employees->search({group_id=>4})->first;
59 $employee->update({position=>3});
60 ok( check_rs($employees->search_rs({group_id=>4})), "overloaded update 2" );
61 $employee = $employees->search({group_id=>4})->first;
62 $employee->group_id(1);
63 $employee->update;
64 ok(
65         check_rs($employees->search_rs({group_id=>1})) && check_rs($employees->search_rs({group_id=>4})),
66         "overloaded update 3"
67 );
68 $employee = $employees->search({group_id=>4})->first;
69 $employee->update({group_id=>2});
70 ok(
71         check_rs($employees->search_rs({group_id=>2})) && check_rs($employees->search_rs({group_id=>4})),
72         "overloaded update 4"
73 );
74 $employee = $employees->search({group_id=>4})->first;
75 $employee->group_id(1);
76 $employee->position(3);
77 $employee->update;
78 ok(
79         check_rs($employees->search_rs({group_id=>1})) && check_rs($employees->search_rs({group_id=>4})),
80         "overloaded update 5"
81 );
82 $employee = $employees->search({group_id=>4})->first;
83 $employee->group_id(2);
84 $employee->position(undef);
85 $employee->update;
86 ok(
87         check_rs($employees->search_rs({group_id=>2})) && check_rs($employees->search_rs({group_id=>4})),
88         "overloaded update 6"
89 );
90 $employee = $employees->search({group_id=>4})->first;
91 $employee->update({group_id=>1,position=>undef});
92 ok(
93         check_rs($employees->search_rs({group_id=>1})) && check_rs($employees->search_rs({group_id=>4})),
94         "overloaded update 7"
95 );
96
97 sub hammer_rs {
98     my $rs = shift;
99     my $employee;
100     my $count = $rs->count();
101     my $position_column = $rs->result_class->position_column();
102     my $row;
103
104     foreach my $position (1..$count) {
105
106         ($row) = $rs->search({ $position_column=>$position })->all();
107         $row->move_previous();
108         ok( check_rs($rs), "move_previous( $position )" );
109
110         ($row) = $rs->search({ $position_column=>$position })->all();
111         $row->move_next();
112         ok( check_rs($rs), "move_next( $position )" );
113
114         ($row) = $rs->search({ $position_column=>$position })->all();
115         $row->move_first();
116         ok( check_rs($rs), "move_first( $position )" );
117
118         ($row) = $rs->search({ $position_column=>$position })->all();
119         $row->move_last();
120         ok( check_rs($rs), "move_last( $position )" );
121
122         foreach my $to_position (1..$count) {
123             ($row) = $rs->search({ $position_column=>$position })->all();
124             $row->move_to($to_position);
125             ok( check_rs($rs), "move_to( $position => $to_position )" );
126         }
127
128         ($row) = $rs->search({ position=>$position })->all();
129         if ($position==1) {
130             ok( !$row->previous_sibling(), 'no previous sibling' );
131             ok( !$row->first_sibling(), 'no first sibling' );
132         }
133         else {
134             ok( $row->previous_sibling(), 'previous sibling' );
135             ok( $row->first_sibling(), 'first sibling' );
136         }
137         if ($position==$count) {
138             ok( !$row->next_sibling(), 'no next sibling' );
139             ok( !$row->last_sibling(), 'no last sibling' );
140         }
141         else {
142             ok( $row->next_sibling(), 'next sibling' );
143             ok( $row->last_sibling(), 'last sibling' );
144         }
145
146     }
147 }
148
149 sub check_rs {
150     my( $rs ) = @_;
151     $rs->reset();
152     my $position_column = $rs->result_class->position_column();
153     my $expected_position = 0;
154     while (my $row = $rs->next()) {
155         $expected_position ++;
156         if ($row->get_column($position_column)!=$expected_position) {
157             return 0;
158         }
159     }
160     return 1;
161 }
162