code: def build_tag_id_dict(
      training_data: "TrainingData",
      tag_name: Text = ENTITY_ATTRIBUTE_TYPE,
  ) -> Optional[Dict[Text, int]]:
      """Create a mapping of unique tags to ids.
  
      Args:
          training_data: the training data
          tag_name: tag name of interest
  
      Returns: a mapping of tags to ids
      """
      bilou_key = get_bilou_key_for_tag(tag_name)
  
      distinct_tags = set(
          [
              tag_without_prefix(e)
              for example in training_data.nlu_examples
              if example.get(bilou_key)
              for e in example.get(bilou_key)
          ]
      ) - {NO_ENTITY_TAG}
  
      if not distinct_tags:
          return None
  
      tag_id_dict = {
          f"{prefix}{tag}": idx_1 * len(BILOU_PREFIXES) + idx_2 + 1
          for idx_1, tag in enumerate(sorted(distinct_tags))
          for idx_2, prefix in enumerate(BILOU_PREFIXES)
      }
      # NO_ENTITY_TAG corresponds to non-entity which should correspond to 0 index
      # needed for correct prediction for padding
      tag_id_dict[NO_ENTITY_TAG] = 0
  
      return tag_id_dict
  
imports: import logging
  import operator
  from collections import defaultdict, Counter
  from typing import List, Tuple, Text, Optional, Dict, Any, TYPE_CHECKING
  from rasa.nlu.constants import TOKENS_NAMES, BILOU_ENTITIES, BILOU_ENTITIES_GROUP, BILOU_ENTITIES_ROLE
  from rasa.shared.nlu.constants import TEXT, ENTITIES, ENTITY_ATTRIBUTE_START, ENTITY_ATTRIBUTE_END, ENTITY_ATTRIBUTE_TYPE, ENTITY_ATTRIBUTE_GROUP, ENTITY_ATTRIBUTE_ROLE, NO_ENTITY_TAG
label_desc: Use image node_id 5 for calling a global function with example usage: build_tag_id_dict(training_data, tag_name) and returns: tag_id_dict, None