Merge pull request #49 from open-sausages/pulls/4.0/app-object

[WIP] App object refactor
This commit is contained in:
Ingo Schommer 2017-06-22 23:01:41 +12:00 committed by GitHub
commit 787ba1cc67
6 changed files with 70 additions and 151 deletions

View File

@ -1,34 +0,0 @@
language: php
sudo: false
env:
global:
- COMPOSER_ROOT_VERSION=2.0.x-dev
- CORE_RELEASE=master
matrix:
include:
- php: 5.6
env:
- PHPUNIT_TEST=1
- DB=PGSQL
- php: 5.6
env:
- PHPUNIT_TEST=1
- DB=MYSQL
- php: 5.6
env:
- PHPCS_TEST=1
- DB=MYSQL
before_script:
- if [[ $PHPCS_TEST ]]; then pyrus install pear/PHP_CodeSniffer; fi
- phpenv rehash
- git clone git://github.com/silverstripe-labs/silverstripe-travis-support.git ~/travis-support
- php ~/travis-support/travis_setup.php --source `pwd` --target ~/builds/ss
- cd ~/builds/ss
script:
- if [[ $PHPUNIT_TEST ]]; then vendor/bin/phpunit testsession/tests/; fi
- if [[ $PHPCS_TEST ]]; then (cd testsession && composer run-script lint); fi

View File

@ -10,21 +10,21 @@ TestSessionEnvironment::singleton()->loadFromFile();
* This closure will run every time a Resque_Event is forked (just before it is forked, so it applies to the parent * This closure will run every time a Resque_Event is forked (just before it is forked, so it applies to the parent
* and child process). * and child process).
*/ */
if(class_exists('Resque_Event') && class_exists('SSResqueRun')) { if (class_exists('Resque_Event') && class_exists('SSResqueRun')) {
Resque_Event::listen('beforeFork', function($data) { Resque_Event::listen('beforeFork', function ($data) {
global $databaseConfig; $databaseConfig = DB::getConfig();
// Reconnect to the database - this may connect to the old DB first, but is required because these processes // Reconnect to the database - this may connect to the old DB first, but is required because these processes
// are long-lived, and MySQL connections often get closed in between worker runs. We need to connect before // are long-lived, and MySQL connections often get closed in between worker runs. We need to connect before
// calling {@link TestSessionEnvironment::loadFromFile()}. // calling {@link TestSessionEnvironment::loadFromFile()}.
DB::connect($databaseConfig); DB::connect($databaseConfig);
$testEnv = TestSessionEnvironment::singleton(); $testEnv = TestSessionEnvironment::singleton();
if($testEnv->isRunningTests()) { if ($testEnv->isRunningTests()) {
$testEnv->loadFromFile(); $testEnv->loadFromFile();
} else { } else {
$testEnv->endTestSession(); $testEnv->endTestSession();
} }
}); });
} }

View File

