2010-07-13 20 views
6

我正在尝试为ObjectContext创建一个抽象层。我了解OC是一个工作单元,但我不完全知道如何为它写一个好的界面。理想情况下,我希望能够将我的'RealDataContext'换成实现IDataContext的类似'FakeDataContext'的内容。为ObjectContext创建接口

原因是我希望能够对内存数据库测试我的存储库。

谢谢!

回答

7

您应该能够创建一个从ObjectContext派生的扩展类,并实现一个IDataContext接口。要真正能够模拟ObjectContext,您的IDataContext接口需要为您正在使用并希望模拟的ObjectContext的任何成员包含匹配签名(或属性)。像下面的内容就足够了:

interface IDataContext, IDisposable 
{ 
    void AddObject(string entitySetName, object entity); 
    void Attach(IEntityWithKey entity); 
    void Detach(object entity); 
    void DeleteObject(object entity); 
    int SaveChanges(); 
    int SaveChanges(bool acceptChangesDuringSave); 
    int SaveChanges(SaveOptions options); 

    // Any other members you wish to be mockable 
} 

class DataContext: ObjectContext, IDataContext 
{ 
    // nothing here 
} 

从技术上来说,因为DataContext的继承ObjectContect,IDataContext的实现是由ObjectContext的照顾一切。你不应该在DataContext类中需要任何额外的实现。

class SomeEntityRepository: IRepository<SomeEntity> 
{ 
    public SomeEntityRepository(IDataContext context) 
    { 
     m_context = context; 
    } 

    private readonly IDataContext m_context; 

    public SomeEntity GetById(long id) 
    { 
     // implementation 
    } 
} 

// xUnit.NET & Moq 
class SomeEntityRepositoryTests 
{ 
    [Fact] 
    public void GetById_returns_entity_when_valid_id_is_passed() 
    { 
     // state and context 
     var mockContext = new Mock<IDataContext>(); 

     // arrangement 
     mockContext.Setup(/* configure mock context here */); 
     var repo = new SomeEntityRepository(mockContext.Object); 

     // activity 
     var entity = repo.GetById(100); 

     // assertions 
    } 
} 
+0

这是我倾向于方向,但并没有真正:只要你总是注入(或使用一个工厂来创建)IDataContext的实例,而不是ObjectContext的,你应该在测试时能够嘲笑IDataContext当然,如果这是一个好方法。谢谢! – TheCloudlessSky 2010-07-14 02:27:18

+0

Glat成为服务。 :) – jrista 2010-07-14 02:28:27