You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为何Mock中配置的Protected方法未返回预期值?

问题原因及解决方案

核心问题

你mock的是IMockTarget接口的MyProtectedGetIntMethod方法,但被测类ClassToTest的GetPrefixedValue方法里,调用的是自身类的MyProtectedGetIntMethod,而非传入的provider(mock对象)的同名方法。这就是为什么你设置的返回值1不生效,实际返回的是ClassToTest自身方法的99。

修复方案

根据测试预期,有两种常见修复方式:

方案1:调整接口方法访问级别(推荐)

把IMockTarget里的MyProtectedGetIntMethod改为public,这样可以直接调用传入对象的方法:

public interface IMockTarget
{
    string PropertyToMock { get; }
    int MyProtectedGetIntMethod(); // 修改为public
}

public class ClassToTest
{
    public string GetPrefixedValue(IMockTarget provider)
    {
        var x = provider.MyProtectedGetIntMethod(); // 调用provider的方法
        return $"Prefixed:{provider.PropertyToMock}{x}";
    }

    protected int MyProtectedGetIntMethod() { return 99; }
}

测试代码无需修改,此时mock的返回值1会正常生效,测试可通过。

方案2:通过反射调用接口的protected方法

如果必须保持接口方法为protected,可以在ClassToTest里用反射调用传入对象的方法:

public class ClassToTest
{
    public string GetPrefixedValue(IMockTarget provider)
    {
        // 反射调用IMockTarget的protected方法
        var method = typeof(IMockTarget).GetMethod("MyProtectedGetIntMethod", 
            System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic);
        var x = (int)method.Invoke(provider, null);
        return $"Prefixed:{provider.PropertyToMock}{x}";
    }

    protected int MyProtectedGetIntMethod() { return 99; }
}

测试代码保持不变,同样能正确调用到mock的方法并返回1。

额外场景:mock被测类自身的保护方法

如果你的测试意图是替换ClassToTest自身的MyProtectedGetIntMethod返回值,那应该mockClassToTest类而非IMockTarget接口,示例代码如下:

[TestMethod]
public void TestMethod2()
{
    // mock ClassToTest类,CallBase确保其他方法正常执行
    var mockSut = new Mock<ClassToTest> { CallBase = true };
    mockSut.Protected()
           .Setup<int>("MyProtectedGetIntMethod")
           .Returns(1);

    var mockTarget = new Mock<IMockTarget>();
    mockTarget.SetupGet(x => x.PropertyToMock).Returns("FixedValue");

    var actualValue = mockSut.Object.GetPrefixedValue(mockTarget.Object);

    Assert.AreEqual("Prefixed:FixedValue1", actualValue);
}

内容的提问来源于stack exchange,提问作者Rod

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.03 14:22:57