2009-10-26 13 views
16

Voglio Unit Test della mia applicazione che utilizza MSMQ ma non ho trovato alcun modo per Mock MessageQueue oggetti.How-To Mock MSMQ MessageQueue

 var queuePath = @".\Private$\MyQueue"; 
     MessageQueue queue = null; 
     if (MessageQueue.Exists(queuePath)) 
     { 
      queue = new MessageQueue(queuePath); 
     } 
     else 
     { 
      queue = MessageQueue.Create(queuePath); 
     } 

Sto usando Moq con xUnit.

risposta

29

Quindi il problema di base qui è che si ha una forte dipendenza dall'oggetto MessageQueue. Generalmente quando ho una situazione come questa, creerò un'interfaccia, come IQueue e quindi creerò un'implementazione di IQueue per MessageQueue.

Quindi è possibile iniettare la dipendenza IQueue con Moq e verificare che la classe funzioni come previsto.

Qualcosa di simile a questo:

public interface IQueue 
{ 
    bool Exists(string path); 
    MessageQueue Create(string path); 
} 

L'implementazione sarebbe qualcosa di simile:

public MessageQueueImplementation : IQueue 
{ 
    public bool Exists(string path) 
    { 
     return MessageQueue.Exists(path); 
    } 

    public MessageQueue Create(string path) 
    { 
     return MessageQueue.Create(path); 
    } 
} 

Poi per la classe che dipende dal qualcosa MessageQueue come questo:

public class DependentOnQueue 
{ 
    private IQueue queue; 
    //inject dependency 
    public DependentOnQueue(IQueue queue) 
    { 
     this.queue = queue; 
    } 

    public MessageQueue CreateQueue(string path) 
    { 
     //implement method that you want to test here 
    } 
} 

Ora puoi iniettare un oggetto IQueue usando moq in questa classe che dipende dal Messaggio Coda l'oggetto e verifica la funzionalità.

+2

word, tutti i miei progetti .NET sembrano finire con queste interfacce/wrapper per tutte le classi sigillate di Microsoft (FileInfo, HttpContext, ecc. Ecc.) – ryber

+3

+1. Questa è anche la risposta accettata negli ultimi 10 "Come faccio a prendere in giro [Classe X]?" domande. Non sono sicuro del motivo per cui le persone non stanno riprendendo questo. –

+4

Una classe wrapper sembra funzionare bene come soluzione, tranne per il metodo 'Create' (che dovrebbe essere statico tra l'altro), perché la firma per quel metodo restituisce un' System.Messaging.MessageQueue', che non implementa 'IQueue'. Qualcuno ha escogitato una soluzione per questo? –