Question

Quelles sont les meilleures méthodes pour suivre et/ou automatiser les modifications du schéma de base de données ?Notre équipe utilise Subversion pour le contrôle de version et nous avons pu automatiser certaines de nos tâches de cette façon (pousser les builds vers un serveur intermédiaire, déployer le code testé sur un serveur de production), mais nous effectuons toujours les mises à jour de la base de données manuellement.J'aimerais trouver ou créer une solution qui nous permette de travailler efficacement sur des serveurs avec différents environnements tout en continuant à utiliser Subversion comme backend à travers lequel les mises à jour du code et de la base de données sont transmises à différents serveurs.

De nombreux progiciels populaires incluent des scripts de mise à jour automatique qui détectent la version de la base de données et appliquent les modifications nécessaires.Est-ce la meilleure façon de le faire, même à plus grande échelle (sur plusieurs projets et parfois plusieurs environnements et langages) ?Si tel est le cas, existe-t-il un code existant qui simplifie le processus ou est-il préférable de simplement déployer notre propre solution ?Quelqu'un a-t-il déjà implémenté quelque chose de similaire et l'a intégré dans les hooks post-commit de Subversion, ou est-ce une mauvaise idée ?

Bien qu'une solution prenant en charge plusieurs plates-formes soit préférable, nous devons absolument prendre en charge la pile Linux/Apache/MySQL/PHP car la majorité de notre travail s'effectue sur cette plate-forme.

Était-ce utile?

La solution

Dans le monde Rails, il existe le concept de migrations, des scripts dans lesquels les modifications de la base de données sont effectuées dans Ruby plutôt qu'une version SQL spécifique à la base de données.Votre code de migration Ruby finit par être converti en DDL spécifique à votre base de données actuelle ;cela rend le changement de plate-forme de base de données très facile.

Pour chaque modification que vous apportez à la base de données, vous écrivez une nouvelle migration.Les migrations ont généralement deux méthodes :une méthode "up" dans laquelle les modifications sont appliquées et une méthode "down" dans laquelle les modifications sont annulées.Une seule commande met la base de données à jour et peut également être utilisée pour amener la base de données vers une version spécifique du schéma.Dans Rails, les migrations sont conservées dans leur propre répertoire dans le répertoire du projet et sont enregistrées dans le contrôle de version comme n'importe quel autre code de projet.

Ce guide Oracle sur les migrations Rails couvre assez bien les migrations.

Les développeurs utilisant d'autres langages ont envisagé les migrations et ont implémenté leurs propres versions spécifiques à chaque langue.je connais Ruckus, un système de migration PHP calqué sur les migrations de Rails ;c'est peut-être ce que vous recherchez.

Autres conseils

Nous utilisons quelque chose de similaire à bcwoord pour garder nos schémas de base de données synchronisés sur 5 installations différentes (production, staging et quelques installations de développement), et sauvegardés dans le contrôle de version, et cela fonctionne plutôt bien.Je vais développer un peu :


Pour synchroniser la structure de la base de données, nous disposons d'un seul script, update.php, et d'un certain nombre de fichiers numérotés 1.sql, 2.sql, 3.sql, etc.Le script utilise une table supplémentaire pour stocker le numéro de version actuelle de la base de données.Les fichiers N.sql sont construits à la main, pour passer de la version (N-1) à la version N de la base de données.

Ils peuvent être utilisés pour ajouter des tables, ajouter des colonnes, migrer des données d'un ancien vers un nouveau format de colonne, puis supprimer la colonne, insérer des lignes de données « principales » telles que les types d'utilisateurs, etc.Fondamentalement, il peut tout faire et avec des scripts de migration de données appropriés, vous ne perdrez jamais de données.

Le script de mise à jour fonctionne comme ceci :

  • Connectez-vous à la base de données.
  • Faites une sauvegarde de la base de données actuelle (car des trucs volonté se tromper) [mysqldump].
  • Créez une table de comptabilité (appelée _meta) si elle n'existe pas.
  • Lisez la VERSION actuelle à partir de la table _meta.Supposons 0 s’il n’est pas trouvé.
  • Pour tous les fichiers .sql dont le numéro est supérieur à VERSION, exécutez-les dans l'ordre
  • Si l'un des fichiers a généré une erreur :revenir à la sauvegarde
  • Sinon, mettez à jour la version dans la table de comptabilité avec le fichier .sql le plus élevé exécuté.

