Top Banner
Matthew Butt Unit Testing the Hard Stuff matthewbutt.com @bnathyuw
67

Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Mar 15, 2020

Download

Documents

dariahiddleston
Welcome message from author
This document is posted to help you gain knowledge. Please leave a comment to let me know what you think about it! Share it to your friends and learn new things together.
Transcript
Page 1: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Matthew Butt

Unit Testing the Hard Stuffmatthewbutt.com @bnathyuw

Page 2: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

NB

There will be codeIt will be C#I will explain it

Page 3: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Axiom:

Unit Tests are Importantfeedback for delivering quality software

Page 4: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

SpeedControl

Precision

Page 5: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Observation:

Some projects have no Unit Tests

Page 6: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Why?

Page 7: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Why?not Designed for Test

few Techniquesfew Tools

not even many Workarounds

Page 8: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Unit Testingthe Easy Stuff

Page 9: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Designed for TestTools

Techniquesor at least Workarounds

Page 10: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

.NET Web API

Page 11: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

[Whiteboard]

Page 12: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Designed for Test

Directly ExecutableObject OrientedAbstractionsDI

Page 13: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Techniques

SOLID designMockingArchitecture Patterns

(MVC, ports & adapters, hexagonal…)

Page 14: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Tools

NUnit… test framework

NSubstitute…mocking framework

OWIN… in-memory host

Page 15: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Workarounds

Adaptersaround leaky abstractions

Mock Clockand other system dependencies

Page 16: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Speed Run locallyControl Test doubles

Precision Class levelClear purpose

Page 17: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Outside-in approach

Acceptance test outer loop

Unit test inner loop

Page 18: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Acceptance Test

In-Memory HostStub Externals

Page 19: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Controller Test

In-Memory HostTreat as adapter

Mock DependenciesTest interactions

Keep it thinNo domain logic

Page 20: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Domain Object Tests

State or Interaction?State: stubs

Interaction: mocks

Single ResponsibilityListen to your tests!

Page 21: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

External dependencies

AbstractionsInterfaces in Domain

Integration testsNo test if trivial

Clock

Page 22: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

namespace EasyStuff.Api.Domain {public interface IClock {

DateTime Now { get; }}

}

namespace EasyStuff.Api.Adapters {public class SystemClock : IClock {

public DateTime Now => DateTime.UtcNow;}

}

var knownDate = new DateTime(2001, 2, 3);var clock = Substitute.For<IClock>();clock.Now.Returns(knownDate);

Page 23: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Unit Testingthe Hard Stuff

Page 24: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Microsoft AzureData Lake Analytics

Page 25: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Financial TransactionsWeather Data

Page 26: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

AberporthLocation: 224100E 252100N, Lat 52.139 Lon -4.570, 133 metres amslEstimated data is marked with a * after the value.Missing data (more than 2 days missing in month) is marked by ---.Sunshine data taken from an automatic Kipp & Zonen sensor marked with a #, otherwise sunshine data taken from a Campbell Stokes recorder. yyyy mm tmax tmin af rain sun degC degC days mm hours 1970 1 7.5 3.1 7 97.5 40.2 1970 2 6.2 1.9 7 79.2 96.2 1970 3 6.6 2.0 8 76.1 101.2 1970 4 8.8 4.2 2 67.0 135.2 1970 5 14.5 8.5 0 28.1 148.9 1970 6 18.5 11.5 0 47.3 206.5 1970 7 16.6 11.3 0 57.4 150.3 1970 8 17.8 12.3 0 42.6 151.8 1970 9 16.8 11.5 0 49.4 120.4 1970 10 13.3 8.6 0 108.3 75.4 1970 11 10.8 6.4 0 181.4 41.7 1970 12 7.5 3.3 6 42.9 69.4 etc. etc. etc.

aberporthdata.txt

Page 27: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

ExtractTransform

Load

Page 28: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

[Whiteboard]

Page 29: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Not Designed for Test

Hosted in CloudNot Directly ExecutableHybrid CodeClosely Coupled

Page 30: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Few Tools

A library from MSabstractions too leaky

Local Test Runnerthis is useful

Page 31: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Few techniques

SQL unit testsfairly gruesome

Page 32: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Few workarounds

Google doesn’t help

Page 33: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Outside-in approach

Acceptance test outer loop

Unit test inner loop

Page 34: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Acceptance Test

Local Run Helper

Page 35: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 36: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 37: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

U-SQL Script TestHybrid code

U-SQL & C#

Data on file system

Page 38: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 39: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Responsibility of Script

Orchestrator or

Query

Page 40: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Seam U-SQL // C#

Inline code Nope!

Code-behindNah…

AssembliesNow you’re talking!

Page 41: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Substitute AssembliesCode is compiled for each execution

Duck typing

Substitute at runtime

Page 42: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 43: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 44: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 45: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Stub or Mock?Not directly availableFakes against file system

Page 46: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 47: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 48: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

User-Defined Objects

Page 49: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 50: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Leaky Abstraction

Use of StreamsTemporal CouplingStrange Idiom>1 Responsibility

Page 51: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 52: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Adapter layerTranslate between framework & domain

Page 53: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 54: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 55: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 56: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 57: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 58: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 59: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Domain Tests

Familiar Territory

Page 60: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 61: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit
Page 62: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

You may still need to Mock the Clock!

Page 63: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

What have we learnt?

Page 64: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Speed Run locallyControl Seams

Test doublesPrecision Small pieces

Clear purposeAdapters

Page 65: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

PatternsPatterns

Patterns

Page 66: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

ResourcesTesting Patterns github.com/bnathyuw/testing-patterns/wiki

Example implementation github.com/bnathyuw/weather-data-iii

Page 67: Matthew Butt Unit Testing the Hard Stuff · .NET Web API [Whiteboard] Designed for Test Directly Executable Object Oriented Abstractions DI. Techniques SOLID design Mocking ... Unit

Dank je wel!