Comment envoyer des données supplémentaires lors de la sauvegarde pour réaliser un traitement spécifique ?
Prérequis
Afin de pouvoir suivre ce guide, il faut préalablement savoir Comment déclencher un code javascript lors de la sélection d’un menu spécifique ?.
Comment procéder ?
Dans notre exemple, on souhaite afficher un message provenant du serveur lorsque le prix d’un PLAT
a été changé. La
méthode addCustomClientData
permet d’ajouter des données supplémentaires depuis le client.
Recommandations
Si vous n’êtes pas familier avec la méthode addCustomClientData
, il est recommandé de lire la documentation associée
disponible ici
Commençons par rajouter le Smart Field plat_price_difference
qui contiendra la différence de prix. Cette différence
sera calculée côté client.
Modifier le fichier src/vendor/Cogip/Restauratec/SmartStructures/Plat/100-PlatStructure.xml
:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<smart:config xmlns:smart="https://platform.anakeen.com/4/schemas/smart/1.0">
<smart:structure-configuration name="PLAT" label="Plat">
<smart:extends ref="CONSOMMABLE"/> <!-- La smart structure PLAT hérite de la smart structure CONSOMMABLE -->
<smart:icon file="plat.png"/>
<smart:class>Cogip\Restauratec\SmartStructures\Plat\PlatBehavior</smart:class>
<smart:fields reset="true">
<!-- extended="true" indique que l’on récupère ici la frame du parent (Consommable) à laquelle on ajoute d’autres Smart Fields -->
<smart:field-set name="consommable_frame" extended="true">
<smart:field-enum name="plat_type" label="Type de plat" relation="Plat_Type" access="Read" />
<smart:field-date name="plat_validity_date" label="Disponible jusqu’au" access="Read" />
<smart:field-text name="plat_abstract" label="Résumé" access="ReadWrite" />
<smart:field-double name="plat_price_difference" label="Différence de prix" access="ReadWrite"/>
<smart:field-date name="plat_creation_date" label="Date de création du plat" access="ReadWrite" />
<smart:field-image name="plat_image" label="Image du plat" access="ReadWrite"/>
</smart:field-set>
</smart:fields>
<smart:hooks />
<smart:defaults>
<smart:default field="plat_abstract">Entrez un résumé...</smart:default>
<smart:default field="plat_creation_date">
<smart:field-callable function="::getCreationDate"/>
</smart:default>
</smart:defaults>
</smart:structure-configuration>
</smart:config>
Modifions le fichier src/public/platEdit.js
pour ajouter nos données supplémentaires :
window.ank.smartElement.globalController.registerFunction("platEdit", (controller) => {
controller.addEventListener("ready", function addListeners(event, documentObject, data) {
controller.addEventListener("afterSave", function fetchConsultationView(
event,
currentSmartElement,
previousSmartElement
) {
controller.fetchSmartElement({
initid: currentSmartElement.initid,
viewId: "!defaultConsultation",
});
});
});
const oldPrice = controller.getValue("consommable_price_incl_vat");
controller.addEventListener("smartFieldChange", function addCustomClientData(
event,
smartElement,
smartField,
values
) {
if (smartField.id === "consommable_price_incl_vat") {
const newPrice = values.current;
const priceDifference = newPrice.value - oldPrice.value;
controller.addCustomClientData({ priceDifference });
}
});
});
On peut alors récupérer les données client supplémentaires du côté du serveur en utilisant la méthode
setCustomClientData
.
Recommandations
Si vous n’êtes pas familier avec la méthode setCustomClientData
, il est recommandé de lire la documentation associée
disponible ici
Modifier le fichier src/vendor/Cogip/Restauratec/SmartStructures/Plat/Render/PlatEditRender.php
:
<?php
namespace Cogip\Restauratec\SmartStructures\Plat\Render;
use Anakeen\Ui\CommonRenderOptions;
use Anakeen\Ui\EnumRenderOptions;
use Anakeen\Ui\FrameRenderOptions;
use Anakeen\Ui\RenderAttributeVisibilities;
use Anakeen\Ui\RenderOptions;
use Cogip\Restauratec\SmartStructures\Consommable\Render\ConsommableEditRender;
use SmartStructure\Fields\Plat as PlatFields;
class PlatEditRender extends ConsommableEditRender
{
public function getOptions(\Anakeen\Core\Internal\SmartElement $document): RenderOptions
{
$options = parent::getOptions($document);
$options->enum(PlatFields::plat_type)->setDisplay(EnumRenderOptions::verticalDisplay);
$options->commonOption()->setLabelPosition(CommonRenderOptions::upPosition);
$options->frame(PlatFields::consommable_frame) ->setResponsiveColumns(
array(
[
"number" => 2,
"minWidth" => "60rem",
"maxWidth" => "100rem",
"direction" => FrameRenderOptions::topBottomDirection
],
[
"number" => 3,
"minWidth" => "100rem",
"maxWidth" => "140rem",
"direction" => FrameRenderOptions::topBottomDirection],
[
"number" => 4,
"minWidth" => "140rem",
"maxWidth" => "160rem",
"direction" => FrameRenderOptions::topBottomDirection],
[
"number" => 5,
"minWidth" => "160rem",
"direction" => FrameRenderOptions::topBottomDirection],
)
);
return $options;
}
public function getJsReferences(\Anakeen\Core\Internal\SmartElement $document = null)
{
$jsRefs = parent::getJsReferences($document);
$jsRefs['platEdit'] = new \Anakeen\Ui\JsAssetReference("/platEdit.js");
return $jsRefs;
}
public function setCustomClientData(\Anakeen\Core\Internal\SmartElement $document, $data)
{
parent::setCustomClientData($document, $data);
if (!empty($data) && array_key_exists("priceDifference", $data)) {
$priceDiff = $data["priceDifference"];
if (!empty($priceDiff)) {
$document->setAttributeValue(PlatFields::plat_price_difference, $priceDiff);
$document->store();
}
}
}
public function getVisibilities(\Anakeen\Core\Internal\SmartElement $document, \SmartStructure\Mask $mask = null): RenderAttributeVisibilities
{
$vis = parent::getVisibilities($document, $mask);
$vis->setVisibility(PlatFields::plat_price_difference, RenderAttributeVisibilities::HiddenVisibility);
return $vis;
}
}
Astuce
Pensez à générer les stubs. Cela a pour but d’extraire les constantes des différents fichiers de configuration .xml
des SmartStructures que vous possédez. Cela apportera ici une complétion sur les Smart Fields, paramètres de Smart
Structure, étapes et transitions des cycles de vie, aussi bien dans le PHP que dans le JavaScript. Pour cela :
npx @anakeen/anakeen-cli generateStubs
Affichons un message sur la vue de consultation en modifiant
src/vendor/Cogip/Restauratec/SmartStructures/Plat/Render/PlatViewRender.php
:
<?php
namespace Cogip\Restauratec\SmartStructures\Plat\Render;
use Anakeen\Core\Internal\SmartElement;
use Anakeen\Routes\Core\Lib\ApiMessage;
use Anakeen\Ui\BarMenu;
use Anakeen\Ui\ItemMenu;
use Anakeen\Ui\MenuTargetOptions;
use Anakeen\Ui\RenderAttributeVisibilities;
use Cogip\Restauratec\SmartStructures\Consommable\Render\ConsommableViewRender;
use SmartStructure\Fields\Plat as PlatFields;
class PlatViewRender extends ConsommableViewRender
{
/**
* @param SmartElement $document
* @return BarMenu
* @throws \Anakeen\Core\DocManager\Exception
* @throws \Anakeen\Exception
* @throws \Anakeen\Database\Exception
* @throws \Anakeen\Search\Exception
*/
public function getMenu(SmartElement $document): BarMenu
{
$menu = parent::getMenu($document);
$imagePlat= $document ->getFileLink(PlatFields::plat_image);
if(!empty($imagePlat)){
$itemImage = new ItemMenu("platImage");
$url = sprintf("%s?inline=true&inline=yes",
$imagePlat
);
$itemImage->setUrl($url);
$option = new MenuTargetOptions();
$option->windowHeight = 400;
$option->windowWidth = 700;
$itemImage->setTarget("_dialog", $option);
$itemImage->setTextLabel("Afficher l’image");
$menu->appendElement($itemImage);
}
return $menu;
}
public function getMessages(\Anakeen\Core\Internal\SmartElement $document)
{
$messages = parent::getMessages($document);
$priceDiff = $document->getAttributeValue(PlatFields::plat_price_difference);
if ($priceDiff !== 0) {
$messages[] = new ApiMessage(sprintf("Le plat a changé de prix de %s euros", $priceDiff), ApiMessage::WARNING);
}
return $messages;
}
public function getVisibilities(\Anakeen\Core\Internal\SmartElement $document, \SmartStructure\Mask $mask = null): RenderAttributeVisibilities
{
$vis = parent::getVisibilities($document, $mask);
$vis->setVisibility(PlatFields::plat_price_difference, RenderAttributeVisibilities::HiddenVisibility);
return $vis;
}
}
Recommandations
Si vous n’êtes pas familier avec les méthodes getMessages
ou getVisibilities
, vous pouvez suivre les How To
correspondants disponibles
ici ou
ici.
Vous pouvez maintenant déployer vos modifications :
npx @anakeen/anakeen-cli deploy -c http://localhost:8080/control -s . -u admin -p anakeen --reinstall
Et voir le résultat sur un PLAT en création ou édition :
http://localhost:8080/api/v2/smart-elements/PLAT/views/!defaultCreation.html
Et ensuite ?
Comment afficher des données serveur spécifiques sur une représentation ?