Drupal Taxonomy — Vocabularies, Terms and Hierarchical Classification
In this tutorial, you'll learn Drupal's taxonomy system including creating vocabularies, managing hierarchical and flat terms, attaching taxonomy to content types, using taxonomy in Views for filtering, and best practices for content categorization.
What You'll Learn
- What taxonomy is and the difference between vocabularies and terms
- Creating vocabularies and configuring their settings
- Adding terms individually and via bulk upload
- Building hierarchical term structures with parent/child relationships
- Attaching taxonomy reference fields to content types
- Integrating taxonomy with Views for content filtering and listing
- Configuring term pages, path aliases, and display
Why It Matters
Taxonomy is Drupal's built-in classification system that lets you organize and relate content in meaningful ways. Unlike simple tags in other CMS platforms, Drupal taxonomy supports hierarchical structures, custom fields on terms, and deep integration with Views, creating a powerful information architecture tool. Proper taxonomy design directly improves content findability and site navigation.
Real-World Use
A recipe website uses hierarchical taxonomy: Cuisine (Italian > Tuscan, Sicilian; Thai > Northern, Southern), Dietary (Vegetarian, Vegan, Gluten-Free, Keto), Meal Type (Breakfast, Lunch, Dinner, Dessert), and Difficulty (Easy, Medium, Hard). Editors assign multiple taxonomy terms per recipe. Views display recipe lists filtered by cuisine with dietary option toggles. The taxonomy terms have custom fields for images and descriptions.
Learning Path
flowchart LR A[Fields System] --> B[Taxonomy] B --> C[Entity System] C --> D[Views] D --> E[Media] E --> F[Revisions]
What is Taxonomy
In Drupal, taxonomy provides a way to classify content. There are two key concepts:
- Vocabulary: A set of categories (like "Cuisine", "Tags", "Departments")
- Term: An individual category within a vocabulary (like "Italian", "Thai", "Dessert")
Think of a vocabulary as a bucket and terms as the items in that bucket. Each vocabulary can have its own settings for hierarchy, field attachments, and display.
Creating a Vocabulary
Navigate to Structure > Taxonomy > Add vocabulary (or /admin/structure/taxonomy/add).
Basic Settings
- Name: Human-readable name, e.g., "Article Categories"
- Description: Explain the vocabulary's purpose
- Machine name: Auto-generated from name, e.g.,
article_categories
Vocabulary Settings
- Hierarchical: Enable to allow parent/child relationships between terms. Disable for flat, tag-like vocabularies.
- Tags: Enable tag-style input on content forms. Editors can type new terms directly without leaving the content form.
Example: Creating a "Department" Vocabulary
Name: Department
Machine name: department
Description: 'Departments within the organization'
Hierarchical: true
Tags: false
Adding Terms
Manual Term Creation
Navigate to Structure > Taxonomy > List terms for your vocabulary > Add term.
Term fields include:
- Name: The term text displayed to users
- Description: Optional description rich text
- Parent: For hierarchical vocabularies, select the parent term
- Weight: Controls sort order in term listings
- URL alias: Optional custom path (requires Pathauto module)
# Add a term using Drush
drush php:eval "
$term = \Drupal\taxonomy\Entity\Term::create([
'name' => 'Engineering',
'vid' => 'department',
'parent' => 0,
]);
$term->save();
echo 'Term created with ID: ' . $term->id();
"
Bulk Term Upload
For adding many terms at once, use the taxonomy_csv module or custom CSV import:
<?php
use Drupal\taxonomy\Entity\Term;
function import_terms_from_csv($csv_file, $vocabulary_id) {
$rows = array_map('str_getcsv', file($csv_file));
$header = array_shift($rows);
foreach ($rows as $row) {
$term = Term::create([
'name' => $row[0],
'vid' => $vocabulary_id,
'description' => $row[1] ?? '',
'parent' => $row[2] ?? 0,
]);
$term->save();
}
}
Term Hierarchy
When a vocabulary is hierarchical, terms can have parent/child relationships. This creates a tree structure.
Example: Geography Vocabulary
Geography
├── North America
│ ├── United States
│ │ ├── New York
│ │ ├── California
│ │ └── Texas
│ └── Canada
│ ├── Ontario
│ └── British Columbia
├── Europe
│ ├── United Kingdom
│ ├── France
│ └── Germany
└── Asia
├── Japan
├── China
└── India
Setting Parents
When adding or editing a term, use the Parent selection to set its parent:
- Top-level terms: Select
<root> - Child terms: Select the parent term
Using Hierarchy in Views
Hierarchical vocabularies allow drill-down navigation:
- List all terms "under" North America (including United States, New York, etc.)
- Show breadcrumb showing current term's ancestry
Taxonomy Field on Content Types
To associate taxonomy with content, add an Entity Reference field pointing to taxonomy terms.
Add the Field
- Navigate to Structure > Content types > Manage fields > Add field
- Select "Taxonomy term" under Reference or "Entity reference"
- Configure:
- Label: "Categories"
- Machine name:
field_categories - Reference type: Taxonomy term
- Vocabulary: Select the vocabulary
- Widget: Autocomplete, Select list, or Checkboxes
Widget Settings
# Configuration for tag-style input
Field: field_tags
Widget: Autocomplete (tag style)
Settings:
match_operator: CONTAINS
size: 60
placeholder: 'Start typing to add tags'
# Configuration for select list with hierarchy
Field: field_category
Widget: Select list
Settings:
size: 1 # single select; use multiple for unlimited
placeholder: '- Select a category -'
Views Integration
Taxonomy integrates deeply with Views for powerful content filtering.
Taxonomy Term View
Views can filter content by taxonomy terms:
# View configuration for filtering by term
Filter criteria:
- field_tags_target_id:
id: field_tags_target_id
table: node__field_tags
field: field_tags_target_id
relationship: none
operator: '='
value:
- 42 # Term ID
Exposed Filters
Create user-facing taxonomy filters:
# Exposed filter by taxonomy
Filter criteria:
- field_tags_target_id:
exposed: true
expose:
label: 'Filter by category'
operator: 'or'
multiple: true
Taxonomy Term Views
Display content associated with a specific term:
- Create a new View of type "Taxonomy term"
- Add fields from the related content
- Contextual filter automatically passes the current term ID
# Contextual filter for taxonomy term view
Contextual filters:
- tid:
id: tid
table: taxonomy_term_data
field: tid
title: 'Posts in %1'
default_argument_type: taxonomy_tid
specifier: 'tid'
Taxonomy Term Page
Each taxonomy term automatically has a page at /taxonomy/term/{tid}. This page can be overridden by a View:
- Go to Structure > Views
- Find the "Taxonomy term" View
- Configure the Page display
- Set path to
/taxonomy/term/%
Term Display
Configuring Term Fields
Taxonomy terms can have custom fields, just like nodes:
- Navigate to Structure > Taxonomy > Manage fields for your vocabulary
- Add fields (e.g., Term image, Description, Color code, Icon)
- Configure form display and view display
# Adding an image field to a taxonomy vocabulary
Field: field_term_image
Type: Image
Widget: Image upload
Formatter: Image with image style
Usage: Display term image on term page and in Views
Term Page Template
Override term page theming with Twig:
{# templates/taxonomy-term.html.twig #}
<article class="term">
<h1>{{ term.name.value }}</h1>
{% if term.field_term_image.value %}
<div class="term-image">
{{ content.field_term_image }}
</div>
{% endif %}
<div class="term-description">
{{ content.description }}
</div>
</article>
Term Path Aliases
With the Pathauto module, taxonomy terms can have clean URL aliases:
# Pathauto pattern for taxonomy terms
Pattern: /[vocabulary:machine-name]/[term:name]
Example: /department/engineering
/geography/north-america/united-states/new-york
Configure at Configuration > URL aliases > Patterns.
REST Export of Taxonomy
Taxonomy terms can be exposed via REST API:
# Fetch taxonomy terms via REST
curl https://example.com/taxonomy/term/42?_format=json
{
"tid": [{ "value": 42 }],
"name": [{ "value": "Engineering" }],
"vid": [{ "target_id": "department" }],
"description": [{ "value": "Engineering department employees" }],
"parent": [{ "target_id": 0 }],
"path": [{ "alias": "/department/engineering" }]
}
Common Mistakes
- Creating multiple flat vocabularies when a hierarchical one would be better: Instead of "Technology" and "Technology > Web Development" as separate vocabularies, create one hierarchical "Technology" vocabulary.
- Not using taxonomy for structured data that could be categorized: When you find yourself creating similar content repeatedly, ask if taxonomy would provide better organization and filtering.
- Creating deep hierarchies that confuse editors: More than three levels of hierarchy becomes hard to navigate in admin forms. Limit to three levels for usability.
- Not adding fields to taxonomy terms: Terms are entities that can have images, descriptions, colors, and other metadata. Use this to display rich category pages.
- Allowing duplicate terms with tag-style widgets: When using tag-style input, train editors to search before creating new terms. Use the "Tags" vocabulary setting with caution in large teams.
Practice Questions
- What is the difference between a vocabulary and a term in Drupal taxonomy?
- How would you set up taxonomy for a blog with categories (hierarchical: Technology > Web Development > PHP, Technology > Mobile > iOS) and tags (flat, non-hierarchical)?
- How do you display all content associated with a taxonomy term, including child terms in hierarchical vocabularies?
- Challenge: Build a complete taxonomy system for a news website with the following requirements: Sections (hierarchical: News > Local, National, World; Opinion > Editorials, Columns), Topics (flat: Health, Education, Environment, Technology, Sports), and Tags (flat, tag-style input with unlimited term creation). Each Section term needs an image field and description. Create Views for section landing pages showing the latest 10 articles in that section and its subsections. Configure Pathauto patterns for clean URLs.
FAQ
Mini Project
Goal: Build a complete taxonomy-driven content architecture for a job board.
- Create three vocabularies:
- Industry: Hierarchical (Technology > Software, Hardware; Healthcare > Medical, Dental; Finance > Banking, Insurance)
- Job Type: Flat (Full-Time, Part-Time, Contract, Freelance, Internship)
- Skills: Tag-style (flat, unlimited, auto-create: PHP, Python, JavaScript, Project Management, Design)
- Add fields to Industry terms:
- Industry Icon (Image)
- Industry Description (Text formatted)
- Create a Job Posting content type with taxonomy reference fields:
- field_industry (single select from Industry vocabulary)
- field_job_type (single select from Job Type vocabulary)
- field_skills (multiple tags from Skills vocabulary)
- Create a View: "Jobs by Industry" showing each Industry term with a count of jobs
- Create a View: "Jobs page" with exposed filters for Industry, Job Type, and Skills
- Configure Pathauto patterns:
/jobs/{field_industry}/{node:title}
What's Next
Taxonomy is part of Drupal's powerful entity system. Dive deeper into the entity system to understand how content entities, config entities, and the entity API work together. Then build dynamic listings with the Views module.
Built by the developers of DodaTech
Doda Browser, DodaZIP & Durga Antivirus Pro