ASP.NET Core 'de birim test denetleyicisi mantığı
Steve Smith tarafından
Birim testleri , bir uygulamanın bir bölümünü altyapısından ve bağımlılıklarından yalıtımıyla test etmeyi içerir. Birim testi denetleyici mantığı olduğunda, yalnızca tek bir eylemin içerikleri test edilir, onun bağımlılıkları veya çerçevenin kendisi değildir.
Birim test denetleyicileri
Denetleyicinin davranışına odaklanmak için denetleyici eylemlerinin birim testlerini ayarlayın. Denetleyici birim testi Filtreler, yönlendirmeve model bağlamagibi senaryoları önler. Bir isteğe topluca yanıt veren bileşenler arasındaki etkileşimleri kapsayan testler, tümleştirme testleri tarafından işlenir. Tümleştirme testleri hakkında daha fazla bilgi için bkz ASP.NET Core tümleştirme testleri ..
Özel filtreler ve rotalar yazıyorsanız, birim, belirli bir denetleyici eyleminde testlerin bir parçası olarak değil, yalıtımına göre test eder.
Denetleyici birim testlerini göstermek için örnek uygulamada aşağıdaki denetleyiciyi gözden geçirin.
Örnek kodu görüntüleme veya indirme (nasıl indirileceği)
HomeDenetleyici, beyin fırtınası oturumlarının bir listesini görüntüler ve yeni beyin fırtınası oturumlarının BIR Post isteğiyle oluşturulmasına izin verir:
public class HomeController : Controller
{
private readonly IBrainstormSessionRepository _sessionRepository;
public HomeController(IBrainstormSessionRepository sessionRepository)
{
_sessionRepository = sessionRepository;
}
public async Task<IActionResult> Index()
{
var sessionList = await _sessionRepository.ListAsync();
var model = sessionList.Select(session => new StormSessionViewModel()
{
Id = session.Id,
DateCreated = session.DateCreated,
Name = session.Name,
IdeaCount = session.Ideas.Count
});
return View(model);
}
public class NewSessionModel
{
[Required]
public string SessionName { get; set; }
}
[HttpPost]
public async Task<IActionResult> Index(NewSessionModel model)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
else
{
await _sessionRepository.AddAsync(new BrainstormSession()
{
DateCreated = DateTimeOffset.Now,
Name = model.SessionName
});
}
return RedirectToAction(actionName: nameof(Index));
}
}
Önceki denetleyici:
- Açık bağımlılıklar ilkesiniizler.
- Bir örneği sağlamak için bağımlılık ekleme (dı) bekliyor
IBrainstormSessionRepository. IBrainstormSessionRepository, Moqgibi bir sahte nesne çerçevesi kullanılarak bir moclenmiş hizmetle test edilebilir. Bir ilişkili nesne , test için kullanılan önceden tanımlanmış bir özellik ve Yöntem davranışları kümesine sahip bir fabricobject nesnesidir. Daha fazla bilgi için bkz. tümleştirme testlerine giriş.
HTTP GET IndexMetodun döngüsü veya dallanmayı yoktur ve yalnızca bir yöntem çağırır. Bu eylemin birim testi:
IBrainstormSessionRepositoryYöntemini kullanarak hizmeti gizlerGetTestSessions.GetTestSessionsTarih ve oturum adlarıyla iki adet sahte beyin fırtınası oturumu oluşturur.- Yöntemini yürütür
Index. - Yöntemi tarafından döndürülen sonuç üzerinde onaylama işlemleri yapar:
- Bir ViewResult döndürülür.
- ViewDataDictionary. model bir
StormSessionViewModel. - İçinde depolanan iki beyin fırtınası oturumu vardır
ViewDataDictionary.Model.
[Fact]
public async Task Index_ReturnsAViewResult_WithAListOfBrainstormSessions()
{
// Arrange
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.ListAsync())
.ReturnsAsync(GetTestSessions());
var controller = new HomeController(mockRepo.Object);
// Act
var result = await controller.Index();
// Assert
var viewResult = Assert.IsType<ViewResult>(result);
var model = Assert.IsAssignableFrom<IEnumerable<StormSessionViewModel>>(
viewResult.ViewData.Model);
Assert.Equal(2, model.Count());
}
private List<BrainstormSession> GetTestSessions()
{
var sessions = new List<BrainstormSession>();
sessions.Add(new BrainstormSession()
{
DateCreated = new DateTime(2016, 7, 2),
Id = 1,
Name = "Test One"
});
sessions.Add(new BrainstormSession()
{
DateCreated = new DateTime(2016, 7, 1),
Id = 2,
Name = "Test Two"
});
return sessions;
}
HomeDenetleyicinin HTTP POST Index Yöntem sınamaları şunları doğrular:
- ModelState. IsValid olduğunda
false, eylem yöntemi uygun verilerle 400 hatalı bir istek döndürür ViewResult . - Ne
ModelState.IsValidzamantrue:AddDepodaki yöntem çağrılır.- RedirectToActionResultDoğru bağımsız değişkenlerle bir döndürülür.
Geçersiz bir model durumu, AddModelError aşağıdaki ilk testte gösterildiği gibi kullanılarak hatalar eklenerek test edilir:
[Fact]
public async Task IndexPost_ReturnsBadRequestResult_WhenModelStateIsInvalid()
{
// Arrange
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.ListAsync())
.ReturnsAsync(GetTestSessions());
var controller = new HomeController(mockRepo.Object);
controller.ModelState.AddModelError("SessionName", "Required");
var newSession = new HomeController.NewSessionModel();
// Act
var result = await controller.Index(newSession);
// Assert
var badRequestResult = Assert.IsType<BadRequestObjectResult>(result);
Assert.IsType<SerializableError>(badRequestResult.Value);
}
[Fact]
public async Task IndexPost_ReturnsARedirectAndAddsSession_WhenModelStateIsValid()
{
// Arrange
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.AddAsync(It.IsAny<BrainstormSession>()))
.Returns(Task.CompletedTask)
.Verifiable();
var controller = new HomeController(mockRepo.Object);
var newSession = new HomeController.NewSessionModel()
{
SessionName = "Test Name"
};
// Act
var result = await controller.Index(newSession);
// Assert
var redirectToActionResult = Assert.IsType<RedirectToActionResult>(result);
Assert.Null(redirectToActionResult.ControllerName);
Assert.Equal("Index", redirectToActionResult.ActionName);
mockRepo.Verify();
}
ModelState geçerli olmadığında, ViewResult bir get isteği için de aynı döndürülür. Test geçersiz bir modeli geçirmeye çalışmıyor. Model bağlama çalışmadığından (bir tümleştirme testi model bağlamayı kullansa da), geçersiz bir modelin geçirilmesi geçerli bir yaklaşım değildir. Bu durumda model bağlama sınanmamıştır. Bu birim testleri yalnızca eylem yöntemindeki kodu test eder.
İkinci test, geçerli olduğunda doğrular ModelState :
- Yeni bir
BrainstormSessioneklendi (depo aracılığıyla). - Yöntemi,
RedirectToActionResultbeklenen özelliklerle bir döndürür.
Çağrılmayan hiçbir çağrı normalde yok sayılır, ancak Verifiable Kurulum çağrısının sonunda çağrılması testte sahte doğrulamaya izin verir. Bu, öğesine yapılan çağrısıyla gerçekleştirilir ve bu, mockRepo.Verify beklenen yöntemin çağrılmaması durumunda test başarısız olur.
Not
Bu örnekte kullanılan moq kitaplığı, doğrulanabilir olmayan bir şekilde ("gevşek" bir veya saplamalar olarak da adlandırılır) doğrulanabilir veya "katı" olarak karışık bir şekilde karışık bir şekilde karıştırılamaz. Moq Ile sahte davranışı özelleştirmehakkında daha fazla bilgi edinin.
Örnek uygulamadaki Sessioncontroller , belirli bir beyin fırtınası oturumuyla ilgili bilgileri görüntüler. Denetleyici geçersiz id değerlerle ilgilenme mantığını içerir ( return Bu senaryoları kapsayan aşağıdaki örnekte iki senaryo vardır). Son return ifade, StormSessionViewModel görünüme (Controllers/sessioncontroller. cs) yeni bir döndürür:
public class SessionController : Controller
{
private readonly IBrainstormSessionRepository _sessionRepository;
public SessionController(IBrainstormSessionRepository sessionRepository)
{
_sessionRepository = sessionRepository;
}
public async Task<IActionResult> Index(int? id)
{
if (!id.HasValue)
{
return RedirectToAction(actionName: nameof(Index),
controllerName: "Home");
}
var session = await _sessionRepository.GetByIdAsync(id.Value);
if (session == null)
{
return Content("Session not found.");
}
var viewModel = new StormSessionViewModel()
{
DateCreated = session.DateCreated,
Name = session.Name,
Id = session.Id
};
return View(viewModel);
}
}
Birim testleri return , oturum denetleyicisi eyleminde her senaryo için bir test içerir Index :
[Fact]
public async Task IndexReturnsARedirectToIndexHomeWhenIdIsNull()
{
// Arrange
var controller = new SessionController(sessionRepository: null);
// Act
var result = await controller.Index(id: null);
// Assert
var redirectToActionResult =
Assert.IsType<RedirectToActionResult>(result);
Assert.Equal("Home", redirectToActionResult.ControllerName);
Assert.Equal("Index", redirectToActionResult.ActionName);
}
[Fact]
public async Task IndexReturnsContentWithSessionNotFoundWhenSessionNotFound()
{
// Arrange
int testSessionId = 1;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync((BrainstormSession)null);
var controller = new SessionController(mockRepo.Object);
// Act
var result = await controller.Index(testSessionId);
// Assert
var contentResult = Assert.IsType<ContentResult>(result);
Assert.Equal("Session not found.", contentResult.Content);
}
[Fact]
public async Task IndexReturnsViewResultWithStormSessionViewModel()
{
// Arrange
int testSessionId = 1;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(GetTestSessions().FirstOrDefault(
s => s.Id == testSessionId));
var controller = new SessionController(mockRepo.Object);
// Act
var result = await controller.Index(testSessionId);
// Assert
var viewResult = Assert.IsType<ViewResult>(result);
var model = Assert.IsType<StormSessionViewModel>(
viewResult.ViewData.Model);
Assert.Equal("Test One", model.Name);
Assert.Equal(2, model.DateCreated.Day);
Assert.Equal(testSessionId, model.Id);
}
Uygulama, fikirler denetleyicisine geçiş yaparken, bir Web API 'SI olarak yol üzerinde işlevselliği kullanıma sunar api/ideas :
IdeaDTOBir beyin fırtınası oturumuyla ilişkili fikirler () listesi, yöntemi tarafından döndürülürForSession.CreateYöntemi bir oturuma yeni fikirler ekler.
[HttpGet("forsession/{sessionId}")]
public async Task<IActionResult> ForSession(int sessionId)
{
var session = await _sessionRepository.GetByIdAsync(sessionId);
if (session == null)
{
return NotFound(sessionId);
}
var result = session.Ideas.Select(idea => new IdeaDTO()
{
Id = idea.Id,
Name = idea.Name,
Description = idea.Description,
DateCreated = idea.DateCreated
}).ToList();
return Ok(result);
}
[HttpPost("create")]
public async Task<IActionResult> Create([FromBody]NewIdeaModel model)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
var session = await _sessionRepository.GetByIdAsync(model.SessionId);
if (session == null)
{
return NotFound(model.SessionId);
}
var idea = new Idea()
{
DateCreated = DateTimeOffset.Now,
Description = model.Description,
Name = model.Name
};
session.AddIdea(idea);
await _sessionRepository.UpdateAsync(session);
return Ok(session);
}
İş etki alanı varlıklarını doğrudan API çağrıları aracılığıyla döndürmekten kaçının. Etki alanı varlıkları:
- Genellikle istemcinin gerektirdiğinden daha fazla veri içerir.
- Genel olarak sunulan API ile uygulamanın iç etki alanı modelini gereksiz bir şekilde yapın.
Etki alanı varlıkları ve istemciye döndürülen türler arasında eşleme gerçekleştirilebilir:
- Örnek uygulamanın kullandığı şekilde bir LINQ ile el ile
Select. Daha fazla bilgi için bkz. LINQ (dil Ile tümleşik sorgu). - Otomatik olarak bir kitaplıkla (örneğin, Automaber).
Ardından, örnek uygulama, Create fikirler denetleyicisinin ve API yöntemlerine yönelik birim testlerini gösterir ForSession .
Örnek uygulama iki test içerir ForSession . İlk test, ForSession NotFoundObjectResult geçersiz bir oturum için (http bulunamadı) döndürüp döndürmeyeceğini belirler:
[Fact]
public async Task ForSession_ReturnsHttpNotFound_ForInvalidSession()
{
// Arrange
int testSessionId = 123;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync((BrainstormSession)null);
var controller = new IdeasController(mockRepo.Object);
// Act
var result = await controller.ForSession(testSessionId);
// Assert
var notFoundObjectResult = Assert.IsType<NotFoundObjectResult>(result);
Assert.Equal(testSessionId, notFoundObjectResult.Value);
}
İkinci ForSession test, ForSession <List<IdeaDTO>> geçerli bir oturum için oturum fikirleri () listesini döndürüp döndürmeyeceğini belirler. Denetimler Ayrıca, özelliğinin doğru olduğunu onaylamak için ilk fikri de inceler Name :
[Fact]
public async Task ForSession_ReturnsIdeasForSession()
{
// Arrange
int testSessionId = 123;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(GetTestSession());
var controller = new IdeasController(mockRepo.Object);
// Act
var result = await controller.ForSession(testSessionId);
// Assert
var okResult = Assert.IsType<OkObjectResult>(result);
var returnValue = Assert.IsType<List<IdeaDTO>>(okResult.Value);
var idea = returnValue.FirstOrDefault();
Assert.Equal("One", idea.Name);
}
Geçersiz olduğunda yönteminin davranışını test etmek için Create ModelState , örnek uygulama, testin bir parçası olarak denetleyiciye bir model hatası ekler. Birim testlerinde model doğrulamayı veya model bağlamayı sınamayı denemeyin, ancak — geçersiz kılma sırasında eylem yönteminin davranışını test edin ModelState :
[Fact]
public async Task Create_ReturnsBadRequest_GivenInvalidModel()
{
// Arrange & Act
var mockRepo = new Mock<IBrainstormSessionRepository>();
var controller = new IdeasController(mockRepo.Object);
controller.ModelState.AddModelError("error", "some error");
// Act
var result = await controller.Create(model: null);
// Assert
Assert.IsType<BadRequestObjectResult>(result);
}
İkinci testi, Create döndürülen depoya bağlıdır null , bu nedenle, sahte depo döndürecek şekilde yapılandırılır null . Bir test veritabanı (bellekte veya başka türlü) oluşturmanız gerekmez ve bu sonucu döndüren bir sorgu oluşturun. Örnek kodun gösterildiği gibi, test tek bir bildirimde gerçekleştirilebilir:
[Fact]
public async Task Create_ReturnsHttpNotFound_ForInvalidSession()
{
// Arrange
int testSessionId = 123;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync((BrainstormSession)null);
var controller = new IdeasController(mockRepo.Object);
// Act
var result = await controller.Create(new NewIdeaModel());
// Assert
Assert.IsType<NotFoundObjectResult>(result);
}
Üçüncü Create test, Create_ReturnsNewlyCreatedIdeaForSession deponun UpdateAsync yönteminin çağrıldığını doğrular. , İle birlikte çağrılır Verifiable ve Verify doğrulanabilen yöntemin yürütüldüğünü onaylamak için, moclenmiş deponun yöntemi çağırılır. UpdateAsyncYöntemin — bir tümleştirme testiyle gerçekleştirilebilecek verileri kaydettiğinizden emin olmak için birim testin sorumluluğu bu değildir.
[Fact]
public async Task Create_ReturnsNewlyCreatedIdeaForSession()
{
// Arrange
int testSessionId = 123;
string testName = "test name";
string testDescription = "test description";
var testSession = GetTestSession();
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(testSession);
var controller = new IdeasController(mockRepo.Object);
var newIdea = new NewIdeaModel()
{
Description = testDescription,
Name = testName,
SessionId = testSessionId
};
mockRepo.Setup(repo => repo.UpdateAsync(testSession))
.Returns(Task.CompletedTask)
.Verifiable();
// Act
var result = await controller.Create(newIdea);
// Assert
var okResult = Assert.IsType<OkObjectResult>(result);
var returnSession = Assert.IsType<BrainstormSession>(okResult.Value);
mockRepo.Verify();
Assert.Equal(2, returnSession.Ideas.Count());
Assert.Equal(testName, returnSession.Ideas.LastOrDefault().Name);
Assert.Equal(testDescription, returnSession.Ideas.LastOrDefault().Description);
}
Test ActionResult<T>
ASP.NET Core 2,1 veya sonraki sürümlerde <T> actionresult ( ActionResult<TValue> ), belirli bir türden türetilen veya döndürülen bir tür döndürmenizi sağlar ActionResult .
Örnek uygulama, belirli bir oturum için döndüren bir yöntemi içerir List<IdeaDTO> id . Oturum id yoksa, denetleyici şunu döndürür NotFound :
[HttpGet("forsessionactionresult/{sessionId}")]
[ProducesResponseType(200)]
[ProducesResponseType(404)]
public async Task<ActionResult<List<IdeaDTO>>> ForSessionActionResult(int sessionId)
{
var session = await _sessionRepository.GetByIdAsync(sessionId);
if (session == null)
{
return NotFound(sessionId);
}
var result = session.Ideas.Select(idea => new IdeaDTO()
{
Id = idea.Id,
Name = idea.Name,
Description = idea.Description,
DateCreated = idea.DateCreated
}).ToList();
return result;
}
Denetleyicinin iki testi ForSessionActionResult uygulamasına dahil edilmiştir ApiIdeasControllerTests .
İlk test, denetleyicinin ActionResult varolmayan bir oturum için varolmayan bir fikirler listesi döndürdüğünü doğrular id :
ActionResultTürüActionResult<List<IdeaDTO>>.- , Result Bir NotFoundObjectResult .
[Fact]
public async Task ForSessionActionResult_ReturnsNotFoundObjectResultForNonexistentSession()
{
// Arrange
var mockRepo = new Mock<IBrainstormSessionRepository>();
var controller = new IdeasController(mockRepo.Object);
var nonExistentSessionId = 999;
// Act
var result = await controller.ForSessionActionResult(nonExistentSessionId);
// Assert
var actionResult = Assert.IsType<ActionResult<List<IdeaDTO>>>(result);
Assert.IsType<NotFoundObjectResult>(actionResult.Result);
}
Geçerli bir oturum için id ikinci test, yöntemin döndürdüğünü onaylar:
- Bir
ActionResulttür ileList<IdeaDTO>. - Eylem sonucu <T> . Değer bir
List<IdeaDTO>türdür. - Listedeki ilk öğe, sahte oturumda saklanan fikrle eşleşen geçerli bir fikrdir (çağırarak elde edilir
GetTestSession).
[Fact]
public async Task ForSessionActionResult_ReturnsIdeasForSession()
{
// Arrange
int testSessionId = 123;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(GetTestSession());
var controller = new IdeasController(mockRepo.Object);
// Act
var result = await controller.ForSessionActionResult(testSessionId);
// Assert
var actionResult = Assert.IsType<ActionResult<List<IdeaDTO>>>(result);
var returnValue = Assert.IsType<List<IdeaDTO>>(actionResult.Value);
var idea = returnValue.FirstOrDefault();
Assert.Equal("One", idea.Name);
}
Örnek uygulama, belirli bir oturum için yeni bir oluşturma yöntemi de içerir Idea . Denetleyici şunu döndürür:
- BadRequest geçersiz bir model.
- NotFound oturum yoksa.
- CreatedAtAction oturum yeni fikrle güncelleştirildiği zaman.
[HttpPost("createactionresult")]
[ProducesResponseType(201)]
[ProducesResponseType(400)]
[ProducesResponseType(404)]
public async Task<ActionResult<BrainstormSession>> CreateActionResult([FromBody]NewIdeaModel model)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
var session = await _sessionRepository.GetByIdAsync(model.SessionId);
if (session == null)
{
return NotFound(model.SessionId);
}
var idea = new Idea()
{
DateCreated = DateTimeOffset.Now,
Description = model.Description,
Name = model.Name
};
session.AddIdea(idea);
await _sessionRepository.UpdateAsync(session);
return CreatedAtAction(nameof(CreateActionResult), new { id = session.Id }, session);
}
CreateActionResult' Ye üç test dahildir ApiIdeasControllerTests .
İlk metin, bir BadRequest geçersiz model için döndürüldüğünü onaylar.
[Fact]
public async Task CreateActionResult_ReturnsBadRequest_GivenInvalidModel()
{
// Arrange & Act
var mockRepo = new Mock<IBrainstormSessionRepository>();
var controller = new IdeasController(mockRepo.Object);
controller.ModelState.AddModelError("error", "some error");
// Act
var result = await controller.CreateActionResult(model: null);
// Assert
var actionResult = Assert.IsType<ActionResult<BrainstormSession>>(result);
Assert.IsType<BadRequestObjectResult>(actionResult.Result);
}
İkinci test, NotFound oturum yoksa bir ' ın döndürülüp döndürülmediğini denetler.
[Fact]
public async Task CreateActionResult_ReturnsNotFoundObjectResultForNonexistentSession()
{
// Arrange
var nonExistentSessionId = 999;
string testName = "test name";
string testDescription = "test description";
var mockRepo = new Mock<IBrainstormSessionRepository>();
var controller = new IdeasController(mockRepo.Object);
var newIdea = new NewIdeaModel()
{
Description = testDescription,
Name = testName,
SessionId = nonExistentSessionId
};
// Act
var result = await controller.CreateActionResult(newIdea);
// Assert
var actionResult = Assert.IsType<ActionResult<BrainstormSession>>(result);
Assert.IsType<NotFoundObjectResult>(actionResult.Result);
}
Geçerli bir oturum için id son test şunları onaylar:
- Yöntemi bir
ActionResulttürü ile döndürürBrainstormSession. - Eylem sonucu <T> . Sonuç bir CreatedAtActionResult .
CreatedAtActionResult, bir üst bilgiyle 201 oluşturulan yanıta benzerdirLocation. - Eylem sonucu <T> . Değer bir
BrainstormSessiontürdür. - Oturumu güncelleştirmek için kullanılan sahte çağrı,
UpdateAsync(testSession)çağrıldı.VerifiableYöntem çağrısımockRepo.Verify()onaylamalarda yürütülerek denetlenir. IdeaOturum için iki nesne döndürülür.- Son öğe (
Ideasahte çağrının eklendiğiUpdateAsync),newIdeatestteki oturuma eklenen ile eşleşir.
[Fact]
public async Task CreateActionResult_ReturnsNewlyCreatedIdeaForSession()
{
// Arrange
int testSessionId = 123;
string testName = "test name";
string testDescription = "test description";
var testSession = GetTestSession();
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(testSession);
var controller = new IdeasController(mockRepo.Object);
var newIdea = new NewIdeaModel()
{
Description = testDescription,
Name = testName,
SessionId = testSessionId
};
mockRepo.Setup(repo => repo.UpdateAsync(testSession))
.Returns(Task.CompletedTask)
.Verifiable();
// Act
var result = await controller.CreateActionResult(newIdea);
// Assert
var actionResult = Assert.IsType<ActionResult<BrainstormSession>>(result);
var createdAtActionResult = Assert.IsType<CreatedAtActionResult>(actionResult.Result);
var returnValue = Assert.IsType<BrainstormSession>(createdAtActionResult.Value);
mockRepo.Verify();
Assert.Equal(2, returnValue.Ideas.Count());
Assert.Equal(testName, returnValue.Ideas.LastOrDefault().Name);
Assert.Equal(testDescription, returnValue.Ideas.LastOrDefault().Description);
}
denetleyiciler herhangi bir ASP.NET Core MVC uygulamasında merkezi bir rol oynar. Bu nedenle, denetleyicilerin amaçlanan gibi davrandığına güvenmelisiniz. Otomatik testler, uygulama bir üretim ortamına dağıtılmadan önce hataları tespit edebilir.
Örnek kodu görüntüleme veya indirme (nasıl indirileceği)
Denetleyici mantığının birim testleri
Birim testleri , bir uygulamanın bir bölümünü altyapısından ve bağımlılıklarından yalıtımıyla test etmeyi içerir. Birim testi denetleyici mantığı olduğunda, yalnızca tek bir eylemin içerikleri test edilir, onun bağımlılıkları veya çerçevenin kendisi değildir.
Denetleyicinin davranışına odaklanmak için denetleyici eylemlerinin birim testlerini ayarlayın. Denetleyici birim testi Filtreler, yönlendirmeve model bağlamagibi senaryoları önler. Bir isteğe topluca yanıt veren bileşenler arasındaki etkileşimleri kapsayan testler, tümleştirme testleri tarafından işlenir. Tümleştirme testleri hakkında daha fazla bilgi için bkz ASP.NET Core tümleştirme testleri ..
Özel filtreler ve rotalar yazıyorsanız, birim, belirli bir denetleyici eyleminde testlerin bir parçası olarak değil, yalıtımına göre test eder.
Denetleyici birim testlerini göstermek için örnek uygulamada aşağıdaki denetleyiciyi gözden geçirin. HomeDenetleyici, beyin fırtınası oturumlarının bir listesini görüntüler ve yeni beyin fırtınası oturumlarının BIR Post isteğiyle oluşturulmasına izin verir:
public class HomeController : Controller
{
private readonly IBrainstormSessionRepository _sessionRepository;
public HomeController(IBrainstormSessionRepository sessionRepository)
{
_sessionRepository = sessionRepository;
}
public async Task<IActionResult> Index()
{
var sessionList = await _sessionRepository.ListAsync();
var model = sessionList.Select(session => new StormSessionViewModel()
{
Id = session.Id,
DateCreated = session.DateCreated,
Name = session.Name,
IdeaCount = session.Ideas.Count
});
return View(model);
}
public class NewSessionModel
{
[Required]
public string SessionName { get; set; }
}
[HttpPost]
public async Task<IActionResult> Index(NewSessionModel model)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
else
{
await _sessionRepository.AddAsync(new BrainstormSession()
{
DateCreated = DateTimeOffset.Now,
Name = model.SessionName
});
}
return RedirectToAction(actionName: nameof(Index));
}
}
Önceki denetleyici:
- Açık bağımlılıklar ilkesiniizler.
- Bir örneği sağlamak için bağımlılık ekleme (dı) bekliyor
IBrainstormSessionRepository. IBrainstormSessionRepository, Moqgibi bir sahte nesne çerçevesi kullanılarak bir moclenmiş hizmetle test edilebilir. Bir ilişkili nesne , test için kullanılan önceden tanımlanmış bir özellik ve Yöntem davranışları kümesine sahip bir fabricobject nesnesidir. Daha fazla bilgi için bkz. tümleştirme testlerine giriş.
HTTP GET IndexMetodun döngüsü veya dallanmayı yoktur ve yalnızca bir yöntem çağırır. Bu eylemin birim testi:
IBrainstormSessionRepositoryYöntemini kullanarak hizmeti gizlerGetTestSessions.GetTestSessionsTarih ve oturum adlarıyla iki adet sahte beyin fırtınası oturumu oluşturur.- Yöntemini yürütür
Index. - Yöntemi tarafından döndürülen sonuç üzerinde onaylama işlemleri yapar:
- Bir ViewResult döndürülür.
- ViewDataDictionary. model bir
StormSessionViewModel. - İçinde depolanan iki beyin fırtınası oturumu vardır
ViewDataDictionary.Model.
[Fact]
public async Task Index_ReturnsAViewResult_WithAListOfBrainstormSessions()
{
// Arrange
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.ListAsync())
.ReturnsAsync(GetTestSessions());
var controller = new HomeController(mockRepo.Object);
// Act
var result = await controller.Index();
// Assert
var viewResult = Assert.IsType<ViewResult>(result);
var model = Assert.IsAssignableFrom<IEnumerable<StormSessionViewModel>>(
viewResult.ViewData.Model);
Assert.Equal(2, model.Count());
}
private List<BrainstormSession> GetTestSessions()
{
var sessions = new List<BrainstormSession>();
sessions.Add(new BrainstormSession()
{
DateCreated = new DateTime(2016, 7, 2),
Id = 1,
Name = "Test One"
});
sessions.Add(new BrainstormSession()
{
DateCreated = new DateTime(2016, 7, 1),
Id = 2,
Name = "Test Two"
});
return sessions;
}
HomeDenetleyicinin HTTP POST Index Yöntem sınamaları şunları doğrular:
- ModelState. IsValid olduğunda
false, eylem yöntemi uygun verilerle 400 hatalı bir istek döndürür ViewResult . - Ne
ModelState.IsValidzamantrue:AddDepodaki yöntem çağrılır.- RedirectToActionResultDoğru bağımsız değişkenlerle bir döndürülür.
Geçersiz bir model durumu, AddModelError aşağıdaki ilk testte gösterildiği gibi kullanılarak hatalar eklenerek test edilir:
[Fact]
public async Task IndexPost_ReturnsBadRequestResult_WhenModelStateIsInvalid()
{
// Arrange
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.ListAsync())
.ReturnsAsync(GetTestSessions());
var controller = new HomeController(mockRepo.Object);
controller.ModelState.AddModelError("SessionName", "Required");
var newSession = new HomeController.NewSessionModel();
// Act
var result = await controller.Index(newSession);
// Assert
var badRequestResult = Assert.IsType<BadRequestObjectResult>(result);
Assert.IsType<SerializableError>(badRequestResult.Value);
}
[Fact]
public async Task IndexPost_ReturnsARedirectAndAddsSession_WhenModelStateIsValid()
{
// Arrange
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.AddAsync(It.IsAny<BrainstormSession>()))
.Returns(Task.CompletedTask)
.Verifiable();
var controller = new HomeController(mockRepo.Object);
var newSession = new HomeController.NewSessionModel()
{
SessionName = "Test Name"
};
// Act
var result = await controller.Index(newSession);
// Assert
var redirectToActionResult = Assert.IsType<RedirectToActionResult>(result);
Assert.Null(redirectToActionResult.ControllerName);
Assert.Equal("Index", redirectToActionResult.ActionName);
mockRepo.Verify();
}
ModelState geçerli olmadığında, ViewResult bir get isteği için de aynı döndürülür. Test geçersiz bir modeli geçirmeye çalışmıyor. Model bağlama çalışmadığından (bir tümleştirme testi model bağlamayı kullansa da), geçersiz bir modelin geçirilmesi geçerli bir yaklaşım değildir. Bu durumda model bağlama sınanmamıştır. Bu birim testleri yalnızca eylem yöntemindeki kodu test eder.
İkinci test, geçerli olduğunda doğrular ModelState :
- Yeni bir
BrainstormSessioneklendi (depo aracılığıyla). - Yöntemi,
RedirectToActionResultbeklenen özelliklerle bir döndürür.
Çağrılmayan hiçbir çağrı normalde yok sayılır, ancak Verifiable Kurulum çağrısının sonunda çağrılması testte sahte doğrulamaya izin verir. Bu, öğesine yapılan çağrısıyla gerçekleştirilir ve bu, mockRepo.Verify beklenen yöntemin çağrılmaması durumunda test başarısız olur.
Not
Bu örnekte kullanılan moq kitaplığı, doğrulanabilir olmayan bir şekilde ("gevşek" bir veya saplamalar olarak da adlandırılır) doğrulanabilir veya "katı" olarak karışık bir şekilde karışık bir şekilde karıştırılamaz. Moq Ile sahte davranışı özelleştirmehakkında daha fazla bilgi edinin.
Örnek uygulamadaki Sessioncontroller , belirli bir beyin fırtınası oturumuyla ilgili bilgileri görüntüler. Denetleyici geçersiz id değerlerle ilgilenme mantığını içerir ( return Bu senaryoları kapsayan aşağıdaki örnekte iki senaryo vardır). Son return ifade, StormSessionViewModel görünüme (Controllers/sessioncontroller. cs) yeni bir döndürür:
public class SessionController : Controller
{
private readonly IBrainstormSessionRepository _sessionRepository;
public SessionController(IBrainstormSessionRepository sessionRepository)
{
_sessionRepository = sessionRepository;
}
public async Task<IActionResult> Index(int? id)
{
if (!id.HasValue)
{
return RedirectToAction(actionName: nameof(Index),
controllerName: "Home");
}
var session = await _sessionRepository.GetByIdAsync(id.Value);
if (session == null)
{
return Content("Session not found.");
}
var viewModel = new StormSessionViewModel()
{
DateCreated = session.DateCreated,
Name = session.Name,
Id = session.Id
};
return View(viewModel);
}
}
Birim testleri return , oturum denetleyicisi eyleminde her senaryo için bir test içerir Index :
[Fact]
public async Task IndexReturnsARedirectToIndexHomeWhenIdIsNull()
{
// Arrange
var controller = new SessionController(sessionRepository: null);
// Act
var result = await controller.Index(id: null);
// Assert
var redirectToActionResult =
Assert.IsType<RedirectToActionResult>(result);
Assert.Equal("Home", redirectToActionResult.ControllerName);
Assert.Equal("Index", redirectToActionResult.ActionName);
}
[Fact]
public async Task IndexReturnsContentWithSessionNotFoundWhenSessionNotFound()
{
// Arrange
int testSessionId = 1;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync((BrainstormSession)null);
var controller = new SessionController(mockRepo.Object);
// Act
var result = await controller.Index(testSessionId);
// Assert
var contentResult = Assert.IsType<ContentResult>(result);
Assert.Equal("Session not found.", contentResult.Content);
}
[Fact]
public async Task IndexReturnsViewResultWithStormSessionViewModel()
{
// Arrange
int testSessionId = 1;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(GetTestSessions().FirstOrDefault(
s => s.Id == testSessionId));
var controller = new SessionController(mockRepo.Object);
// Act
var result = await controller.Index(testSessionId);
// Assert
var viewResult = Assert.IsType<ViewResult>(result);
var model = Assert.IsType<StormSessionViewModel>(
viewResult.ViewData.Model);
Assert.Equal("Test One", model.Name);
Assert.Equal(2, model.DateCreated.Day);
Assert.Equal(testSessionId, model.Id);
}
Uygulama, fikirler denetleyicisine geçiş yaparken, bir Web API 'SI olarak yol üzerinde işlevselliği kullanıma sunar api/ideas :
IdeaDTOBir beyin fırtınası oturumuyla ilişkili fikirler () listesi, yöntemi tarafından döndürülürForSession.CreateYöntemi bir oturuma yeni fikirler ekler.
[HttpGet("forsession/{sessionId}")]
public async Task<IActionResult> ForSession(int sessionId)
{
var session = await _sessionRepository.GetByIdAsync(sessionId);
if (session == null)
{
return NotFound(sessionId);
}
var result = session.Ideas.Select(idea => new IdeaDTO()
{
Id = idea.Id,
Name = idea.Name,
Description = idea.Description,
DateCreated = idea.DateCreated
}).ToList();
return Ok(result);
}
[HttpPost("create")]
public async Task<IActionResult> Create([FromBody]NewIdeaModel model)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
var session = await _sessionRepository.GetByIdAsync(model.SessionId);
if (session == null)
{
return NotFound(model.SessionId);
}
var idea = new Idea()
{
DateCreated = DateTimeOffset.Now,
Description = model.Description,
Name = model.Name
};
session.AddIdea(idea);
await _sessionRepository.UpdateAsync(session);
return Ok(session);
}
İş etki alanı varlıklarını doğrudan API çağrıları aracılığıyla döndürmekten kaçının. Etki alanı varlıkları:
- Genellikle istemcinin gerektirdiğinden daha fazla veri içerir.
- Genel olarak sunulan API ile uygulamanın iç etki alanı modelini gereksiz bir şekilde yapın.
Etki alanı varlıkları ve istemciye döndürülen türler arasında eşleme gerçekleştirilebilir:
- Örnek uygulamanın kullandığı şekilde bir LINQ ile el ile
Select. Daha fazla bilgi için bkz. LINQ (dil Ile tümleşik sorgu). - Otomatik olarak bir kitaplıkla (örneğin, Automaber).
Ardından, örnek uygulama, Create fikirler denetleyicisinin ve API yöntemlerine yönelik birim testlerini gösterir ForSession .
Örnek uygulama iki test içerir ForSession . İlk test, ForSession NotFoundObjectResult geçersiz bir oturum için (http bulunamadı) döndürüp döndürmeyeceğini belirler:
[Fact]
public async Task ForSession_ReturnsHttpNotFound_ForInvalidSession()
{
// Arrange
int testSessionId = 123;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync((BrainstormSession)null);
var controller = new IdeasController(mockRepo.Object);
// Act
var result = await controller.ForSession(testSessionId);
// Assert
var notFoundObjectResult = Assert.IsType<NotFoundObjectResult>(result);
Assert.Equal(testSessionId, notFoundObjectResult.Value);
}
İkinci ForSession test, ForSession <List<IdeaDTO>> geçerli bir oturum için oturum fikirleri () listesini döndürüp döndürmeyeceğini belirler. Denetimler Ayrıca, özelliğinin doğru olduğunu onaylamak için ilk fikri de inceler Name :
[Fact]
public async Task ForSession_ReturnsIdeasForSession()
{
// Arrange
int testSessionId = 123;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(GetTestSession());
var controller = new IdeasController(mockRepo.Object);
// Act
var result = await controller.ForSession(testSessionId);
// Assert
var okResult = Assert.IsType<OkObjectResult>(result);
var returnValue = Assert.IsType<List<IdeaDTO>>(okResult.Value);
var idea = returnValue.FirstOrDefault();
Assert.Equal("One", idea.Name);
}
Geçersiz olduğunda yönteminin davranışını test etmek için Create ModelState , örnek uygulama, testin bir parçası olarak denetleyiciye bir model hatası ekler. Birim testlerinde model doğrulamayı veya model bağlamayı sınamayı denemeyin, ancak — geçersiz kılma sırasında eylem yönteminin davranışını test edin ModelState :
[Fact]
public async Task Create_ReturnsBadRequest_GivenInvalidModel()
{
// Arrange & Act
var mockRepo = new Mock<IBrainstormSessionRepository>();
var controller = new IdeasController(mockRepo.Object);
controller.ModelState.AddModelError("error", "some error");
// Act
var result = await controller.Create(model: null);
// Assert
Assert.IsType<BadRequestObjectResult>(result);
}
İkinci testi, Create döndürülen depoya bağlıdır null , bu nedenle, sahte depo döndürecek şekilde yapılandırılır null . Bir test veritabanı (bellekte veya başka türlü) oluşturmanız gerekmez ve bu sonucu döndüren bir sorgu oluşturun. Örnek kodun gösterildiği gibi, test tek bir bildirimde gerçekleştirilebilir:
[Fact]
public async Task Create_ReturnsHttpNotFound_ForInvalidSession()
{
// Arrange
int testSessionId = 123;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync((BrainstormSession)null);
var controller = new IdeasController(mockRepo.Object);
// Act
var result = await controller.Create(new NewIdeaModel());
// Assert
Assert.IsType<NotFoundObjectResult>(result);
}
Üçüncü Create test, Create_ReturnsNewlyCreatedIdeaForSession deponun UpdateAsync yönteminin çağrıldığını doğrular. , İle birlikte çağrılır Verifiable ve Verify doğrulanabilen yöntemin yürütüldüğünü onaylamak için, moclenmiş deponun yöntemi çağırılır. UpdateAsyncYöntemin — bir tümleştirme testiyle gerçekleştirilebilecek verileri kaydettiğinizden emin olmak için birim testin sorumluluğu bu değildir.
[Fact]
public async Task Create_ReturnsNewlyCreatedIdeaForSession()
{
// Arrange
int testSessionId = 123;
string testName = "test name";
string testDescription = "test description";
var testSession = GetTestSession();
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(testSession);
var controller = new IdeasController(mockRepo.Object);
var newIdea = new NewIdeaModel()
{
Description = testDescription,
Name = testName,
SessionId = testSessionId
};
mockRepo.Setup(repo => repo.UpdateAsync(testSession))
.Returns(Task.CompletedTask)
.Verifiable();
// Act
var result = await controller.Create(newIdea);
// Assert
var okResult = Assert.IsType<OkObjectResult>(result);
var returnSession = Assert.IsType<BrainstormSession>(okResult.Value);
mockRepo.Verify();
Assert.Equal(2, returnSession.Ideas.Count());
Assert.Equal(testName, returnSession.Ideas.LastOrDefault().Name);
Assert.Equal(testDescription, returnSession.Ideas.LastOrDefault().Description);
}
Test ActionResult<T>
ASP.NET Core 2,1 veya sonraki sürümlerde <T> actionresult ( ActionResult<TValue> ), belirli bir türden türetilen veya döndürülen bir tür döndürmenizi sağlar ActionResult .
Örnek uygulama, belirli bir oturum için döndüren bir yöntemi içerir List<IdeaDTO> id . Oturum id yoksa, denetleyici şunu döndürür NotFound :
[HttpGet("forsessionactionresult/{sessionId}")]
[ProducesResponseType(200)]
[ProducesResponseType(404)]
public async Task<ActionResult<List<IdeaDTO>>> ForSessionActionResult(int sessionId)
{
var session = await _sessionRepository.GetByIdAsync(sessionId);
if (session == null)
{
return NotFound(sessionId);
}
var result = session.Ideas.Select(idea => new IdeaDTO()
{
Id = idea.Id,
Name = idea.Name,
Description = idea.Description,
DateCreated = idea.DateCreated
}).ToList();
return result;
}
Denetleyicinin iki testi ForSessionActionResult uygulamasına dahil edilmiştir ApiIdeasControllerTests .
İlk test, denetleyicinin ActionResult varolmayan bir oturum için varolmayan bir fikirler listesi döndürdüğünü doğrular id :
ActionResultTürüActionResult<List<IdeaDTO>>.- , Result Bir NotFoundObjectResult .
[Fact]
public async Task ForSessionActionResult_ReturnsNotFoundObjectResultForNonexistentSession()
{
// Arrange
var mockRepo = new Mock<IBrainstormSessionRepository>();
var controller = new IdeasController(mockRepo.Object);
var nonExistentSessionId = 999;
// Act
var result = await controller.ForSessionActionResult(nonExistentSessionId);
// Assert
var actionResult = Assert.IsType<ActionResult<List<IdeaDTO>>>(result);
Assert.IsType<NotFoundObjectResult>(actionResult.Result);
}
Geçerli bir oturum için id ikinci test, yöntemin döndürdüğünü onaylar:
- Bir
ActionResulttür ileList<IdeaDTO>. - Eylem sonucu <T> . Değer bir
List<IdeaDTO>türdür. - Listedeki ilk öğe, sahte oturumda saklanan fikrle eşleşen geçerli bir fikrdir (çağırarak elde edilir
GetTestSession).
[Fact]
public async Task ForSessionActionResult_ReturnsIdeasForSession()
{
// Arrange
int testSessionId = 123;
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(GetTestSession());
var controller = new IdeasController(mockRepo.Object);
// Act
var result = await controller.ForSessionActionResult(testSessionId);
// Assert
var actionResult = Assert.IsType<ActionResult<List<IdeaDTO>>>(result);
var returnValue = Assert.IsType<List<IdeaDTO>>(actionResult.Value);
var idea = returnValue.FirstOrDefault();
Assert.Equal("One", idea.Name);
}
Örnek uygulama, belirli bir oturum için yeni bir oluşturma yöntemi de içerir Idea . Denetleyici şunu döndürür:
- BadRequest geçersiz bir model.
- NotFound oturum yoksa.
- CreatedAtAction oturum yeni fikrle güncelleştirildiği zaman.
[HttpPost("createactionresult")]
[ProducesResponseType(201)]
[ProducesResponseType(400)]
[ProducesResponseType(404)]
public async Task<ActionResult<BrainstormSession>> CreateActionResult([FromBody]NewIdeaModel model)
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState);
}
var session = await _sessionRepository.GetByIdAsync(model.SessionId);
if (session == null)
{
return NotFound(model.SessionId);
}
var idea = new Idea()
{
DateCreated = DateTimeOffset.Now,
Description = model.Description,
Name = model.Name
};
session.AddIdea(idea);
await _sessionRepository.UpdateAsync(session);
return CreatedAtAction(nameof(CreateActionResult), new { id = session.Id }, session);
}
CreateActionResult' Ye üç test dahildir ApiIdeasControllerTests .
İlk metin, bir BadRequest geçersiz model için döndürüldüğünü onaylar.
[Fact]
public async Task CreateActionResult_ReturnsBadRequest_GivenInvalidModel()
{
// Arrange & Act
var mockRepo = new Mock<IBrainstormSessionRepository>();
var controller = new IdeasController(mockRepo.Object);
controller.ModelState.AddModelError("error", "some error");
// Act
var result = await controller.CreateActionResult(model: null);
// Assert
var actionResult = Assert.IsType<ActionResult<BrainstormSession>>(result);
Assert.IsType<BadRequestObjectResult>(actionResult.Result);
}
İkinci test, NotFound oturum yoksa bir ' ın döndürülüp döndürülmediğini denetler.
[Fact]
public async Task CreateActionResult_ReturnsNotFoundObjectResultForNonexistentSession()
{
// Arrange
var nonExistentSessionId = 999;
string testName = "test name";
string testDescription = "test description";
var mockRepo = new Mock<IBrainstormSessionRepository>();
var controller = new IdeasController(mockRepo.Object);
var newIdea = new NewIdeaModel()
{
Description = testDescription,
Name = testName,
SessionId = nonExistentSessionId
};
// Act
var result = await controller.CreateActionResult(newIdea);
// Assert
var actionResult = Assert.IsType<ActionResult<BrainstormSession>>(result);
Assert.IsType<NotFoundObjectResult>(actionResult.Result);
}
Geçerli bir oturum için id son test şunları onaylar:
- yöntemi,
ActionResulttürüyle birBrainstormSessiondöndürür. - ActionResult <T> . Sonuç bir CreatedAtActionResult 'dır.
CreatedAtActionResult, üst bilgisi olan 201 Oluşturuldu yanıtınaLocationbenzer. - ActionResult <T> . Değer bir
BrainstormSessiontür. - oturum güncelleştirmeye yapılan sahte çağrı
UpdateAsync(testSession)çağrıldı. YöntemVerifiableçağrısı onaylarda yürüterekmockRepo.Verify()denetlenir. - Oturum
Ideaiçin iki nesne döndürülür. - Son öğe
Idea(sahte çağrısı tarafından eklenenUpdateAsyncöğe)newIdeatestte oturuma eklenen öğeyle eştir.
[Fact]
public async Task CreateActionResult_ReturnsNewlyCreatedIdeaForSession()
{
// Arrange
int testSessionId = 123;
string testName = "test name";
string testDescription = "test description";
var testSession = GetTestSession();
var mockRepo = new Mock<IBrainstormSessionRepository>();
mockRepo.Setup(repo => repo.GetByIdAsync(testSessionId))
.ReturnsAsync(testSession);
var controller = new IdeasController(mockRepo.Object);
var newIdea = new NewIdeaModel()
{
Description = testDescription,
Name = testName,
SessionId = testSessionId
};
mockRepo.Setup(repo => repo.UpdateAsync(testSession))
.Returns(Task.CompletedTask)
.Verifiable();
// Act
var result = await controller.CreateActionResult(newIdea);
// Assert
var actionResult = Assert.IsType<ActionResult<BrainstormSession>>(result);
var createdAtActionResult = Assert.IsType<CreatedAtActionResult>(actionResult.Result);
var returnValue = Assert.IsType<BrainstormSession>(createdAtActionResult.Value);
mockRepo.Verify();
Assert.Equal(2, returnValue.Ideas.Count());
Assert.Equal(testName, returnValue.Ideas.LastOrDefault().Name);
Assert.Equal(testDescription, returnValue.Ideas.LastOrDefault().Description);
}
Ek kaynaklar
- ASP.NET Core tümleştirme testleri
- Visual Studio ile birim testleri oluşturma ve çalıştırma
- MyTested.AspNetCore.Mvc - Fluent MVCiçin ASP.NET Core Test Kitaplığı: MVC ve web API'si uygulamalarını test etmek için akıcı bir arabirim sağlayan türü kesin olarak türü kesin olan birim testi kitaplığı. (Microsoft tarafından sağlanmaz veya desteklanmaz.)
- JustMockLite:.NET geliştiricileri için sahte bir çerçeve. (Microsoft tarafından sağlanmaz veya desteklanmaz.)