
jester at panix
Jun 17, 2009, 3:58 AM
Post #1 of 2
(353 views)
Permalink
|
|
Testing--best-practice help (long; will wiki the responses)
|
|
Back in April I posted for help here, asking specifically how to use a test database with Test::WWW::Mechanize::Catalyst. I am grateful for the helpful responses I got, and apologize that it took me so long to start working on them. My recent switch from CVS to git has enabled me to get going on lots of things, now that I can reorganize and rename without fear of losing history. With a lot of help from kd, I have gotten a basic setup going, and while it works, there are various things I specifically don't like and various more that I probably need to be told are bad. So, I'd be grateful for any pointers, and will post my final setup to the wiki. Code will be pasted below. My basic setup is a MySQL database and a not-that-unusual DBIC-based Cat app, with login, CRUD functionality (requiring various levels of authz), some graphical output, e-mailing, etc. I mainly would like to run TWAM-based tests of the working app; I'd also be interested in running other tests, of the actual components, but since I've never quite understood how to do this, it's not my main priority (my main priority is making sure the app works). Originally, various people suggested using environment variables to declare whether testing was happening, but in retrospect I didn't see the need for this; the test script knows it's testing so it can just use the testing config and database. So, I have a test database that is just one of my regular backups, and a config file that is my regular config file with the database connection info changed to the test database. I have two files right now, t/test_infrastructure.t, which is my actual test file, and t/lib/test_setup.pl, which creates the database from my backup, sets config info, and deletes the database when I'm done. (The t/lib/ directory is used for the support files.) Here are some specific questions: * Is there any solution to using %ENV for global variables in the setup script? I need the same info to be available in the BEGIN and the END blocks; using "our" in the BEGIN doesn't work. %ENV looks ugly and feels wrong. * Is there any alternative to the ugliness of stuff like $ENV{USER_NAME} = $config{'Model::LibraryDB'}->{'connect_info'}->[1]; to get the data I need from the config file? That's where this info is in that file, but this looks horrific. Similarly, how do I get the database name from the config file? It's there, but only included in the query string: <Model::LibraryDB> schema_class Library::Schema::Main connect_info DBI:mysql:host=localhost;database=library_test connect_info library_test connect_info library_test <connect_info> mysql_enable_utf8 1 </connect_info> </Model::LibraryDB> I believe this is the usual form for such config files, but if I need the database name separately, as I do here.... * How do I properly test the database creation (or is it even necessary to do so--if it doesn't work, the tests won't run)? I know that wrapping system calls in "ok" won't necessarily work because the return values aren't predictable. Alternately, should I create and delete the database in a different way? I am concerned about speed; some of my databases are large enough that I think I do need the fastest way to load them, which is mysql from the commandline. BTW I did look at Fixtures, as some people suggested, but it seemed unnecessary for my needs here, unless I was misunderstanding it. * Currently this will only work with one big test file. But I'm sure I'd want to have multiple test files, either breaking the mech testing up just for convenience (because the app is large), or doing real non-mech unit tests in separate files. How can I set this up such that the database is created before the tests, and deleted after the tests? And if the answer is to put the database creation in the first file and the deletion in the last, what if I just wanted to run a single test file (but still need the database to be there for it)? I'm open to other methods or locations for the creation/deletion stuff; originally I had it all in the same file as the test, but kd suggested putting it in a file in lib/ to keep setup separate from testing. (Of course, keeping it in the same file also doesn't help if the goal is to have separate test files that can work on the same database.) * Finally (for now) I note that when I run the file below with "prove -v --lib lib t/test_infrastructure.t", it does pass all the tests, but I get an error of "Use of uninitialized value $buffer in concatenation (.) or string at /usr/share/perl5/Catalyst/Engine/CGI.pm line 220" at the $mech->get_ok("/") call. Thanks very much.... Jesse --- t/test_infrastructure.t #!/usr/bin/perl use strict; use warnings; use Test::More qw/no_plan/; use FindBin qw/$Bin/; require "$Bin/lib/test_setup.pl"; use Test::WWW::Mechanize::Catalyst; ok( my $mech = Test::WWW::Mechanize::Catalyst->new(catalyst_app => 'Library'), " Created mech object" ); $mech->get_ok("/", "Hits root page"); --- t/lib/test_setup.pl #!/usr/bin/perl use strict; use warnings; BEGIN { # this is identical to regular conf file, but connects to test db our $config_file = "$Bin/lib/library_test.conf"; our $test_database = "$Bin/lib/library_test_db.sql"; use Config::General; our %config = Config::General->new($config_file)->getall; $ENV{USER_NAME} = $config{'Model::LibraryDB'}->{'connect_info'}->[1]; $ENV{PASSWORD} = $config{'Model::LibraryDB'}->{'connect_info'}->[2]; # how to set "library_test" as name for the database, # while keeping format of existing config file? $ENV{DATABASE_NAME} = "library_test"; # assumes there's a MySQL user library_test with rights to # library_test database system("mysqladmin -u $ENV{USER_NAME} -p$ENV{PASSWORD} create $ENV{DATABASE_NAME}"); system("mysql -u $ENV{USER_NAME} -p$ENV{PASSWORD} $ENV{DATABASE_NAME} < $test_database"); $ENV{CATALYST_CONFIG} = $config_file; $ENV{CATALYST_DEBUG} = 0 ; }; END { system("mysqladmin -u $ENV{USER_NAME} -p$ENV{PASSWORD} --force drop $ENV{DATABASE_NAME}"); }; 1; _______________________________________________ List: Catalyst[at]lists.scsys.co.uk Listinfo: http://lists.scsys.co.uk/cgi-bin/mailman/listinfo/catalyst Searchable archive: http://www.mail-archive.com/catalyst[at]lists.scsys.co.uk/ Dev site: http://dev.catalyst.perl.org/
|