2010-10-31 21 views
6

Est-il possible de générer des entités Doctrine 2, avec les annotations docblock pertinentes, à partir d'un schéma de base de données existant?Générer des entités doctrine2 annotées à partir du schéma db

+0

Envisagez de ne pas le faire. Vous allez créer de meilleures entités si vous les créez à partir de zéro spécifiquement pour votre application. Mappez-les avec des annotations plus tard. – rojoca

Répondre

8

je devais fait ces changements pour le code ci-dessus pour travailler ..

<?php 
use Doctrine\ORM\Tools\EntityGenerator; 
ini_set("display_errors", "On"); 
$libPath = __DIR__; // Set this to where you have doctrine2 installed 
// autoloaders 
require_once $libPath . '/Doctrine/Common/ClassLoader.php'; 

$classLoader = new \Doctrine\Common\ClassLoader('Doctrine', $libPath); 
$classLoader->register(); 

$classLoader = new \Doctrine\Common\ClassLoader('Entities', __DIR__); 
$classLoader->register(); 

$classLoader = new \Doctrine\Common\ClassLoader('Proxies', __DIR__); 
$classLoader->register(); 

// config 
$config = new \Doctrine\ORM\Configuration(); 
$config->setMetadataDriverImpl($config->newDefaultAnnotationDriver(__DIR__ . '/Entities')); 
$config->setMetadataCacheImpl(new \Doctrine\Common\Cache\ArrayCache); 
$config->setProxyDir(__DIR__ . '/Proxies'); 
$config->setProxyNamespace('Proxies'); 


$connectionParams = array(
    'path' => 'test.sqlite3', 
    'driver' => 'pdo_sqlite', 
); 

$em = \Doctrine\ORM\EntityManager::create($connectionParams, $config); 

// custom datatypes (not mapped for reverse engineering) 
$em->getConnection()->getDatabasePlatform()->registerDoctrineTypeMapping('set', 'string'); 
$em->getConnection()->getDatabasePlatform()->registerDoctrineTypeMapping('enum', 'string'); 

// fetch metadata 
$driver = new \Doctrine\ORM\Mapping\Driver\DatabaseDriver(
    $em->getConnection()->getSchemaManager() 
); 
$em->getConfiguration()->setMetadataDriverImpl($driver); 
$cmf = new \Doctrine\ORM\Tools\DisconnectedClassMetadataFactory($em); 
$cmf->setEntityManager($em); 
$classes = $driver->getAllClassNames(); 
$metadata = $cmf->getAllMetadata(); 
$generator = new EntityGenerator(); 
$generator->setUpdateEntityIfExists(true); 
$generator->setGenerateStubMethods(true); 
$generator->setGenerateAnnotations(true); 
$generator->generate($metadata, __DIR__ . '/Entities'); 
print 'Done!'; 
?> 

et configuration de connexion mysql comme:

$connectionParams = array(
    'driver' => 'pdo_mysql', 
    'host' => 'localhost', 
    'port' => '3306', 
    'user' => 'root', 
    'password' => 'root', 
    'dbname' => 'database', 
    'charset' => 'utf8', 
); 
+0

Merci! Cela a réellement fonctionné. (Pas comme le programme inclus avec la doctrine). - Bien que je n'ai utilisé votre code que sous $ connectionParams parce que je ne suis pas sûr de la configuration de votre environnement. Par exemple, la fonction 'register();' est clairement indéfinie. Big +1 de toute façon! – vbence

+0

Cela fonctionne très bien pour moi ... Un gros +1 pour vous. Pour les autres qui ont le même problème s'il vous plaît utiliser cette réponse, tous les autres ne fonctionneront pas ... – Tareq

+0

@dminer: Votre script a fonctionné avec succès et a sauvé beaucoup de temps à moi comme je suis nouveau bie à Doctrine. Ce script a créé l'entité à partir de la base de données avec la méthode setter et getter excluant les opérations CRUD. Que faire ensuite si je veux ajouter toutes les opérations de base de CRUD dans cette entité. Veuillez noter que mon projet n'est pas un projet symphonique mais un projet de base simple. – neeraj

2

