(Déplacement de ma réponse de l'utilisation de PostgreSQL en mémoire et généralisation) :
Vous ne pouvez pas exécuter Pg en cours, en mémoire
Je n'arrive pas à comprendre comment exécuter la base de données Postgres en mémoire pour les tests. Est-ce possible ?
Non ce n'est pas possible. PostgreSQL est implémenté en C et compilé en code de plate-forme. Contrairement à H2 ou Derby, vous ne pouvez pas simplement charger le jar
et lancez-le comme une base de données en mémoire jetable.
Contrairement à SQLite, qui est également écrit en C et compilé en code de plate-forme, PostgreSQL ne peut pas non plus être chargé in-process. Il nécessite plusieurs processus (un par connexion) car il s'agit d'une architecture multitraitement et non multithreading. L'exigence de multitraitement signifie que vous devez lancer le postmaster en tant que processus autonome.
À la place :préconfigurez une connexion
Je suggère simplement d'écrire vos tests pour s'attendre à ce qu'un nom d'hôte/nom d'utilisateur/mot de passe particulier fonctionne, et d'avoir le harnais de test CREATE DATABASE
une base de données jetable, puis DROP DATABASE
à la fin de la course. Obtenez les détails de connexion à la base de données à partir d'un fichier de propriétés, créez des propriétés cibles, une variable d'environnement, etc.
Il est sûr d'utiliser une instance PostgreSQL existante dans laquelle vous avez déjà des bases de données qui vous intéressent, tant que l'utilisateur que vous fournissez à vos tests unitaires n'est pas un superutilisateur, uniquement un utilisateur avec CREATEDB
droits. Au pire, vous créerez des problèmes de performances dans les autres bases de données. Je préfère exécuter une installation PostgreSQL complètement isolée pour les tests pour cette raison.
À la place :lancez une instance PostgreSQL jetable pour les tests
Alternativement, si vous êtes vraiment vivement que votre harnais de test localise le initdb
et postgres
binaires, exécutez initdb
pour créer une base de données, modifiez pg_hba.conf
faire trust
, exécutez postgres
pour le démarrer sur un port aléatoire, créez un utilisateur, créez une base de données et exécutez les tests. Vous pouvez même regrouper les binaires PostgreSQL pour plusieurs architectures dans un jar et décompresser ceux de l'architecture actuelle dans un répertoire temporaire avant d'exécuter les tests.
Personnellement, je pense que c'est une douleur majeure qui devrait être évitée; il est beaucoup plus facile d'avoir simplement une base de données de test configurée. Cependant, c'est devenu un peu plus facile avec l'avènement de include_dir
prise en charge dans postgresql.conf
; maintenant, vous pouvez simplement ajouter une ligne, puis écrire un fichier de configuration généré pour tout le reste.
Tests plus rapides avec PostgreSQL
Pour plus d'informations sur la façon de sécuriser améliorer les performances de PostgreSQL à des fins de test, voir une réponse détaillée que j'ai écrite sur ce sujet plus tôt :Optimiser PostgreSQL pour des tests rapides
Le dialecte PostgreSQL de H2 n'est pas un véritable substitut
Certaines personnes utilisent à la place la base de données H2 en mode dialecte PostgreSQL pour exécuter des tests. Je pense que c'est presque aussi mauvais que les gens de Rails qui utilisent SQLite pour les tests et PostgreSQL pour le déploiement en production.
H2 prend en charge certaines extensions PostgreSQL et émule le dialecte PostgreSQL. Cependant, ce n'est que cela - une émulation. Vous trouverez des zones où H2 accepte une requête mais pas PostgreSQL, où le comportement diffère, etc. écrit.
Si vous comprenez les limites de cette approche et que votre accès à la base de données est simple, H2 peut convenir. Mais dans ce cas, vous êtes probablement un meilleur candidat pour un ORM qui résume la base de données car vous n'utilisez de toute façon pas ses fonctionnalités intéressantes - et dans ce cas, vous n'avez plus à vous soucier autant de la compatibilité de la base de données.
Les tablespaces ne sont pas la solution !
Ne pas utiliser un tablespace pour créer une base de données "en mémoire". Non seulement c'est inutile car cela n'améliorera pas les performances de manière significative de toute façon, mais c'est aussi un excellent moyen de perturber l'accès à tout autre qui pourrait vous intéresser dans la même installation PostgreSQL. La documentation 9.4 contient désormais l'avertissement suivant :
AVERTISSEMENT
Même s'ils sont situés en dehors du répertoire de données principal de PostgreSQL, les tablespaces font partie intégrante du cluster de bases de données et ne peuvent pas être traités comme une collection autonome de fichiers de données. Ils dépendent des métadonnées contenues dans le répertoire de données principal et ne peuvent donc pas être attachés à un cluster de base de données différent ou sauvegardés individuellement. De même, si vous perdez un tablespace (suppression de fichier, panne de disque, etc.), le cluster de base de données peut devenir illisible ou incapable pour commencer.Placer un tablespace sur un système de fichiers temporaire comme un disque virtuel risque de compromettre la fiabilité de l'ensemble du cluster.
parce que j'ai remarqué que trop de gens faisaient ça et avaient des problèmes.
(Si vous avez fait cela, vous pouvez mkdir
le répertoire tablespace manquant pour que PostgreSQL redémarre, puis DROP
les bases de données manquantes, les tables, etc. Il vaut mieux ne pas le faire.)