RASA - Synonyms
Tags: rasa, chatbot, nlp, ai
Published: 2021-08-07 11:39:21

Synonyms map extracted entities to a value other than the literal text extracted. You can use synonyms when there are multiple ways users refer to the same thing. Think of the end goal of extracting an entity and from there, figure out which values should be considered equivalent.

We have a frequency entity.
```yml
# domain.yml
# ... previous content ...
entities:
  # ... other entities ...
  - frequency
```

This entity is used to fill the frequency slot that has two possible values: **once a week** and **twice a week**.
```yml
# domain.yml
# ... previous content ...
slots:
  # ... other slots ...
  frequency:
    type: categorical
    values:
      - once a week
      - twice a week
    influence_conversation: true
```

The slot is filled during the **newsletter_form**.
```yml
# domain.yml
# ... previous content ...
forms:
  newsletter_form:
    # ... other slots ...
    frequency:
      - type: from_entity
        entity: frequency
```

Users might also refer to the **once a week** value as **once** or **once per week**

In this case, we will define **once** and **once per week** as synonyms to **once a week**:
Then, if either of these phrases is extracted as an entity, it will be mapped to the value **once a week**.

There are two ways of defining synonyms:

## First option
Create a `synonym` key and list the mapped synonyms.
```yml
# data/nlu.yml
# ... previous content ...
  - intent: inform_frequency
    examples: |
      # ... other examples ...
      - [once a week](frequency)
      - [once](frequency)
      - [once per week](frequency)
      
  - synonym: once a week
    examples: |
      - once
      - once per week
```

![Once per week changed to once a week](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/3an9nan1ipzldsqbtr5b.png)

We can see, that even though user entered *"once per week"*, the extracted entity was *"once a week"*.

## Second option
We can also define synonyms in-line in our training examples by specifying the value of the entity:
```yml
# data/nlu.yml
# ... previous content ...
  - intent: inform_frequency
    examples: |
      # ... other examples ...
      - [twice a week](frequency)
      - [twice]{"entity": "frequency", "value": "twice a week"}
      - [twice per week]{"entity": "frequency", "value": "twice a week"}
```

![Twice changed to twice a week](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/z0rx5merozjwlbct5k47.png)

We can see, that even though user entered *"twice"*, the extracted entity was *"twice a week"*.

Since **frequency** is now an entity, we need to [annotate it in the test stories](https://github.com/petr7555/rasa-dev-tutorial/commit/72d1245ba667672b949acfa39f1126cb086ae556#diff-00f496b9f74b4c5708a1b045a7e2684f9219b6e7462796bbed1daec94c1aa342).

You can learn more about synonyms in the documentation [here](https://rasa.com/docs/rasa/nlu-training-data#synonyms) and [here](https://rasa.com/docs/rasa/training-data-format#synonyms).

Repository for this tutorial:
{% github petr7555/rasa-dev-tutorial no-readme %}

You can checkout the state of the repository at the end of this tutorial by running:
```bash
git clone --branch 20-synonyms git@github.com:petr7555/rasa-dev-tutorial.git
```