Reputation: 121
I'm mocking SQLConnection for my derived class tests and noticed that it seems to make XUnit(?) ignore the results.
Example to reproduce behavior:
using System.Data.SqlClient;
using System.Threading.Tasks;
using Telerik.JustMock;
using Xunit;
namespace JustMockTesting {
public abstract class BaseClass {
protected abstract Task<int> ConnectTask();
}
public class Derived1 : BaseClass {
protected override Task<int> ConnectTask() {
return Task.FromResult( 1 );
}
}
public class Derived2 : BaseClass {
protected override Task<int> ConnectTask() {
return Task.FromResult( 2 );
}
}
public class Derived1Tests {
private Derived1 derived1;
public Derived1Tests() {
derived1 = Mock.Create<Derived1>();
}
[Fact]
public void Test1() {
Mock.NonPublic.Arrange( derived1, "ConnectTask" ).CallOriginal();
Mock.Arrange( () => Mock.Create<SqlConnection>().Open() ).DoNothing();
Task<int> i = (Task<int>)new PrivateAccessor( derived1 ).CallMethod( "ConnectTask" );
Assert.Equal( 1, i.Result );
}
}
public class Derived2Tests {
private Derived2 derived2;
public Derived2Tests() {
derived2 = Mock.Create<Derived2>();
}
[Fact]
public void Test2() {
Mock.NonPublic.Arrange( derived2, "ConnectTask" ).CallOriginal();
//Mock.Arrange( () => Mock.Create<SqlConnection>().Open() ).DoNothing();
Task<int> i = (Task<int>)new PrivateAccessor( derived2 ).CallMethod( "ConnectTask" );
Assert.Equal( 2, i.Result );
}
}
}
Environment
Findings
int
instead of Task<int>
.The following exception will get thrown sometimes (rest of the trace omitted to keep the post short):
System.ArgumentException : 'this' type cannot be an interface itself.
Stack Trace:
at System.RuntimeTypeHandle.VerifyInterfaceIsImplemented(RuntimeTypeHandle handle, RuntimeTypeHandle interfaceHandle)
at System.RuntimeTypeHandle.VerifyInterfaceIsImplemented(RuntimeTypeHandle interfaceHandle)
Not sure if this is an issue with JustMock or XUnit. Googling hasn't provided much info so any insight would be appreciated.
Update 1 - Example based on @Nkosi's Comments:
public abstract class BaseClass {
protected abstract Task<bool> ConnectTask();
}
public class Derived1 : BaseClass {
protected async override Task<bool> ConnectTask() {
return await Task.FromResult( true );
}
}
public class Derived2 : BaseClass {
protected async override Task<bool> ConnectTask() {
using ( SqlConnection conn = new SqlConnection( "someConnectionString" ) ) {
try {
conn.Open();
return await Task.FromResult( true );
} catch {
return await Task.FromResult( false );
}
}
}
}
public class Derived1Tests {
private Derived1 derived1;
public Derived1Tests() {
derived1 = Mock.Create<Derived1>();
}
[Fact]
public async Task Test1() {
Mock.NonPublic.Arrange( derived1, "ConnectTask" ).CallOriginal();
//SqlConnection mockSqlConnection = Mock.Create<SqlConnection>();
//Mock.Arrange( () => mockSqlConnection.Open() ).DoNothing();
//Mock.Arrange( () => mockSqlConnection.Close() ).DoNothing();
//Mock.Arrange( () => new SqlConnection( Arg.IsAny<string>() ) ).Returns( mockSqlConnection );
bool b = await (Task<bool>)new PrivateAccessor( derived1 ).CallMethod( "ConnectTask" );
Assert.True( b );
}
}
public class Derived2Tests {
private Derived2 derived2;
public Derived2Tests() {
derived2 = Mock.Create<Derived2>();
}
[Fact]
public async Task Test2() {
Mock.NonPublic.Arrange( derived2, "ConnectTask" ).CallOriginal();
SqlConnection mockSqlConnection = Mock.Create<SqlConnection>();
Mock.Arrange( () => mockSqlConnection.Open() ).DoNothing();
Mock.Arrange( () => mockSqlConnection.Close() ).DoNothing();
Mock.Arrange( () => new SqlConnection( Arg.IsAny<string>() ) ).Returns( mockSqlConnection );
bool b = await (Task<bool>)new PrivateAccessor( derived2 ).CallMethod( "ConnectTask" );
Assert.True( b );
}
}
Findings
Upvotes: 1
Views: 449