Okay, der Kommentarraum ist viel zu klein, um alles über das zu sagen, was Sie archivieren wollen. Lassen Sie uns jeden einzelnen Schritt, den Sie im Startpost erwähnt haben, umgestalten. Dies wird uns zu Ihrem Ziel führen. Es geht um Hydration.
Dies ist ein kleines Beispiel, wie eine Bestelleinheit mit Produkten darin aussehen könnte. Nach der Auftragsentität folgt die Produkteinheit, die wir für dieses Beispiel benötigen.
namespace Application\Entity;
class Order implements \JsonSerializable
{
/**
* ID of the order
* @var integer
*/
protected $orderID;
/**
* Array of \Application\Entity\Product
* @var array
*/
protected $products;
public function getOrderID() : integer
{
return $this->orderID;
}
public function setOrderID(integer $orderID) : Order
{
$this->orderID = $orderID;
return $this;
}
public function getProducts()
{
if ($this->products == null) {
$this->products = [];
}
return $this->products;
}
public function setProducts(array $products) : Order
{
$this->products = $products;
return $this;
}
/**
* @see \JsonSerializable::jsonSerialize()
*/
public function jsonSerialize()
{
return get_object_vars($this);
}
}
Die folgende Einheit stellt ein Produkt dar.
class Product implements \JsonSerializable
{
protected $productID;
protected $name;
public function getProductID() : integer
{
return $this->productID;
}
public function setProductID(integer $productID) : Product
{
$this->productID = $productID;
return $this;
}
public function getName() : string
{
return $this->name;
}
public function setName(string $name) : Product
{
$this->name = $name;
return $this;
}
/**
* @see \JsonSerializable::jsonSerialize()
*/
public function jsonSerialize()
{
return get_object_vars($this);
}
}
Oben sehen Sie unsere Entität, die eine einzelne Bestellung mit mehreren möglichen Produkten darstellt. Das zweite Element Produkte kann ein Array mit Product entities sein. Diese Entität repräsentiert die Datenstruktur unserer einfachen Reihenfolge.
An dieser Stelle benötigen wir ein Formular, das diese Objekte als Objekte für die darin enthaltenen Daten verwendet. Eine mögliche Fabrik für unser Formular könnte so aussehen.
namespace Application\Form\Factory;
class OrderFormFactory implements FactoryInterface
{
public function createService(ServiceLocatorInterface $serviceLocator)
{
$parentLocator = $serviceLocator->getServiceLocator();
$inputFilter = $parentLocator->get('InputFilterManager')->get(OrderInputFiler::class);
$hydrator = new ClassMethods(false);
$entity = new OrderEntity();
return (new OrderForm())
->setInputFilter($inputFilter)
->setHydrator($hydrator)
->setObject($entity);
}
}
Dies ist die Fabrik für unser Formular. Wir setzen einen Hydrator, einen Eingabefilter und eine Entität für das Formular. Du musst also nichts binden. Der folgende Code zeigt, wie Daten mit diesem Formular behandelt werden.
// retrieve an order from database by id
// This returns a order entity as result
$order = $this->getServiceLocator()->get(OrderTableGateway::class)->fetchById($id);
// Extract the order data from object to array assumed the
// retrieved data from data base is an OrderEntity object
// the hydrator will use the get* methods of the entity and returns an array
$data = (new ClassMethods(false))->extract($order);
// fill the form with the extracted data
$form = $this->getServiceLocator()->get('FormElementManager')->get(OrderForm::class);
$form->setData($data);
if ($form->isValid()) {
// returns a validated order entity
$order = $form->getData();
}
Es ist absolut nicht möglich, Daten von einem Formular zu erhalten, das noch nicht validiert ist. Sie müssen die Formulardaten validieren und danach können Sie die gefilterten/validierten Daten aus dem Formular abrufen. Hydratoren und Einheiten werden Ihnen sehr helfen, wenn Sie mit vielen Daten umgehen müssen.
Die letzte Fehlermeldung besagt, dass die Daten, die Sie mit der setData-Methode festlegen möchten, null sind. Sie müssen Ihr Formular mit Daten füllen, bevor Sie es validieren. Lass uns deinen Weg umgestalten. Erstens: Holen Sie sich die ID der Bestellung. Zweitens: Holen Sie das Auftragsobjekt durch die ID. Drittens: Extrahieren Sie die Daten Ihres Auftragsobjekts mit einem Hydrator. Viertens: Geben Sie die extrahierten Daten (Array) über die Methode setData Ihres Formulars an das Formular weiter. Fünftens: bestätige es. Sechstens: Holen Sie sich die gefilterten, validierten Daten Ihres Formulars über die getData-Methode. Sie können das Bestellobjekt nicht direkt an Ihr Formular binden. – Marcel