[Symfony 4] Update multiple

Le problème exposé dans ce sujet a été résolu.

Bonjour à tous,

Je reviens vers vous car je fais face à un petit contretemps.

J’ai une liste qui regroupe toutes les offres de l’utilisateur qu’il peut ensuite gérer (supprimer, modifier, etc) et une des possibilités qu’il a lui permet de cocher une case afin de sélectionner plusieurs offres pour pouvoir les renouveler.

Malheureusement, l’update ne fonctionne pas, tout simplement.

<?php
    /**
     * @Route("renouveler-offre", name="renewOffer")
     */
    public function renewOffer(Request $request, EntityManagerInterface $entity)
    {
        if($request->isXmlHttpRequest())
        {
            $id = explode(',', $request->get('data'));

            for($i = 0; $i < count($id); $i++)
            {
                $jobOffer = $entity->getRepository(JobOffer::class)->findOneBy(array(
                    'id' => $id[$i]
                ));

                $entity->persist($jobOffer);

                dump($jobOffer);

                $newRenewalDate = $jobOffer->getRenewalDate()->add(new \DateInterval($this->getParameter('datetime_interval')));
                dump($jobOffer);

                $jobOffer->setRenewalDate($newRenewalDate);
            }
            
            $entity->flush();

            $this->addFlash('success', 'Toutes les annonces sélectionnées ont été renouvelées');

            return new JsonResponse(array(
               'url' => $this->generateUrl('manageOffers')
            ));
        }
    }
?>

Ma date de renouvellement se met bien à jour dans ma boucle mais, pour une raison que j’ignore, $entity->flush() ne semble pas fonctionner. J’ai essayé de le mettre dans la boucle mais cela donne le même résultat.

Du coup, est-ce qu’il y a une manière spécifique de faire un update multiple ?

Salut,

Tu fais appel à $entity->persist($jobOffer) avant de modifier $jobOffer. Donc le flush va enregistrer en BDD l’état non modifié (celui persisté en fait).

Décale ton persist à après $jobOffer->setRenewalDate($newRenewalDate);, ça devrait déjà mieux marcher. :)

+0 -0

Salut !

persist() sert à dire à l’objet UnitOfWork que l’objet qui lui est passé est tout nouveau (implique qu’il n’a pas d’ID) et qu’il faudra donc l’insérer en base de données. Pour une mise à jour, l’appel à persist() ne sert à rien, sinon éventuellement à avoir cet effet de bord qui fait que les modifications ne sont pas persistées (mais ça me paraît étrange).

Fais attention avec les modifications par référence ($jobOffer->getRenewalDate()->add(new \DateInterval($this->getParameter('datetime_interval')))), ça m’a eu créé des surprises – parce que oui, pas besoin de récupérer le résultat de cette ligne et d’appeler setRenewalDate() normalement, la méthode DateTime::add modifie bien l’objet sous-jacent — la preuve en est que ton dump() affichait la bonne valeur alors que tu n’avais pas encore appelé setRenewalDate().

+0 -0

Salut,

Tu fais appel à $entity->persist($jobOffer) avant de modifier $jobOffer. Donc le flush va enregistrer en BDD l’état non modifié (celui persisté en fait).

Décale ton persist à après $jobOffer->setRenewalDate($newRenewalDate);, ça devrait déjà mieux marcher. :)

melepe

J’ai décalé mais toujours le même problème. Je n’ai aucune erreur mais il n’y a aucune modification dans la base de donnée.

J’ai même tenté de mettre $entity->flush dans ma boucle ou de supprimer $entity->persist mais cela ne change rien.

@Ymox

Je ne suis sûr de ce que tu veux dire. Dans mon premier dump, j’ai bien la date de renouvellement actuelle (celle inscrite en BDD) et au 2ème dump, j’ai bien la nouvelle date de renouvellement (celle actuelle + 2 mois).

Effectivement, faire un ->add() modifie automatiquement la date.

Par contre, j’ai toujours ce problème avec la base.

<?php
    /**
     * @Route("renouveler-offre", name="renewOffer")
     * Description : S'occupe de renouveler les offres d'emplois sélectionnées dans la gestion de ses propres offres
     */
    public function renewOffer(Request $request, EntityManagerInterface $entity)
    {
        if($request->isXmlHttpRequest())
        {
            $id = explode(',', $request->get('data'));

            for($i = 0; $i < count($id); $i++)
            {
                $jobOffer = $entity->getRepository(JobOffer::class)->findOneBy(array(
                    'id' => $id[$i]
                ));

                $jobOffer->getRenewalDate()->add(new \DateInterval($this->getParameter('datetime_interval')));

                //$entity->persist($jobOffer);
                $entity->flush();
            }

            $this->addFlash('success', 'Toutes les annonces sélectionnées ont été renouvelées');

            return new JsonResponse(array(
               'url' => $this->generateUrl('manageOffers')
            ));
        }
    }
?>

D’accord. Du coup, j’aimerais tenter autre chose.

Récupère la date de renouvellement initiale, puis clone-la, modifie-la et réutilise setRenewalDate().

Si ça fonctionne, je supposerais que parce que l’objet DateTime n’est pas remplacé, il n’est pas considéré comme ayant été modifié.

+0 -0

C’est encore moi. Je ne vais pas ouvrir un nouveau sujet.

J’essaie d’utiliser VichUploadBundle pour télécharger des images et documents mais impossible de le faire fonctionner.

Quand je clique sur Télécharger, j’ai droit au message d’erreur suivant :

No route found for "GET /public/build/profile_images/C:/xampp/tmp/php7CB2.tmp" (from "http://localhost:8000/mon-compte")

Pourtant, j’ai suivi la doc mais cela ne veut pas.

Le fichier de configuration

vich_uploader:
    db_driver: orm

    mappings:
        image_profile:
            uri_prefix: /public/build/profile_images
            upload_destination: '%kernel.project_dir%/public/build/profile_images'
            namer: Vich\UploaderBundle\Naming\UniqidNamer

Les deux propriétés

<?php
    /**
     * @ORM\Column(type="string", nullable=true)

     */
    private $picture;

    /**
     * @Vich\UploadableField(mapping="image_profile", fileNameProperty="picture")
     *
     * @var File
     */
    private $pictureFile;
?>

La partie de mon formulaire

<?php
->add('pictureFile', VichImageType::class, array(
           'data_class' => null,
           'required' => false,
           'attr' => array('placeholder' => 'Télécharger une image de profil (120x120)'),
           'label' => false,
           'mapped' => false
))
?>

Du coup, j’aimerais bien savoir pourquoi j’ai droit à cette erreur.

D’après un des projets où j’utilise ce bundle, mais le projet est en Symfony 2.8, il manquerait une partie /.. après %kernel.project_dir% dans upload_destination.

Ensuite, il faut voir quel est le chemin enregistré dans la base de données, si c’est le chemin absolu machine ou juste le nom. Je ne sais pas quelle est la valeur par défaut du paramètre namer qui serait au même niveau que uri_prefix dans la configuration.

+0 -0

Si je me souviens bien, il te faut toi-même créer le dossier, s’il n’existe pas, ça pourrait ne pas passer.

Bon, ça n’explique toujours pas pourquoi tu as un chemin absolu qui apparaît au milieu de celui que tu as mentionné dans l’erreur.

+0 -0
Connectez-vous pour pouvoir poster un message.
Connexion

Pas encore membre ?

Créez un compte en une minute pour profiter pleinement de toutes les fonctionnalités de Zeste de Savoir. Ici, tout est gratuit et sans publicité.
Créer un compte