Commit | Line | Data |
c9d2e0a2 |
1 | use strict; |
2 | use warnings; |
68de9438 |
3 | |
c9d2e0a2 |
4 | use Test::More; |
d7a58a29 |
5 | use Test::Warn; |
6 | use Test::Exception; |
7 | |
4bea1fe7 |
8 | use Path::Class; |
9 | use File::Copy; |
10 | use Time::HiRes qw/time sleep/; |
11 | |
12 | use lib qw(t/lib); |
8d6b1478 |
13 | use DBICTest; |
4bea1fe7 |
14 | |
1d48fcff |
15 | my ($dsn, $user, $pass); |
16 | |
c9d2e0a2 |
17 | BEGIN { |
1d48fcff |
18 | ($dsn, $user, $pass) = @ENV{map { "DBICTEST_MYSQL_${_}" } qw/DSN USER PASS/}; |
19 | |
20 | plan skip_all => 'Set $ENV{DBICTEST_MYSQL_DSN}, _USER and _PASS to run this test' |
8424c090 |
21 | unless ($dsn); |
1d48fcff |
22 | |
2527233b |
23 | require DBIx::Class; |
7f6f5b69 |
24 | plan skip_all => |
2527233b |
25 | 'Test needs ' . DBIx::Class::Optional::Dependencies->req_missing_for ('deploy') |
49b3a264 |
26 | unless DBIx::Class::Optional::Dependencies->req_ok_for ('deploy'); |
27 | |
28 | plan skip_all => |
29 | 'Test needs ' . DBIx::Class::Optional::Dependencies->req_missing_for ('test_rdbms_mysql') |
30 | unless DBIx::Class::Optional::Dependencies->req_ok_for ('test_rdbms_mysql'); |
c9d2e0a2 |
31 | } |
32 | |
8d6b1478 |
33 | # this is just to grab a lock |
34 | { |
35 | my $s = DBICTest::Schema->connect($dsn, $user, $pass); |
36 | } |
37 | |
eed5492f |
38 | # in case it came from the env |
39 | $ENV{DBIC_NO_VERSION_CHECK} = 0; |
40 | |
b9ae34d3 |
41 | use_ok('DBICVersion_v1'); |
b9ae34d3 |
42 | |
b4b1e91c |
43 | my $version_table_name = 'dbix_class_schema_versions'; |
44 | my $old_table_name = 'SchemaVersions'; |
45 | |
8d6b1478 |
46 | my $ddl_dir = dir(qw/t var/, "versioning_ddl-$$"); |
47 | $ddl_dir->mkpath unless -d $ddl_dir; |
b9ae34d3 |
48 | |
1475105d |
49 | my $fn = { |
d7a58a29 |
50 | v1 => $ddl_dir->file ('DBICVersion-Schema-1.0-MySQL.sql'), |
51 | v2 => $ddl_dir->file ('DBICVersion-Schema-2.0-MySQL.sql'), |
d40a22fc |
52 | v3 => $ddl_dir->file ('DBICVersion-Schema-3.0-MySQL.sql'), |
4f591da2 |
53 | trans_v12 => $ddl_dir->file ('DBICVersion-Schema-1.0-2.0-MySQL.sql'), |
54 | trans_v23 => $ddl_dir->file ('DBICVersion-Schema-2.0-3.0-MySQL.sql'), |
1475105d |
55 | }; |
56 | |
d2bc7045 |
57 | my $schema_v1 = DBICVersion::Schema->connect($dsn, $user, $pass, { ignore_version => 1 }); |
58 | eval { $schema_v1->storage->dbh->do('drop table ' . $version_table_name) }; |
59 | eval { $schema_v1->storage->dbh->do('drop table ' . $old_table_name) }; |
c9d2e0a2 |
60 | |
d2bc7045 |
61 | is($schema_v1->ddl_filename('MySQL', '1.0', $ddl_dir), $fn->{v1}, 'Filename creation working'); |
1475105d |
62 | unlink( $fn->{v1} ) if ( -e $fn->{v1} ); |
d2bc7045 |
63 | $schema_v1->create_ddl_dir('MySQL', undef, $ddl_dir); |
c9d2e0a2 |
64 | |
1475105d |
65 | ok(-f $fn->{v1}, 'Created DDL file'); |
d2bc7045 |
66 | $schema_v1->deploy({ add_drop_table => 1 }); |
c9d2e0a2 |
67 | |
d2bc7045 |
68 | my $tvrs = $schema_v1->{vschema}->resultset('Table'); |
69 | is($schema_v1->_source_exists($tvrs), 1, 'Created schema from DDL file'); |
c9d2e0a2 |
70 | |
1475105d |
71 | # loading a new module defining a new version of the same table |
72 | DBICVersion::Schema->_unregister_source ('Table'); |
7eb9a6f1 |
73 | use_ok('DBICVersion_v2'); |
1475105d |
74 | |
d2bc7045 |
75 | my $schema_v2 = DBICVersion::Schema->connect($dsn, $user, $pass, { ignore_version => 1 }); |
f925f7cb |
76 | { |
1475105d |
77 | unlink($fn->{v2}); |
d2bc7045 |
78 | unlink($fn->{trans_v12}); |
f925f7cb |
79 | |
d2bc7045 |
80 | is($schema_v2->get_db_version(), '1.0', 'get_db_version ok'); |
81 | is($schema_v2->schema_version, '2.0', 'schema version ok'); |
82 | $schema_v2->create_ddl_dir('MySQL', '2.0', $ddl_dir, '1.0'); |
83 | ok(-f $fn->{trans_v12}, 'Created DDL file'); |
1475105d |
84 | |
d7a58a29 |
85 | warnings_like ( |
d40a22fc |
86 | sub { $schema_v2->upgrade() }, |
d7a58a29 |
87 | qr/DB version .+? is lower than the schema version/, |
88 | 'Warn before upgrade', |
89 | ); |
1475105d |
90 | |
d2bc7045 |
91 | is($schema_v2->get_db_version(), '2.0', 'db version number upgraded'); |
f925f7cb |
92 | |
d7a58a29 |
93 | lives_ok ( sub { |
d2bc7045 |
94 | $schema_v2->storage->dbh->do('select NewVersionName from TestVersion'); |
d7a58a29 |
95 | }, 'new column created' ); |
96 | |
97 | warnings_exist ( |
d40a22fc |
98 | sub { $schema_v2->create_ddl_dir('MySQL', '2.0', $ddl_dir, '1.0') }, |
d7a58a29 |
99 | [ |
475713af |
100 | qr/Overwriting existing DDL file - \Q$fn->{v2}\E/, |
101 | qr/Overwriting existing diff file - \Q$fn->{trans_v12}\E/, |
d7a58a29 |
102 | ], |
103 | 'An overwrite warning generated for both the DDL and the diff', |
104 | ); |
f925f7cb |
105 | } |
b4b1e91c |
106 | |
107 | { |
108 | my $schema_version = DBICVersion::Schema->connect($dsn, $user, $pass); |
d7a58a29 |
109 | lives_ok (sub { |
b4b1e91c |
110 | $schema_version->storage->dbh->do('select * from ' . $version_table_name); |
d7a58a29 |
111 | }, 'version table exists'); |
b4b1e91c |
112 | |
d7a58a29 |
113 | lives_ok (sub { |
b4b1e91c |
114 | $schema_version->storage->dbh->do("DROP TABLE IF EXISTS $old_table_name"); |
86456031 |
115 | $schema_version->storage->dbh->do("RENAME TABLE $version_table_name TO $old_table_name"); |
d7a58a29 |
116 | }, 'versions table renamed to old style table'); |
b4b1e91c |
117 | |
118 | $schema_version = DBICVersion::Schema->connect($dsn, $user, $pass); |
119 | is($schema_version->get_db_version, '2.0', 'transition from old table name to new okay'); |
120 | |
d7a58a29 |
121 | dies_ok (sub { |
b4b1e91c |
122 | $schema_version->storage->dbh->do('select * from ' . $old_table_name); |
d7a58a29 |
123 | }, 'old version table gone'); |
b4b1e91c |
124 | |
125 | } |
f81b9157 |
126 | |
d2bc7045 |
127 | # repeat the v1->v2 process for v2->v3 before testing v1->v3 |
128 | DBICVersion::Schema->_unregister_source ('Table'); |
7eb9a6f1 |
129 | use_ok('DBICVersion_v3'); |
d2bc7045 |
130 | |
131 | my $schema_v3 = DBICVersion::Schema->connect($dsn, $user, $pass, { ignore_version => 1 }); |
132 | { |
133 | unlink($fn->{v3}); |
134 | unlink($fn->{trans_v23}); |
135 | |
136 | is($schema_v3->get_db_version(), '2.0', 'get_db_version 2.0 ok'); |
137 | is($schema_v3->schema_version, '3.0', 'schema version 3.0 ok'); |
138 | $schema_v3->create_ddl_dir('MySQL', '3.0', $ddl_dir, '2.0'); |
139 | ok(-f $fn->{trans_v23}, 'Created DDL 2.0 -> 3.0 file'); |
140 | |
b9ae34d3 |
141 | warnings_exist ( |
142 | sub { $schema_v3->upgrade() }, |
143 | qr/DB version .+? is lower than the schema version/, |
144 | 'Warn before upgrade', |
145 | ); |
d2bc7045 |
146 | |
147 | is($schema_v3->get_db_version(), '3.0', 'db version number upgraded'); |
148 | |
b9ae34d3 |
149 | lives_ok ( sub { |
d2bc7045 |
150 | $schema_v3->storage->dbh->do('select ExtraColumn from TestVersion'); |
b9ae34d3 |
151 | }, 'new column created'); |
d2bc7045 |
152 | } |
153 | |
154 | # now put the v1 schema back again |
155 | { |
156 | # drop all the tables... |
157 | eval { $schema_v1->storage->dbh->do('drop table ' . $version_table_name) }; |
158 | eval { $schema_v1->storage->dbh->do('drop table ' . $old_table_name) }; |
159 | eval { $schema_v1->storage->dbh->do('drop table TestVersion') }; |
160 | |
161 | { |
162 | local $DBICVersion::Schema::VERSION = '1.0'; |
163 | $schema_v1->deploy; |
164 | } |
165 | is($schema_v1->get_db_version(), '1.0', 'get_db_version 1.0 ok'); |
166 | } |
167 | |
b9ae34d3 |
168 | # attempt v1 -> v3 upgrade |
d2bc7045 |
169 | { |
70c28808 |
170 | local $SIG{__WARN__} = sub { warn $_[0] if $_[0] !~ /Attempting upgrade\.$/ }; |
7eb9a6f1 |
171 | $schema_v3->upgrade(); |
d2bc7045 |
172 | is($schema_v3->get_db_version(), '3.0', 'db version number upgraded'); |
173 | } |
174 | |
b703fec7 |
175 | # Now, try a v1 -> v3 upgrade with a file that has comments strategically placed in it. |
176 | # First put the v1 schema back again... |
177 | { |
178 | # drop all the tables... |
179 | eval { $schema_v1->storage->dbh->do('drop table ' . $version_table_name) }; |
180 | eval { $schema_v1->storage->dbh->do('drop table ' . $old_table_name) }; |
181 | eval { $schema_v1->storage->dbh->do('drop table TestVersion') }; |
182 | |
183 | { |
184 | local $DBICVersion::Schema::VERSION = '1.0'; |
185 | $schema_v1->deploy; |
186 | } |
187 | is($schema_v1->get_db_version(), '1.0', 'get_db_version 1.0 ok'); |
188 | } |
189 | |
190 | # add a "harmless" comment before one of the statements. |
f3ec358e |
191 | { |
192 | my ($perl) = $^X =~ /(.+)/; |
193 | local $ENV{PATH}; |
194 | system( qq($perl -pi.bak -e "s/ALTER/-- this is a comment\nALTER/" $fn->{trans_v23}) ); |
195 | } |
b703fec7 |
196 | |
197 | # Then attempt v1 -> v3 upgrade |
198 | { |
70c28808 |
199 | local $SIG{__WARN__} = sub { warn $_[0] if $_[0] !~ /Attempting upgrade\.$/ }; |
b703fec7 |
200 | $schema_v3->upgrade(); |
201 | is($schema_v3->get_db_version(), '3.0', 'db version number upgraded to 3.0'); |
202 | |
203 | # make sure that the column added after the comment is actually added. |
204 | lives_ok ( sub { |
205 | $schema_v3->storage->dbh->do('select ExtraColumn from TestVersion'); |
206 | }, 'new column created'); |
207 | } |
208 | |
209 | |
f81b9157 |
210 | # check behaviour of DBIC_NO_VERSION_CHECK env var and ignore_version connect attr |
211 | { |
212 | my $schema_version = DBICVersion::Schema->connect($dsn, $user, $pass); |
213 | eval { |
d0dfedc2 |
214 | $schema_version->storage->dbh->do("DELETE from $version_table_name"); |
f81b9157 |
215 | }; |
216 | |
d0dfedc2 |
217 | |
d7a58a29 |
218 | warnings_like ( sub { |
219 | $schema_version = DBICVersion::Schema->connect($dsn, $user, $pass); |
220 | }, qr/Your DB is currently unversioned/, 'warning detected without env var or attr' ); |
f81b9157 |
221 | |
d7a58a29 |
222 | warnings_like ( sub { |
223 | $schema_version = DBICVersion::Schema->connect($dsn, $user, $pass, { ignore_version => 1 }); |
224 | }, [], 'warning not detected with attr set'); |
d0dfedc2 |
225 | |
f81b9157 |
226 | |
1475105d |
227 | local $ENV{DBIC_NO_VERSION_CHECK} = 1; |
d7a58a29 |
228 | warnings_like ( sub { |
229 | $schema_version = DBICVersion::Schema->connect($dsn, $user, $pass); |
230 | }, [], 'warning not detected with env var set'); |
f81b9157 |
231 | |
d7a58a29 |
232 | warnings_like ( sub { |
233 | $schema_version = DBICVersion::Schema->connect($dsn, $user, $pass, { ignore_version => 0 }); |
234 | }, qr/Your DB is currently unversioned/, 'warning detected without env var or attr'); |
f81b9157 |
235 | } |
1475105d |
236 | |
237 | # attempt a deploy/upgrade cycle within one second |
7eb9a6f1 |
238 | { |
d2bc7045 |
239 | eval { $schema_v2->storage->dbh->do('drop table ' . $version_table_name) }; |
240 | eval { $schema_v2->storage->dbh->do('drop table ' . $old_table_name) }; |
241 | eval { $schema_v2->storage->dbh->do('drop table TestVersion') }; |
1475105d |
242 | |
243 | # this attempts to sleep until the turn of the second |
244 | my $t = time(); |
245 | sleep (int ($t) + 1 - $t); |
7eb9a6f1 |
246 | note ('Fast deploy/upgrade start: ', time() ); |
1475105d |
247 | |
248 | { |
d2bc7045 |
249 | local $DBICVersion::Schema::VERSION = '2.0'; |
250 | $schema_v2->deploy; |
1475105d |
251 | } |
1475105d |
252 | |
70c28808 |
253 | local $SIG{__WARN__} = sub { warn $_[0] if $_[0] !~ /Attempting upgrade\.$/ }; |
d2bc7045 |
254 | $schema_v2->upgrade(); |
1475105d |
255 | |
d2bc7045 |
256 | is($schema_v2->get_db_version(), '3.0', 'Fast deploy/upgrade'); |
e9fbbbf4 |
257 | }; |
1475105d |
258 | |
8012b15c |
259 | # Check that it Schema::Versioned deals with new/all forms of connect arguments. |
260 | { |
261 | my $get_db_version_run = 0; |
262 | |
263 | no warnings qw/once redefine/; |
264 | local *DBIx::Class::Schema::Versioned::get_db_version = sub { |
265 | $get_db_version_run = 1; |
266 | return $_[0]->schema_version; |
267 | }; |
268 | |
269 | # Make sure the env var isn't whats triggering it |
270 | local $ENV{DBIC_NO_VERSION_CHECK} = 0; |
271 | |
272 | DBICVersion::Schema->connect({ |
273 | dsn => $dsn, |
8273e845 |
274 | user => $user, |
8012b15c |
275 | pass => $pass, |
276 | ignore_version => 1 |
277 | }); |
8273e845 |
278 | |
8012b15c |
279 | ok($get_db_version_run == 0, "attributes pulled from hashref connect_info"); |
280 | $get_db_version_run = 0; |
281 | |
282 | DBICVersion::Schema->connect( $dsn, $user, $pass, { ignore_version => 1 } ); |
283 | ok($get_db_version_run == 0, "attributes pulled from list connect_info"); |
284 | } |
285 | |
8d6b1478 |
286 | END { |
287 | unless ($ENV{DBICTEST_KEEP_VERSIONING_DDL}) { |
288 | $ddl_dir->rmtree; |
289 | } |
1475105d |
290 | } |
7f6f5b69 |
291 | |
292 | done_testing; |