批量刷新对象原则出错

时间:2017-05-18 12:48:21

标签: php symfony doctrine-orm doctrine symfony-2.8

这会导致错误:

$em = $this->getDoctrine()->getManager();
$courses = $em->getRepository(Course::class)->findBy(['id' => $ids]);

foreach ($courses as $course) {
    $data = $form->getData();
    $course->setProperties($data);
    $em->persist($course);
}

$em->flush();

出现以下错误:

Type error: 
Argument 3 passed to Doctrine\ORM\Event\PreUpdateEventArgs::
 __construct() must be of the type array, null given, called in:

/var/www/bib/vendor/doctrine/orm/lib/Doctrine/ORM/UnitOfWork.php on line 1064

但是当我在一个循环中插入$em->flush();时 - 一切正常。 怎么了?

课程实体:

namespace AppBundle\Entity;

use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\Validator\Constraints as Assert;

use CoreBundle\Entity\GuidTrait;
use CoreBundle\Entity\Typo3Trait;
use Knp\DoctrineBehaviors\Model\Timestampable\Timestampable;
use CoreBundle\Entity\LoggableTrait;

/**
 * @ORM\Entity(repositoryClass="AppBundle\Repository\CourseRepository")
 * @ORM\Table(name="courses")
 * @ORM\HasLifecycleCallbacks()
 */
class Course
{
    use GuidTrait, Typo3Trait, Timestampable, LoggableTrait;

    const STATUS_INACTIVE = 0;
    const STATUS_ACTIVE = 1;

    /**
     * @ORM\Column(type="string", length=150, nullable=true)
     */
    protected $title;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(type="string")
     */
    protected $code;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(name="`order`", type="integer")
     */
    protected $order;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(type="smallint")
     */
    protected $status;

    /**
     * @Assert\NotBlank()
     * @Assert\DateTime()
     * @ORM\Column(type="datetime", nullable=false)
     */
    protected $date;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(type="text", nullable=false)
     */
    protected $enrolmentDetails;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(type="text", nullable=false)
     */
    protected $durationDetails;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(type="text", nullable=false)
     */
    protected $timetable;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(type="string", nullable=false)
     */
    protected $contactName;

    /**
     * @Assert\NotBlank()
     * @Assert\Email
     * @ORM\Column(type="string", nullable=false)
     */
    protected $contactEmail;

    /**
     * @Assert\NotBlank()
     * @ORM\Column(type="string", nullable=false)
     */
    protected $contactPhone;

    /**
     * @ORM\Column(type="string", nullable=true)
     */
    protected $contactFax;

    /**
     * @Assert\NotBlank()
     * @Assert\Type(type="float")
     * @Assert\GreaterThanOrEqual(0)
     *
     * @ORM\Column(type="decimal", precision=8, scale=2, nullable=false)
     */
    protected $price;

    /**
     * @Assert\NotBlank()
     * @Assert\GreaterThanOrEqual(0)
     * @Assert\Type(type="integer")
     *
     * @ORM\Column(type="integer", nullable=false)
     */
    protected $availability;

    /**
     * @ORM\Column(type="text", nullable=true)
     */
    protected $courseNotes;

    /**
     * @ORM\ManyToOne(targetEntity="Centre", inversedBy="courses")
     * @ORM\JoinColumn(name="centre_id", referencedColumnName="uid")
     */
    protected $centre;

    /**
     * @Assert\NotBlank()
     * @ORM\ManyToOne(targetEntity="Qualification", inversedBy="courses")
     * @ORM\JoinColumn(name="qualification_id", referencedColumnName="uid",onDelete="CASCADE")
     */
    protected $qualification;

    /**
     * @Assert\NotBlank()
     * @ORM\ManyToOne(targetEntity="Venue", inversedBy="courses")
     * @ORM\JoinColumn(name="venue_id", referencedColumnName="uid")
     */
    protected $venue;

    /**
     * @ORM\OneToMany(targetEntity="Booking", mappedBy="course", cascade={"remove"})
     */
    protected $bookings;

    /**
     * @ORM\Column(type="string", nullable=false)
     */
    protected $reference;

    public function __construct()
    {
        $this->status = self::STATUS_ACTIVE;
        $this->code = 'CODE';
        $this->order = 1;
    }

    /**
     * @ORM\PreFlush
     */
    public function updateReference()
    {
        $q = $this->getQualification()->getCode();
        $c = $this->getCentre()->getCode();
        $v = $this->getVenue()->getCode();
        $d = $this->getDate()->format('d/m/Y');
        $this->setReference("$q - $c - $v - $d");
    }

     /**
     * @return mixed
     */
    public function getTitle()
    {
        return $this->title;
    }

