Skip to content

Base de données

Anis Safine edited this page Nov 23, 2021 · 2 revisions

✍🏽 Nomenclature

  • pour les tables et vues :
    • snake case (un_nom_de_table)
    • tout en minuscule
    • au pluriel (ex : shantytowns, users, ...)
  • pour les colonnes :
    • snake case (un_nom_de_colonne)
    • tout en minuscule
    • pour les clés primaires auto-incremented : le nom de table au singulier + _id (ex : shantytown_id, user_id, ...)
    • pour les clés étrangères : fk_ + le nom de table étrangère au singulier (ex : fk_organization dans la table users)

⚠️ Initialement, tous les noms de tables et colonnes étaient en anglais. Cette règle a depuis été remise en question du fait des difficultés à traduire fidèlement des spécificités françaises (notamment des acronymes comme SIAO, UP2A, ...). Le mot d'ordre à ce jour est donc : anglais tant que faire se peut, et français dès qu'une traduction paraît impossible ou risque de faire perdre du sens.

🏛 Structure de la base de données

La structure de la base de données est gérée par les migrations Sequelize, trouvables dans le dossier db/migrations. Chaque migration est représentée par un fichier dans laquelle on trouve deux fonctions :

  • une fonction up() qui est utilisée pour appliquer une évolution à la base de données (ajouter / supprimer une colonne, ou une table, insérer des données, etc.)
  • une fonction down() qui est utilisée pour annuler les changements faits par la fonction up() (fonction indispensable pour revenir en arrière en cas de problème, notamment après une mise en production)

Les migrations sont exécutées par ordre alphabétique et de manière séquentielle (l'une après l'autre, jamais en même temps) :

  • c'est la raison pour laquelle le nom de chaque fichier de migration est préfixé d'un nombre : cela permet de définir l'ordre d'exécution
  • si une migration échoue, Sequelize s'arrête et n'exécute pas les éventuelles migrations suivantes

Enfin, il est à noter que Sequelize enregistre dans une table spéciale (SequelizeMeta) la liste des migrations qui ont été jouées. Cela lui permet de ne pas jouer deux fois la même migration et, surtout, quelle est la précédente migration (si l'on veut faire un down()) et quelle est la suivante (si l'on veut faire un up()).

Voici les commandes les plus courantes concernant les migrations :

  • sequelize db:migrate:status : affiche la liste de tous les fichiers de migrations trouvés, et leur statut (exécuté ou non)
  • sequelize db:migrate : lance l'exécution de toutes les migrations encore en attente (exécution = exécution de la fonction up() de chacune de ces migrations)
  • sequelize db:migrate:undo : annule la dernière migration qui a été jouée (annule = exécution de la fonction down() de la migration en question)
  • sequelize db:migrate:undo:all --to nom-de-fichier-de-migration.js : annule toutes les migrations, par ordre antéchronologique, jusqu'à la migration qui s'appelle nom-de-fichier-de-migration.js (note : nom-de-fichier-de-migration.js n'est pas annulée, c'est une limite exclusive)

Quelques remarques importantes :

  • l'utilitaire sequelize se trouve dans le dossier node_modules/.bin de l'API, qui lui-même se trouve à l'intérieur du conteneur rb_api. Pour l'utiliser il faudrait donc théoriquement se connecter au conteneur avec make dev exec rb_api bash puis écrire la commande ./node_modules/.bin/sequelize db:migrate. C'est largement simplifiable de la façon suivante :
    • remplacer ./node_modules/.bin/sequelize par yarn sequelize car yarn donne un accès direct au dossier .bin
    • exécuter directement la commande yarn sans démarrer de session bash : make dev exec rb_api yarn sequelize db:migrate
  • Sequelize s'appuie sur le nom des fichiers de migration pour savoir s'ils ont déjà été joués ou non. Cela veut dire que si l'on exécute une migration puis qu'on modifie le nom du fichier, la migration sera considérée comme nouvelle et non exécutée. Deux possibilités alors, si on veut juste renommer un fichier de migration déjà exécuté :
    • l'annuler, le renommer, puis le re-éxecuter sous son nouveau nom
    • le renommer, et mettre à jour la ligne correspondante dans SequelizeMeta pour que les noms correspondent
  • à chaque changement de branche, il ne faut pas oublier d'annuler les éventuelles migrations spécifiques à la branche sur laquelle on était

📚 Données

Sur une nouvelle instance de la plateforme, la base de données est pratiquement vide : aucun utilisateur n'est référencé, ni aucun site, ni aucun dispositif. En fait, seules les données utilitaires sont insérées par les migrations : la liste des villes, départements, régions, et structures institutionnelles.

Pour insérer des données, Sequelize met à disposition des seeders. Ce sont des fichiers qui ont exactement la même structure que des migrations avec une fonction up() et une fonction down() qui ont exactement la même utilité théorique.

Il y a tout de même plusieurs différences importantes :

  • on les trouve dans le dossier db/seeders
  • les seeders ne sont pas nécessairement joués par ordre chronologique
  • les seeders servent à insérer des données exclusivement, et non pas à modifier la structure de la base de données de quelque manière que ce soit (on ne touche pas aux tables/vues/colonnes/contraintes etc.)
  • les seeders sont dispensables sur un environnement de production : les données insérées par les seeders le sont à des fins de tests

Voici les commandes les plus courantes pour gérer les seeders :

  • sequelize db:seed:all : exécuter tous les seeders
  • sequelize db:seed --seed nom-du-seeder.js : exécuter un seeder spécifique
  • sequelize db:seed:undo --seed nom-du-seeder.js : annuler un seeder spécifique

À ce jour, le seul seeder indispensable pour une nouvelle instance de dev est le seeder 000001-users.js, qui insérer l'utilisateur admin@resorption-bidonvilles.beta.gouv.fr.

Clone this wiki locally