Meine Entität verwendet diese Anmerkung für ihre ID:
/**
* @orm:Id
* @orm:Column(type="integer")
* @orm:GeneratedValue(strategy="AUTO")
*/
protected $id;
Aus einer sauberen Datenbank importiere ich vorhandene Datensätze aus einer älteren Datenbank und versuche, dieselben IDs beizubehalten. Wenn ich dann neue Datensätze hinzufüge, möchte ich, dass MySQL die ID-Spalte wie gewohnt automatisch inkrementiert.
Leider scheint Doctrine2 die angegebene ID vollständig zu ignorieren.
Neue Lösung
Gemäß den folgenden Empfehlungen ist Folgendes die bevorzugte Lösung:
$this->em->persist($entity);
$metadata = $this->em->getClassMetaData(get_class($entity));
$metadata->setIdGeneratorType(\Doctrine\ORM\Mapping\ClassMetadata::GENERATOR_TYPE_NONE);
$metadata->setIdGenerator(new \Doctrine\ORM\Id\AssignedGenerator());
Alte Lösung
Da Doctrine zur Bestimmung der Generatorstrategie von ClassMetaData abweicht, muss sie nach der Verwaltung der Entität im EntityManager geändert werden:
$this->em->persist($entity);
$metadata = $this->em->getClassMetaData(get_class($entity));
$metadata->setIdGeneratorType(\Doctrine\ORM\Mapping\ClassMetadata::GENERATOR_TYPE_NONE);
$this->em->flush();
Ich habe dies gerade unter MySQL getestet und es hat wie erwartet funktioniert, was bedeutet, dass Entitäten mit einer benutzerdefinierten ID mit dieser ID gespeichert wurden, während diejenigen ohne angegebene ID die verwendeten lastGeneratedId() + 1
.
quelle
$metadata = $this->getEntityManager()->getClassMetaData(User::class); $metadata->setIdGenerator(new AssignedGenerator()); $metadata->setIdGeneratorType(ClassMetadata::GENERATOR_TYPE_NONE);
Antworten:
Obwohl Ihre Lösung mit MySQL einwandfrei funktioniert, konnte ich sie mit PostgreSQL nicht als sequenzbasiert einsetzen.
Ich muss diese Zeile hinzufügen, damit sie perfekt funktioniert:
$metadata->setIdGenerator(new \Doctrine\ORM\Id\AssignedGenerator());
Freundliche Grüße,
quelle
$em->persist($entity)
.Vielleicht hat sich die Lehre geändert, aber jetzt ist der richtige Weg:
quelle
ClassMetadata
es sich um eine Schnittstelle handelt und daher keine Konstanten haben kann.$metadata::GENERATOR_TYPE_NONE
Wenn die Entität Teil einer Klassentabellenvererbung ist , müssen Sie den ID-Generator in den Klassenmetadaten für beide Entitäten (die Entität, die Sie beibehalten, und die Stammentität) ändern.
quelle
SQLSTATE[23000]: Integrity constraint violation: 1452 Cannot add or update a child row: a foreign key constraint fails
Fehler. DownvotedNeue Lösung funktioniert nur, wenn ALLE Entitäten vor dem Einfügen eine ID haben. Wenn eine Entität eine ID hat und eine andere nicht - schlägt eine neue Lösung fehl.
Ich benutze diese Funktion zum Importieren aller meiner Daten:
quelle
Lösung für Doctrine 2.5 und MySQL
Die "neue Lösung" funktioniert nicht mit Doctrine 2.5 und MySQL. Sie müssen verwenden:
Dies kann ich jedoch nur für MySQL bestätigen, da ich noch kein anderes DBMS ausprobiert habe.
quelle
Ich habe eine Bibliothek erstellt , um zukünftige IDs für Doctrine-Entitäten festzulegen. Es wird zur ursprünglichen ID-Generierungsstrategie zurückgekehrt, wenn alle IDs in der Warteschlange verwendet werden, um die Auswirkungen zu minimieren. Es sollte ein einfaches Drop-In für Unit-Tests sein, damit Code wie dieser nicht wiederholt werden muss.
quelle
Inspiriert von der Arbeit von Villermen habe ich die Bibliothek Tseho / Doctrine-Assigned-Identity erstellt , mit der Sie einer Doctrine-Entität manuell IDs zuweisen können, selbst wenn die Entität die Strategien AUTO, SEQUENCE, IDENTITY oder UUID verwendet.
Sie sollten es niemals in der Produktion verwenden aber es ist wirklich nützlich für Funktionstests.
Die Bibliothek erkennt automatisch die Entitäten mit einer zugewiesenen ID und ersetzt den Generator nur bei Bedarf. Die Bibliothek greift auf den ursprünglichen Generator zurück, wenn einer Instanz keine ID zugewiesen wurde.
Der Austausch des Generators erfolgt in einem Doctrine EventListener, ohne dass Sie zusätzlichen Code in Ihre Geräte einfügen müssen.
quelle