@ -4,10 +4,8 @@ namespace SilverStripe\TestSession;
use SilverStripe\Control\Controller; use SilverStripe\Control\Controller;
use SilverStripe\Control\Director; use SilverStripe\Control\Director;
use SilverStripe\Control\Session;
use SilverStripe\Control\HTTPRequest; use SilverStripe\Control\HTTPRequest;
use SilverStripe\Core\Injector\Injector; use SilverStripe\Core\Injector\Injector;
use SilverStripe\Dev\Deprecation;
use SilverStripe\Dev\SapphireTest; use SilverStripe\Dev\SapphireTest;
use SilverStripe\Forms\CheckboxField; use SilverStripe\Forms\CheckboxField;
use SilverStripe\Forms\DatetimeField; use SilverStripe\Forms\DatetimeField;
@ -18,6 +16,7 @@ use SilverStripe\Forms\FormAction;
use SilverStripe\Forms\HiddenField; use SilverStripe\Forms\HiddenField;
use SilverStripe\Forms\TextField; use SilverStripe\Forms\TextField;
use SilverStripe\ORM\ArrayList; use SilverStripe\ORM\ArrayList;
use SilverStripe\ORM\Connect\TempDatabase;
use SilverStripe\ORM\DB; use SilverStripe\ORM\DB;
use SilverStripe\ORM\FieldType\DBHTMLText; use SilverStripe\ORM\FieldType\DBHTMLText;
use SilverStripe\Security\Permission; use SilverStripe\Security\Permission;
@ -104,14 +103,14 @@ class TestSessionController extends Controller
*/ */
public function start() public function start()
{ {
$params = $this->request->requestVars(); $params = $this->getRequest()->requestVars();
if (!empty($params['globalTestSession'])) { if (!empty($params['globalTestSession'])) {
$id = null; $id = null;
} else { } else {
$generator = Injector::inst()->get(RandomGenerator::class); $generator = Injector::inst()->get(RandomGenerator::class);
$id = substr($generator->randomToken(), 0, 10); $id = substr($generator->randomToken(), 0, 10);
Session::set('TestSessionId', $id); $this->getRequest()->getSession()->set('TestSessionId', $id);
} }
// Convert datetime from form object into a single string // Convert datetime from form object into a single string
@ -181,14 +180,15 @@ class TestSessionController extends Controller
throw new LogicException('No query parameters detected'); throw new LogicException('No query parameters detected');
} }
$sessionStates = (array)Session::get('_TestSessionController.BrowserSessionState'); $session = $this->getRequest()->getSession();
$sessionStates = (array)$session->get('_TestSessionController.BrowserSessionState');
foreach ($newSessionStates as $k => $v) { foreach ($newSessionStates as $k => $v) {
Session::set($k, $v); $session->set($k, $v);
} }
// Track which state we're setting so we can unset later in end() // Track which state we're setting so we can unset later in end()
Session::set('_TestSessionController.BrowserSessionState', array_merge($sessionStates, $newSessionStates)); $session->set('_TestSessionController.BrowserSessionState', array_merge($sessionStates, $newSessionStates));
} }
public function StartForm() public function StartForm()
@ -316,8 +316,9 @@ class TestSessionController extends Controller
$this->extend('onBeforeClear'); $this->extend('onBeforeClear');
if (SapphireTest::using_temp_db()) { $tempDB = new TempDatabase();
SapphireTest::empty_temp_db(); if ($tempDB->isUsed()) {
$tempDB->clearAllData();
} }
if (isset($_SESSION['_testsession_codeblocks'])) { if (isset($_SESSION['_testsession_codeblocks'])) {
@ -341,17 +342,17 @@ class TestSessionController extends Controller
} }
$this->environment->endTestSession(); $this->environment->endTestSession();
Session::clear('TestSessionId'); $session = Controller::curr()->getRequest()->getSession();
$session->clear('TestSessionId');
// Clear out all PHP session states which have been set previously // Clear out all PHP session states which have been set previously
if ($sessionStates = Session::get('_TestSessionController.BrowserSessionState')) { if ($sessionStates = $session->get('_TestSessionController.BrowserSessionState')) {
foreach ($sessionStates as $k => $v) { foreach ($sessionStates as $k => $v) {
Session::clear($k); $session->clear($k);
} }
Session::clear('_TestSessionController'); $session->clear('_TestSessionController');
} }
return $this->renderWith('TestSession_end'); return $this->renderWith('TestSession_end');
} }
@ -360,7 +361,8 @@ class TestSessionController extends Controller
*/ */
public function isTesting() public function isTesting()
{ {
return SapphireTest::using_temp_db(); $tempDB = new TempDatabase();
return $tempDB->isUsed();
} }
/** /**
@ -394,7 +396,7 @@ class TestSessionController extends Controller
$templates = array(); $templates = array();
if (!$path) { if (!$path) {
$path = $this->config()->database_templates_path; $path = $this->config()->get('database_templates_path');
} }
// TODO Remove once we can set BASE_PATH through the config layer // TODO Remove once we can set BASE_PATH through the config layer

View File

@ -2,21 +2,21 @@
namespace SilverStripe\TestSession; namespace SilverStripe\TestSession;
use Exception;
use InvalidArgumentException;
use LogicException;
use SilverStripe\Control\Director; use SilverStripe\Control\Director;
use SilverStripe\Control\Session; use SilverStripe\Control\HTTPRequest;
use SilverStripe\Core\Config\Configurable; use SilverStripe\Core\Config\Configurable;
use SilverStripe\Core\Extensible; use SilverStripe\Core\Extensible;
use SilverStripe\Core\Injector\Injectable; use SilverStripe\Core\Injector\Injectable;
use SilverStripe\Core\Injector\Injector; use SilverStripe\Core\Injector\Injector;
use SilverStripe\Dev\FixtureFactory; use SilverStripe\Dev\FixtureFactory;
use SilverStripe\Dev\SapphireTest; use SilverStripe\ORM\Connect\TempDatabase;
use SilverStripe\ORM\DB;
use SilverStripe\ORM\DatabaseAdmin; use SilverStripe\ORM\DatabaseAdmin;
use SilverStripe\ORM\DB;
use SilverStripe\ORM\FieldType\DBDatetime; use SilverStripe\ORM\FieldType\DBDatetime;
use SilverStripe\Versioned\Versioned; use SilverStripe\Versioned\Versioned;
use InvalidArgumentException;
use LogicException;
use Exception;
use stdClass; use stdClass;
/** /**
@ -77,19 +77,23 @@ class TestSessionEnvironment
public function __construct($id = null) public function __construct($id = null)
{ {
$this->constructExtensions(); $this->constructExtensions();
if ($id) { if ($id) {
$this->id = $id; $this->id = $id;
} else { }
Session::start(); }
public function init(HTTPRequest $request)
{
if (!$this->id) {
$request->getSession()->init();
// $_SESSION != Session::get() in some execution paths, suspect Controller->pushCurrent() // $_SESSION != Session::get() in some execution paths, suspect Controller->pushCurrent()
// as part of the issue, easiest resolution is to use session directly for now // as part of the issue, easiest resolution is to use session directly for now
$this->id = (isset($_SESSION['TestSessionId'])) ? $_SESSION['TestSessionId'] : null; $this->id = $request->getSession()->get('TestSessionId');
} }
} }
/** /**
* @return String Absolute path to the file persisting our state. * @return string Absolute path to the file persisting our state.
*/ */
public function getFilePath() public function getFilePath()
{ {
@ -191,7 +195,7 @@ class TestSessionEnvironment
$this->extend('onBeforeApplyState', $state); $this->extend('onBeforeApplyState', $state);
// back up source // back up source
global $databaseConfig; $databaseConfig = DB::getConfig();
$this->oldDatabaseName = $databaseConfig['database']; $this->oldDatabaseName = $databaseConfig['database'];
// Load existing state from $this->state into $state, if there is any // Load existing state from $this->state into $state, if there is any
@ -239,7 +243,8 @@ class TestSessionEnvironment
if (!$dbExists) { if (!$dbExists) {
// Create a new one with a randomized name // Create a new one with a randomized name
$dbName = SapphireTest::create_temp_db(); $tempDB = new TempDatabase();
$dbName = $tempDB->build();
$state->database = $dbName; // In case it's changed by the call to SapphireTest::create_temp_db(); $state->database = $dbName; // In case it's changed by the call to SapphireTest::create_temp_db();
@ -351,9 +356,12 @@ class TestSessionEnvironment
$this->applyState($json); $this->applyState($json);
} catch (Exception $e) { } catch (Exception $e) {
throw new \Exception("A test session appears to be in progress, but we can't retrieve the details. " throw new Exception(
. "Try removing the " . $this->getFilePath() . " file. Inner " "A test session appears to be in progress, but we can't retrieve the details.\n"
. "error: " . $e->getMessage()); . "Try removing the " . $this->getFilePath() . " file.\n"
. "Inner error: " . $e->getMessage() . "\n"
. "Stacktrace: " . $e->getTraceAsString()
);
} }
} }
} }
@ -385,7 +393,8 @@ class TestSessionEnvironment
{ {
$this->extend('onBeforeEndTestSession'); $this->extend('onBeforeEndTestSession');
if (SapphireTest::using_temp_db()) { $tempDB = new TempDatabase();
if ($tempDB->isUsed()) {
$state = $this->getState(); $state = $this->getState();
$dbConn = DB::get_schema(); $dbConn = DB::get_schema();
$dbExists = $dbConn->databaseExists($state->database); $dbExists = $dbConn->databaseExists($state->database);
@ -396,8 +405,6 @@ class TestSessionEnvironment
} }
// End test session mode // End test session mode
$this->resetDatabaseName(); $this->resetDatabaseName();
SapphireTest::set_is_running_test(false);
} }
$this->removeStateFile(); $this->removeStateFile();
@ -443,9 +450,9 @@ class TestSessionEnvironment
public function resetDatabaseName() public function resetDatabaseName()
{ {
if ($this->oldDatabaseName) { if ($this->oldDatabaseName) {
global $databaseConfig; $databaseConfig = DB::getConfig();
$databaseConfig['database'] = $this->oldDatabaseName; $databaseConfig['database'] = $this->oldDatabaseName;
DB::setConfig($databaseConfig);
$conn = DB::get_conn(); $conn = DB::get_conn();

View File

@ -2,17 +2,15 @@
namespace SilverStripe\TestSession; namespace SilverStripe\TestSession;
use SilverStripe\Control\Director;
use SilverStripe\Control\Email\Email; use SilverStripe\Control\Email\Email;
use SilverStripe\Control\Email\Mailer; use SilverStripe\Control\Email\Mailer;
use SilverStripe\ORM\DataModel;
use SilverStripe\ORM\FieldType\DBDatetime;
use SilverStripe\ORM\DB;
use SilverStripe\Core\Injector\Injector;
use SilverStripe\Control\Session;
use SilverStripe\Control\Director;
use SilverStripe\Control\RequestFilter;
use SilverStripe\Control\HTTPRequest; use SilverStripe\Control\HTTPRequest;
use SilverStripe\Control\HTTPResponse; use SilverStripe\Control\HTTPResponse;
use SilverStripe\Control\RequestFilter;
use SilverStripe\Core\Injector\Injector;
use SilverStripe\ORM\DB;
use SilverStripe\ORM\FieldType\DBDatetime;
/** /**
* Sets state previously initialized through {@link TestSessionController}. * Sets state previously initialized through {@link TestSessionController}.
@ -29,9 +27,10 @@ class TestSessionRequestFilter implements RequestFilter
$this->testSessionEnvironment = TestSessionEnvironment::singleton(); $this->testSessionEnvironment = TestSessionEnvironment::singleton();
} }
public function preRequest(HTTPRequest $request, Session $session, DataModel $model) public function preRequest(HTTPRequest $request)
{ {
$isRunningTests = $this->testSessionEnvironment->isRunningTests(); $isRunningTests = $this->testSessionEnvironment->isRunningTests();
$this->testSessionEnvironment->init($request);
if (!$isRunningTests) { if (!$isRunningTests) {
return; return;
} }
@ -59,7 +58,7 @@ class TestSessionRequestFilter implements RequestFilter
$file = $testState->stubfile; $file = $testState->stubfile;
if (!Director::isLive() && $file && file_exists($file)) { if (!Director::isLive() && $file && file_exists($file)) {
// Connect to the database so the included code can interact with it // Connect to the database so the included code can interact with it
global $databaseConfig; $databaseConfig = DB::getConfig();
if ($databaseConfig) { if ($databaseConfig) {
DB::connect($databaseConfig); DB::connect($databaseConfig);
} }
@ -68,7 +67,7 @@ class TestSessionRequestFilter implements RequestFilter
} }
} }
public function postRequest(HTTPRequest $request, HTTPResponse $response, DataModel $model) public function postRequest(HTTPRequest $request, HTTPResponse $response)
{ {
if (!$this->testSessionEnvironment->isRunningTests()) { if (!$this->testSessionEnvironment->isRunningTests()) {
return; return;
@ -76,7 +75,7 @@ class TestSessionRequestFilter implements RequestFilter
// Store PHP session // Store PHP session
$state = $this->testSessionEnvironment->getState(); $state = $this->testSessionEnvironment->getState();
$state->session = Session::get_all(); $state->session = $request->getSession()->getAll();
$this->testSessionEnvironment->applyState($state); $this->testSessionEnvironment->applyState($state);
} }
} }

View File

@ -1,55 +0,0 @@
<?php
namespace SilverStripe\TestSession\Tests;
use SilverStripe\Dev\SapphireTest;
use SilverStripe\TestSession\TestSessionStubCodeWriter;
class TestSessionStubCodeWriterTest extends SapphireTest
{
public function tearDown()
{
parent::tearDown();
$file = TEMP_FOLDER . '/TestSessionStubCodeWriterTest-file.php';
if (file_exists($file)) {
unlink($file);
}
}
public function testWritesHeaderOnNewFile()
{
$file = TEMP_FOLDER . '/TestSessionStubCodeWriterTest-file.php';
$writer = new TestSessionStubCodeWriter($file);
$writer->write('foo();', false);
$this->assertFileExists($file);
$this->assertEquals(
file_get_contents($writer->getFilePath()),
"<?php\nfoo();\n"
);
}
public function testWritesWithAppendOnExistingFile()
{
$file = TEMP_FOLDER . '/TestSessionStubCodeWriterTest-file.php';
$writer = new TestSessionStubCodeWriter($file);
$writer->write('foo();', false);
$writer->write('bar();', false);
$this->assertFileExists($file);
$this->assertEquals(
file_get_contents($writer->getFilePath()),
"<?php\nfoo();\nbar();\n"
);
}
public function testReset()
{
$file = TEMP_FOLDER . '/TestSessionStubCodeWriterTest-file.php';
$writer = new TestSessionStubCodeWriter($file);
$writer->write('foo();', false);
$this->assertFileExists($file);
$writer->reset();
$this->assertFileNotExists($file);
}
}