使用moq模拟具有泛型参数的类型

时间:2012-03-29 09:32:38

标签: c# unit-testing generics moq

我有以下界面。由于T是通用的,我不确定如何使用Moq来模拟IRepository。我确定有办法,但我没有找到任何东西通过搜索这里或谷歌。有谁知道我怎么能做到这一点?

我对Moq很新,但可以看到花时间学习它的好处。

    /// <summary>
    /// This is a marker interface that indicates that an 
    /// Entity is an Aggregate Root.
    /// </summary>
    public interface IAggregateRoot
    {
    } 


/// <summary>
    /// Contract for Repositories. Entities that have repositories
    /// must be of type IAggregateRoot as only aggregate roots
    /// should have a repository in DDD.
    /// </summary>
    /// <typeparam name="T"></typeparam>
    public interface IRepository<T> where T : IAggregateRoot
    {
        T FindBy(int id);
        IList<T> FindAll();
        void Add(T item);
        void Remove(T item);
        void Remove(int id);
        void Update(T item);
        void Commit();
        void RollbackAllChanges();
    }

3 个答案:

答案 0 :(得分:13)

根本不应该是一个问题:

public interface IAggregateRoot { }

class Test : IAggregateRoot { }

public interface IRepository<T> where T : IAggregateRoot
{
    // ...
    IList<T> FindAll();
    void Add(T item);
    // ...
 }

class Program
{
    static void Main(string[] args)
    {
        // create Mock
        var m = new Moq.Mock<IRepository<Test>>();

        // some examples
        m.Setup(r => r.Add(Moq.It.IsAny<Test>()));
        m.Setup(r => r.FindAll()).Returns(new List<Test>());
        m.VerifyAll();
    }
}

答案 1 :(得分:3)

我在测试中创建了一个虚拟具体类 - 或者使用现有的实体类型。

有可能在没有创建具体课程的情况下完成100个篮球,但我认为这不值得。

答案 2 :(得分:2)

你必须指定类型,据我所知,没有直接的方式返回泛型类型的项目。

mock = new Mock<IRepository<string>>();    
mock.Setup(x => x.FindAll()).Returns("abc");