---
title: "Expressions de requête"
version: 1.9
locale: fr
source: https://docs.djangoproject.com/fr/1.9/ref/models/expressions/
canonical: https://djangodocs.dev/fr/1.9/ref/models/expressions/
---
# Expressions de requête

Les expressions de requête décrivent une valeur ou un calcul pouvant faire partie d’une mise à jour, d’une création, d’un filtre, d’un tri, d’une annotation ou d’une agrégation. Il existe un certain nombre d’expressions intégrées (documentées ci-dessous) pouvant aider à construire des requêtes. Les expressions peuvent être combinées, ou même imbriquées dans certains cas, afin de former des calculs plus complexes.

> **Changed in Django 1.9**
>
> La prise en charge des expressions au moment de la création de nouvelles instances de modèles a été ajoutée.

## Arithmétique prise en charge

Django prend en charge l’addition, la soustraction, la multiplication, la division, l’arithmétique modulo ainsi que l’opérateur de puissance pour les expressions de requête, à l’aide de constantes Python, de variables et même d’autres expressions.

## Quelques exemples

> **Changed in Django 1.8**
>
> Certains de ces exemples se basent sur des fonctionnalités nouvelles dans Django 1.8.

```python
from django.db.models import F, Count, Value
from django.db.models.functions import Length, Upper

# Find companies that have more employees than chairs.
Company.objects.filter(num_employees__gt=F('num_chairs'))

# Find companies that have at least twice as many employees
# as chairs. Both the querysets below are equivalent.
Company.objects.filter(num_employees__gt=F('num_chairs') * 2)
Company.objects.filter(
    num_employees__gt=F('num_chairs') + F('num_chairs'))

# How many chairs are needed for each company to seat all employees?
>>> company = Company.objects.filter(
...    num_employees__gt=F('num_chairs')).annotate(
...    chairs_needed=F('num_employees') - F('num_chairs')).first()
>>> company.num_employees
120
>>> company.num_chairs
50
>>> company.chairs_needed
70

# Create a new company using expressions.
>>> company = Company.objects.create(name='Google', ticker=Upper(Value('goog')))
# Be sure to refresh it if you need to access the field.
>>> company.refresh_from_db()
>>> company.ticker
'GOOG'

# Annotate models with an aggregated value. Both forms
# below are equivalent.
Company.objects.annotate(num_products=Count('products'))
Company.objects.annotate(num_products=Count(F('products')))

# Aggregates can contain complex computations also
Company.objects.annotate(num_offerings=Count(F('products') + F('services')))

# Expressions can also be used in order_by()
Company.objects.order_by(Length('name').asc())
Company.objects.order_by(Length('name').desc())
```

## Expressions intégrées

