我正在使用ASP.net MVC 3.0应用程序。我正在MSTest
与一起Moq
用于单元测试。我已经为控制器编写了所有测试方法,并运行了这些测试,从而获得了成功的结果。
现在,我怀疑我是否已经正确进行了单元测试。因为,几乎我的大多数控制器操作都包含数据库调用。
我不是在嘲笑他们,我只是在嘲笑Session
和Request
使用Moq对象。
因为单元测试意味着测试单个代码单元,所以真的有必要模拟数据库调用吗?我认为带有数据库调用的单元测试控制器违反了上面的声明。
如果是这样,任何人都可以向我解释如何模拟数据库调用吗?我没有使用任何实体框架。
更新2:
[httppost]
public void AjaxSave(Model m)
{
m.update(); // Database call
}
您应该提取使数据库调用成为单独对象的代码(请参阅“单一职责原理”)。例如,您有控制器
public class PersonController : Controller
{
public ActionResult Index()
{
var connectionString =
ConfigurationManager.ConnectionStrings["foo"].ConnectionString;
using(var connection = new SqlConnection(connectionString))
{
string sql = "SELECT Name FROM People";
var command = connection.CreateCommand(sql);
var reader = command.ExecuteReader();
List<Person> people = new List<Person>();
while(reader.Read())
{
Person p = new Person();
p.Name = reader["Name"].ToString();
people.Add(p);
}
return View(people);
}
}
}
将数据访问代码提取到单独的类(通常称为存储库的类)中:
public class PersonRepository : IPersonRepository
{
public List<Person> GetAllPeople()
{
var connectionString =
ConfigurationManager.ConnectionStrings["foo"].ConnectionString;
using(var connection = new SqlConnection(connectionString))
{
string sql = "SELECT Name FROM People";
var command = connection.CreateCommand(sql);
var reader = command.ExecuteReader();
List<Person> people = new List<Person>();
while(reader.Read())
{
Person p = new Person();
p.Name = reader["Name"].ToString();
people.Add(p);
}
return people;
}
}
}
您已经注意到,我声明了抽象,它是由数据访问类实现的:
public interface IPersonRepository
{
List<Person> GetAllPeople();
// other data access API will go here
}
使控制器依赖于此抽象(这很重要-抽象很容易模拟):
public class PersonController : Controller
{
private IPersonRepository _personRepository;
public PersonController(IPersonRepository personRepository)
{
_personRepository = personRepository;
}
public ActionResult Index()
{
var people = _personRepository.GetAllPeople();
return View(people);
}
}
然后将存储库实现注入到控制器中(.NET中的依赖注入),并对其进行模拟以进行测试:
var repositoryMock = new Mock<IPersonRepository>();
var people = new List<People>(); // provide some sample list
repositoryMock.Setup(r => r.GetAllPeople()).Return(people);
var controller = new PersonController(repositoryMock.Object);
var result = (ViewResult)controller.Index();
// Assert here
Assert.AreEqual(result.ViewName, "Index");
Assert.AreEqual(result.Model, people);
repositoryMock.VerifyAll();
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句