Données initiales pour les modèles

Il est parfois utile de pré-remplir la base de données avec des données fixes au moment de la première configuration d’une application. Il existe plusieurs façons pour que Django crée automatiquement ces données : vous pouvez fournir des données initiales via des instantanés ou alors fournir des données initiales en SQL.

En général, l’utilisation d’un instantané est une méthode plus propre car elle est indépendante de la base de données ; par contre, le SQL initial est de son côté bien plus souple.

Données initiales par les instantanés

Un instantané (fixture en anglais) est un ensemble de données que Django peut importer dans une base de données. La façon la plus directe de créer un instantané si vous avez déjà les données dans votre base est d’utiliser la commande manage.py dumpdata. Sinon, vous pouvez aussi créer des instantanés manuellement ; ils peuvent être écrits sous forme de documents XML, YAML ou JSON. La documentation sur la sérialisation contient plus de détails sur chacun de ces formats de sérialisation.

Comme exemple, voici à quoi pourrait ressembler un instantané pour un simple modèle Person en JSON :

[
  {
    "model": "myapp.person",
    "pk": 1,
    "fields": {
      "first_name": "John",
      "last_name": "Lennon"
    }
  },
  {
    "model": "myapp.person",
    "pk": 2,
    "fields": {
      "first_name": "Paul",
      "last_name": "McCartney"
    }
  }
]

Et voici le même instantané en YAML :

- model: myapp.person
  pk: 1
  fields:
    first_name: John
    last_name: Lennon
- model: myapp.person
  pk: 2
  fields:
    first_name: Paul
    last_name: McCartney

Ces données doivent se trouver dans un répertoire fixtures à l’intérieur de votre application.

Le chargement des données est simple : il suffit d’appeler manage.py loaddata <nom_instantané>, où <nom_instantané> est le nom du fichier instantané que vous avez créé. Lors de chaque lancement de loaddata, les données de l’instantané sont lues et rechargées dans la base de données. Notez que cela signifie que si vous modifiez l’un des objets créés par l’instantané et que vous relancez loaddata, vous écraserez toute modification effectuée en base de données.

Chargement automatique des instantanés de données initiales

Si vous créez un instantané nommé initial_data.[xml/yaml/json], celui-ci sera chargé à chaque lancement de syncdb. C’est très pratique, mais il faut rester prudent : rappelez-vous que les données seront réinstallées à chaque fois que vous lancez syncdb. N’utilisez donc pas initial_data pour des données que vous souhaitez modifier en base de données.

Emplacements de recherche des instantanés

Par défaut, Django recherche des instantanés dans un répertoire fixtures pour chaque application. Vous pouvez définir le réglage FIXTURE_DIRS à une liste de répertoires supplémentaires dans lesquels Django doit chercher.

Quand vous lancez manage.py loaddata, vous pouvez aussi indiquer un chemin absolu vers un fichier instantané, ce qui remplace la recherche dans les répertoires habituels.

Voir aussi

Les instantanés sont aussi employés par l’infrastructure de test pour aider à la préparation d’environnements de tests cohérents.

Données initiales en SQL

Django propose un mécanisme pour transmettre à la base de données du code SQL arbitraire qui sera exécuté juste après les commandes CREATE TABLE durant le lancement de syncdb. Ce mécanisme peut être exploité pour remplir des enregistrements par défaut, ou pour créer des fonctions SQL, des vues, des déclencheurs (triggers), etc.

Le mécanisme est simple : Django cherche un fichier nommé sql/<nom_modèle>.sql dans votre répertoire d’application, où <nom_modèle> est le nom du modèle concerné en minuscules.

Par exemple, pour un modèle Person dans une application nommée myapp, vous pourriez ajouter du code SQL dans le fichier sql/person.sql dans le répertoire myapp. Voici un exemple de ce que ce fichier pourrait contenir :

INSERT INTO myapp_person (first_name, last_name) VALUES ('John', 'Lennon');
INSERT INTO myapp_person (first_name, last_name) VALUES ('Paul', 'McCartney');

Chaque fichier SQL, si présent, doit contenir des commandes SQL valables qui vont insérer les données souhaitées (par ex. des commandes INSERT correctement formées séparées par des points-virgules).

Les fichiers SQL sont lus par les commandes sqlcustom et sqlall de manage.py. Référez-vous à la documentation de manage.py pour plus d’informations.

Notez que si vous avec plusieurs fichiers de données SQL, vous n’avez aucune garantie au sujet de l’ordre dans lequel ils seront exécutés. La seule chose dont vous pouvez être sûr est qu’au moment où ces fichiers sont exécutés, toutes les tables de bases de données auront déjà été créées.

Données SQL initiales et tests

Cette technique ne peut pas être utilisée pour fournir des données initiales dans le contexte des tests. L’infrastructure de test de Django réinitialise le contenu de la base de données de test après chaque test ; en conséquence, toute donnée insérée à l’aide du mécanisme de code SQL sera effacée.

Si vous avez besoin de données pour un cas de test, vous devez les ajouter en utilisant soit un instantané de test, soit de manière programmée dans la méthode setUp() de votre cas de test.

Données SQL spécifiques à un moteur de base de données

Il existe aussi un mécanisme pour des données SQL spécifiques à une base de données. Par exemple, vous pouvez avoir des fichiers de données initiales différents pour PostgreSQL et SQLite. Pour chaque application, Django cherche un fichier nommé <nom_app>/sql/<nom_modèle>.<moteur>.sql, où <nom_app> est le répertoire de l’application, <nom_modèle> est le nom du modèle en minuscules et <moteur> est la dernière partie du nom de module indiqué dans le réglage ENGINE du fichier settings (si vous avez défini une base de données en mettant la valeur django.db.backends.sqlite3 dans ENGINE, Django cherchera <nom_app>/sql/<nom_modèle>.sqlite3.sql).

Les données SQL spécifiques au moteur de base de données sont exécutées avant les données SQL non spécifiques. Par exemple, si votre application contient les fichiers sql/person.sql et sql/person.sqlite3.sql et que vous installez l’application sur SQLite, Django exécute d’abord le contenu de sql/person.sqlite3.sql, puis de sql/person.sql.