在我extbase /流体工程,除了标准的动作,如创建,删除,列出等等,我想创造出存储在库中的模型类对象的一个副本。 使用的findAll(),所有对象均显示在列表旁边将显示每个如删除,编辑相应的行动。 用于复制的对象,我已经建立在相应的控制器重复动作和这里是代码:
public function dupcliateAction(Tx_CcCompanylogin_Domain_Model_MyObject $testObject)
{
$this->myObjectRepository->add($testObject);
$this->redirect('list');//Lists the objects again from the repository
}
似乎很straitforward但没有新的对象被添加到存储库和我没有得到一个error.I已经检查的文件并没有可供复制没有明确的方法。
注意:当一个对象被克隆,PHP 5将执行的所有对象的属性的浅拷贝。 任何性质对其他变量的引用,将继续引用。
替代你可以使用反射来创建对象的(深)复印件。
$productClone = $this->objectManager->create('Tx_Theext_Domain_Model_Product');
// $product = source object
$productProperties = Tx_Extbase_Reflection_ObjectAccess::getAccessibleProperties($product);
foreach ($productProperties as $propertyName => $propertyValue) {
Tx_Extbase_Reflection_ObjectAccess::setProperty($productClone, $propertyName, $propertyValue);
}
// $productAdditions = ObjectStorage property
$productAdditions = $product->getProductAddition();
$newStorage = $this->objectManager->get('Tx_Extbase_Persistence_ObjectStorage');
foreach ($productAdditions as $productAddition) {
$productAdditionClone = $this->objectManager->create('Tx_Theext_Domain_Model_ProductAddition');
$productAdditionProperties = Tx_Extbase_Reflection_ObjectAccess::getAccessibleProperties($productAddition);
foreach ($productAdditionProperties as $propertyName => $propertyValue) {
Tx_Extbase_Reflection_ObjectAccess::setProperty($productAdditionClone, $propertyName, $propertyValue);
}
$newStorage->attach($productAdditionClone);
}
$productClone->setProductAddition($newStorage);
// This have to be repeat for every ObjectStorage property, or write a service.
对我来说,解决方案“在潜行克隆$对象和resetUid()”不工作..也许这个解决方案中老年TYPO3版本,但在7.6干过。 LTS它抛出一个异常
#1222871239: The uid "61" has been modified, that is simply too much.
所以也许有人能找到我的解决方案有帮助的,因为它比其他反射代码的解决方案要少得多:(你不必去想设置所有单一属性..)
鉴于 :一个对象调用$注册的所有数据。 通缉的结果 :与相同数据对象的副本,但新的UID ..
/** @var \JVE\JvEvents\Domain\Model\Registrant $newregistrant */
$newregistrant = $this->objectManager->get( "JVE\\JvEvents\\Domain\\Model\\Registrant") ;
$properties = $registrant->_getProperties() ;
unset($properties['uid']) ;
foreach ($properties as $key => $value ) {
$newregistrant->_setProperty( $key , $value ) ;
}
对于那些谁可能关注:
你并不需要调用反射API在这一点上。 你只需要在你的模型像这样实现了一个名为如resetUid()方法:
public function resetUid() {
$this->uid = NULL;
$this->_setClone(FALSE);
}
那么你可以使用神奇的clone
方法克隆对象在您的控制器。 之后,你必须调用新resetUid()
方法,然后你可以用旧的属性坚持新对象。
我认为add命令忽略已经存在的对象。
您可以尝试克隆对象,然后添加克隆到存储库$copy_of_object = clone $object;
。 或者,也许创建具有完全相同的属性的新对象。