# Documentation Django 5.2.8

# Configuration et utilisation de la journalisation

Voir aussi

- Référence de la journalisation dans Django

- Aperçu de la journalisation dans Django

Django contient une configuration de journalisation par défaut fonctionnelle qui peut facilement être étendue.

## Appel de journalisation basique

Pour envoyer un message de journalisation à partir de votre code, écrivez un appel de journalisation.

Ne soyez pas tenté-e-s d’utiliser des appels de journalisation dans `settings.py`.

La façon dont la journalisation de Django est configuré dans le cadre de la fonction `setup()` signifie que les appels de journalisation placés dans `settings.py` peuvent ne pas fonctionner comme prévu, car la journalisation n’est pas encore configurée à ce stade. Pour explorer la journalisation, utilisez une fonction de vue comme suggéré dans l’exemple ci-dessous.

First, import the Python logging library, and then obtain a logger instance with `logging.getLogger()`. Provide the `getLogger()` method with a name to identify it and the records it emits. A good option is to use `__name__` (see Utilisation de l’espace de noms des journaliseurs below for more on this) which will provide the name of the current Python module as a dotted path:

    import logging

    logger = logging.getLogger(__name__)

Par convention, il est bon d’effectuer cette déclaration au niveau du module.

Puis dans une fonction, par exemple dans une vue, envoyez un enregistrement au journaliseur

    def some_view(request):
        ...
        if some_risky_state:
            logger.warning("Platform is running at risk")

When this code is executed, a `LogRecord` containing that message will be sent to the logger. If you’re using Django’s default logging configuration, the message will appear in the console.

Le niveau `WARNING` utilisé dans l’exemple ci-dessus est l’un des quelques niveaux de sévérité de journalisation: DEBUG`, `INFO`, `WARNING`, `ERROR`, `CRITICAL`. Un autre exemple pourrait être

    logger.critical("Payment system is not responding")

Important

Les enregistrements ayant un niveau plus faible que `WARNING` n’apparaîtront pas dans la console par défaut. La modification de ce comportement nécessite une configuration supplémentaire.

## Personnalisation de la configuration de journalisation

Même si la configuration de journalisation de Django fonctionne telle quelle, vous pouvez contrôler exactement la manière dont vos journaux sont envoyés à diverses destinations, vers des fichiers journaux, des services externes, par courriel, etc. en ajoutant un peu de configuration supplémentaire.

Vous pouvez configurer :

- les correspondances des journaliseurs (logger) pour déterminer quels enregistrements sont envoyés à quels gestionnaires

- les gestionnaires (handler) pour déterminer ce qu’ils font des enregistrements qu’ils reçoivent

- les filtres, pour ajouter du contrôle supplémentaire sur le transfert des enregistrements, et même les modifier sur place

- les formateurs, pour convertir les objets `LogRecord` en une chaîne ou toute autre forme qui soit lisible par les humains ou un autre système

Il existe plusieurs manières de configurer la journalisation. Dans Django, le réglage `LOGGING` est le plus couramment utilisé. Ce réglage utilise le format dictConfig, et étend la configuration de journalisation par défaut.

Consultez Configuration de la journalisation pour une explication sur la manière dont vos réglages personnalisés sont fusionnés avec ceux de Django.

Consultez la `documentation de journalisation de Python` pour plus de détails sur les autres manières de configurer la journalisation. Par simplification, cette documentation ne va considérer que la configuration au travers du réglage `LOGGING`.

### Configuration de journalisation basique

Lors de la configuration de la journalisation, il est raisonnable de

#### Créer un dictionnaire `LOGGING`

Dans votre fichier `settings.py`:

    LOGGING = {
        "version": 1,  # the dictConfig format version
        "disable_existing_loggers": False,  # retain the default loggers
    }

Il est presque toujours recommandé de conserver et étendre la configuration de journalisation par défaut en définissant `disable_existing_loggers` à `False`.

#### Configurer un gestionnaire

Cet exemple configure un seul gestionnaire (handler) nommé `file`, qui utilise la classe `FileHandler` de Python pour enregistrer les journaux de niveau `DEBUG` et plus élevé dans le fichier `general.log` (à la racine du projet) :

    LOGGING = {
        # ...
        "handlers": {
            "file": {
                "class": "logging.FileHandler",
                "filename": "general.log",
            },
        },
    }

Different handler classes take different configuration options. For more information on available handler classes, see the `AdminEmailHandler` provided by Django and the various `handler classes` provided by Python.

Les niveaux de journalisation peuvent aussi être définis sur les gestionnaires (par défaut, elles acceptent des messages de tous les niveaux). En utilisant l’exemple ci-dessus, l’ajout de :

    {
        "class": "logging.FileHandler",
        "filename": "general.log",
        "level": "DEBUG",
    }

définirait une configuration de gestionnaire n’acceptant que des enregistrements de niveau `DEBUG` ou supérieur.

#### Configuration d’une correspondance de journaliseur

Pour envoyer des enregistrements à ce gestionnaire, configurez une correspondance pour l’utiliser, par exemple :

    LOGGING = {
        # ...
        "loggers": {
            "": {
                "level": "DEBUG",
                "handlers": ["file"],
            },
        },
    }

Le nom de correspondance détermine quels sont les enregistrements de journaux qu’il va traiter. Cette configuration (`''`) is anonyme. Cela signifie qu’elle traitera les enregistrements de tous les journaliseurs (voir Utilisation de l’espace de noms des journaliseurs ci-dessous sur la manière d’utiliser les noms de correspondance pour déterminer les journaliseurs concernés par le traitement de ses enregistrements).

Ceci va transmettre les messages de niveau `DEBUG` et supérieur au gestionnaire nommé `file`.

Notez qu’un journaliseur peut transmettre des messages à plusieurs gestionnaires, il existe donc une relation de type plusieurs-à-plusieurs entre les journaliseurs et les gestionnaires.

Si vous exécutez

    logger.debug("Attempting to connect to API")

dans vote code, vous trouverez ce message dans le fichier general.log` à la racine de votre projet.

