Search code examples
phpsymfonysonata-adminsonata

Sonata approve functionality


I've an Entity that contains comments. It has a very simple structure

sent_at | DateTime
comment_author | Text
comment_text | Text
approved_at | DateTime (null when the comments is inserted)

I've set up sonata and I can now manage comments.

The "Edit" page it has a group of drop down to set the date and the time for the field approved_at What I would like to do is to have a check box in the "Edit" page that if checked save the current date&time in approved_at

How can I do this ?


Solution

  • SonataAdminBundle provides 3 Saving hooks. Straight from documentation:

    new object : prePersist($object) / postPersist($object)
    edited object : preUpdate($object) / postUpdate($object)
    deleted object : preRemove($object) / postRemove($object)
    

    So, the one you're interested with, is preUpdate()

    In order to achieve what you want, you have to add new non-mapped field to your form:

     // This is needed to check the checkbox if the message has been already approved
     $approved = false;
    
     $review = $this->getSubject();
    
     if ($review->getApprovedAt()) {
        $approved = true;
     }
    
     [..]
    
     $builder->add('approve', 'checkbox',
         array(
              // We don't need this as property in our entity.
              'mapped' => false,
              // The field should not be required, so that you can skip approving specific comment at the time
              'required' => false,
              'data' => $approved
         )
     );
    

    Now, all you have to do is read the value on update and set the datetime if checked:

     public function preUpdate($object) {
          /* @var $isApproved boolean */
          $isApproved = $this->getForm()->get('approve')->getData();
    
          if( $isApproved ) {
              $object->setApprovedAt( new \DateTime('now') );
          }
     }
    

    And this should do the trick. The chapter from documentation - here.