Doctrine2 duplicate properties and methods from trait

I have an Entity, where I want to use trait "TimestampableEntity" for mapping some properties:

namespace WbudowiePortalBundleEntity;

use DoctrineORMMapping as ORM;
use GedmoMappingAnnotation as Gedmo;
use WbudowiePortalBundleTraitsTimestampableEntity;

/**
 * Category
 * 
 * @GedmoTree(type="materializedPath")
 * @GedmoSoftDeleteable(fieldName="deletedAt", timeAware=false)
 * @ORMTable(name="categories")
 * @ORMEntity(repositoryClass="CategoryRepository")
 */
class Category {

    use TimestampableEntity;

    /**
     * @var integer
     *
     * @ORMColumn(name="id", type="integer")
     * @ORMId
     * @ORMGeneratedValue(strategy="IDENTITY")
     */
    private $id;

This is my TimestampableEntity trait:

namespace WbudowiePortalBundleTraits;

use DoctrineORMMapping as ORM;
use GedmoMappingAnnotation as Gedmo;

trait TimestampableEntity {

    /**
     * @var DateTime
     *
     * @GedmoTimestampable(on="create")
     * @ORMColumn(name="created_at", type="datetime")
     */
    private $createdAt;

    /**
     * @var DateTime
     *
     * @GedmoTimestampable(on="update")
     * @ORMColumn(name="edited_at", type="datetime", nullable=true)
     */
    private $editedAt;

    /**
     * @var DateTime
     * @ORMColumn(name="deleted_at",type="datetime", nullable=true)
     */
    private $deletedAt;

    /**
     * @var boolean
     *
     * @ORMColumn(name="is_active", type="boolean")
     */
    private $isActive;

    /**
     * Sets createdAt.
     *
     * @param  DateTime $createdAt
     * @return $this
     */
    public function setCreatedAt(DateTime $createdAt) {
        $this->createdAt = $createdAt;

        return $this;
    }

    /**
     * Returns createdAt.
     *
     * @return DateTime
     */
    public function getCreatedAt() {
        return $this->createdAt;
    }

    /**
     * Sets updatedAt.
     *
     * @param  DateTime $updatedAt
     * @return $this
     */
    public function setUpdatedAt(DateTime $updatedAt) {
        $this->updatedAt = $updatedAt;

        return $this;
    }

    /**
     * Returns updatedAt.
     *
     * @return DateTime
     */
    public function getUpdatedAt() {
        return $this->updatedAt;
    }

    /**
     * Sets deletedAt.
     *
     * @param Datetime|null $deletedAt
     * 
     * @return $this
     */
    public function setDeletedAt(DateTime $deletedAt = null) {
        $this->deletedAt = $deletedAt;

        return $this;
    }

    /**
     * Returns deletedAt.
     *
     * @return DateTime
     */
    public function getDeletedAt() {
        return $this->deletedAt;
    }

    /**
     * Is deleted?
     * 
     * @return bool
     */
    public function isDeleted() {
        return null !== $this->deletedAt;
    }

    /**
     * Set isActive
     *
     * @param boolean $isActive
     * @return $this
     */
    public function setIsActive($isActive) {
        $this->isActive = $isActive;

        return $this;
    }

    /**
     * Get isActive
     *
     * @return boolean 
     */
    public function getIsActive() {
        return $this->isActive;
    }

}

When I run php bin/console doctrine:generate:entities WbudowiePortalBundle on my entity has been added this code:

/**
 * @var DateTime
 */
private $createdAt;

/**
 * @var DateTime
 */
private $editedAt;

/**
 * @var DateTime
 */
private $deletedAt;

/**
 * @var boolean
 */
private $isActive;


/**
 * Set createdAt
 *
 * @param DateTime $createdAt
 * @return Category
 */
public function setCreatedAt($createdAt)
{
    $this->createdAt = $createdAt;

    return $this;
}

/**
 * Get createdAt
 *
 * @return DateTime 
 */
public function getCreatedAt()
{
    return $this->createdAt;
}

/**
 * Set editedAt
 *
 * @param DateTime $editedAt
 * @return Category
 */
public function setEditedAt($editedAt)
{
    $this->editedAt = $editedAt;

    return $this;
}

/**
 * Get editedAt
 *
 * @return DateTime 
 */
public function getEditedAt()
{
    return $this->editedAt;
}

/**
 * Set deletedAt
 *
 * @param DateTime $deletedAt
 * @return Category
 */
public function setDeletedAt($deletedAt)
{
    $this->deletedAt = $deletedAt;

    return $this;
}

/**
 * Get deletedAt
 *
 * @return DateTime 
 */
public function getDeletedAt()
{
    return $this->deletedAt;
}

/**
 * Set isActive
 *
 * @param boolean $isActive
 * @return Category
 */
public function setIsActive($isActive)
{
    $this->isActive = $isActive;

    return $this;
}

/**
 * Get isActive
 *
 * @return boolean 
 */
public function getIsActive()
{
    return $this->isActive;
}

After that when I try do do anything I'm getting this error, so I have to remove generated code:

Runtime Notice: WbudowiePortalBundleEntityCategory and WbudowiePortalBundleTraitsTimestampableEntity define the same property ($createdAt) in the composition of WbudowiePortalBundleEntityCategory. This might be incompatible, to improve maintainability consider using accessor methods in traits instead. Class was composed in /mnt/DANE/projekty/wbudowie/src/Wbudowie/PortalBundle/Entity/Category.php line 607

What is wrong? I'm using PHP 5.5.9, Doctrine 2.4.* and Symfony 2.5.*


Edit: It,s doctrine bug. It is fixed, but not in 2.4.x version.

https://github.com/doctrine/doctrine2/pull/632

https://github.com/doctrine/doctrine2/pull/763


Here

That's all what you would possibly need to achieve your goal.

And according to this, it's something you can't do anything about. Just don't use generate entities :)


I have had success with this. Try these steps:

First add the entity annotation to your trait:

/**
* @ORMEntity 
*/
trait TimestampableEntity

Temporarily change it to a class

/**
* @ORMEntity 
*/
class TimestampableEntity

Run generate:entities on your trait:

app/console doctrine:generate:entities WbudowiePortalBundle:Traits/TimestampableEntity

Change TimestampableEntity back to a trait:

/**
* @ORMEntity 
*/
trait TimestampableEntity

Add the trait to Category

class Category {

    use TimestampableEntity;

If you now use:

app/console doctrine:generate:entities WbudowiePortalBundle:Category

You shouldn't see the duplicates. I'm not sure, but I believe this works because your trait's getters and setters will now be identical to those that might have been created in Category so they aren't replaced. Hand coding the getters and settings might cause discrepancies that cause Doctrine to think new code is required in Category .

链接地址: http://www.djcxy.com/p/69382.html

上一篇: 在尝试从FOSUserBundle中的BaseUser进行扩展时发生MappingException

下一篇: Doctrine2重复来自trait的属性和方法