API CHANGE Deprecated use of SapphireTest->fixture to access YML fixtures, please use gateway methods on SapphireTest instead (e.g. $this->objFromFixture() instead of $this->fixture->objFromFixture())

ENHANCEMENT Allowing multiple fixtures to be defined in SapphireTest::$fixture_file through array notation. 
BUGFIX Disabling DataObject validation in YamlFixture->saveIntoDatabase() instead of SapphireTest->setUp()
MINOR Adapted sapphire unit tests to deprecated $this->fixture usage

git-svn-id: svn://svn.silverstripe.com/silverstripe/open/modules/sapphire/trunk@81286 467b73ca-7a2a-4603-9d3b-597d59a354a9
This commit is contained in:
Ingo Schommer 2009-07-08 00:06:16 +00:00
parent 2000087dd6
commit f3959b038d
7 changed files with 133 additions and 60 deletions

View File

@ -96,7 +96,17 @@ class YamlFixture extends Object {
* @param $identifier The identifier string, as provided in your fixture file
*/
public function idFromFixture($className, $identifier) {
return $this->fixtureDictionary[$className][$identifier];
if(isset($this->fixtureDictionary[$className][$identifier])) {
return $this->fixtureDictionary[$className][$identifier];
} else {
user_error(sprintf(
"Couldn't find object #%d (%s) in file %s",
$identifier,
$className,
$this->fixtureFile
), E_USER_ERROR);
}
}
/**
@ -105,7 +115,16 @@ class YamlFixture extends Object {
* @return A map of fixture-identifier => object-id
*/
public function allFixtureIDs($className) {
return $this->fixtureDictionary[$className];
if(isset($this->fixtureDictionary[$className])) {
return $this->fixtureDictionary[$className];
} else {
user_error(sprintf(
"Couldn't find objects of type %s in file %s",
$className,
$this->fixtureFile
), E_USER_ERROR);
}
}
/**
@ -128,6 +147,12 @@ class YamlFixture extends Object {
* then again after populating all relations (has_one, has_many, many_many).
*/
public function saveIntoDatabase() {
// We have to disable validation while we import the fixtures, as the order in
// which they are imported doesnt guarantee valid relations until after the
// import is complete.
$validationenabled = DataObject::get_validation_enabled();
DataObject::set_validation_enabled(false);
$parser = new Spyc();
$fixtureContent = $parser->load(Director::baseFolder().'/'.$this->fixtureFile);
$this->fixtureDictionary = array();
@ -138,6 +163,8 @@ class YamlFixture extends Object {
$this->writeSQL($dataClass, $items);
}
}
DataObject::set_validation_enabled($validationenabled);
}
/**

View File

@ -14,8 +14,11 @@ require_once 'PHPUnit/Framework.php';
class SapphireTest extends PHPUnit_Framework_TestCase {
/**
* Path to fixture data for this test run.
* If passed as an array, multiple fixture files will be loaded.
* Please note that you won't be able to refer with "=>" notation
* between the fixtures, they act independent of each other.
*
* @var string
* @var string|array
*/
static $fixture_file = null;
@ -33,9 +36,9 @@ class SapphireTest extends PHPUnit_Framework_TestCase {
}
/**
* @var YamlFixture
* @var array $fixtures Array of {@link YamlFixture} instances
*/
protected $fixture;
protected $fixtures;
function setUp() {
// Mark test as being run
@ -67,14 +70,15 @@ class SapphireTest extends PHPUnit_Framework_TestCase {
$dbadmin = new DatabaseAdmin();
$dbadmin->clearAllData();
// We have to disable validation while we import the fixtures, as the order in
// which they are imported doesnt guarantee valid relations until after the
// import is complete.
$validationenabled = DataObject::get_validation_enabled();
DataObject::set_validation_enabled(false);
$this->fixture = new YamlFixture($fixtureFile);
$this->fixture->saveIntoDatabase();
DataObject::set_validation_enabled($validationenabled);
$fixtureFiles = (is_array($fixtureFile)) ? $fixtureFile : array($fixtureFile);
foreach($fixtureFiles as $fixtureFilePath) {
$fixture = new YamlFixture($fixtureFilePath);
$fixture->saveIntoDatabase();
$this->fixtures[] = $fixture;
}
}
// Set up email
@ -105,21 +109,43 @@ class SapphireTest extends PHPUnit_Framework_TestCase {
* Get the ID of an object from the fixture.
* @param $className The data class, as specified in your fixture file. Parent classes won't work
* @param $identifier The identifier string, as provided in your fixture file
* @return int
*/
protected function idFromFixture($className, $identifier) {
if($this->fixture) return $this->fixture->idFromFixture($className, $identifier);
else user_error("You've called \$this->objFromFixture() but you haven't specified static \$fixture_file.\n" .
"Ensure that static \"\$fixture_file = 'module/tests/fixturefile.yml';\" is specified in your " .get_class($this). " class.", E_USER_WARNING);
if(!$this->fixtures) {
user_error("You've called \$this->objFromFixture() but you haven't specified static \$fixture_file.\n" .
"Ensure that static \"\$fixture_file = 'module/tests/fixturefile.yml';\" is specified in your " .get_class($this). " class.", E_USER_WARNING);
return;
}
foreach($this->fixtures as $fixture) {
$match = $fixture->idFromFixture($className, $identifier);
if($match) return $match;
}
return false;
}
/**
* Return all of the IDs in the fixture of a particular class name.
* Will collate all IDs form all fixtures if multiple fixtures are provided.
*
* @param string $className
* @return A map of fixture-identifier => object-id
*/
protected function allFixtureIDs($className) {
if($this->fixture) return $this->fixture->allFixtureIDs($className);
else user_error("You've called \$this->objFromFixture() but you haven't specified static \$fixture_file.\n" .
if(!$this->fixtures) {
user_error("You've called \$this->objFromFixture() but you haven't specified static \$fixture_file.\n" .
"Ensure that static \"\$fixture_file = 'module/tests/fixturefile.yml';\" is specified in your " .get_class($this). " class.", E_USER_WARNING);
return;
}
$ids = array();
foreach($this->fixtures as $fixture) {
$ids += $fixture->allFixtureIDs($className);
}
return $ids;
}
/**
@ -128,22 +154,42 @@ class SapphireTest extends PHPUnit_Framework_TestCase {
* @param $identifier The identifier string, as provided in your fixture file
*/
protected function objFromFixture($className, $identifier) {
if($this->fixture) return $this->fixture->objFromFixture($className, $identifier);
else user_error("You've called \$this->objFromFixture() but you haven't specified static \$fixture_file.\n" .
if(!$this->fixtures) {
user_error("You've called \$this->objFromFixture() but you haven't specified static \$fixture_file.\n" .
"Ensure that static \"\$fixture_file = 'module/tests/fixturefile.yml';\" is specified in your " .get_class($this). " class.", E_USER_WARNING);
return;
}
foreach($this->fixtures as $fixture) {
$match = $fixture->objFromFixture($className, $identifier);
if($match) return $match;
}
return false;
}
/**
* Load a YAML fixture file into the database.
* Once loaded, you can use idFromFixture() and objFromFixture() to get items from the fixture
* Once loaded, you can use idFromFixture() and objFromFixture() to get items from the fixture.
* Doesn't clear existing fixtures.
*
* @param $fixtureFile The location of the .yml fixture file, relative to the site base dir
*/
function loadFixture($fixtureFile) {
$parser = new Spyc();
$fixtureContent = $parser->load(Director::baseFolder().'/'.$fixtureFile);
$this->fixture = new YamlFixture($fixtureFile);
$this->fixture->saveIntoDatabase();
$fixture = new YamlFixture($fixtureFile);
$fixture->saveIntoDatabase();
$this->fixtures[] = $fixture;
}
/**
* Clear all fixtures which were previously loaded through
* {@link loadFixture()}.
*/
function clearFixtures() {
$this->fixtures = array();
}
function tearDown() {

View File

@ -15,25 +15,25 @@ class DataObjectTest extends SapphireTest {
function testDelete() {
// Test deleting using delete() on the DataObject
// Get the first page
$page = $this->fixture->objFromFixture('Page', 'page1');
$page = $this->objFromFixture('Page', 'page1');
// Check the page exists before deleting
$this->assertTrue(is_object($page) && $page->exists());
// Delete the page
$page->delete();
// Check that page does not exist after deleting
$page = $this->fixture->objFromFixture('Page', 'page1');
$page = $this->objFromFixture('Page', 'page1');
$this->assertTrue(!$page || !$page->exists());
// Test deleting using DataObject::delete_by_id()
// Get the second page
$page2 = $this->fixture->objFromFixture('Page', 'page2');
$page2 = $this->objFromFixture('Page', 'page2');
// Check the page exists before deleting
$this->assertTrue(is_object($page2) && $page2->exists());
// Delete the page
DataObject::delete_by_id('Page', $page2->ID);
// Check that page does not exist after deleting
$page2 = $this->fixture->objFromFixture('Page', 'page2');
$page2 = $this->objFromFixture('Page', 'page2');
$this->assertTrue(!$page2 || !$page2->exists());
}
@ -131,7 +131,7 @@ class DataObjectTest extends SapphireTest {
*
*/
function testWritePropertyWithoutDBField() {
$page = $this->fixture->objFromFixture('Page', 'page1');
$page = $this->objFromFixture('Page', 'page1');
$page->ParentID = 99;
$page->write();
// reload the page from the database
@ -145,7 +145,7 @@ class DataObjectTest extends SapphireTest {
* - Test the IDs on the DataObjects are set correctly
*/
function testHasManyRelationships() {
$page = $this->fixture->objFromFixture('Page', 'home');
$page = $this->objFromFixture('Page', 'home');
// Test getComponents() gets the ComponentSet of the other side of the relation
$this->assertTrue($page->getComponents('Comments')->Count() == 2);
@ -157,8 +157,8 @@ class DataObjectTest extends SapphireTest {
}
function testHasOneRelationship() {
$team1 = $this->fixture->objFromFixture('DataObjectTest_Team', 'team1');
$player1 = $this->fixture->objFromFixture('DataObjectTest_Player', 'player1');
$team1 = $this->objFromFixture('DataObjectTest_Team', 'team1');
$player1 = $this->objFromFixture('DataObjectTest_Player', 'player1');
// Add a captain to team 1
$team1->setField('CaptainID', $player1->ID);
@ -175,10 +175,10 @@ class DataObjectTest extends SapphireTest {
* @todo Test removeMany() and addMany() on $many_many relationships
*/
function testManyManyRelationships() {
$player1 = $this->fixture->objFromFixture('DataObjectTest_Player', 'player1');
$player2 = $this->fixture->objFromFixture('DataObjectTest_Player', 'player2');
$team1 = $this->fixture->objFromFixture('DataObjectTest_Team', 'team1');
$team2 = $this->fixture->objFromFixture('DataObjectTest_Team', 'team2');
$player1 = $this->objFromFixture('DataObjectTest_Player', 'player1');
$player2 = $this->objFromFixture('DataObjectTest_Player', 'player2');
$team1 = $this->objFromFixture('DataObjectTest_Team', 'team1');
$team2 = $this->objFromFixture('DataObjectTest_Team', 'team2');
// Test adding single DataObject by reference
$player1->Teams()->add($team1);
@ -225,7 +225,7 @@ class DataObjectTest extends SapphireTest {
* @todo Extend type change tests (e.g. '0'==NULL)
*/
function testChangedFields() {
$page = $this->fixture->objFromFixture('Page', 'home');
$page = $this->objFromFixture('Page', 'home');
$page->Title = 'Home-Changed';
$page->ShowInMenus = true;
@ -274,7 +274,7 @@ class DataObjectTest extends SapphireTest {
}
function testIsChanged() {
$page = $this->fixture->objFromFixture('Page', 'home');
$page = $this->objFromFixture('Page', 'home');
$page->Title = 'Home-Changed';
$page->ShowInMenus = true; // type change only, database stores "1"
@ -298,7 +298,7 @@ class DataObjectTest extends SapphireTest {
$this->assertFalse($newPage->isChanged('Content', 1));
$this->assertFalse($newPage->isChanged('Content', 2));
$page = $this->fixture->objFromFixture('Page', 'home');
$page = $this->objFromFixture('Page', 'home');
$page->Title = null;
$this->assertTrue($page->isChanged('Title', 1));
$this->assertTrue($page->isChanged('Title', 2));
@ -639,7 +639,7 @@ class DataObjectTest extends SapphireTest {
}
function testNewClassInstance() {
$page = $this->fixture->objFromFixture('Page', 'page1');
$page = $this->objFromFixture('Page', 'page1');
$changedPage = $page->newClassInstance('RedirectorPage');
$changedFields = $changedPage->getChangedFields();
@ -658,8 +658,8 @@ class DataObjectTest extends SapphireTest {
}
function testManyManyExtraFields() {
$player = $this->fixture->objFromFixture('DataObjectTest_Player', 'player1');
$team = $this->fixture->objFromFixture('DataObjectTest_Team', 'team1');
$player = $this->objFromFixture('DataObjectTest_Player', 'player1');
$team = $this->objFromFixture('DataObjectTest_Team', 'team1');
// Extra fields are immediately available on the Team class (defined in $many_many_extraFields)
$teamExtraFields = $team->many_many_extraFields('Players');

View File

@ -29,7 +29,7 @@ class SiteTreeTest extends SapphireTest {
);
foreach($expectedURLs as $fixture => $urlSegment) {
$obj = $this->fixture->objFromFixture('Page', $fixture);
$obj = $this->objFromFixture('Page', $fixture);
$this->assertEquals($urlSegment, $obj->URLSegment);
}
}
@ -38,7 +38,7 @@ class SiteTreeTest extends SapphireTest {
* Test that publication copies data to SiteTree_Live
*/
function testPublishCopiesToLiveTable() {
$obj = $this->fixture->objFromFixture('Page','about');
$obj = $this->objFromFixture('Page','about');
$obj->publish('Stage', 'Live');
$createdID = DB::query("SELECT \"ID\" FROM \"SiteTree_Live\" WHERE \"URLSegment\" = '$obj->URLSegment'")->value();
@ -49,7 +49,7 @@ class SiteTreeTest extends SapphireTest {
* Test that field which are set and then cleared are also transferred to the published site.
*/
function testPublishDeletedFields() {
$obj = $this->fixture->objFromFixture('Page', 'about');
$obj = $this->objFromFixture('Page', 'about');
$obj->MetaTitle = "asdfasdf";
$obj->write();
$obj->doPublish();

View File

@ -16,7 +16,7 @@ class CheckboxSetFieldTest extends SapphireTest {
}
function testSaveWithNothingSelected() {
$article = $this->fixture->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithouttags');
$article = $this->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithouttags');
/* Create a CheckboxSetField with nothing selected */
$field = new CheckboxSetField("Tags", "Test field", DataObject::get("CheckboxSetFieldTest_Tag")->map());
@ -34,10 +34,10 @@ class CheckboxSetFieldTest extends SapphireTest {
}
function testSaveWithArrayValueSet() {
$article = $this->fixture->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithouttags');
$articleWithTags = $this->fixture->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithtags');
$tag1 = $this->fixture->objFromFixture('CheckboxSetFieldTest_Tag', 'tag1');
$tag2 = $this->fixture->objFromFixture('CheckboxSetFieldTest_Tag', 'tag2');
$article = $this->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithouttags');
$articleWithTags = $this->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithtags');
$tag1 = $this->objFromFixture('CheckboxSetFieldTest_Tag', 'tag1');
$tag2 = $this->objFromFixture('CheckboxSetFieldTest_Tag', 'tag2');
/* Create a CheckboxSetField with 2 items selected. Note that the array is in the format (key) => (selected) */
$field = new CheckboxSetField("Tags", "Test field", DataObject::get("CheckboxSetFieldTest_Tag")->map());
@ -68,10 +68,10 @@ class CheckboxSetFieldTest extends SapphireTest {
}
function testLoadDataFromObject() {
$article = $this->fixture->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithouttags');
$articleWithTags = $this->fixture->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithtags');
$tag1 = $this->fixture->objFromFixture('CheckboxSetFieldTest_Tag', 'tag1');
$tag2 = $this->fixture->objFromFixture('CheckboxSetFieldTest_Tag', 'tag2');
$article = $this->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithouttags');
$articleWithTags = $this->objFromFixture('CheckboxSetFieldTest_Article', 'articlewithtags');
$tag1 = $this->objFromFixture('CheckboxSetFieldTest_Tag', 'tag1');
$tag2 = $this->objFromFixture('CheckboxSetFieldTest_Tag', 'tag2');
$field = new CheckboxSetField("Tags", "Test field", DataObject::get("CheckboxSetFieldTest_Tag")->map());
$form = new Form(

View File

@ -3,7 +3,7 @@ class ImageTest extends SapphireTest {
static $fixture_file = 'sapphire/tests/model/ImageTest.yml';
function testGetTagWithTitle() {
$image = $this->fixture->objFromFixture('Image', 'imageWithTitle');
$image = $this->objFromFixture('Image', 'imageWithTitle');
$expected = '<img src="' . Director::baseUrl() . 'sapphire/tests/model/testimages/test_image.png" alt="This is a image Title" />';
$actual = $image->getTag();
@ -11,7 +11,7 @@ class ImageTest extends SapphireTest {
}
function testGetTagWithoutTitle() {
$image = $this->fixture->objFromFixture('Image', 'imageWithoutTitle');
$image = $this->objFromFixture('Image', 'imageWithoutTitle');
$expected = '<img src="' . Director::baseUrl() . 'sapphire/tests/model/testimages/test_image.png" alt="test_image" />';
$actual = $image->getTag();
@ -19,7 +19,7 @@ class ImageTest extends SapphireTest {
}
function testGetTagWithoutTitleContainingDots() {
$image = $this->fixture->objFromFixture('Image', 'imageWithoutTitleContainingDots');
$image = $this->objFromFixture('Image', 'imageWithoutTitleContainingDots');
$expected = '<img src="' . Director::baseUrl() . 'sapphire/tests/model/testimages/test.image.with.dots.png" alt="test.image.with.dots" />';
$actual = $image->getTag();

View File

@ -29,13 +29,13 @@ class GroupTest extends FunctionalTest {
function testMemberGroupRelationForm() {
Session::set('loggedInAs', $this->idFromFixture('GroupTest_Member', 'admin'));
$adminGroup = $this->fixture->objFromFixture('Group', 'admingroup');
$parentGroup = $this->fixture->objFromFixture('Group', 'parentgroup');
$childGroup = $this->fixture->objFromFixture('Group', 'childgroup');
$adminGroup = $this->objFromFixture('Group', 'admingroup');
$parentGroup = $this->objFromFixture('Group', 'parentgroup');
$childGroup = $this->objFromFixture('Group', 'childgroup');
// Test single group relation through checkboxsetfield
$form = new GroupTest_MemberForm($this, 'Form');
$member = $this->fixture->objFromFixture('GroupTest_Member', 'admin');
$member = $this->objFromFixture('GroupTest_Member', 'admin');
$form->loadDataFrom($member);
$checkboxSetField = $form->Fields()->fieldByName('Groups');
$checkboxSetField->setValue(array(