![Page 1: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/1.jpg)
Unit Testing in .NET
![Page 2: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/2.jpg)
Philosophy of Unit Testing
• What?
• Where?
• Why?
• How?
• What it is not?
![Page 3: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/3.jpg)
• Test individual components (units)
• in isolation
• to confirm preexisting specification.
• Inputs … -> expected results
• Test functions, methods.
• Use a framework to make it easier (xUnit or ?Unit)
isolate and validate
verify
![Page 4: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/4.jpg)
• Write tests after creating specification, but before implementing methods.
• Best if written by the developer or the development team. Why?
• Test-driven development
• Supports regression testing
![Page 5: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/5.jpg)
The Art of Unit Testing, by R Osherov
![Page 6: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/6.jpg)
![Page 7: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/7.jpg)
Assertions
http://junit.sourceforge.net/javadoc/org/junit/Assert.html
JUnit
assertEquals() assertFalse() assertNotNull() assertNotSame() assertNull() assertSame() …
By the way, you should use assertions in everyday programming
Java: assert i > 0; C#: Debug.Assert( i > 0 ); Python: assert i > 0
![Page 8: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/8.jpg)
Unit Assertions
Classic ModelAssert.isEmpty() Assert.areEqual() Assert.Null() Assert.notNull() …
https://github.com/nunit/docs/wiki/Classic-Modelhttps://github.com/nunit/docs/wiki/Constraint-Model
![Page 9: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/9.jpg)
Good Habits• Try to make tests independent or orthogonal to other tests
• Test only one code unit at a time
• Don’t name your tests: test0, test1, …
• Use setup and teardown to create a clean environment for each test
• Don’t have unit tests access your database — use fake data (write a “mock” object that meets the same interface) ==> break dependencies
• Refactor to make your code more testable
• Discover a flaw at the component level? Write unit tests first to expose it (reproduce it). Then fix the error.
• Run tests prior to committing (or merging) your code
![Page 10: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/10.jpg)
Start Simple• Test methods with no dependencies
• Make sure constructor doesn’t have dependencies
input Method output
![Page 11: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/11.jpg)
Find something to test
public ActionResult ChangeLoginName(string oldName, string newName) { User user = repository.FetchByLoginName(oldName); user.LoginName = newName; repository.SubmitChanges(); // render some view to show the result return View(); }
![Page 12: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/12.jpg)
Arrange — Act — Assert• Arrange
Set up for the test. Configure the system one way or another. Must be able to do this.
• Act
Execute or invoke something, with some input, to obtain some output. Must be able to do this.
• Assert
Usually the easy part.
![Page 13: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/13.jpg)
Run Tests: Test -> Run -> All Tests
![Page 14: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/14.jpg)
Unit Testing Demo
![Page 15: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/15.jpg)
Harder
input
Function
output
Database
Internet
![Page 16: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/16.jpg)
Not Unit Testable
![Page 17: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/17.jpg)
Why Not?
• “Uncontrolled” dependencies
• All or most functionality in 1 method, with no separation and no “control” over it
• Code is doing more than 1 thing
![Page 18: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/18.jpg)
SOLID• Single responsibility principle
a class (module, method or function) should do one thing and one thing only
• Open/closed principle
• Liskov substitution principle it should be possible to substitute in fakes, stubs or mocks without fundamentally changing anything
• Interface segregation principle create segregation of responsibilities and become agnostic of implementors by replacing concrete classes with interfaces (having the minimum of functionality required)
• Dependency inversion principle (and Inversion of Control) invert the “high-level module depends on low-level module” pattern. Break direct dependencies by using dependency injection pattern and providers.
https://en.wikipedia.org/wiki/SOLID_(object-oriented_design)
![Page 19: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/19.jpg)
The Art of Unit Testing, by R Osherov
![Page 20: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/20.jpg)
![Page 21: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/21.jpg)
![Page 22: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/22.jpg)
![Page 23: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/23.jpg)
![Page 24: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/24.jpg)
![Page 25: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/25.jpg)
Problem?
Just a stub for now
![Page 26: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/26.jpg)
One Solution: inject via
constructor
will be other logic here, i.e. test the name not just the extension
![Page 27: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/27.jpg)
![Page 28: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/28.jpg)
![Page 29: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/29.jpg)
• Up Next …
• Testing code that reads/writes to a database
• Use a “mocking framework” to make it easier, i.e.
• Moq: https://github.com/Moq/moq4
• Use [SetUp] and [TearDown] to seed your mock object
![Page 30: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/30.jpg)
Controller
DbContext
EntityFramework
Database
Default Setup
![Page 31: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/31.jpg)
Controller
DbContext
EntityFramework
Database
Using Repository Pattern
ActualRepoForTestingRepo
ISomethingRepository
An interface
![Page 32: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/32.jpg)
Need to modify to allow constructor
injection
![Page 33: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/33.jpg)
Inject mock object
![Page 34: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/34.jpg)
Sports Store Example from
Entity - Single table
![Page 35: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/35.jpg)
Break dependency with Repository pattern
![Page 36: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/36.jpg)
pagination
constructor injection
![Page 37: Unit Testing in - wou.edumorganb/lecture/SP19UnitTesting.pdf · •Test individual components (units) • in isolation • to confirm preexisting specification. • Inputs … ->](https://reader035.vdocuments.mx/reader035/viewer/2022070616/5d4876c188c993fc4f8bd3d5/html5/thumbnails/37.jpg)
Unit Test Pagination