#### Configuration d’un formateur

Par défaut, le résultat final de journalisation contient la partie message de chaque `enregistrement de journal`. Utilisez un formateur si vous souhaitez inclure des données supplémentaires. Commencez par nommer et définir vos formateurs. Cet exemple définit des formateurs nommés `verbose` et `simple`:

    LOGGING = {
        # ...
        "formatters": {
            "verbose": {
                "format": "{name} {levelname} {asctime} {module} {process:d} {thread:d} {message}",
                "style": "{",
            },
            "simple": {
                "format": "{levelname} {message}",
                "style": "{",
            },
        },
    }

Le mot-clé `style` permet d’indiquer `{` pour la mise en forme `str.format()` ou `$` pour `string.Template`; la valeur par défaut est `$`.

Voir LogRecord attributes au sujet des attributs de `LogRecord` qu’il est possible d’inclure.

Pour appliquer un formateur à un gestionnaire, ajoutez une entrée `formatter` au dictionnaire du gestionnaire en vous référant au formateur par son nom, par exemple :

    "handlers": {
        "file": {
            "class": "logging.FileHandler",
            "filename": "general.log",
            "formatter": "verbose",
        },
    }

#### Utilisation de l’espace de noms des journaliseurs

La configuration de journalisation anonyme `''` capture les journaux de n’importe quelle application Python. Une configuration de journalisation nommée ne capturera que les journaux de journaliseurs dont le nom correspond.

The namespace of a logger instance is defined using `getLogger()`. For example in `views.py` of `my_app`:

    logger = logging.getLogger(__name__)

va créer un journaliseur dans l’espace de noms `my_app.views`. `__name__` permet d’organiser automatiquement les messages de journalisation en fonction de leur provenance dans les applications de votre projet. Cela garantit par la même occasion que les collisions de noms seront évitées.

Une correspondance de journaliseur nommée `my_app.views` va capturer les enregistrements de ce journaliseur :

    LOGGING = {
        # ...
        "loggers": {
            "my_app.views": {...},
        },
    }

Une correspondance de journaliseur nommée `my_app` sera plus permissive, capturant les enregistrements de journaliseurs partout dans l’espace de noms `my_app` (y compris my_app.views`, `my_app.utils` et ainsi de suite) :

    LOGGING = {
        # ...
        "loggers": {
            "my_app": {...},
        },
    }

Il est aussi possible de définir les espaces de noms des journaliseurs de manière explicite

    logger = logging.getLogger("project.payment")

et de définir ensuite en fonction les correspondances de journaliseurs.

##### Utilisation des hiérarchies et de la propagation des journaliseurs

La nomenclature des journaliseurs est hiérarchique. `my_app` est le parent de `my_app.views`, qui est le parent de `my_app.views.private`. Sans autre indication, les correspondances de journaliseurs vont propager les enregistrements qu’elles traitent à leurs parents ; un enregistrement d’un journaliseur dans l’espace de noms `my_app.views.private` sera traité à la fois par les correspondances de `my_app` et de `my_app.views`.

Pour contrôler ce comportement, donnez une valeur à la clé de propagation sur les correspondances que vous définissez

    LOGGING = {
        # ...
        "loggers": {
            "my_app": {
                # ...
            },
            "my_app.views": {
                # ...
            },
            "my_app.views.private": {
                # ...
                "propagate": False,
            },
        },
    }

`propagate` vaut `True` par défaut. Dans cet exemple, les journaux de `my_app.views.private` ne seront pas traités par les parents, mais les journaux de `my_app.views` le seront.

### Configuration de journalisation réactive

La journalisation est d’autant plus utile qu’elle contient des informations riches, mais sans information inutile, et cette pesée d’intérêts dépend de ce que vous faites. Lorsque vous êtes en mode débogage, le niveau d’informations souhaité dépasse largement ce qui sera nécessaire lorsque vous passerez votre projet en production.

Vous pouvez configurer la journalisation pour qu’elle vous offre le niveau de détail nécessaire au moment où vous en avez besoin. Au lieu de modifier manuellement la configuration pour cet objectif, une meilleure façon est d’appliquer une configuration automatiquement en fonction de l’environnement.

Par exemple, vous pouvez définir une variable d’environnement `DJANGO_LOG_LEVEL` appropriée dans vos environnements de développement et de pré-production, et en faire usage dans une configuration de journaliseur de cette façon

    "level": os.getenv("DJANGO_LOG_LEVEL", "WARNING")

de cette manière, tant que l’environnement n’indique par un niveau de journalisation plus bas, cette configuration ne propagera que les enregistrements de sévérité `WARNING` et supérieure à son gestionnaire.

D’autres options de la configuration (comme les options `level` ou `formatter` des gestionnaires) peuvent également être ajustées de cette façon.