    /**
     * @param $title
     * @return $this
     */
    public function setTitle($title)
    {
        $this->title = $title;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getCode()
    {
        return $this->code;
    }

    /**
     * @param $code
     * @return $this
     */
    public function setCode($code)
    {
        $this->code = $code;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getOrder()
    {
        return $this->order;
    }

    /**
     * @param $order
     * @return $this
     */
    public function setOrder($order)
    {
        $this->order = $order;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getStatus()
    {
        return $this->status;
    }

    /**
     * @param $status
     * @return $this
     */
    public function setStatus($status)
    {
        $this->status = $status;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getDate()
    {
        return $this->date;
    }

    /**
     * @param $date
     * @return $this
     */
    public function setDate($date)
    {
        $this->date = $date;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getEnrolmentDetails()
    {
        return $this->enrolmentDetails;
    }

    /**
     * @param $enrolmentDetails
     * @return $this
     */
    public function setEnrolmentDetails($enrolmentDetails)
    {
        $this->enrolmentDetails = $enrolmentDetails;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getDurationDetails()
    {
        return $this->durationDetails;
    }

    /**
     * @param $durationDetails
     * @return $this
     */
    public function setDurationDetails($durationDetails)
    {
        $this->durationDetails = $durationDetails;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getTimetable()
    {
        return $this->timetable;
    }

    /**
     * @param $timetable
     * @return $this
     */
    public function setTimetable($timetable)
    {
        $this->timetable = $timetable;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getContactName()
    {
        return $this->contactName;
    }

    /**
     * @param $contactName
     * @return $this
     */
    public function setContactName($contactName)
    {
        $this->contactName = $contactName;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getContactEmail()
    {
        return $this->contactEmail;
    }

    /**
     * @param $contactEmail
     * @return $this
     */
    public function setContactEmail($contactEmail)
    {
        $this->contactEmail = $contactEmail;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getContactPhone()
    {
        return $this->contactPhone;
    }

    /**
     * @param $contactPhone
     * @return $this
     */
    public function setContactPhone($contactPhone)
    {
        $this->contactPhone = $contactPhone;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getContactFax()
    {
        return $this->contactFax;
    }

    /**
     * @param $contactFax
     * @return $this
     */
    public function setContactFax($contactFax)
    {
        $this->contactFax = $contactFax;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getPrice()
    {
        return $this->price;
    }

    /**
     * @param $price
     * @return $this
     */
    public function setPrice($price)
    {
        $this->price = $price;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getAvailability()
    {
        return $this->availability;
    }

    /**
     * @param $availability
     * @return $this
     */
    public function setAvailability($availability)
    {
        $this->availability = $availability;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getCourseNotes()
    {
        return $this->courseNotes;
    }

    /**
     * @param $courseNotes
     * @return $this
     */
    public function setCourseNotes($courseNotes)
    {
        $this->courseNotes = $courseNotes;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getCentre()
    {
        return $this->centre;
    }

    /**
     * @param $centre
     * @return $this
     */
    public function setCentre($centre)
    {
        $this->centre = $centre;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getQualification()
    {
        return $this->qualification;
    }

    /**
     * @param $qualification
     * @return $this
     */
    public function setQualification($qualification)
    {
        $this->qualification = $qualification;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getVenue()
    {
        return $this->venue;
    }

    /**
     * @param $venue
     * @return $this
     */
    public function setVenue($venue)
    {
        $this->venue = $venue;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getReference()
    {
        return $this->reference;
    }

    /**
     * @param $reference
     * @return $this
     */
    public function setReference($reference)
    {
        $this->reference = $reference;
        return $this;
    }

    /**
     * @return mixed
     */
    public function getBookings()
    {
        return $this->bookings;
    }

    /**
     * @param mixed $bookings
     */
    public function setBookings($bookings)
    {
        $this->bookings = $bookings;
    }

    public function getVat( $amount = 0 )
    {
        if (empty($amount)) {
            return round( $this->price * $this->centre->getVat()->getRate()/100, 2 );
        } else {
            return round( $amount * $this->centre->getVat()->getRate()/100, 2 );
        }
    }

    public function setProperties(Course $course)
    {
        foreach ($this as $key=>$value) {
            if ($course->$key) {
                $this->$key = $course->$key;
            }
        }
    }
}

这个实体没有任何超自然现象。 有没有人对我问过的问题有答案?

1 个答案:

答案 0 :(得分:1)

执行flush()方法时,Symfony和Doctrine中存在许多问题。例如,在Doctrine侦听器中调用flush()不是受支持的Doctrine用法。这意味着你试图在彼此内部嵌入几次冲洗,这确实会破坏工作单元。

this StackOverflow Answer中有一个非常完整的示例,但我认为可能无法理解你的问题,所以如果你想要,你可以查看所有可能失败的情况:

https://github.com/doctrine/doctrine2/issues/4004