New to Telerik JustMock? Download free 30-day trial

Mock Non-Abstract and Non-Virtual Classes or Members

The advanced features supported in Telerik® JustMock enables you to mock any class or member, including non-virtual and non-abstract implementations. The mocking of non-abstract classes is also available in the free edition but it only supports mocking a concrete class with virtual methods. The commercial version also includes mocking of non-abstract and non-virtual members of classes.

The commercial edition allows you to mock concrete objects without having to change anything in their interface.

This is an elevated feature. Refer to this topic to learn more about the differences between the commercial and the free versions of Telerik JustMock.

Here is the example class we are going to use:

Sample setup

public class Customer 
{ 
    public Customer() 
    { 
        throw new NotImplementedException("Constructor"); 
    } 
    public string Name { get; set; } 
 
    public int GetNumberOfOrders() 
    { 
        throw new NotImplementedException(); 
    } 
    public int GetNumberOfOrders(bool includeCompleted) 
    { 
        throw new NotImplementedException(); 
    } 
 
    public void AddOrder(string productName) 
    { 
        throw new NotImplementedException(); 
    } 
 
    public delegate void OrderAddedEventHandler(bool added); 
    public event OrderAddedEventHandler OnOrderAddedCallback; 
} 
Public Class Customer 
    Public Sub New() 
        Throw New NotImplementedException("Constructor") 
    End Sub 
 
    Public Property Name As String 
 
    Public Function GetNumberOfOrders() As Integer 
        Throw New NotImplementedException() 
    End Function 
 
    Public Function GetNumberOfOrders(ByVal includeCompleted As Boolean) As Integer 
        Throw New NotImplementedException() 
    End Function 
 
    Public Sub AddOrder(ByVal productName As String) 
        Throw New NotImplementedException() 
    End Sub 
 
    Public Delegate Sub OrderAddedEventHandler(ByVal added As Boolean) 
    Public Event OnOrderAddedCallback As OrderAddedEventHandler 
End Class 

Important

To use this kind of object mocking, you first need to go to elevated mode by enabling Telerik JustMock from the menu. Learn how to do that in the How to Enable/Disable Telerik JustMock topic.

Arrange Property

You can arrange the property get and set even when the property is not marked as abstract or virtual.

Example 1: Mock concrete implementation of property getter

[TestMethod] 
public void ShouldSetupACallToAFinalProperty() 
{ 
    // Arrange  
    var customerMock = Mock.Create<Customer>(); 
    Mock.Arrange(() => customerMock.Name).Returns("TestName"); 
 
    // Act  
    var actual = string.Empty; 
    actual = customerMock.Name; 
 
    // Assert  
    Assert.AreEqual("TestName", actual); 
} 
<TestMethod> 
Public Sub ShouldSetupACallToAFinalProperty() 
    ' Arrange 
    Dim customerMock = Mock.Create(Of Customer)() 
    Mock.Arrange(Function() customerMock.Name).Returns("TestName") 
 
    ' Act 
    Dim actual = String.Empty 
    actual = customerMock.Name 
 
    ' Assert 
    Assert.AreEqual("TestName", actual) 
End Sub 

Example 2 defines that setting the final customerMock.Name property to any string value other than "TestName" will cause an exception of type StrictMockException to be thrown.

If you would like to learn more about mocking properties, check the Mock Properties help topic.

Example 2: Mock concrete implementation of property setter

[TestMethod] 
[ExpectedException(typeof(StrictMockException))] 
public void ShouldAssertPropertySet() 
{ 
    // Arrange  
    var customerMock = Mock.Create<Customer>(Behavior.Strict); 
    Mock.ArrangeSet(() => customerMock.Name = "TestName"); 
 
    // Act  
    customerMock.Name = "Sample"; 
} 
<TestMethod> 
<ExpectedException(GetType(StrictMockException))> 
Public Sub ShouldAssertPropertySet() 
    ' Arrange 
    Dim customerMock = Mock.Create(Of Customer)(Behavior.Strict) 
    Mock.ArrangeSet(Function() customerMock.Name = "TestName") 
 
    ' Act 
    customerMock.Name = "Sample" 
End Sub 

Arrange Method

Note that here we are going to mock an instance of the Customer class in the same way as we would do that for non-abstract classes whose members are declared as virtual.

Example 3: Mock concrete implementation of class and its members

