Bonjour tout le monde,

Je m'adresse à vous aujourd'hui car je suis bloqué depuis deux jours, et je n'en peux plus de fouiller le book officiel de CakePhp.

En effet, j'ai développé un behavior pour gérer l'upload de fichier pour CakePhp3 (similaire au plugin Upload pour CakePhp2 de Jonathan Boyer) mais je suis bloqué au moment de sauvegarder le chemin du fichier uploadé en base de donnée.

Concrétement, l'upload du fichier se fait sans problème, et il ne reste plus qu'à sauvegarder le chemin du fichier dans la base de donnée (le tout est géré dans la fonction afterSave() de mon behavior). Sur CakePhp2, j'aurais simplement effectué un :

$this->Model->saveField(...);

mais sur CakePhp3, je ne trouve aucun équivalent...

J'espère que vous saurez m'aider à résoudre ce problème,
Merci d'avance,

Arkantos.

6 réponses


Lartak
Réponse acceptée

Les requêtes SQL sont à la base prévues pour être effectuées depuis un model, bien qu'elle soient également disponibles depuis les controller.
S'il te crée un nouvel enregistrement, c'est qu'il n'a pas comme information l'ID de l'enregistrement à modifier, du coup il effectue un INSERT au lieu d'un UPDATE, le mieux serait peut-être que tu fasse ta manip dans le beforeSave.
Dans tous les cas, comme tu peux le voir, ce que je t'ai donné c'est bien l'équivalent du saveField, tu voulais l'équivalent de la méthode, je te l'ai fournie, maintenant à toi de l'utiliser comme il le faut.
Essai d'abord de renseigner l'ID comme pour un saveField.

Si tu veux te baser sur un plugin d'upload pour CakePHP3, tu peux regarder celui de Xeta.

Bonsoir.
Peut-être que tu aurais trouvé en jettant un oeil sur la doc :

$articles = TableRegistry::get('Articles');
$article = $articles->find('all')->where(['id' => 2])->first();

$article->title = 'My new title';
$articles->save($article);

Le save() ci-dessus va générer le code SQL suivant:

UPDATE articles SET title = 'My new title' WHERE id = 2;

Si vous avez une nouvelle entity, le code SQL suivant serait généré:

INSERT INTO articles (title) VALUES ('My new title');

Source : Sauvegarder les Entities
Après, à toi d'adapter pour' le beforeSave de ton behavior.

Arkantos
Auteur

Bonsoir,

Merci de ta réponse rapide. Effectivement, j'ai bien vu ce code dans sur le book, mais c'est un code à utiliser au sein d'un controller (du moins c'est ce qu'il est écrit). J'ai quand même essayé de l'adapter au beforeSave(), mais je n'y suis pas arriver. Au lieu de mettre à jour, ce code créait un nouvel enregistrement. Et l'enregistrement initial n'était pas sauvegardé (il était pris en temps que ligne vide).
Donc je me demande si c'est bien la bonne méthode à utiliser pour sauvegarder une entité depuis la partie model, ou s'il y en a une plus adaptée.

Edit : je viens de retenter une adaptation du code, et il me sort la même erreur qu'auparavant : "Some of the Table objects in your application were created by instantiating "Cake\ORM\Table" instead of any other specific subclass. "

Le code en question (dans l'afterSave()) :

$table = TableRegistry::get($this->alias);
$ent = $table->find()->where(['id' => $entity->get('id')])->first();
$ent->$field = $path;
$table->save($ent);

Merci,
Arkantos.

Arkantos
Auteur

Merci de ta réponse, j'ai réussi à régler le problème ! Et merci pour le lien vers le plugin Upload de Xeta, c'est intéressant de voir la manière dont il a développé son code. :)

Bonne soirée et joyeux noël !
Arkantos.

Merci, bonne soirée à toi aussi.
Si tu veux t'exercer un peu plus sur la version 3 de CakePHP, tu peux jetter un oeil à l'application qu'il a fait et mit à notre disposition, personnellement, j'aime bien le système de débug pour les erreurs qu'il utilise dans son application.

Arkantos
Auteur

Oh oui merci, super pour le lien, j'irai voir ça. :)