> **Note**
>
> Ces expressions sont définies dans `django.db.models.expressions` et `django.db.models.aggregates`, mais par commodité elles sont disponibles et habituellement importées à partir de [`django.db.models`](/fr/1.9/topics/db/models/#module-django.db.models).

### Expressions `F()`

#### `class F`

Un objet `F()` représente la valeur d’un champ de modèle ou d’une colonne annotée. Il permet de se référer à des valeurs de champs de modèles et d’effectuer avec elles des opérations en base de données sans avoir à les récupérer préalablement de la base de données vers la mémoire Python.

Instead, Django uses the `F()` object to generate an SQL expression that
describes the required operation at the database level.

Il est plus simple de faire comprendre cela par un exemple. Normalement, on peut faire quelque chose comme ceci :

```
# Tintin filed a news story!
reporter = Reporters.objects.get(name='Tintin')
reporter.stories_filed += 1
reporter.save()
```

Ici, nous avons obtenu en mémoire la valeur de `reporter.stories_filed` à partir de la base de données et nous l’avons manipulée avec des opérateurs Python familiers. Nous avons ensuite enregistré l’objet modifié en base de données. Cependant, nous aurions tout aussi bien pu écrire :

```
from django.db.models import F

reporter = Reporters.objects.get(name='Tintin')
reporter.stories_filed = F('stories_filed') + 1
reporter.save()
```

Même si `reporter.stories_filed = F('stories_filed') + 1` apparaît comme une attribution normale de valeur à un attribut d’instance en Python, il s’agit en réalité d’une construction SQL décrivant une opération en base de données.

Lorsque Django rencontre une instance de `F()`, il surcharge les opérateurs Python standards pour créer une expression SQL encapsulée ; dans ce cas, une instruction qui demande à la base de données d’incrémenter le champ de base de données représenté par `reporter.stories_filed`.

Quelle que soit la valeur que contenait `reporter.stories_filed`, Python n’a jamais besoin de la connaître, car tout se passe en base de données. Tout ce que Python fait à travers la classe `F()` de Django est de créer la syntaxe SQL pour se référer au champ et décrire l’opération.

> **Note**
>
> Afin de pouvoir accéder à la nouvelle valeur qui a été enregistrée de cette manière, l’objet a besoin d’être rechargé :
>
> ```
> reporter = Reporters.objects.get(pk=reporter.pk)
> # Or, more succinctly:
> reporter.refresh_from_db()
> ```

En plus d’être utilisée dans les opérations sur des instances uniques comme ci-dessus, `F()` peut être utilisée sur des jeux `QuerySets` d’instances d’objets, avec `update()`. Cela permet de réduire les deux requêtes utilisées ci-dessus, `get()` et [`save()`](/fr/1.9/ref/models/instances/#django.db.models.Model.save), à une seule :

```
reporter = Reporters.objects.filter(name='Tintin')
reporter.update(stories_filed=F('stories_filed') + 1)
```

Nous pouvons aussi utiliser [`update()`](/fr/1.9/ref/models/querysets/#django.db.models.query.QuerySet.update) pour incrémenter la valeur du champ sur plusieurs objets, ce qui peut être beaucoup plus rapide que de récupérer toutes les valeurs en Python depuis la base de données, de les passer en boucle en incrémentant la valeur des champs pour chacun, et de les réenregistrer individuellement dans la base de données :

```
Reporter.objects.all().update(stories_filed=F('stories_filed') + 1)
```

`F()` peut donc offrir des avantages de performance en :

- faisant travailler la base de données plutôt que le code Python ;
- réduisant le nombre de requêtes de certaines opérations.

#### Prévention des conflits de concurrence avec `F()`

Un autre bénéfice notable de `F()` est que de faire mettre à jour la valeur d’un champ par la base de données plutôt qu’en Python évite un *conflit de concurrence*.

Si deux fils d’exécution Python exécutent le code du premier exemple ci-dessus, un des fils pourrait obtenir, incrémenter et enregistrer une valeur de champ après que l’autre fil l’ait obtenu de la base de données. La valeur enregistrée par le second fil d’exécution sera basé sur la valeur d’origine ; le travail du premier fil d’exécution sera tout simplement perdu.

Si c’est la base de données qui est responsable de la mise à jour du champ, le processus est plus robuste : la valeur du champ sera toujours mise à jour en fonction de sa valeur en base de données au moment même de l’appel à [`save()`](/fr/1.9/ref/models/instances/#django.db.models.Model.save) ou `update()`, et non pas en fonction de la valeur obtenue au moment de la création de l’instance de modèle.

#### `F()` assignments persist after `Model.save()`

`F()` objects assigned to model fields persist after saving the model
instance and will be applied on each [`save()`](/fr/1.9/ref/models/instances/#django.db.models.Model.save). For example:

```
reporter = Reporters.objects.get(name='Tintin')
reporter.stories_filed = F('stories_filed') + 1
reporter.save()

reporter.name = 'Tintin Jr.'
reporter.save()
```

`stories_filed` will be updated twice in this case. If it’s initially `1`,
the final value will be `3`.

#### Utilisation de `F()` dans les filtres

`F()` est aussi très utile dans les filtres `QuerySet`, là où il est possible de filtrer un jeu d’objets en fonction de critères basés sur les valeurs des champs, plutôt que sur des valeurs Python.

Cette utilisation est documentée dans [Expressions F() dans les requêtes](/fr/1.9/topics/db/queries/#using-f-expressions-in-filters).

#### Utilisation de `F()` avec les annotations

`F()` peut être utilisée pour créer des champs dynamiques pour les modèles en combinant plusieurs champs de manière arithmétique :

```
company = Company.objects.annotate(
    chairs_needed=F('num_employees') - F('num_chairs'))
```

Si les champs que vous combinez sont de types différents, il est nécessaire d’indiquer à Django le type de champ qui en résultera. Comme `F()` ne prend pas directement en charge `output_field`, il faut envelopper l’expression dans [`ExpressionWrapper`](#django.db.models.ExpressionWrapper):

```
from django.db.models import DateTimeField, ExpressionWrapper, F

Ticket.objects.annotate(
    expires=ExpressionWrapper(
        F('active_at') + F('duration'), output_field=DateTimeField()))
```

### Expressions `Func()`

> **New in Django 1.8**

Les expressions `Func()` sont le type de base de toutes les expressions qui impliquent des fonctions de base de données telles que `COALESCE` et `LOWER`, ou des agrégations comme `SUM`. Elles peuvent être utilisées directement :

```
from django.db.models import Func, F

queryset.annotate(field_lower=Func(F('field'), function='LOWER'))
```

ou elles peuvent être utilisées pour bâtir une bibliothèque de fonctions de base de données :

```
class Lower(Func):
    function = 'LOWER'

queryset.annotate(field_lower=Lower('field'))
```

Mais dans les deux cas, chaque modèle du jeu de requête résultant sera annoté avec un attribut supplémentaire `field_lower` dont le contenu correspondra plus ou moins au code SQL suivant :

```
SELECT
    ...
    LOWER("db_table"."field") as "field_lower"
```

Voir [Fonctions de base de données](/fr/1.9/ref/models/database-functions/) pour une liste de fonctions de base de données intégrées.

L’API `Func` se présente comme suit :

#### `class Func(*expressions, **extra)`

#### `function`

Un attribut de classe décrivant la fonction qui sera générée. Plus précisément, `function` sera inséré par le substituant `function` à l’intérieur de [`template`](#django.db.models.Func.template). Sa valeur par défaut est `None`.

#### `template`

Un attribut de classe, sous forme de chaîne de format, qui décrit le code SQL généré pour cette fonction. Sa valeur par défaut est `'%(function)s(%(expressions)s)'`.

#### `arg_joiner`

Un attribut de classe qui précise la séquence de caractères utilisée pour joindre les éléments de la liste d”`expressions`. Sa valeur par défaut est `', '`.

Le paramètre `*expressions` est une liste d’expressions positionnelles auxquelles la fonction s’applique. Les expressions sont converties en chaînes, jointes par `arg_joiner`, puis insérées dans `template` par le substituant `expressions`.

Les paramètres positionnels peuvent être des expressions ou des valeurs Python. Les chaînes sont censées être des références de colonnes et seront enveloppées dans des expressions `F()` alors que les autres valeurs sont enveloppées dans des expressions `Value()`.

Les paramètres nommés `**extra` sont des paires `clé=valeur` qui peuvent être insérées dans l’attribut `template`. Notez que les mots-clés `function` et `template` peuvent être utilisés pour remplacer respectivement les attributs `function` et `template`, sans avoir besoin de définir une classe spécifique. `output_field` peut être utilisé pour définir le type de la valeur renvoyée.

### Expressions `Aggregate()`

Une expression d’agrégation est un cas particulier d’une [expression Func()](#func-expressions) qui informe la requête qu’une clause `GROUP BY` est nécessaire. Toutes les [fonctions d’agrégation](/fr/1.9/ref/models/querysets/#aggregation-functions) comme `Sum()` et `Count()` héritent de `Aggregate()`.

Comme les `Aggregate` sont des des expressions et enveloppent des expressions, il est possible de représenter des calculs complexes :

```
from django.db.models import Count

Company.objects.annotate(
    managers_required=(Count('num_employees') / 4) + Count('num_managers'))
```

L’API `Aggregate` se présente comme suit :

#### `class Aggregate(expression, output_field=None, **extra)`

#### `template`

Un attribut de classe, sous forme de chaîne de format, qui décrit le code SQL généré pour cette agrégation. Sa valeur par défaut est `'%(function)s(%(expressions)s)'`.

#### `function`

Un attribut de classe décrivant la fonction d’agrégation qui sera générée. Plus précisément, `function` sera inséré par le substituant `function` à l’intérieur de [`template`](#django.db.models.Aggregate.template). Sa valeur par défaut est `None`.

Le paramètre `expression` peut être le nom d’un champ de modèle ou une autre expression. Il sera converti en texte et utilisé comme substituant `expressions` à l’intérieur de `template`.

Le paramètre `output_field` doit être une instance de champ de modèle, comme `IntegerField()` ou `BooleanField()`, dans laquelle Django chargera la valeur après qu’elle aura été reçue de la base de données. Aucun paramètre n’est habituellement nécessaire lors de la création de l’instance du champ de modèle car aucun paramètre lié à la validation de données (`max_length`, `max_digits`, etc.) ne sera appliqué à la valeur résultante de l’expression.

Notez que `output_field` n’est obligatoire que lorsque Django est incapable de déterminer le type de champ du résultat. Les expressions complexes qui mélangent des types de champs doivent définir avec `output_field` le type de résultat attendu. Par exemple, l’addition d’un `IntegerField()` et d’un `FloatField()` va probablement demander la définition de `output_field=FloatField()`.

> **Changed in Django 1.8**
>
> `output_field` est un nouveau paramètre.

Les paramètres nommés `**extra` sont des paires `clé=valeur` qui peuvent être insérées par interpolation dans l’attribut `template`.

> **New in Django 1.8**
>
> Les fonctions d’agrégation sont dorénavant capables de contenir de l’arithmétique et de référencer plusieurs champs de modèle dans une seule fonction.

### Création de ses propres fonctions d’agrégation

La création de ses propres agrégations est très facile. Il faut définir au minimum `function`, mais vous pouvez aussi personnaliser complètement le code SQL produit. Voici un court exemple :

```
from django.db.models import Aggregate

class Count(Aggregate):
    # supports COUNT(distinct field)
    function = 'COUNT'
    template = '%(function)s(%(distinct)s%(expressions)s)'

    def __init__(self, expression, distinct=False, **extra):
        super(Count, self).__init__(
            expression,
            distinct='DISTINCT ' if distinct else '',
            output_field=IntegerField(),
            **extra
        )
```

### Expressions `Value()`

#### `class Value(value, output_field=None)`

Un objet `Value()` représente le composant le plus petit possible d’une expression : une simple valeur. Lorsque vous avez besoin de représenter la valeur d’un nombre entier, d’un booléen ou d’une chaîne à l’intérieur d’une expression, vous pouvez insérer cette valeur dans un objet `Value()`.

Il est rarement nécessaire de faire appel directement à `Value()`. Lorsque vous écrivez l’expression `F('champ') + 1`, Django insère implicitement le `1` dans un objet `Value()`, ce qui permet d’utiliser des valeurs simples dans des expressions plus complexes. `Value()` devra être utilisé lors du passage d’une chaîne à une expression. La plupart des expressions interprètent un paramètre textuel comme le nom d’un champ, comme par exemple `Lower('name')`.

Le paramètre `value` décrit la valeur à inclure dans l’expression, comme `1`, `True` ou `None`. Django sait comment convertir ces valeurs Python dans le bon type de la base de données correspondante.

Le paramètre `output_field` doit être une instance de champ de modèle, comme `IntegerField()` ou `BooleanField()`, dans laquelle Django chargera la valeur après qu’elle aura été reçue de la base de données. Aucun paramètre n’est habituellement nécessaire lors de la création de l’instance du champ de modèle car aucun paramètre lié à la validation de données (`max_length`, `max_digits`, etc.) ne sera appliqué à la valeur résultante de l’expression.

### Expressions `ExpressionWrapper()`

#### `class ExpressionWrapper(expression, output_field)`

> **New in Django 1.8**

`ExpressionWrapper` ne fait qu’entourer une autre expression et permet d’accéder aux propriétés, telles que `output_field`, qui pourraient ne pas être disponibles dans d’autres expressions. `ExpressionWrapper` est nécessaire lorsqu’on utilise de l’arithmétique avec les expressions `F()` avec différents types, comme décrit dans [Utilisation de F() avec les annotations](#using-f-with-annotations).

### Expressions conditionnelles

> **New in Django 1.8**

Les expressions conditionnelles permettent d’utiliser de la logique [`if`](https://docs.python.org/3/reference/compound_stmts.html#if) … [`elif`](https://docs.python.org/3/reference/compound_stmts.html#elif) … [`else`](https://docs.python.org/3/reference/compound_stmts.html#else) dans les requêtes. Django prend nativement en charge les expressions SQL `CASE`. Pour plus de détails, consultez [Expressions conditionnelles](/fr/1.9/ref/models/conditional-expressions/).

### Expressions SQL brutes

> **New in Django 1.8**

#### `class RawSQL(sql, params, output_field=None)`

Parfois, les expressions de base de données ne peuvent pas facilement exprimer une clause `WHERE` complexe. Dans ces cas limites, utilisez l’expression `RawSQL`. Par exemple :

```
>>> from django.db.models.expressions import RawSQL
>>> queryset.annotate(val=RawSQL("select col from sometable where othercol = %s", (someparam,)))
```

Ces expressions brutes ne sont pas toujours portables entre moteurs de base de données (parce que vous écrivez du code SQL explicitement) et elles violent le principe DRY (ne pas se répéter), il s’agit donc de les éviter autant que possible.

> **Warning**
>
> You should be very careful to escape any parameters that the user can
> control by using `params` in order to protect against [SQL injection
> attacks](/fr/1.9/topics/security/#sql-injection-protection). `params` is a required argument to
> force you to acknowledge that you’re not interpolating your SQL with user
> provided data.

## Informations techniques

Vous trouverez ci-après des détails d’implémentation technique pouvant être utiles aux auteurs de bibliothèques. L’API technique et les exemples qui suivent aident à créer des expressions de requête génériques pouvant étendre les fonctionnalités intégrées que Django propose.

### API d’expression

Les expressions de requête implémentent l”[API d’expressions de requête](/fr/1.9/ref/models/lookups/#query-expression), mais exposent également un certain nombre de méthodes et d’attributs supplémentaires énumérés ci-dessous. Toutes les expressions de requête doivent hériter de `Expression()` ou d’une sous-classe appropriée.

Lorsqu’une expression de requête englobe une autre expression, elle est responsable d’appeler les méthodes appropriées de l’expression englobée.

#### `class Expression`

#### `contains_aggregate`

Indique à Django que cette expression contient une agrégation et qu’une clause `GROUP BY` doit être ajoutée à la requête.

#### `resolve_expression(query=None, allow_joins=True, reuse=None, summarize=False, for_save=False)`

Offre l’opportunité d’effectuer un éventuel pré-traitement ou validation de l’expression avant que celle-ci ne soit ajoutée à la requête. `resolve_expression()` doit aussi être appelée pour toute expression imbriquée. Une copie `copy()` de `self` devrait être renvoyée avec les éventuelles transformations nécessaires.

`query` est l’implémentation de la requête en fonction du moteur de base de données.

`allow_joins` est une valeur booléenne permettant ou interdisant l’utilisation de jointures dans la requête.

`reuse` est un ensemble de jointures réutilisables dans des scénarios de jointures multiples.

`summarize` est une valeur booléenne qui, quand elle vaut `True`, signale que la requête en cours de calcul est une requête d’agrégation terminale.

#### `get_source_expressions()`

Renvoie une liste triée d’expressions internes. Par exemple :

```
>>> Sum(F('foo')).get_source_expressions()
[F('foo')]
```

#### `set_source_expressions(expressions)`

Accepte une liste d’expressions et les stocke afin que `get_source_expressions()` puisse les restituer.

#### `relabeled_clone(change_map)`

Renvoie un clone (copie) de `self`, sachant que tout alias de colonne aura été renommé. Les alias de colonnes sont renommés lorsque des sous-requêtes sont créées. `relabeled_clone()` doit également être appelée pour toute expression imbriquée et attribuée au clone.

`change_map` est un dictionnaire faisant correspondre les anciens alias aux nouveaux.

Exemple :

```
def relabeled_clone(self, change_map):
    clone = copy.copy(self)
    clone.expression = self.expression.relabeled_clone(change_map)
    return clone
```

#### `convert_value(self, value, expression, connection, context)`

Un point d’entrée permettant à l’expression de forcer `value` à un type plus approprié.

#### `refs_aggregate(existing_aggregates)`

Renvoie un tuple contenant les valeurs `(agrégation, chemin_recherche)` de la première agrégation que cette expression (ou d’éventuelles expressions imbriquées) référence, ou `(False, ())` si aucune agrégation n’est référencée. Par exemple :

```
queryset.filter(num_chairs__gt=F('sum__employees'))
```

L’expression `F()` référence ici un calcul `Sum()` précédent, ce qui signifie que cette expression de filtre doit être ajoutée à la clause `HAVING` plutôt qu’à la clause `WHERE`.

Dans la majorité des cas, le renvoi du résultat de `refs_aggregate` de n’importe quelle expression imbriquée devrait être approprié, car les expressions intégrées nécessaires vont renvoyer les valeurs correctes.

#### `get_group_by_cols()`

Responsable du renvoi de la liste des colonnes référencées par cette expression. `get_group_by_cols()` doit être appelée sur toute expression imbriquée. Les objets `F()` en particulier détiennent une référence sur une colonne.

#### `asc()`

Renvoie l’expression prête à être triée dans l’ordre croissant.

#### `desc()`

Renvoie l’expression prête à être triée dans l’ordre décroissant.

#### `reverse_ordering()`

Renvoie `self` avec toute modification nécessaire pour inverser l’ordre de tri à l’intérieur d’un appel `order_by`. Comme exemple, une expression implémentant `NULLS LAST` changerait sa valeur pour devenir `NULLS FIRST`. Les modifications sont uniquement requises pour les expressions qui implémentent l’ordre de tri telles que `OrderBy`. Cette méthode est appelée lorsque [`reverse()`](/fr/1.9/ref/models/querysets/#django.db.models.query.QuerySet.reverse) est appelée sur un jeu de requête (`QuerySet`).

### Écriture de ses propres expressions de requête

Vous pouvez écrire vos propres classes d’expression de requête qui utilisent et peuvent s’intégrer avec d’autres expressions de requête. Prenons un exemple en écrivant une implémentation de la fonction SQL `COALESCE`, sans utiliser les [expressions Func()](#func-expressions) intégrées.

La fonction SQL `COALESCE` est définie comme acceptant une liste de colonnes ou de valeurs. Elle renvoie la première colonne ou valeur qui n’est pas `NULL`.

Commençons par définir le gabarit à utiliser pour la génération du SQL ainsi qu’une méthode `__init__()` pour définir quelques attributs :

```
import copy
from django.db.models import Expression

class Coalesce(Expression):
    template = 'COALESCE( %(expressions)s )'

    def __init__(self, expressions, output_field, **extra):
      super(Coalesce, self).__init__(output_field=output_field)
      if len(expressions) < 2:
          raise ValueError('expressions must have at least 2 elements')
      for expression in expressions:
          if not hasattr(expression, 'resolve_expression'):
              raise TypeError('%r is not an Expression' % expression)
      self.expressions = expressions
      self.extra = extra
```

Nous effectuons quelques validations de base sur les paramètres, y compris le minimum de 2 colonnes ou valeurs, et nous nous assurons qu’il s’agisse bien d’expressions. `output_field` est ici obligatoire afin que Django sache à quel type de champ de modèle attribuer l’éventuel résultat.

Nous implémentons maintenant le prétraitement et la validation. Comme nous n’avons aucune validation propre à ce stade, nous ne faisons que la déléguer aux expressions imbriquées :

```
def resolve_expression(self, query=None, allow_joins=True, reuse=None, summarize=False, for_save=False):
    c = self.copy()
    c.is_summary = summarize
    for pos, expression in enumerate(self.expressions):
        c.expressions[pos] = expression.resolve_expression(query, allow_joins, reuse, summarize, for_save)
    return c
```

Ensuite, nous écrivons la méthode responsable de la génération du code SQL :

```
def as_sql(self, compiler, connection):
    sql_expressions, sql_params = [], []
    for expression in self.expressions:
        sql, params = compiler.compile(expression)
        sql_expressions.append(sql)
        sql_params.extend(params)
    self.extra['expressions'] = ','.join(sql_expressions)
    return self.template % self.extra, sql_params

def as_oracle(self, compiler, connection):
    """
    Example of vendor specific handling (Oracle in this case).
    Let's make the function name lowercase.
    """
    self.template = 'coalesce( %(expressions)s )'
    return self.as_sql(compiler, connection)
```

Nous générons le code SQL pour chacune des `expressions` en utilisant la méthode `compiler.compile()` et en combinant les résultats avec des virgules. Puis le gabarit est complété avec nos données et le code SQL est renvoyé avec ses paramètres.

Nous avons également défini une implémentation personnalisée spécifique au moteur Oracle. La fonction `as_oracle()` sera appelée à la place de `as_sql()` quand le moteur Oracle est en fonction.

Finalement, nous implémentons les autres méthodes qui permettent à notre expression de requête de collaborer harmonieusement avec d’autres expressions de requête :

```
def get_source_expressions(self):
    return self.expressions

def set_source_expressions(self, expressions):
    self.expressions = expressions
```

Voyons comment cela fonctionne :

```
>>> from django.db.models import F, Value, CharField
>>> qs = Company.objects.annotate(
...    tagline=Coalesce([
...        F('motto'),
...        F('ticker_name'),
...        F('description'),
...        Value('No Tagline')
...        ], output_field=CharField()))
>>> for c in qs:
...     print("%s: %s" % (c.name, c.tagline))
...
Google: Do No Evil
Apple: AAPL
Yahoo: Internet Company
Django Software Foundation: No Tagline
```

### Ajout de la prise en charge de moteurs de base de données externes

Si vous utilisez un moteur de base de données qui utilise une syntaxe SQL différente pour certaines fonctions, vous pouvez ajouter sa prise en charge en greffant une nouvelle méthode dans la classe de la fonction.

Admettons que nous écrivons un moteur pour SQL Server de Microsoft qui utilise l’instruction SQL `LEN` au lieu de `LENGTH` pour la fonction [`Length`](/fr/1.9/ref/models/database-functions/#django.db.models.functions.Length). Nous allons greffer une nouvelle méthode appelée `as_sqlserver()` dans la classe `Length`:

```
from django.db.models.functions import Length

def sqlserver_length(self, compiler, connection):
    return self.as_sql(compiler, connection, function='LEN')

Length.as_sqlserver = sqlserver_length
```

Il est aussi possible de personnaliser le code SQL en utilisant le paramètre `template` de `as_sql()`.

Nous utilisons `as_sqlserver()` parce que `django.db.connection.vendor` renvoie `sqlserver` comme moteur.

Les moteurs tiers peuvent inscrire leurs fonctions dans le fichier `__init__.py` de premier niveau du paquet de moteur ou dans un fichier (ou paquet) `expressions.py` de premier niveauqui est lui-même importé depuis `__init__.py`.

Pour les projets d’utilisateurs qui souhaitent adapter le moteur qu’ils utilisent, ce code devrait se trouver dans une méthode [`AppConfig.ready()`](/fr/1.9/ref/applications/#django.apps.AppConfig.ready).
