Controller加入單元測試

前言

前面介紹過Repository Pattern用來隔離資料庫,和Autoface注入介面,接下來可以在Controller中寫一些測試項目來驗證流程正確與否

首先加入一個測試專案,名稱為要測試的專案名稱後面加.Tests

加入一個測試專案

依照MVC的習慣,加入一個Controllers資料夾

在資料夾下新增一個單元測試檔案,名稱為要測試的控制器名稱後面加Test
加入一個Controllers資料夾

首先初始化一些要共用的變數

1
2
3
4
5
6
7
8
9
10
11
12
private Mock<IGuestbookRepository> repository;
private GuestbookController ctrl;

[TestInitialize]
public void GuestbookControllerTestInitialize()
{
this.repository = new Mock<IGuestbookRepository>();
this.repository
.Setup(x => x.Find(It.IsIn<int>(1)))
.Returns(new Guestbook());
this.ctrl = new GuestbookController(this.repository.Object);
}

Index相關測試

1
2
3
4
5
6
[TestMethod]
public void Index_GET_Return_ViewResult()
{
var view = this.ctrl.Index() as ViewResult;
Assert.IsNotNull(view);
}

Create相關測試

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
[TestMethod]
public void Create_GET_Return_ViewResult()
{
var view = this.ctrl.Create() as ViewResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Create_POST_Success_Return_RedirectToRouteResult()
{
var model = new Guestbook();
var view = this.ctrl.Create(model) as RedirectToRouteResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Create_POST_Fail_Return_ViewResult()
{
var model = new Guestbook();
this.ctrl.ModelState.AddModelError("key", "message");
var view = this.ctrl.Create(model) as ViewResult;
Assert.IsNotNull(view);
}

Edit相關測試

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
[TestMethod]
public void Edit_GET_Null_ID_Return_HttpStatusCodeResult()
{
int? id = null;
var view = this.ctrl.Edit(id) as HttpStatusCodeResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Edit_GET_Invalid_ID_Return_HttpNotFoundResult()
{
int id = 0;
var view = this.ctrl.Edit(id) as HttpNotFoundResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Edit_GET_Valid_ID_Return_ViewResult()
{
int id = 1;
var view = this.ctrl.Edit(id) as ViewResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Edit_POST_Success_Return_RedirectToRouteResult()
{
var model = new Guestbook();
var view = this.ctrl.Edit(model) as RedirectToRouteResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Edit_POST_Fail_Return_ViewResult()
{
var model = new Guestbook();
this.ctrl.ModelState.AddModelError("key", "message");
var view = this.ctrl.Edit(model) as ViewResult;
Assert.IsNotNull(view);
}

Delete相關測試

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
[TestMethod]
public void Delete_GET_Null_ID_Return_HttpStatusCodeResult()
{
int? id = null;
var view = this.ctrl.Delete(id) as HttpStatusCodeResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Delete_GET_Invalid_ID_Return_HttpNotFound()
{
int? id = 0;
var view = this.ctrl.Delete(id) as HttpNotFoundResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Delete_GET_Valid_ID_Return_ViewResult()
{
int? id = 1;
var view = this.ctrl.Delete(id) as ViewResult;
Assert.IsNotNull(view);
}

[TestMethod]
public void Delete_POST_Return_RedirectToRouteResult()
{
int id = 1;
var view = this.ctrl.DeleteConfirmed(id) as RedirectToRouteResult;
Assert.IsNotNull(view);
}

單元測試涵蓋率可以參考NCover、NCrunch等工具