queto putito
queto putito

Reputation: 253

Symfony2 test database production environment

Before every code update on the production server, I perform phpunit tests by inserting rows in the test database. As the test database doesn't reflect the content of the production database, I would like to perform the tests on the production database. When the tests are done, I want to remove all the created rows during the tests. What would be the best way to achieve this ? I can't think to a method which is perfectly fine and with no risk to alter production data.

Upvotes: 1

Views: 856

Answers (2)

Zeljko
Zeljko

Reputation: 5158

I would recommend you to use sqlite (default) for tests as it is much faster and you don't have to worry if they will screw something on production database. What I did was that every

EntityTest.php extends TestsHelper.php extends PHPUnit_Framework_TestCase

and in setup(), I create database and fixtures.

I took the code from internet and it works. You might find it usefull.

 // class TestsHelper

 /**
 * @var Symfony\Component\DependencyInjection\Container
 */
protected $container;

public function setUp()
{
    // Boot the AppKernel in the test environment and with the debug.
    $this->kernel = new \AppKernel('test', true);
    $this->kernel->boot();

    // Store the container and the entity manager in test case properties
    $this->container = $this->kernel->getContainer();
    $this->em = $this->container->get('doctrine')->getEntityManager();

    // Build the schema for sqlite
    $this->generateSchema();

    $this->generateFixtures() ;

    parent::setUp();
}

public function tearDown()
{
    // Shutdown the kernel.
    $this->kernel->shutdown();

    parent::tearDown();
}

protected function generateSchema()
{
    // Get the metadatas of the application to create the schema.
    $metadatas = $this->getMetadatas();

    if ( ! empty($metadatas)) {
        // Create SchemaTool

        /**
        * @var \Doctrine\ORM\Tools\SchemaTool
        */
        $tool = new SchemaTool($this->em);
//            $tool->dropDatabase() ;
        $tool->createSchema($metadatas);
    } else {
        throw new Doctrine\DBAL\Schema\SchemaException('No Metadata Classes to process.');
    }
}
/**
 * Overwrite this method to get specific metadatas.
 *
 * @return Array
 */
protected function getMetadatas()
{
    return $this->em->getMetadataFactory()->getAllMetadata();
}

And in generateFixtures() you would create them as usual:

$entity = new MyEntity() ;
$this->em->persist($entity) ;
$this->em->flush() ;

Upvotes: 0

redbirdo
redbirdo

Reputation: 4957

I use the approach described by Alexandre Salome in Isolation of tests in Symfony2 to isolate my tests with a transaction and rollback at the end. This approach works really well although obviously you'll want to test it thoroughly before you use it on a production database!

Upvotes: 1

Related Questions