
Benutzerdefinierte Entitätsformulare am Beispiel der Benutzerbearbeitung und -registrierung
Bei der Verwendung von CMS Drupal können Sie viele für die Projektumsetzung notwendige Elemente erhalten, ohne auch nur eine einzige Zeile Code zu schreiben. Wenn Sie jedoch beispielsweise ein Benutzerbearbeitungsformular auf eine benutzerdefinierte Weise anzeigen möchten, muss eine solche Komponente einigen Programmierarbeiten unterzogen werden. In diesem Artikel erkläre ich Ihnen, wie Sie benutzerdefinierte Modi zum Anzeigen von Entitätsformularen in Drupal registrieren und anzeigen, und wie dies für Ihr Projekt nützlich sein kann.
In Version 8 hat Drupal eine der wichtigen Funktionalitäten eingeführt – nämlich die Anzeigemodi für Entitätsformulare. Grundsätzlich können Sie für jede feldbasierte Entität, d.h. jene, die das Interface Drupal\Core\Entity\FieldableEntityInterface implementieren, Felder auf einem Standardformular konfigurieren. Sie können auch einen neuen Formularanzeigemodus hinzufügen und ihn direkt im Administrationspanel auf der gewählten Entität aktivieren.
Im vorgestellten Beispiel werde ich das neue experimentelle Claro-Administrations-Theme verwenden.
Erstkonfiguration in der Benutzeroberfläche
Jede Entität (wie eingebaute Entitäten – Knoten, Taxonomie, Benutzer) hat einen integrierten Mechanismus zur Verwaltung der Formularanzeige. Im Fall von Benutzertyp-Entitäten können Sie auf ein solches Formular unter folgender Adresse zugreifen:
/admin/config/people/accounts/form-display
Zusätzlich zum Standardanzeigemodus können Sie benutzerdefinierte Anzeigemodi verwenden, indem Sie ausgewählte Modi im unteren Abschnitt aktivieren:
Wenn Ihre Liste leer ist, bedeutet dies, dass Sie in Ihrem CMS noch keinen benutzerdefinierten Modus für Ihre Entität registriert haben. Sie können dies tun, indem Sie auf das folgende Formular zugreifen:
/admin/structure/display-modes/form/add
Dann klicken Sie auf den Namen der ausgewählten Entität. In unserem Fall wird es ein Benutzer sein:
Im folgenden Formular geben Sie nur die Bezeichnung und den Maschinenname an.
Registrierung des Formularmodus
Standardmäßig können Sie in Drupal ein Entitätsformular, nachdem es erstellt und in der Benutzeroberfläche entsperrt wurde, nicht einfach anzeigen. Wir müssen Ihrer Entität explizit "sagen", welche Klasse für die Handhabung der Anzeige Ihres Formulars verantwortlich ist. Es gibt zwei Hooks zu verwenden: hook_entity_type_build und hook_entity_type_alter.
Eine Beispielimplementierung eines Hooks für eine Benutzerentität könnte folgendermaßen aussehen:
/**
* Implementiert hook_entity_type_build().
*/
function my_module_entity_type_build(array &$entity_types) {
$form_modes = ['custom_form_mode_1', 'custom_form_mode_2'];
foreach ($form_modes as $mode) {
$entity_types['user']->setFormClass($mode, 'Drupal\user\ProfileForm');
}
}
Die meisten der eingebauten Entitäten haben bereits Klassen für die Formularhandhabung, und wir können diese erfolgreich verwenden. Es ist wichtig, dass unsere Klasse die Klasse erweitert:
namespace Drupal\Core\Entity\ContentEntityForm;
Eigene Seite mit einem Formular
Um ein benutzerdefiniertes Entitätsformular als eigenständige Seite mit einem Formular anzuzeigen, können Sie die Option nutzen, Ihr eigenes Routing zu erstellen, das automatisch das Laden übernimmt. Es ist von entscheidender Bedeutung, in seiner Konfiguration den Wert _entity_form zu setzen, dank dessen die entsprechende Klasse gefunden wird, die für die Generierung der Formularstruktur verantwortlich ist.
Eine Beispiel-Routing-Konfiguration für eine Benutzerformularseite könnte folgendermaßen aussehen:
my_custom_module.user.edit_form:
path: '/user/{user}/custom-form-mode-1'
defaults:
_entity_form: user.custom_form_mode_1
_title: 'Benutzerentität benutzerdefinierter Formularmodus 1'
requirements:
_permission: 'erforderliche Berechtigung einfügen'
Es ist nicht notwendig, einen zusätzlichen Controller oder ein separates Formular zu deklarieren.
Unabhängiges Laden des Formulars
Das Anzeigen eines Entitätsformulars auf einer separaten Seite entspricht oft nicht den Design-Erwartungen. Daher besteht die Notwendigkeit für Mechanismen, um es in anderen Fällen zu laden, z.B. als Blockinhalt oder als Element einer eingebauten oder benutzerdefinierten Vorlage. Im Fall von Benutzerentitäten kann es sich um ein einfaches Formular zum Bearbeiten des Avatars oder der Profildaten handeln, das z.B. in einem Block angezeigt werden soll.
Um das Ziel zu erreichen, ist es notwendig, mehrere Schritte durchzuführen, die Operationen ausführen, die ähnlich denjenigen sind, die beim Anzeigen Ihrer eigenen Seite auf Basis von Routing implizit durchgeführt werden, jedoch in einem viel allgemeineren Sinne.
Zunächst benötigen Sie einen der am häufigsten verwendeten Dienste zur Verwaltung von Entitätstypen:
$entityTypeManager = \Drupal::entityTypeManager();
Natürlich empfehle ich die Injektion des Dienstes, wenn die Implementierung im Klassenkörper erfolgt.
Dieser Manager kann Ihnen die entsprechende Klasse anzeigen, die für die Formularanzeige verantwortlich ist und \Drupal\Core\Entity\EntityFormInterface implementiert, indem der ID-Parameter des Entitätstyps und der Formularmodus bereitgestellt werden.
$entity_type_id = 'user';
$form_mode = 'my_custom_form_mode_2';
$userForm = $entityTypeManager->getEntityForm($entity_type_id, $form_mode);
Dann müssen Sie Ihr Entitätsformular darüber informieren, auf welcher spezifischen Instanz dieser Art von Entität Sie arbeiten werden. Wir können sowohl eine vorhandene Entität laden als auch eine neue erstellen:
$existingUser = $entityTypeManager->getStorage('user')->load($user_id);
// oder
$newUser = $entityTypeManager->getStorage('user')->create();
und dann als Formularentität festlegen:
$userForm->setEntity($existingUser);
// oder
$userForm->setEntity($newUser);
Mit einem auf diese Weise vorbereiteten Entitätsformularobjekt können Sie schließlich auf dessen Grundlage die Struktur des endgültigen Formulars mit dem \Drupal::formBuilder() Dienst erstellen.
$form = \Drupal::formBuilder()->getForm($userForm);
Ein solches Formular ist eine Tabelle, die gemäß der Dokumentation der getForm-Methode aus dem Interface Drupal\Core\Form\FormBuilderInterface direkt überall in Ihrem Code gerendert werden kann.
Nützliche Module
Leider gibt es im Drupal-Ökosystem nicht viele Module, die die Lösung des von uns betrachteten Problems erleichtern. Eines davon ist das Entityform Blockmodul, das es ermöglicht, das Formular einer ausgewählten Entität in einem Block anzuzeigen. Ein weiteres Modul, das das Problem nur indirekt löst, ist das Inline Entity Form, das ein Widget bereitstellt, das es erlaubt, ein Feld mit einer Entitätsreferenz als Entitätsformular anzuzeigen. Erwähnenswert ist auch das Paragrafen Modul, das ebenfalls ein Widget bereitstellt, um das Formular für ein Feld mit einer Referenz zur Absatzentität anzuzeigen.
Zusammenfassung
Benutzerdefinierte Entitätsformulare sind eine sehr praktische Funktionalität, erfordern jedoch immer noch etwas Arbeit eines Drupal-Entwicklers. Glücklicherweise zeigt sich, dass viele fertige Mechanismen es uns ermöglichen, mit einer schnellen Konfiguration der .yml-Datei oder einigen wenigen Codezeilen den gewünschten Effekt zu erzielen. Die Implementierung eines solchen Formulars auf einer dedizierten Seite oder in Form eines eigenen Blocks sollte daher keine größeren Probleme bereiten. Viel Erfolg!