Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Generate Symfony2 fixtures from DB?

Is it possible to generate fixtures from an existing DB in Symfony2/Doctrine? How could I do that?

Example:

I have defined 15 entities and my symfony2 application is working. Now some people are able to browse to the application and by using it it had inserted about 5000 rows until now. Now I want the stuff inserted as fixtures, but I don’t want to do this by hand. How can I generate them from the DB?

like image 878
Stuck Avatar asked Jun 11 '11 20:06

Stuck


People also ask

How to load fixtures in Symfony?

One of the most popular methods for the Symfony framework is to use the data fixtures bundle that helps you create objects and store them to the database programmatically. Once you write the code for fixtures, you can load them by using a single command – php bin/console doctrine:fixtures:load.

What is schema Symfony?

In order to create the data object model that symfony will use, you need to translate whatever relational model your database has to an object data model. The ORM needs a description of the relational model to do the mapping, and this is called a schema.

Does Symfony use doctrine?

Symfony provides all the tools you need to use databases in your applications thanks to Doctrine, the best set of PHP libraries to work with databases. These tools support relational databases like MySQL and PostgreSQL and also NoSQL databases like MongoDB.


2 Answers

There's no direct manner within Doctrine or Symfony2, but writing a code generator for it (either within or outside of sf2) would be trivial. Just pull each property and generate a line of code to set each property, then put it in your fixture loading method. Example:

<?php $i = 0; $entities = $em->getRepository('MyApp:Entity')->findAll(); foreach($entities as $entity) {    $code .= "$entity_{$i} = new MyApp\Entity();\n";    $code .= "$entity_{$i}->setMyProperty('" . addslashes($entity->getMyProperty()); . "'); \n");    $code .= "$manager->persist($entity_{$i}); \n $manager->flush();";    ++$i; } // store code somewhere with file_put_contents 
like image 54
Lusitanian Avatar answered Sep 18 '22 18:09

Lusitanian


As I understand your question, you have two databases: the first is already in production and filled with 5000 rows, the second one is a new database you want to use for new test and development. Is that right ?

If it is, I suggest you to create in you test environment two entity manager: the first will be the 'default' one, which will be used in your project (your controllers, etc.). The second one will be used to connect to your production database. You will find here how to deal with multiple entity manager : http://symfony.com/doc/current/cookbook/doctrine/multiple_entity_managers.html

Then, you should create a Fixture class which will have access to your container. There is an "how to" here : http://symfony.com/doc/current/bundles/DoctrineFixturesBundle/index.html#using-the-container-in-the-fixtures.

Using the container, you will have access to both entity manager. And this is the 'magic': you will have to retrieve the object from your production database, and persist them in the second entity manager, which will insert them in your test database.

I point your attention to two points:

  • If there are relationship between object, you will have to take care to those dependencies: owner side, inversed side, ...
  • If you have 5000 rows, take care on the memory your script will use. Another solution may be use native sql to retrieve all the rows from your production database and insert them in your test database. Or a SQL script...

I do not have any code to suggest to you, but I hope this idea will help you.

like image 44
Julien Fastré Avatar answered Sep 17 '22 18:09

Julien Fastré