aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHakim Cassimally <hakim@mysociety.org>2014-05-21 11:42:23 +0000
committerMatthew Somerville <matthew@mysociety.org>2014-12-12 12:41:32 +0000
commit244b2876c837f65ed9477a57c3ed297f493b44a5 (patch)
tree0f8c3eb297e59fe98ffc79b74137c5fd5e8f4784
parent43c98742ee85c73c4783451ceeea28108bb793c6 (diff)
Add a script to always test on a clean db/config.
Fixes #786.
-rw-r--r--.gitignore1
-rwxr-xr-xbin/test-wrapper35
-rw-r--r--conf/.gitignore1
-rw-r--r--cpanfile4
-rw-r--r--cpanfile.snapshot18
-rw-r--r--perllib/FixMyStreet/TestAppProve.pm94
-rw-r--r--t/00-check-config.t3
-rw-r--r--t/00-check-we-are-staging.t3
8 files changed, 157 insertions, 2 deletions
diff --git a/.gitignore b/.gitignore
index 72bc29420..777f3bafd 100644
--- a/.gitignore
+++ b/.gitignore
@@ -2,6 +2,7 @@
*.swp
*~
._*
+.prove
.vagrant
.bundle
diff --git a/bin/test-wrapper b/bin/test-wrapper
new file mode 100755
index 000000000..9cb1791a1
--- /dev/null
+++ b/bin/test-wrapper
@@ -0,0 +1,35 @@
+#!/usr/bin/env perl
+use strict; use warnings;
+
+BEGIN {
+ use FindBin;
+ require "$FindBin::Bin/../setenv.pl";
+}
+
+use FixMyStreet::TestAppProve;
+
+=head1 NAME
+
+bin/test-wrapper - spin up a clean database and configuration for tests
+
+=head1 USAGE
+
+ bin/test-wrapper t/ # runs prove -r t/ (recursively, saving state)
+ bin/test-wrapper --state=failed # runs just failing tests
+ # delete .prove to reset
+
+ bin/test-wrapper t/foo.t # runs with prove -v (single test)
+
+By default we use conf/general.yml-example as the template, and spin up a fresh
+Postgres cluster and database. We can override this by doing:
+
+ bin/test-wrapper --config=general.mycobrand.yml
+ bin/test-wrapper --db-config=general.yml # e.g. use your current DB settings
+ bin/test-wrapper --all-config=general.yml # e.g. use your current DB settings
+
+(NB: passing --state=save automagically is experimental, and will be removed if
+it turns out to be annoying.)
+
+=cut
+
+FixMyStreet::TestAppProve->run(@ARGV);
diff --git a/conf/.gitignore b/conf/.gitignore
index 8fa665744..6e77101a1 100644
--- a/conf/.gitignore
+++ b/conf/.gitignore
@@ -1,5 +1,6 @@
/general.yml
/general.yml.deployed
+/general.test-autogenerated.yml
/httpd.conf
/httpd.conf.deployed
/crontab
diff --git a/cpanfile b/cpanfile
index b50e433a8..cda6cc131 100644
--- a/cpanfile
+++ b/cpanfile
@@ -110,6 +110,10 @@ requires 'File::ChangeNotify';
requires 'Path::Tiny';
requires 'File::Find::Rule';
+feature 'test-wrapper', 'Spin up a test database and config to run tests' => sub {
+ requires 'Test::PostgreSQL';
+};
+
# Modules used by the test suite
requires 'CGI::Simple';
requires 'HTTP::Headers';
diff --git a/cpanfile.snapshot b/cpanfile.snapshot
index c4362b4d1..e5d8b9afc 100644
--- a/cpanfile.snapshot
+++ b/cpanfile.snapshot
@@ -620,6 +620,12 @@ DISTRIBUTIONS
Test::Exception 0.31
Test::More 0.94
perl 5.006
+ Class-Accessor-Lite-0.06
+ pathname: K/KA/KAZUHO/Class-Accessor-Lite-0.06.tar.gz
+ provides:
+ Class::Accessor::Lite 0.06
+ requirements:
+ ExtUtils::MakeMaker 6.42
Class-C3-0.24
pathname: F/FL/FLORA/Class-C3-0.24.tar.gz
provides:
@@ -5798,6 +5804,18 @@ DISTRIBUTIONS
Test::More 0
Test::Tester 0.107
perl 5.006
+ Test-PostgreSQL-1.05
+ pathname: T/TJ/TJC/Test-PostgreSQL-1.05.tar.gz
+ provides:
+ Test::PostgreSQL 1.05
+ requirements:
+ Class::Accessor::Lite 0
+ DBD::Pg 0
+ DBI 0
+ ExtUtils::MakeMaker 6.59
+ Test::SharedFork 0.06
+ Time::HiRes 0
+ perl 5.008
Test-Requires-0.06
pathname: T/TO/TOKUHIROM/Test-Requires-0.06.tar.gz
provides:
diff --git a/perllib/FixMyStreet/TestAppProve.pm b/perllib/FixMyStreet/TestAppProve.pm
new file mode 100644
index 000000000..4d8cdaccb
--- /dev/null
+++ b/perllib/FixMyStreet/TestAppProve.pm
@@ -0,0 +1,94 @@
+use strict; use warnings;
+package FixMyStreet::TestAppProve;
+use App::Prove;
+
+use YAML ();
+use Path::Tiny 'path';
+use Test::PostgreSQL;
+use Data::Dumper;
+use Getopt::Long ':config' => qw(bundling pass_through no_ignore_case);
+
+=head1 NAME
+
+FixMyStreet::TestAppProve - spin up a clean database and configuration for tests
+
+=head1 USAGE
+
+see bin/test-wrapper for usage
+
+=cut
+
+sub run {
+ my ($class, @args) = @_;
+ local @ARGV = @args;
+
+ my $config_file = 'conf/general.yml-example';
+ my $db_config_file;
+
+ my $recurse;
+ my @state;
+
+ GetOptions (
+ # our own config variables
+ 'config=s' => \$config_file,
+ 'db-config=s' => \$db_config_file,
+
+ # App::Prove variables we want to munge
+ 'r|recurse' => \$recurse,
+ 'state=s@' => \@state,
+ );
+
+ my $config = YAML::Load( path($config_file)->slurp );
+ my $pg;
+ if ($db_config_file) {
+ my $db_config = YAML::Load( path($db_config_file)->slurp );
+ $config->{FMS_DB_PORT} = $db_config->{FMS_DB_PORT};
+ $config->{FMS_DB_NAME} = $db_config->{FMS_DB_NAME};
+ $config->{FMS_DB_USER} = $db_config->{FMS_DB_USER};
+ $config->{FMS_DB_HOST} = $db_config->{FMS_DB_HOST};
+ $config->{FMS_DB_PASS} = $db_config->{FMS_DB_PASS};
+ }
+ else {
+ warn "Spinning up a Pg cluster/database...\n";
+ $pg = Test::PostgreSQL->new();
+
+ warn sprintf "# Connected to %s\n", $pg->dsn;
+
+ my $dbh = DBI->connect($pg->dsn);
+
+ my $tmpwarn = $SIG{__WARN__};
+ $SIG{__WARN__} =
+ sub { print STDERR @_ if $_[0] !~ m/NOTICE: CREATE TABLE/; };
+ $dbh->do( path('db/schema.sql')->slurp ) or die $!;
+ $dbh->do( path('db/alert_types.sql')->slurp ) or die $!;
+ $dbh->do( path('db/generate_secret.sql')->slurp ) or die $!;
+ $SIG{__WARN__} = $tmpwarn;
+
+ $config->{FMS_DB_PORT} = $pg->port;
+ $config->{FMS_DB_NAME} = 'test';
+ $config->{FMS_DB_USER} = 'postgres';
+ $config->{FMS_DB_HOST} = 'localhost';
+ $config->{FMS_DB_PASS} = '';
+ }
+
+ my $config_out = 'general.test-autogenerated';
+ path("conf/$config_out.yml")->spew( YAML::Dump($config) );
+
+ local $ENV{FMS_OVERRIDE_CONFIG} = $config_out;
+
+ if (@ARGV and -e $ARGV[-1]) {
+ unshift @ARGV, '--verbose'
+ if -f $ARGV[-1];
+ # verbose if we have a single file
+ }
+
+ unshift @ARGV,
+ '--recurse', # we always want to recurse
+ '--state', (join ',' => @state, 'save'); # we always want to save state
+
+ my $prove = App::Prove->new;
+ $prove->process_args(@ARGV);
+ $prove->run;
+}
+
+1;
diff --git a/t/00-check-config.t b/t/00-check-config.t
index 20f0fe8cf..00e782e74 100644
--- a/t/00-check-config.t
+++ b/t/00-check-config.t
@@ -16,7 +16,8 @@ use FixMyStreet;
# load the config file and store the contents in a readonly hash
my $example_config = YAML::LoadFile( FixMyStreet->path_to("conf/general.yml-example") );
-my $local_config = YAML::LoadFile( FixMyStreet->path_to("conf/general.yml") );
+my $CONF_FILE = $ENV{FMS_OVERRIDE_CONFIG} || 'general';
+my $local_config = YAML::LoadFile( FixMyStreet->path_to("conf/${CONF_FILE}.yml") );
# find all keys missing from each config
my @missing_from_example = find_missing( $example_config, $local_config );
diff --git a/t/00-check-we-are-staging.t b/t/00-check-we-are-staging.t
index a1da68798..4c9a255fe 100644
--- a/t/00-check-we-are-staging.t
+++ b/t/00-check-we-are-staging.t
@@ -14,7 +14,8 @@ use FixMyStreet;
# load the config file and store the contents in a readonly hash
-mySociety::Config::set_file( FixMyStreet->path_to("conf/general") );
+my $CONF_FILE = $ENV{FMS_OVERRIDE_CONFIG} || 'general';
+mySociety::Config::set_file( FixMyStreet->path_to("conf/${CONF_FILE}") );
BAIL_OUT( "Test suite modifies databases so should not be run on live servers" )
unless mySociety::Config::get('STAGING_SITE', undef);