65 votes

Comment puis-je tester la base de données de code avec NUnit?

Je veux écrire des tests unitaires avec NUnit qui a frappé la base de données. J'aimerais avoir la base de données dans un état cohérent pour chaque test. Je pensais que les transactions pourraient me permettre de "undo" de chaque test, j'ai donc cherché et trouvé plusieurs articles de 2004-05 sur le sujet:

Ceux-ci semblent résoudre autour de la mise en œuvre d'un attribut personnalisé pour NUnit qui construit dans la capacité de restauration DB opérations à l'issue de chaque test s'exécute.

C'est génial mais...

  1. Cette fonctionnalité existe quelque part dans NUnit nativement?
  2. A cette technique à été amélioré dans les 4 dernières années?
  3. Est-ce encore le meilleur moyen de tester la base de données de code?


Edit: c'est pas que je veux tester mon DAL en particulier, c'est plus que je veux tester des morceaux de mon code qui interagissent avec la base de données. Pour que ces tests soient "no-touch" et reproductibles, ce serait génial si je pouvais réinitialiser la base de données après chacun d'eux.

Plus loin, je tiens à vous soulager dans un projet existant qui n'a pas lieu d'examen à l'heure actuelle. Pour cette raison, je ne peux pas pratiquement script d'une base de données et des données à partir de zéro pour chaque test.

79voto

Mike Two Points 16706

NUnit a maintenant un [Restauration] attribut, mais je préfère le faire d'une autre manière. J'utilise le TransactionScope classe. Il ya un couple de façons de l'utiliser.

[Test]
public void YourTest() 
{
    using (TransactionScope scope = new TransactionScope())
    {
        // your test code here
    }
}

Puisque vous n'avez pas dire TransactionScope à la commettre annulera automatiquement. Il fonctionne même si un échec d'assertion ou une autre exception est levée.

L'autre moyen est d'utiliser le bouton [SetUp] pour créer le TransactionScope et [Permutation] pour appeler Jeter sur elle. Il supprime certains duplication de code, mais accomplit la même chose.

[TestFixture]
public class YourFixture
{
    private TransactionScope scope;

    [SetUp]
    public void SetUp()
    {
        scope = new TransactionScope();
    }

    [TearDown]
    public void TearDown()
    {
        scope.Dispose();
    }


    [Test]
    public void YourTest() 
    {
        // your test code here
    }
}

C'est aussi sûr que l'instruction d'utilisation dans un test parce que NUnit permettra de garantir que le Démontage est appelé.

Après avoir dit tout cela, je ne pense que les tests qui ont frappé la base de données ne sont pas vraiment des tests unitaires. Je reste à écrire, mais je pense à eux comme à des tests d'intégration. Je les vois encore que de fournir de la valeur. Un endroit je les utilise souvent dans les tests de LINQ to SQL code. Je n'utilise pas le concepteur. - Je écrire à la main la DTO et attributs. J'ai été connu pour avoir tort. Les tests d'intégration de l'aider à rattraper mon erreur.

3voto

nportelli Points 2350

Je suis juste allé à un .NET groupe d'utilisateur et le présentateur a dit qu'il a utilisé SQLlite de tester l'installation et le démontage et utilisés dans le mémoire en option. Il avait à fudge de la connexion un peu et explicite de détruire la connexion, mais ce serait donner une propre DB à chaque fois.

http://houseofbilz.com/archive/2008/11/14/update-for-the-activerecord-quotmockquot-framework.aspx

2voto

tvanfosson Points 268301

Je voudrais appeler ces tests d'intégration, mais peu importe. Ce que j'ai fait pour de tels tests est de ma configuration méthodes dans la classe de test effacer toutes les tables d'intérêts avant chaque test. En général, je écrire à la main le SQL de le faire alors que je ne suis pas en utilisant les classes de test.

Généralement, je m'appuie sur un ORM pour mon datalayer et donc je ne suis pas d'écrire des tests unitaires pour beaucoup il. Je ne ressens pas un besoin de l'unité de test de code que je n'écris pas. Pour le code que j'ai ajouté dans la couche, en général, je utiliser l'injection de dépendance à l'abrégé de la connexion à la base de données de sorte que lorsque je test mon code, il ne touche pas à la base de données réelle. De concert avec un moqueur cadre pour de meilleurs résultats.

0voto

Scott A. Lawrence Points 1730

Pour ce genre de tests, j'ai expérimenté avec NDbUnit (en travaillant de concert avec NUnit). Si ma mémoire est bonne, c'était un port de DbUnit à partir de la plate-forme Java. Il y avait beaucoup de nappe de commandes pour exactement le genre de chose que vous essayez de faire. Le projet semble avoir déplacé ici:

http://code.google.com/p/ndbunit/

(il sert à être au http://ndbunit.org).

La source semble être disponible via ce lien: http://ndbunit.googlecode.com/svn/trunk/

0voto

Mike Points 1113

Envisager la création d'un script de base de données de sorte que vous pouvez l'exécuter automatiquement à partir de NUnit ainsi que manuellement pour d'autres types de tests. Par exemple, si vous utilisez Oracle puis le coup d'envoi de SqlPlus de l'intérieur NUnit et exécuter les scripts. Ces scripts sont généralement plus rapides à écrire et plus facile à lire. Aussi, très important, de l'exécution de SQL à partir de Crapaud ou l'équivalent est plus éclairante que l'exécution de SQL à partir du code ou de passer par un ORM de code. En général, je vais créer à la fois une installation et le démontage de script et de les mettre dans l'installation et le démontage des méthodes.

Si vous devez passer par la DB à tous à partir de tests unitaires est un autre débat. Je crois qu'il le fait souvent du bon sens. Pour de nombreuses applications de la base de données est le centre absolu de l'action, la logique est fortement basée, et toutes les autres technologies et langages de programmation et les techniques sont de passage des fantômes. Et avec la hausse des langages fonctionnels, nous commençons à réaliser que SQL, comme JavaScript, est en fait une grande langue qui était juste là, sous notre nez toutes ces années.

Juste en aparté, Linq to SQL (que j'aime dans le concept mais n'ont jamais utilisé) presque me semble être une façon de le faire raw SQL dans le code sans l'admettre ce que nous faisons. Certaines personnes aiment SQL et je sais qu'ils aiment, d'autres l'aiment et qui ne savent pas ce qu'ils aiment. :)

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X