# La bibliothèque rougail

Rougail est une bibliothèque simple a utiliser.

Dans les exemples suivant, nous utilisons la configuration par défaut de Rougail. Vous pouvez [personnaliser les répertoires utilisés](config.md).

## Convertisons un dictionnaire en objet tiramisu

Commençons par créer un dictionnaire simple.

Voici un premier dictionnaire /srv/rougail/dictionaries/00-base.xml :

```
<?xml version='1.0' encoding='UTF-8'?>
<rougail>
  <variables>
    <variable name="my_variable">
      <value>my_value</value>
    </variable>
  </variables>
</rougail>
```

Construisons les objets tiramisu :

```python
from rougail import RougailConvert

rougail = RougailConvert()
rougail.save('example.py')
```

Un nouveau fichier 'example.py' va être créé dans le répertoire local

## Convertisons un dictionnaire extra en objet tiramisu

En plus du dictionnaire précédent, créons un dictionnaire extra /srv/rougail/extra_dictionaries/00-base.xml

```
<?xml version='1.0' encoding='UTF-8'?>
<rougail>
  <variables>
    <variable name="my_variable_extra">
      <value>my_value_extra</value>
    </variable>
  </variables>
</rougail>
```

Construisons les objets tiramisu :

```python
from rougail import RougailConvert, RougailConfig

RougailConfig['extra_dictionaries']['example'] = ['/srv/rougail/extra_dictionaries/']

rougail = RougailConvert()
rougail.save('example.py')
```

## Templatisons un template

Nous créons un dictionnaire complémentaire pour ajouter notre template /srv/rougail/dictionaries/00-template.xml :

```
<?xml version='1.0' encoding='UTF-8'?>
<rougail>
  <services>
    <service name="example">
      <file name="/etc/example.conf"/>
    </service>
  </services>
</rougail>
```

Et un template /srv/rougail/templates/example.conf :

```
The value: %%my_variable

The extra value: %%example.my_variable_extra
```

Générons le fichier tiramisu :

```python
from rougail import RougailConvert, RougailConfig

RougailConfig['extra_dictionaries']['example'] = ['/srv/rougail/extra_dictionaries/']

rougail = RougailConvert()
rougail.save('example.py')
```

Créer les répertoires utils pour la templatisation :

```bash
mkdir /srv/rougail/destinations /srv/rougail/tmp
```

Générons le template :

```python
import asyncio
from example import option_0
from tiramisu import Config
from rougail import RougailSystemdTemplate

async def template():
    config = await Config(option_0)
    engine = RougailSystemdTemplate(config)
    await engine.instance_files()

loop = asyncio.get_event_loop()
loop.run_until_complete(template())
loop.close()
```

Le fichier /srv/rougail/destinations/etc/example.conf est maintenant créé avec le contenu attendu suivant :

```
The value: my_value

The extra value: my_value_extra
```

## Appliquons un patch au template

Il peut être intéressant de réaliser un patch à un template pour corriger un problème spécifique à notre environnement, sans attendre que le mainteneur du template n'est fait la correction.

Testons en créant le patch /srv/rougail/patches/example.conf.patch :

```
--- /srv/rougail/templates/example.conf	2021-02-13 19:41:38.677491087 +0100
+++ tmp/example.conf	2021-02-13 20:12:55.525089820 +0100
@@ -1,3 +1,5 @@
 The value: %%my_variable
 
 The extra value: %%example.my_variable_extra
+
+Add by a patch
```

Le patch est bien appliquer sur notre fichier /srv/rougail/destinations/etc/example.conf :

```
The value: my_value

The extra value: my_value_extra

Add by a patch
```

Deux choses importantes à savoir sur les patchs :

- le nom du patch est obligatoire le nom du template source + ".patch"
- la deuxième ligne doit toujours commencer par "+++ tmp/" + le nom du template source

## Créons une fonction personnalisé

Nous créons un dictionnaire complémentaire pour ajouter un calcul à la variable "my_variable" dans /srv/rougail/dictionaries/00-fill.xml :

```
<?xml version='1.0' encoding='UTF-8'?>
<rougail>
  <constraints>
    <fill name="return_no">
      <target>my_variable</target>
    </fill>
  </constraints>
</rougail>
```

Puis créons la fonction "return_no" dans /srv/rougail/functions.py :

```python
def return_no():
    return 'no'
```

Après avoir reconverti les dictionnaires et regénérer le template nous avons donc le contenu du fichier /srv/rougail/destinations/etc/example.conf :

```
The value: no

The extra value: my_value_extra

Add by a patch
```

La valeur de la variable "my_variable" est bien calculé à partir de la fonction "return_no".