Skip to content

Instantly share code, notes, and snippets.

  • Save IProSoft/5061bdd4f761d0281582e8ab254adcd8 to your computer and use it in GitHub Desktop.
Save IProSoft/5061bdd4f761d0281582e8ab254adcd8 to your computer and use it in GitHub Desktop.
Drupal 8 || 9 - Getting Taxonomy Terms from different levels programmatically

Introduction

In this snippet I've gathered some examples and cases about how to get taxonomy terms programmatically in Drupal, using always the same method and the same mechanics: get terms and then processing it in order to get only the required under certain criteria.

Author

0 - The loadTree() method

For all the next cases we will use the loadTree() method, from the TermStorage class in Drupal. This method finds all terms in a given vocabulary ID, using the next parameters:

  • string $vid: Vocabulary ID to retrieve terms for.
  • int $parent: The term ID under which to generate the tree. If 0, generate the tree for the entire vocabulary.
  • int $max_depth: The number of levels of the tree to return. Leave NULL to return all levels.
  • bool $load_entities: If TRUE, a full entity load will occur on the term objects. Otherwise they are partial objects queried directly from the {taxonomy_term_data} table to save execution time and memory consumption when listing large numbers of terms. Defaults to FALSE.

And this method will return an array of terms objects that are the children of the vocabulary $vid. We're gonna to play extracting terms and then processing the values cutting some levels (up or down) in order to get only the terms from the desired levels.

1- Load Taxonomy Terms by Name only first level

// Load the taxonomy tree using values.
$tree = \Drupal::entityTypeManager()->getStorage('taxonomy_term')->loadTree(
  'vocabulary_name', // The taxonomy term vocabulary machine name.
  0,                 // The "tid" of parent using "0" to get all.
  1,                 // Get only 1st level.
  TRUE               // Get full load of taxonomy term entity.
);
 
$results = [];
 
foreach ($tree as $term) {
  $results[] = $term->getName();
}

2- Load Taxonomy Terms by Name getting the first level from a whole taxonomy terms tree

// Load the whole taxonomy tree using values.
$manager = \Drupal::entityTypeManager()->getStorage('taxonomy_term');
$taxonomy_tree = $manager->loadTree(
        'vocabulary_name', // The taxonomy term vocabulary machine name.
        0,                 // The "tid" of parent using "0" to get all.
        NULL,                 // Get all available levels.
        TRUE               // Get full load of taxonomy term entity.
        );

$results_terms = [];

// By now we need only the first level.
foreach ($taxonomy_tree as $term) {
  // Filtering asking for parents first level hasn't got any parent.
  if(empty($manager->loadParents($term->id()))) {
    // We need a normalized version of the string without accents nor diacritics
    $results_terms[] = preg_replace('/[\x{0300}-\x{036f}]/u', "", Normalizer::normalize($term->getName() , Normalizer::FORM_D));
  }
}

3- Load Taxonomy Terms by Name first and second level

// Load the taxonomy tree using values.
$tree = \Drupal::entityTypeManager()->getStorage('taxonomy_term')->loadTree(
  'some_vocabulary', // The taxonomy term vocabulary machine name.
  0,                 // The "tid" of parent using "0" to get all.
  2,                 // Get terms from 1st and 2nd levels.
  TRUE               // Get full load of taxonomy term entity.
);
 
$results = [];
 
foreach ($tree as $term) {
  $results[] = $term->getName();
}

4- Getting Taxonomy Terms only the second level

// Load the taxonomy tree using values.
$manager = \Drupal::entityTypeManager()->getStorage('taxonomy_term');
$tree = $manager->loadTree(
  'some_vocabulary', // The taxonomy term vocabulary machine name.
  0,                 // The "tid" of parent using "0" to get all.
  2,                 // Get terms from 1st and 2nd levels.
  TRUE               // Get full load of taxonomy term entity.
);
 
$results = [];
 
foreach ($tree as $term) {
  // We get 1st and 2nd levels so we check parents cause only 2nd level has parents.
  if (!empty($manager->loadParents($term->id()))) {
    $results[] = $term->getName();
    }
}

5- Getting Taxonomy Terms only second and third level

// Getting first the entity type manager service.
$manager = \Drupal::entityTypeManager()->getStorage('taxonomy_term');

// Load the taxonomy tree using values.
$tree = $manager->loadTree(
  'some_vocabulary', // The taxonomy term vocabulary machine name.
  0,                 // The "tid" of parent using "0" to get all.
  3,                 // Get terms from 1st, 2nd and 3rd levels.
  TRUE               // Get full load of taxonomy term entity.
);
 
$results = [];
 
foreach ($tree as $term) {
  // We want only 2nd and 3rd levels so we check parents cause 1st level does not have parents.
  if (!empty($manager->loadParents($term->id()))) {
    $results[] = $term->getName();
  }
}

6- Getting Taxonomy Terms only the last level

// Getting first the entity type manager service.
$manager = \Drupal::entityTypeManager()->getStorage('taxonomy_term');

// Load the taxonomy tree using values.
$tree = $manager->loadTree(
  'some_vocabulary', // The taxonomy term vocabulary machine name.
  0,                 // The "tid" of parent using "0" to get all tree.
  NULL,              // Get all levels.
  TRUE               // Get full load of taxonomy term entity.
);
 
$results = [];
 
foreach ($tree as $term) {
  // Check if has children or not to validate if is at last level.
  if (empty($manager->loadChildren($term->id()))) {
    $results[] = $term->getName();
  }
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment