> ## Documentation Index
> Fetch the complete documentation index at: https://docs.mixpeek.com/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Taxonomy Enrich

> Classify and tag documents using predefined taxonomies

![Taxonomy Enrich stage showing document classification with hierarchical taxonomies](https://mintcdn.com/mixpeek/TmiAqiYj-LwmWL2a/assets/retrievers/taxonomy-enrich.svg?fit=max\&auto=format\&n=TmiAqiYj-LwmWL2a\&q=85\&s=64bc8288d3799384b8bd0097193b27e3)

The Taxonomy Enrich stage classifies documents against predefined taxonomies, adding structured category labels and hierarchical classifications to your search results.

> [!NOTE]
>
> **Stage Category**: ENRICH (Enriches documents with classifications)
>
> **Transformation**: N documents → N documents (with taxonomy labels added)

## When to Use

| Use Case | Description |
| - | - |
| **Content categorization** | Auto-classify documents into topics |
| **Faceted search** | Add filterable category facets |
| **Compliance tagging** | Apply regulatory classifications |
| **Product taxonomy** | Classify into product hierarchies |

## When NOT to Use

| Scenario | Recommended Alternative |
| - | - |
| Free-form tagging | `llm_enrich` |
| Pre-classified content | Skip this stage |
| Custom classification logic | `api_call` to custom service |

## Parameters

| Parameter | Type | Default | Description |
| - | - | - | - |
| `taxonomy_id` | string | `{{TAXONOMY_ID}}` | ID of the taxonomy to use. Replace the placeholder with a real taxonomy ID. The taxonomy's `input_mappings` decide which vector field of each document is matched |
| `fields` | array | `[]` | Taxonomy node fields to merge into the document. Each item has `field_path`, an optional `target_field` to rename it, and `merge_mode` (`replace` or `append`). When empty, the fields configured on the taxonomy's source collection are used |
| `top_k` | integer | `3` | Maximum taxonomy assignments kept per document (1 to 50) |
| `min_score` | float | `0.0` | Minimum similarity score (0.0 to 1.0) an assignment needs to be kept |
| `when` | object | `null` | Condition that selects which documents are classified. Documents that do not match pass through unchanged |

Each document stays one document: `top_k` limits how many assignments are considered for it and does not duplicate the document.

## Configuration Examples

```json Basic Classification theme={null}
{
  "stage_name": "taxonomy_enrich",
  "stage_type": "enrich",
  "config": {
    "stage_id": "taxonomy_enrich",
    "parameters": {
      "taxonomy_id": "product_categories"
    }
  }
}
```

```json High-Confidence Only theme={null}
{
  "stage_name": "taxonomy_enrich",
  "stage_type": "enrich",
  "config": {
    "stage_id": "taxonomy_enrich",
    "parameters": {
      "taxonomy_id": "topics",
      "top_k": 1,
      "min_score": 0.8
    }
  }
}
```

```json Limit Matches Per Document theme={null}
{
  "stage_name": "taxonomy_enrich",
  "stage_type": "enrich",
  "config": {
    "stage_id": "taxonomy_enrich",
    "parameters": {
      "taxonomy_id": "industry_taxonomy",
      "top_k": 3
    }
  }
}
```

```json Multiple Classifications theme={null}
{
  "stage_name": "taxonomy_enrich",
  "stage_type": "enrich",
  "config": {
    "stage_id": "taxonomy_enrich",
    "parameters": {
      "taxonomy_id": "content_types",
      "top_k": 5,
      "min_score": 0.3
    }
  }
}
```

## Output Schema

The stage writes assignments as flat fields on the document. Field names start with a prefix taken from the taxonomy ID: a leading `tax_` is removed, the rest is lowercased, and runs of characters other than letters and digits become `_`. The taxonomy `tax_product_categories` gives the prefix `product_categories`.

| Field | Written when |
| - | - |
| `_taxonomy_{prefix}_taxonomy_id` | An assignment is kept |
| `_taxonomy_{prefix}_id` | The matched node has an ID |
| `_taxonomy_{prefix}_label` | The matched node has a label |
| `_taxonomy_{prefix}_score` | The assignment has a similarity score |
| `_taxonomy_{prefix}_matched_at` | The match has a timestamp |
| `_taxonomy_{prefix}_source_document_id` | The matched node's source document ID is known |
| `{prefix}_path` | The assignment carries a hierarchy path |
| `{prefix}_hierarchy_level` and `{prefix}_level` | The assignment carries a hierarchy level, or a path from which one is derived |

When several assignments are kept, these fields describe the highest-scoring one. Values selected by `fields` are merged for every kept assignment, from the highest score to the lowest.

### Basic Classification

```json theme={null}
{
  "document_id": "doc_123",
  "content": "Latest smartphone with 5G connectivity...",
  "_taxonomy_product_categories_taxonomy_id": "tax_product_categories",
  "_taxonomy_product_categories_id": "col_smartphones",
  "_taxonomy_product_categories_label": "Smartphones",
  "_taxonomy_product_categories_score": 0.95
}
```

### Hierarchical Taxonomy

For a hierarchical taxonomy the path and level fields are added as well.

```json theme={null}
{
  "document_id": "doc_456",
  "content": "Investment banking services...",
  "_taxonomy_industry_taxonomy_id": "tax_industry",
  "_taxonomy_industry_label": "Investment Banking",
  "_taxonomy_industry_score": 0.91,
  "industry_path": ["finance", "banking", "investment"],
  "industry_hierarchy_level": 2,
  "industry_level": 2
}
```

### Merged Enrichment Fields

Fields listed in `fields` are copied from the matched node onto the document, under `target_field` when one is set. With `fields` set to `[{"field_path": "label", "target_field": "visual_style"}]`, the node's `label` lands in `visual_style`.

```json theme={null}
{
  "document_id": "doc_789",
  "content": "Sunset over the harbor...",
  "visual_style": "Golden hour"
}
```

### No Match

When no assignment reaches `min_score`, the document continues without any taxonomy fields added.

```json theme={null}
{
  "document_id": "doc_000",
  "content": "Random unrelated content..."
}
```

## Taxonomy Structure

Taxonomies are hierarchical classification systems:

```
Electronics
├── Mobile Devices
│   ├── Smartphones
│   ├── Tablets
│   └── Wearables
├── Computers
│   ├── Laptops
│   ├── Desktops
│   └── Components
└── Audio
    ├── Headphones
    └── Speakers
```

A match reports:

* **ID**: Identifier of the matched node, usually a collection ID (`_taxonomy_{prefix}_id`)
* **Label**: Human-readable name (`_taxonomy_{prefix}_label`)
* **Level**: Depth in the hierarchy, where 0 is the root (`{prefix}_hierarchy_level`)

## Performance

| Metric | Value |
| - | - |
| **Latency** | 10-50ms per document |
| **Batch processing** | Automatic |
| **Model type** | Embedding-based classification |
| **Engine calls** | One taxonomy join call per stage run, covering every document that passes `when` |

> [!TIP]
>
> Pre-compute taxonomy embeddings for faster classification. Use `top_k: 1` and higher `min_score` when you only need the best match.

## Common Pipeline Patterns

### Search + Classify + Filter

```json theme={null}
[
  {
    "stage_name": "semantic_search",
    "stage_type": "filter",
    "config": {
      "stage_id": "feature_search",
      "parameters": {
        "searches": [
          { "feature_uri": "mixpeek://text_extractor@v1/multilingual_e5_large_instruct_v1", "query": { "input_mode": "text", "value": "{{INPUT.query}}" }, "top_k": 100 }
        ],
        "final_top_k": 100
      }
    }
  },
  {
    "stage_name": "taxonomy_enrich",
    "stage_type": "enrich",
    "config": {
      "stage_id": "taxonomy_enrich",
      "parameters": {
        "taxonomy_id": "product_categories",
        "top_k": 1,
        "min_score": 0.7
      }
    }
  },
  {
    "stage_name": "structured_filter",
    "stage_type": "filter",
    "config": {
      "stage_id": "attribute_filter",
      "parameters": {
        "conditions": {
          "field": "_taxonomy_product_categories_label",
          "operator": "starts_with",
          "value": "{{INPUT.category_filter}}"
        }
      }
    }
  }
]
```

### Multi-Taxonomy Classification

```json theme={null}
[
  {
    "stage_name": "semantic_search",
    "stage_type": "filter",
    "config": {
      "stage_id": "feature_search",
      "parameters": {
        "searches": [
          { "feature_uri": "mixpeek://text_extractor@v1/multilingual_e5_large_instruct_v1", "query": { "input_mode": "text", "value": "{{INPUT.query}}" }, "top_k": 50 }
        ],
        "final_top_k": 50
      }
    }
  },
  {
    "stage_name": "taxonomy_enrich",
    "stage_type": "enrich",
    "config": {
      "stage_id": "taxonomy_enrich",
      "parameters": {
        "taxonomy_id": "topics"
      }
    }
  },
  {
    "stage_name": "taxonomy_enrich",
    "stage_type": "enrich",
    "config": {
      "stage_id": "taxonomy_enrich",
      "parameters": {
        "taxonomy_id": "sentiment"
      }
    }
  }
]
```

### Faceted Search Results

```json theme={null}
[
  {
    "stage_name": "hybrid_search",
    "stage_type": "filter",
    "config": {
      "stage_id": "feature_search",
      "parameters": {
        "searches": [
          { "feature_uri": "mixpeek://text_extractor@v1/multilingual_e5_large_instruct_v1", "query": { "input_mode": "text", "value": "{{INPUT.query}}" }, "top_k": 100 }
        ],
        "final_top_k": 100
      }
    }
  },
  {
    "stage_name": "taxonomy_enrich",
    "stage_type": "enrich",
    "config": {
      "stage_id": "taxonomy_enrich",
      "parameters": {
        "taxonomy_id": "categories",
        "top_k": 3
      }
    }
  }
]
```

## Error Handling

| Condition | Behavior |
| - | - |
| Unknown `taxonomy_id` | Documents pass through unchanged and a warning names the taxonomy |
| No match found | Document continues with no taxonomy fields added |
| Taxonomy join call fails | Documents continue with no taxonomy fields added |
| Low confidence | Assignments below `min_score` are dropped |

## Related

* [LLM Enrich](https://docs.mixpeek.com/docs/retrieval/stages/llm-enrich.md) - Free-form extraction
* [Document Enrich](https://docs.mixpeek.com/docs/retrieval/stages/document-enrich.md) - Collection joins
* [Attribute Filter](https://docs.mixpeek.com/docs/retrieval/stages/attribute-filter.md) - Filter by categories


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.