Tout va dans le contrôle de source, et chaque installation dispose d'un script pour mettre à jour vers la dernière version avec une seule exécution de script (en appelant update.php avec le mot de passe de base de données approprié, etc.).Nous mettons à jour les environnements de préparation et de production SVN via un script qui appelle automatiquement le script de mise à jour de la base de données, de sorte qu'une mise à jour du code est accompagnée des mises à jour de la base de données nécessaires.

Nous pouvons également utiliser le même script pour recréer l’intégralité de la base de données à partir de zéro ;nous supprimons et recréons simplement la base de données, puis exécutons le script qui repeuplera complètement la base de données.Nous pouvons également utiliser le script pour remplir une base de données vide à des fins de tests automatisés.


Il n'a fallu que quelques heures pour mettre en place ce système, il est conceptuellement simple et tout le monde obtient le schéma de numérotation des versions, et cela a été inestimable pour pouvoir avancer et faire évoluer la conception de la base de données, sans avoir à communiquer ou à exécuter manuellement les modifications. sur toutes les bases de données.

Attention cependant lorsque vous collez des requêtes depuis phpMyAdmin ! Ces requêtes générées incluent généralement le nom de la base de données, ce que vous ne voulez certainement pas car cela briserait vos scripts !Quelque chose comme CRÉER UNE TABLE mydb.newtable(...) échouera si la base de données sur le système ne s'appelle pas mydb.Nous avons créé un hook SVN pré-commentaire qui interdira les fichiers .sql contenant le mydb chaîne, ce qui est un signe certain que quelqu'un a copié/collé depuis phpMyAdmin sans vérification appropriée.

Mon équipe écrit toutes les modifications de la base de données et valide ces scripts dans SVN, avec chaque version de l'application.Cela permet des modifications incrémentielles de la base de données, sans perdre aucune donnée.

Pour passer d'une version à la suivante, il vous suffit d'exécuter l'ensemble des scripts de modification, votre base de données est à jour et vous disposez toujours de toutes vos données.Ce n’est peut-être pas la méthode la plus simple, mais elle est certainement efficace.

Le problème ici est vraiment de permettre aux développeurs de scripter facilement leurs propres modifications locales dans le contrôle de source pour les partager avec l'équipe.Je suis confronté à ce problème depuis de nombreuses années et j'ai été inspiré par les fonctionnalités de Visual Studio pour les professionnels des bases de données.Si vous souhaitez un outil open source avec les mêmes fonctionnalités, essayez ceci : http://dbsourcetools.codeplex.com/ Amusez-vous, - Nathan.

Si vous cherchez encore des solutions :nous proposons un outil appelé neXtep designer.Il s'agit d'un environnement de développement de base de données avec lequel vous pouvez mettre l'ensemble de votre base de données sous contrôle de version.Vous travaillez sur un référentiel à version contrôlée où chaque modification peut être suivie.

Lorsque vous devez publier une mise à jour, vous pouvez valider vos composants et le produit générera automatiquement le script de mise à niveau SQL à partir de la version précédente.Bien entendu, vous pouvez générer ce SQL à partir de 2 versions quelconques.

Ensuite vous avez plusieurs options :vous pouvez prendre ces scripts et les mettre dans votre SVN avec le code de votre application afin qu'il soit déployé par votre mécanisme existant.Une autre option consiste à utiliser le mécanisme de livraison de neXtep :les scripts sont exportés dans ce qu'on appelle un "package de livraison" (scripts SQL + descripteur XML), et un installateur peut comprendre ce package et le déployer sur un serveur cible tout en garantissant la cohérence structurelle, la vérification des dépendances, l'enregistrement de la version installée, etc.

Le produit est GPL et est basé sur Eclipse et fonctionne donc sous Linux, Mac et Windows.Il prend également en charge Oracle, Mysql et Postgresql pour le moment (le support de DB2 est en cours).Jetez un œil au wiki où vous trouverez des informations plus détaillées :http://www.nextep-softwares.com/wiki

Videz votre schéma dans un fichier et ajoutez-le au contrôle de code source.Ensuite, une simple comparaison vous montrera ce qui a changé.

Scott Ambler produit une grande série d'articles (et est co-auteur d'un livre) sur la refactorisation de bases de données, avec l'idée que vous devez essentiellement appliquer les principes et pratiques TDD pour maintenir votre schéma.Vous configurez une série de tests unitaires de structure et de données de départ pour la base de données.Ensuite, avant de changer quoi que ce soit, vous modifiez/écrivez des tests pour refléter ce changement.

