【发布时间】:2015-01-23 12:26:57
【问题描述】:
我有这段重复的代码,将在我的 Symfony2 项目中的多个实体中使用,所以如果可能的话,当然可以应用某种 DRY,我正在考虑 PHP Traits。
private static $preDeletedEntities;// static array that will contain entities due to deletion.
private static $deletedEntities;// static array that will contain entities that were deleted (well, at least the SQL was thrown).
/**
* This callback will be called on the preRemove event
* @ORM\PreRemove
*/
public function entityDueToDeletion()
{
// This entity is due to be deleted though not deleted yet.
self::$preDeletedEntities[] = $this->getId();
}
/**
* This callback will be called in the postRemove event
* @ORM\PostRemove
*/
public function entityDeleted()
{
// The SQL to delete the entity has been issued. Could fail and trigger the rollback in which case the id doesn't get stored in the array.
self::$deletedEntities[] = $this->getId();
}
public static function getDeletedEntities()
{
return array_slice(self::$preDeletedEntities, 0, count(self::$deletedEntities));
}
public static function getNotDeletedEntities()
{
return array_slice(self::$preDeletedEntities, count(self::$deletedEntities)+1, count(self::$preDeletedEntities));
}
public static function getFailedToDeleteEntity()
{
if(count(self::$preDeletedEntities) == count(self::$deletedEntities)) {
return NULL; // Everything went ok
}
return self::$preDeletedEntities[count(self::$deletedEntities)]; // We return the id of the entity that failed.
}
public static function prepareArrays()
{
self::$preDeletedEntities = array();
self::$deletedEntities = array();
}
这是我想到的代码:
use Doctrine\ORM\Mapping as ORM;
/**
* @ORM\HasLifecycleCallbacks()
*/
trait DeleteLifeCycleCallbacksTrait
{
// write things here
}
但是注释会应用于实体吗?可以吗?你会怎么做才能避免重复代码?
编辑:试图找到最佳方法
从 @Cerad 用户那里得到一些想法,因为正如文档所说,生命周期事件侦听器比简单的生命周期回调更强大,那么我将开始使用它们。
所以,首先,Lifecycle Callbacks|Listener|Suscribers 的目的是存储每个持久对象的 ID,以便我可以通过某种方式获取它并从控制器发送回视图。作为一个简单的视觉示例,假设我从视图向控制器发送了这个值数组(1, 2, 3, 4, 5),并且由于某种 X 原因,只有 1 ,4 和 5 被持久化(意味着从 DB 中完全删除)到 DB,对吗?
还可以说,我将在Producto 实体中使用事件侦听器。因此,无需测试并仅从示例中获取代码,Listener 的代码应该是这样的:
use Doctrine\ORM\Event\LifecycleEventArgs;
use Entity\Producto;
class StoreDeletedIds
{
private $deletedItems = [];
public function postDelete(LifecycleEventArgs $args)
{
$entity = $args->getEntity();
$entityManager = $args->getEntityManager();
if ($entity instanceof Producto) {
array_push($deletedItems, $entity->getId());
}
}
}
我的问题|对此的疑问是:
- 上面的代码好还是不好?
- 每次 Doctrine 调用侦听器时是否都会清理
$deletedItems? - 如何返回
$deletedItems以便在控制器上捕获它并发送回视图? - 我是否也需要定义订阅者?为什么?
这对我来说是新话题,所以我需要一些建议
【问题讨论】:
-
在这种情况下我不会使用 trait。你有没有考虑过给它上课?还是服务?
-
@SergioCosta 不,实际上我不知道如何使用服务,使用一个类,我认为您的意思是稍后从实体本身扩展该类,对吗?
-
看这里:symfony.com/doc/current/book/service_container.html 并尝试了解服务的工作原理。如果您有任何问题,请告诉我!
-
@SergioCosta 我知道服务是如何工作的,以及在这种情况下如何将它们构建到这个我应该通过 EntityManager 来访问它,我现在不知道这将如何在 DRY 方面帮助我,使用服务有什么优势以及如何从 Doctrine Entity 本身使用它
-
Doctrine and DRY 是矛盾的。
标签: php symfony lifecycle traits