Faking All Instances of a Non-Visible Type

Faking all instances of the same type sets the same behavior on all past and future instances of that type. The same method used for faking all future instances also fakes instances that were previously created, even before the test ran (for example, in the test class setup method). You can use this capability to fake singletons.

When to Use

When you want to fake all objects of a specific hidden type.

Syntax

C#

var handle = Isolate.Fake.AllInstances(type);

VB

Dim handle = Isolate.Fake.AllInstances(type)

By default, constructors are faked on future objects. To change this behavior, use the overloaded versions of Isolate.NonPublic.Fake.Instance() or Isolate.NonPublic.Fake.AllInstances().

Resulting Fake in the test will have type 'object'. For setting behavior on it use Isolate.NonPublic API or by casting to visible base class if this is permissible.

Samples

Sample: Faking All Instances of the Same Type

The following sample shows how to fake all instances of the same hidden type.

C#

[TestMethod, Isolated]
public void FakingAllInstanceOfNotVisibleType()
{
  //Arrange
  var internalType = typeof(VisibleType).Assembly.GetType("ThirdPartyProject.NotVisibleTypeToFake");
  Isolate.NonPublic.Fake.AllInstances(internalType);
  
  //Act
  var result = new VisibleType().Calculate(0.5);
  
  //Assert
  Assert.AreEqual(0.25, result);
}

public class VisibleType
{
  private NotVisibleTypeToFake internalField = new NotVisibleTypeToFake();
  
  public double Calculate(double i)
  {
    internalField.Check();

    return i * i;
  } 
}

internal class NotVisibleTypeToFake
{
  public void Check()
  {
    throw new Exception("No Entry");
  }
}

VB

<TestMethod(), Isolated()> _
Public Sub FakingAllInstanceOfNotVisibleType()
  'Arrange
  Dim internalType = GetType(VisibleType).Assembly.GetType("ThirdPartyProject.NotVisibleTypeToFake")
  Isolate.NonPublic.Fake.AllInstances(internalType)
  
  'Act
  Dim result = New VisibleType().Calculate(0.5)
  
  'Assert
  Assert.AreEqual(0.25, result)
End Sub

Public Class VisibleType
  Private internalField As NotVisibleTypeToFake = New NotVisibleTypeToFake()
  
  Public Function Calculate(i As Double) As Double
    internalField.Check()
    Return i * i
  End Function
End Class

Friend Class NotVisibleTypeToFake
  Public Sub Check()
    Throw New Exception("No Entry")
  End Sub
End Class

Sample 2: Faking Singletons

The following sample shows how to replace the singleton object with a fake object that has a specific behavior, even if the Singleton type is not visible.

Isolate.Fake.NextInstance() fakes has precedence over Isolate.Fake.AllInstances().

C#

[TestMethod, Isolated]
public void FakingAllInstanceOfNotVisibleType_Singletons()
{
  // Here we are setting the same behavior on all instances.
  // The behavior we set on fake will apply to past instance as well
  var internalType = typeof(VisibleType).Assembly.GetType("ThirdPartyProject.InternalSingleton");
  var handle = Isolate.NonPublic.Fake.AllInstances(internalType);
  Isolate.NonPublic.WhenCalled(handle, "ReturnZero").WillReturn(10);

  //Act
  var result = new VisibleType().CalculateWithSingleton(1);
  
  // Assert
  Assert.AreEqual(11, result);
}

public class VisibleType
{
  public long CalculateWithSingleton(long i)
  {
    return InternalSingleton.ReturnZero() + i;
  }
}

internal class InternalSingleton
{
  private InternalSingleton() { }
  static readonly InternalSingleton instance = new InternalSingleton();

  public static InternalSingleton Instance { get { return instance; } }

  public int ReturnZero()
  {
    return 0;
  }
}

VB

<TestMethod(), Isolated()> _
Public Sub FakeSingletonExample()
  
  ' Here we are setting the same behavior on all instances.
  ' The behavior we set on fake will apply to past instance as well
  Dim internalType = GetType(VisibleType).Assembly.GetType("ThirdPartyProject.ThirdPartyProject.InternalSingleton")
  Dim handle = Isolate.NonPublic.Fake.AllInstances(internalType)
  Isolate.NonPublic.WhenCalled(handle, "ReturnZero").WillReturn(10)
  
  'Act
  Dim result = New VisibleType().CalculateWithSingleton(1)

  ' Assert
  Assert.AreEqual(Of Long)(11, result)
End Sub
 
Public Class VisibleType
  Public Function CalculateWithSingleton(i As Long) As Long
    Return InternalSingleton.Instance.ReturnZero + i
  End Function
End Class 
 
Friend Class InternalSingleton 
  Private Sub New()
  End Sub
 
  Shared ReadOnly m_instance As New InternalSingleton()
 
  Public Shared ReadOnly Property Instance() As InternalSingleton
    Get
      Return m_instance
    End Get
  End Property
 
  Public Function ReturnZero() As Integer
    Return 0
  End Function
End Class

Verifying is done on the instance returned from Isolate.Fake.NextInstance.

Use Isolate.Verify.GetInstancesOf to get the future instances, this can be used for Argument Validations and field Assertions.

See another example of Faking Singleton with HttpContext here.