Nous faisons cela depuis un moment maintenant et cela semble fonctionner.Nous avons écrit du code pour générer des vérifications de base du nom de colonne et du type de données dans une suite de tests unitaires.Nous pouvons réexécuter ces tests à tout moment pour vérifier que la base de données dans la caisse SVN correspond à la base de données en direct que l'application exécute réellement.

Il s'avère que les développeurs modifient parfois leur base de données sandbox et négligent de mettre à jour le fichier de schéma dans SVN.Le code dépend alors d'un changement de base de données qui n'a pas été archivé.Ce genre de bug peut être extrêmement difficile à cerner, mais la suite de tests le détectera immédiatement.C'est particulièrement intéressant si vous l'intégrez dans un plan d'intégration continue plus large.

K.Scott Allen a un ou deux articles décents sur la gestion des versions de schéma, qui utilise le concept de scripts/migrations de mise à jour incrémentielle référencé dans d'autres réponses ici ;voir http://odetocode.com/Blogs/scott/archive/2008/01/31/11710.aspx.

C'est un peu low-tech, et il existe peut-être une meilleure solution, mais vous pouvez simplement stocker votre schéma dans un script SQL qui peut être exécuté pour créer la base de données.Je pense que vous pouvez exécuter une commande pour générer ce script, mais je ne connais malheureusement pas la commande.

Ensuite, validez le script dans le contrôle de source avec le code qui fonctionne dessus.Lorsque vous devez modifier le schéma avec le code, le script peut être archivé avec le code qui nécessite le schéma modifié.Ensuite, les différences sur le script indiqueront les différences sur les modifications de schéma.

Avec ce script, vous pouvez l'intégrer à DBUnit ou à une sorte de script de construction, il semble donc qu'il pourrait s'intégrer à vos processus déjà automatisés.

Si vous utilisez C#, jetez un œil à Subsonic, un outil ORM très utile, mais qui génère également un script SQL pour recréer votre schéma et/ou vos données.Ces scripts peuvent ensuite être placés dans le contrôle de code source.

http://subsonicproject.com/

J'ai utilisé la structure de projet de base de données suivante dans Visual Studio pour plusieurs projets et cela a plutôt bien fonctionné :

Base de données

Modifier les scripts

0.PreDeploy.sql

1.SchemaChanges.sql

2.DataChanges.sql

3.Permissions.sql

Créer des scripts

Sprocs

Les fonctions

Vues

Notre système de build met ensuite à jour la base de données d'une version à la suivante en exécutant les scripts dans l'ordre suivant :

1.PreDeploy.sql

2.SchemaChanges.sql

Contenu du dossier Créer des scripts

2.DataChanges.sql

3.Permissions.sql

Chaque développeur vérifie ses modifications pour un bug/une fonctionnalité particulière en ajoutant son code à la fin de chaque fichier.Une fois qu'une version majeure est terminée et branchée dans le contrôle de source, le contenu des fichiers .sql dans le dossier Change Scripts est supprimé.

Nous utilisons une solution très simple mais efficace.

Pour les nouvelles installations, nous avons un fichier metadata.sql dans le référentiel qui contient tout le schéma de base de données, puis dans le processus de construction, nous utilisons ce fichier pour générer la base de données.

Pour les mises à jour, nous ajoutons les mises à jour dans le logiciel codé en dur.Nous le gardons codé en dur parce que nous n'aimons pas résoudre les problèmes avant qu'ils ne soient vraiment un problème, et ce genre de chose ne s'est pas avéré être un problème jusqu'à présent.

Donc dans notre logiciel nous avons quelque chose comme ceci :

RegisterUpgrade(1, 'ALTER TABLE XX ADD XY CHAR(1) NOT NULL;');

Ce code vérifiera si la base de données est en version 1 (qui est stockée dans une table créée automatiquement), si elle est obsolète, alors la commande est exécutée.

Pour mettre à jour le fichier metadata.sql dans le référentiel, nous exécutons ces mises à niveau localement, puis extrayons les métadonnées complètes de la base de données.

La seule chose qui arrive de temps en temps, c'est d'oublier de valider le fichier metadata.sql, mais ce n'est pas un problème majeur car il est facile à tester sur le processus de construction et la seule chose qui pourrait arriver est de faire une nouvelle installation avec une base de données obsolète et je l'ai mise à niveau lors de la première utilisation.

