No Drupal 8, você pode carregar uma entidade com:
$node = \Drupal::entityManager()->getStorage('node')->load(123);
Ele procura as definições de entidade e descobre que o nó é definido por Drupal \ node \ Entity \ Node - então (eu acho) Drupal \ node \ NodeStorage instancia uma nova instância Drupal \ node \ Entity \ Node .
O que eu gostaria de alcançar é a subclasse de Drupal \ node \ Entity \ Node e a capacidade de instanciar essa subclasse quando for apropriado. Por exemplo, se eu tiver um artigo de pacote configurável de nó, haveria uma classe:
namespace Drupal\my_module\Entity\Article;
class Article extends Drupal\node\Entity\Node {
}
E eu ligaria para:
$node = \Drupal::entityManager()->getStorage('node_article')->load(123);
E o retorno seria minha Article
subclasse.
Eu posso conseguir isso criando um novo tipo de entidade e conectando-o novamente a outras definições de entidade existentes, por exemplo, o exemplo de artigo do nó seria esta classe:
namespace Drupal\my_module\Entity;
use Drupal\node\Entity\Node;
/**
* @ContentEntityType(
* id = "node_article",
* label = @Translation("Content"),
* bundle_label = @Translation("Content type"),
* handlers = {
* "storage" = "Drupal\node\NodeStorage",
* "storage_schema" = "Drupal\node\NodeStorageSchema",
* "view_builder" = "Drupal\node\NodeViewBuilder",
* "access" = "Drupal\node\NodeAccessControlHandler",
* "views_data" = "Drupal\node\NodeViewsData",
* "form" = {
* "default" = "Drupal\node\NodeForm",
* "delete" = "Drupal\node\Form\NodeDeleteForm",
* "edit" = "Drupal\node\NodeForm"
* },
* "route_provider" = {
* "html" = "Drupal\node\Entity\NodeRouteProvider",
* },
* "list_builder" = "Drupal\node\NodeListBuilder",
* "translation" = "Drupal\node\NodeTranslationHandler"
* },
* base_table = "node",
* data_table = "node_field_data",
* revision_table = "node_revision",
* revision_data_table = "node_field_revision",
* translatable = TRUE,
* list_cache_contexts = { "user.node_grants:view" },
* entity_keys = {
* "id" = "nid",
* "revision" = "vid",
* "bundle" = "type",
* "label" = "title",
* "langcode" = "langcode",
* "uuid" = "uuid",
* "status" = "status",
* "uid" = "uid",
* },
* bundle_entity_type = "node_type",
* field_ui_base_route = "entity.node_type.edit_form",
* common_reference_target = TRUE,
* permission_granularity = "bundle",
* links = {
* "canonical" = "/node/{node}",
* "delete-form" = "/node/{node}/delete",
* "edit-form" = "/node/{node}/edit",
* "version-history" = "/node/{node}/revisions",
* "revision" = "/node/{node}/revisions/{node_revision}/view",
* }
* )
*/
class Article extends Node { }
// Results my Article sub type.
$node = \Drupal::entityManager()->getStorage('node_article')->load(123);
Isso funciona bem (tanto quanto eu posso ver); no entanto, cheira. Ele adiciona um novo tipo de entidade, o que não é verdade e pode causar outros problemas no futuro.
Como defino uma subclasse para um pacote de entidades para que o carregamento da entidade retorne um objeto dessa classe?
hook_entity_type_alter()
para fazer a mudança de forma mais limpa, mas eu não sei como você iria limitar isso a um pacote específicoRespostas:
Crie uma nova classe no seu módulo que se estenda
\Drupal\node\Entity\Node
.Implementar
hook_entity_type_build()
.Lembre-se de reconstruir o cache.
Funciona bem ao carregar nós por meio do serviço do gerenciador de tipos de entidade e do armazenamento do nó. Até funciona quando você usa,
Drupal\node\Entity\Node::load($nid)
graças ao fato de que essaload()
função é apenas um invólucro estático para a chamada de serviço do gerenciador de tipo de entidade fornecida pelaEntity
classe que é estendida daNode
classe.Isso também funciona bem com a
entity_load_multiple()
função que será removida em breve , então acho que isso abrange todos os casos de uso padrão para carregar nós.Obviamente, se seu módulo fizer isso e outro módulo fizer o mesmo, você terá um problema, mas acho que não é um cenário comum, e faz sentido apenas para casos de uso muito específicos.
fonte
Tive o mesmo problema e decidi criar um módulo que altera a classe de tipo de entidade das entidades Drupal por meio do sistema de plug-ins. Atualmente, ele suporta a alteração das classes
Node
,User
eFile
entidade. Ao alterar aNode
entidade, você pode alterar a classe de tipo por pacote configurável do nó.Confira a descrição do módulo para um exemplo:
https://www.drupal.org/project/entity_type_class
O módulo usa hook_entity_type_alter () para definir uma classe de manipulador nas entidades que você fornece na anotação do plug-in.
fonte
Este módulo também oferece classes de pacotes reais - https://github.com/amcgowanca/discoverable_entity_bundle_classes
fonte
Esta é uma pergunta antiga, mas a resposta real deve ser:
Se você precisar de um comportamento diferente entre os pacotes configuráveis, deverá usar tipos de entidade diferentes, não pacotes diferentes.
Entidades de conteúdo personalizadas são cidadãos de primeira classe no D8. De fato, estimamos que leva cerca de 30 minutos para obter uma nova entidade de conteúdo personalizada no nível em que está o nó (o que realmente se resume em adicionar a UI do formulário para obter o bom painel lateral e os campos alias / revisão). não inclui adicionar as páginas de tradução, mas isso não é muito mais.
Se você ainda não viu, dê uma olhada nos recursos generate: custom: entity do Drupal Console.
fonte