Obter todos os campos definidos em um pacote

16

para obter todos os campos usados ​​em um tipo de conteúdo, no Drupal 7 eu uso o código a seguir.

$fields = field_info_instances('node', 'article');

Qual é o equivalente para o Drupal 8?

Pravin Ajaaz
fonte
1
Você está trabalhando com uma entidade? Se sim: $fields = $entity->getFieldDefinitions();fará isso. Não sei ao certo qual é o equivalente field_info_instances(), FieldStorageConfignão parece ter um
Clive
Não, eu só quero alterar o node_type_edit_form e adicionar uma lista de campos definidos pelo tipo de nó no formulário. Portanto, o tipo do nó é o único argumento que tenho. Então, pensei que funções como field_info_instances podem ajudar.
Pravin Ajaaz
@Clive: posso criar um objeto de entidade usando o nome do tipo de entidade. Existe uma função NodeType :: load ('article') que cria um objeto para os tipos de nós.
Pravin Ajaaz
\Drupal::entityManager()->getFieldDefinitions('node', 'article')fez o Clive trabalho :)
Pravin Ajaaz

Respostas:

31

O EntityManager está obsoleto no futuro. Em vez disso, pode ser usado o seguinte:

$entityFieldManager = \Drupal::service('entity_field.manager');
$fields = $entityFieldManager->getFieldDefinitions($entity_type, $bundle);
NewZeal
fonte
Existe alguma maneira de obter apenas a lista de campos cck?
Rajesh Vishwakarma
2
Essa deve ser a resposta aceita agora.
Bram
25

Eu consegui usando getFieldDefinitions()definido em Class EntityManager. Portanto, para obter todos os campos usados ​​em um pacote específico, aqui está uma maneira:

$bundle_fields = \Drupal::entityManager()->getFieldDefinitions('node', 'article');

Embora o acima $bundle_fieldstambém contenha nid, uuid, revisions, langcode, etccomo campos. Então, para obter uma saída precisa, fiz algo assim:

  $entity_type_id = 'node';
  $bundle = 'article';
  foreach (\Drupal::entityManager()->getFieldDefinitions($entity_type_id, $bundle) as $field_name => $field_definition) {
    if (!empty($field_definition->getTargetBundle())) {
      $bundleFields[$entity_type_id][$field_name]['type'] = $field_definition->getType();
      $bundleFields[$entity_type_id][$field_name]['label'] = $field_definition->getLabel();
    }
  }
Pravin Ajaaz
fonte
2
Isso funciona, no entanto, o entityManager está obsoleto. O comentário acima da definição da função diz use entityTypeManager ou se o método não for implementado (getFieldDefinitions não é) "consulte o \ Drupal \ Core \ Entity \ EntityManager descontinuado para encontrar a interface ou o serviço correto." Eu não entendo esse comentário. Onde posso procurar a função correta a ser usada?
Felix Eve
5
Para filtrar os campos base ( nid, uuid, revisions, langcode, etc), você pode fazerif($field->getFieldStorageDefinition()->isBaseField() == FALSE)
leon.nk
1
Existe uma maneira de obter as Definições de campo para todos os tipos de conteúdo e não apenas um?
Matt
1
@ leon.nk yes <code> if ($ field-> getFieldStorageDefinition () -> isBaseField () == FALSE) </code> que é mais preciso que <code> if (! empty ($ field_definition-> getTargetBundle ()) ) </code> para filtrar os campos base.
Hanmant
6

O EntityManager está obsoleto e usei o próximo código. Eu adicionei à classe Controller:

 /**
   * The entity field manager.
   *
   * @var \Drupal\Core\Entity\EntityFieldManager
   */
  protected $entityFieldManager;

  /**
   * Constructor.
   *
   * @param \Drupal\Core\Entity\EntityFieldManager $entity_field_manager
   *   The entity field manager.
   */
  public function __construct(EntityFieldManager $entity_field_manager) {
    $this->entityFieldManager = $entity_field_manager;
  }

  /**
   * {@inheritdoc}
   */
  public static function create(ContainerInterface $container) {
    return new static(
      $container->get('entity_field.manager')
    );
  }

// Aqui algumas das suas funções

 /**
   * Build table rows.
   */
  protected function buildRows() {
    $entity_type_id = 'node';
    $bundle = 'article';
$fields = $this->entityFieldManager->getFieldDefinitions($entity_type_id, $bundle);
foreach ($fields as $field_name => $field_definition) {
  if (!empty($field_definition->getTargetBundle())) {               
    $listFields[$field_name]['type'] = $field_definition->getType();
    $listFields[$field_name]['label'] = $field_definition->getLabel();                  
  }
}
$rows = [];
foreach ($listFields as $field_name => $info) {
  $rows[] = $this->buildRow($info, $field_name);
}
return $rows;

}

https://www.drupal.org/node/2549139 me ajudou

Maria
fonte
Algumas dicas: Nos construtores (e em geral), use sempre interfaces. A maioria das implementações de serviço drupal possui interfaces bem definidas.
ssibal