[TestMethod] 
[ExpectedException(typeof(NotImplementedException))] 
public void ShouldCallOriginalForNonVirtualExactlyOnce() 
{ 
    // Arrange 
    // Create a mock of the object 
    var customerMock = Mock.Create<Customer>(); 
    // Arrange your expectations 
    Mock.Arrange(() => customerMock.GetNumberOfOrders()).CallOriginal().OccursOnce(); 
 
    //Act 
    customerMock.GetNumberOfOrders(); 
 
    //Assert 
    Mock.Assert(customerMock); 
} 
<TestMethod> 
<ExpectedException(GetType(NotImplementedException))> 
Public Sub ShouldCallOriginalForNonVirtualExactlyOnce() 
    ' Arrange 
    ' Create a mock of the object 
    Dim customerMock = Mock.Create(Of Customer)() 
    ' Arrange your expectations 
    Mock.Arrange(Function() customerMock.GetNumberOfOrders()).CallOriginal().OccursOnce() 
 
    ' Act 
    customerMock.GetNumberOfOrders() 
 
    ' Assert 
    Mock.Assert(customerMock) 
End Sub 

Generic methods and classes can also be mocked. Check the Generics topic for more details on that functionality.

Arrange Method Overloads

The following example shows how to mock different overloads of the concrete implementation of a method. Customer.GetNumberOfOrders has two overloads - one without arguments and one with a boolean argument. Here we mock them both by Returns. In the first case, we return just the argument that has been passed. In the second case we return the sum of the two integer values. After that, we act by calling both overloads and assert what we have arranged.

Example 4: Mock concrete implementation of methods with overloads

[TestMethod] 
public void ShouldAssertOnMethodOverload() 
{ 
    // Arrange  
    var customerMock = Mock.Create<Customer>(); 
 
    Mock.Arrange(() => customerMock.GetNumberOfOrders()).Returns(30); 
    Mock.Arrange(() => customerMock.GetNumberOfOrders(Arg.Is(true))).Returns(10); 
 
    // Assert  
    Assert.AreEqual(customerMock.GetNumberOfOrders(), 30); 
    Assert.AreEqual(customerMock.GetNumberOfOrders(true), 10); 
} 
<TestMethod> 
Public Sub ShouldAssertOnMethodOverload() 
    ' Arrange 
    Dim customerMock = Mock.Create(Of Customer)() 
    Mock.Arrange(Function() customerMock.GetNumberOfOrders()).Returns(30) 
    Mock.Arrange(Function() customerMock.GetNumberOfOrders(Arg.Is)).Returns(10) 
 
    ' Assert 
    Assert.AreEqual(customerMock.GetNumberOfOrders(), 30) 
    Assert.AreEqual(customerMock.GetNumberOfOrders(True), 10) 
End Sub 

Arrange Method Callbacks

In this sections, you will find how to use the Raises method to fire a callback and pass event arguments once a final method is called.

Example 5: Fire callback and pass event arguments when non-virtual method is called

[TestMethod] 
public void ShouldAssertOnMethodCallbacks() 
{ 
    // Arrange  
    var customerMock = Mock.Create<Customer>(); 
 
    Mock.Arrange(() => customerMock.AddOrder(Arg.IsAny<string>())).Raises(() => customerMock.OnOrderAddedCallback += null, true); 
 
    bool called = false; 
 
    customerMock.OnOrderAddedCallback += delegate (bool added) 
    { 
        called = added; 
    }; 
 
    // Act  
    customerMock.AddOrder("test"); 
 
    // Assert  
    Assert.IsTrue(called); 
} 
<TestMethod> 
Public Sub ShouldAssertOnMethodCallbacks() 
    ' Arrange 
    Dim customerMock = Mock.Create(Of Customer)() 
    Mock.Arrange(Function() customerMock.AddOrder(Arg.IsAny(Of String)())).Raises(Sub() AddHandler customerMock.OnOrderAddedCallback, Nothing, True) 
    Dim called As Boolean = False 
    AddHandler customerMock.OnOrderAddedCallback, Sub(added As Boolean) called = added  
 
    ' Act 
    customerMock.AddOrder("test") 
 
    ' Assert 
    Assert.IsTrue(called) 
End Sub 

More information on raising mocked events is available in the Basic Usage | Raise topic.

See Also

In this article