De plus, nous ne prenons pas en charge les rétrogradations, mais c'est par conception que si quelque chose tombe en panne lors d'une mise à jour, nous avons restauré la version précédente et corrigé la mise à jour avant de réessayer.

Je crée des dossiers nommés d'après les versions de build et j'y place des scripts de mise à niveau et de rétrogradation.Par exemple, vous pourriez avoir les dossiers suivants :1.0.0, 1.0.1 et 1.0.2.Chacun contient le script qui vous permet de mettre à niveau ou de rétrograder votre base de données entre les versions.

Si un client vous appelle avec un problème avec la version 1.0.1 et que vous utilisez la version 1.0.2, ramener la base de données à sa version ne posera pas de problème.

Dans votre base de données, créez une table appelée « schéma » dans laquelle vous insérez la version actuelle de la base de données.Il est alors facile d'écrire un programme capable de mettre à niveau ou de rétrograder votre base de données.

Tout comme Joey l'a dit, si vous êtes dans un monde Rails, utilisez Migrations.:)

Pour mon projet PHP actuel, nous utilisons l'idée des migrations Rails et nous avons un répertoire de migrations dans lequel nous conservons le titre des fichiers "migration_XX.sql" où XX est le numéro de la migration.Actuellement, ces fichiers sont créés manuellement au fur et à mesure des mises à jour, mais leur création pourrait être facilement modifiée.

Ensuite, nous avons un script appelé "Migration_watcher" qui, comme nous sommes en pré-alpha, s'exécute actuellement à chaque chargement de page et vérifie s'il existe un nouveau fichier migration_XX.sql où XX est plus grand que la version de migration actuelle.Si tel est le cas, il exécute tous les fichiers migration_XX.sql jusqu'au plus grand nombre sur la base de données et le tour est joué !les modifications de schéma sont automatisées.

Si vous avez besoin de pouvoir revenir en arrière, le système nécessitera de nombreux ajustements, mais c'est simple et cela a très bien fonctionné jusqu'à présent pour notre équipe assez petite.

Je recommanderais d'utiliser Ant (multiplateforme) pour le côté "script" (car il peut pratiquement communiquer avec n'importe quelle base de données via jdbc) et Subversion pour le référentiel source.Ant vous permettra de "sauvegarder" votre base de données dans des fichiers locaux avant d'apporter des modifications.1.Sauvegarder le schéma de base de données existant à déposer via ANT 2.Contrôle de version vers le référentiel de subversion via ANT 3.envoyer de nouvelles instructions SQL à la base de données via Ant

Toad pour MySQL possède une fonction appelée comparaison de schémas qui vous permet de synchroniser 2 bases de données.C'est le meilleur outil que j'ai utilisé jusqu'à présent.

Les migrations à mon humble avis ont un énorme problème :

La mise à niveau d'une version vers une autre fonctionne bien, mais effectuer une nouvelle installation d'une version donnée peut prendre une éternité si vous avez des centaines de tables et un long historique de modifications (comme nous le faisons).

L'exécution de l'historique complet des deltas depuis la ligne de base jusqu'à la version actuelle (pour des centaines de bases de données clients) peut prendre beaucoup de temps.

J'aime la façon dont Oui gère les migrations de bases de données.Une migration est essentiellement un script PHP implémentant CDbMigration. CDbMigration définit un up méthode qui contient la logique de migration.Il est également possible de mettre en œuvre un down méthode pour prendre en charge l’inversion de la migration.Alternativement, safeUp ou safeDown peut être utilisé pour s’assurer que la migration est effectuée dans le contexte d’une transaction.

L'outil de ligne de commande de Yii yiic contient un support pour créer et exécuter des migrations.Les migrations peuvent être appliquées ou annulées, une par une ou par lots.La création d'une migration génère du code pour une classe PHP implémentant CDbMigration, nommé de manière unique en fonction d'un horodatage et d'un nom de migration spécifiés par l'utilisateur.Toutes les migrations précédemment appliquées à la base de données sont stockées dans une table de migration.

Pour plus d'informations, consultez le Migration de base de données article du manuel.

Essayez db-deploy - principalement un outil Java mais qui fonctionne également avec PHP.

Il y a une ligne de commande mysql-diff outil qui compare les schémas de base de données, où le schéma peut être une base de données en direct ou un script SQL sur disque.C'est bon pour la plupart des tâches de migration de schéma.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top