4

Doctrine EventListener の実装に問題があります。新しい請求書を作成するとき、フォームに含まれる項目 (タイトル、価格、金額) のコレクションがありますInvoiceType。請求書の場合、priceフィールドに、購入したすべての製品の合計を挿入したいと考えています。ReportListener で合計を取得しますが、EventListener はデータを事前に永続化せず、コードはエラーが表示されずに停止します ( $entityManager->persist($entity)ReportListener で実行するとプログラムが停止します)コントローラー

のコードの一部を次に示します。


class InvoiceController extends Controller
{
    public function createAction(Request $request)
    {
        $em = $this->getDoctrine()->getManager();
        $company = $em->getRepository('DemoBundle:Company')
                      ->findOneByUser($this->getUser()->getId());
        $invoice = new Invoice();
        $item = new Item();
        $form = $this->createForm(new InvoiceType($company->getId()), $invoice);

        if($request->isMethod('POST')){
            if($form->isValid()){
                $em->persist($invoice);
                $em->flush();
            }
        }
    }
}

レポートリスナー

namespace Demo\Bundle\EventListener;

use Doctrine\ORM\Event\LifecycleEventArgs;
use Demo\Bundle\Entity\Invoice;

class ReportListener
{
    public function prePersist(LifecycleEventArgs $args)
    {
        $entity = $args->getEntity();
        $em = $args->getEntityManager();

        $priceTotal = 0;
        foreach ($entity->getItems() as $item)
        {
            $price = &$priceTotal;
            $price += $item->getPrice() * $item->getAmount();
        }

        $entity->setPriceTotal($priceTotal);       // this works
        $em->persist($entity);                     // here code stops
        $em->flush();
    }
}

service.yml

report.listener:
    class: Faktura\FakturaBundle\EventListener\ReportListener
    tags:
        - { name: doctrine.event_listener, event: prePersist }
4

2 に答える 2

9

prePersist は発生するイベントです。そのイベントで永続化してフラッシュしようとする必要はありません。Doctrine は準備ができたらそこに到達します。基本的に、最後の数行を削除するだけです。

$em->persist($entity);                     // here code stops
$em->flush();
于 2013-07-03T22:19:18.760 に答える
3

$form->handleRequest($request);そうしないと、リクエストからの値が Invoice Object に割り当てられません。

リスナーでは、請求書を永続化して再度フラッシュする必要はありません。必要なプロパティを設定するだけです。

于 2013-07-03T22:18:58.813 に答える