Oui, bien que les types de données SGBDR ne soient pas entièrement pris en charge, vous devrez peut-être jouer un peu avec votre code avant de l'utiliser dans votre projet. Ce n'est pas simple comme Doctrine 1.x l'habitude d'être mais encore assez facile. Voici quelques exemples de code, je me suis utilisé (créer des dossiers correctement avant de l'utiliser)

 
use Doctrine\ORM\Tools\EntityGenerator; 

ini_set("display_errors", "On"); 

$libPath = __DIR__ . '/../lib/doctrine2'; 

// autoloaders 
require_once $libPath . '/Doctrine/Common/ClassLoader.php'; 

$classLoader = new \Doctrine\Common\ClassLoader('Doctrine', $libPath); 
$classLoader->register(); 

$classLoader = new \Doctrine\Common\ClassLoader('Entities', __DIR__); 
$classLoader->register(); 

$classLoader = new \Doctrine\Common\ClassLoader('Proxies', __DIR__); 
$classLoader->register(); 

// config 
$config = new \Doctrine\ORM\Configuration(); 
$config->setMetadataDriverImpl($config->newDefaultAnnotationDriver(__DIR__ . '/Entities')); 
$config->setMetadataCacheImpl(new \Doctrine\Common\Cache\ArrayCache); 
$config->setProxyDir(__DIR__ . '/Proxies'); 
$config->setProxyNamespace('Proxies'); 


$connectionParams = array(
    'dbname' => 'xx', 
    'user' => 'root', 
    'password' => '', 
    'host' => 'localhost', 
    'driver' => 'pdo_mysql', 
); 

$em = \Doctrine\ORM\EntityManager::create($connectionParams, $config); 

// custom datatypes (not mapped for reverse engineering) 
$em->getConnection()->getDatabasePlatform()->registerDoctrineTypeMapping('set', 'string'); 
$em->getConnection()->getDatabasePlatform()->registerDoctrineTypeMapping('enum', 'string'); 

// fetch metadata 
$driver = new \Doctrine\ORM\Mapping\Driver\DatabaseDriver(
    $em->getConnection()->getSchemaManager() 
); 
$classes = $driver->getAllClassNames(); 
foreach ($classes as $class) { 
    //any unsupported table/schema could be handled here to exclude some classes 
    if (true) { 
     $metadata[] = $cmf->getMetadataFor($class); 
    } 
} 

$em->getConfiguration()->setMetadataDriverImpl($driver); 
$cmf = new \Doctrine\ORM\Tools\DisconnectedClassMetadataFactory($em); 

$generator = new EntityGenerator(); 
$generator->setUpdateEntityIfExists(true); 
$generator->setGenerateStubMethods(true); 
$generator->setGenerateAnnotations(true); 
$generator->generate($metadata, __DIR__ . '/Entities'); 

print 'Done!'; 
+0

Echec de la ligne $ metadata [] = $ cmf-> getMetadataFor ($ class); Pourquoi essaie-t-il d'obtenir le parent d'une classe qui n'existe pas encore? Je veux dire, ce sont les noms des entités qui vont faire de l'ingénierie inverse. – DaTroop

+0

Cela ne fonctionne pas ... – Tareq

0

J'ai mis en place une nouvelle commande pour atteindre cet https://github.com/umpirsky/doctrine2/blob/master/lib/Doctrine/ORM/Tools/Console/Command/GenerateEntitiesDbCommand.php

Ajoutez juste comme ceci:

$cli->addCommands(array(
// DBAL Commands 
new \Doctrine\DBAL\Tools\Console\Command\RunSqlCommand(), 
new \Doctrine\DBAL\Tools\Console\Command\ImportCommand(), 

// ORM Commands 
new \Doctrine\ORM\Tools\Console\Command\ClearCache\MetadataCommand(), 
new \Doctrine\ORM\Tools\Console\Command\ClearCache\ResultCommand(), 
new \Doctrine\ORM\Tools\Console\Command\ClearCache\QueryCommand(), 
new \Doctrine\ORM\Tools\Console\Command\SchemaTool\CreateCommand(), 
new \Doctrine\ORM\Tools\Console\Command\SchemaTool\UpdateCommand(), 
new \Doctrine\ORM\Tools\Console\Command\SchemaTool\DropCommand(), 
new \Doctrine\ORM\Tools\Console\Command\EnsureProductionSettingsCommand(), 
new \Doctrine\ORM\Tools\Console\Command\ConvertDoctrine1SchemaCommand(), 
new \Doctrine\ORM\Tools\Console\Command\GenerateRepositoriesCommand(), 
new \Doctrine\ORM\Tools\Console\Command\GenerateEntitiesCommand(), 
new \Doctrine\ORM\Tools\Console\Command\GenerateEntitiesDbCommand(), 
new \Doctrine\ORM\Tools\Console\Command\GenerateProxiesCommand(), 
new \Doctrine\ORM\Tools\Console\Command\ConvertMappingCommand(), 
new \Doctrine\ORM\Tools\Console\Command\RunDqlCommand(), 
new \Doctrine\ORM\Tools\Console\Command\ValidateSchemaCommand(), 

)) ; $ cli-> run();