如何模拟一个带有final方法的类?

6

假设我有一个A类,其中包含

class A {
  final String foo() {
    // .. computing result, contacting database, whatever ..
    return "some computed value";
  }
  // ... and a bazillion other methods, some of them final.
}

现在我有一个B类,其中包含以下内容:
class B {
  String methodIWantToTest(A a) {
      String output = a.foo();
      // ... whatever this method does, e.g.:
      output += "_suffix";
      return output;
  }
}

我该如何对这个方法进行单元测试呢?foo()方法被声明为final是因为我们不希望继承A类的子类改变其功能。但是,为了真正地对该方法进行单元测试,我不想让它执行实际的A.foo()方法。
是否有一种方法,例如删除final关键字并添加一个类似于@finalUnlessTest的注解?您会推荐什么?将A重构为接口可能非常困难,因为它是我们中心类之一,而且遗憾的是和其他部分紧密耦合。
编辑#1:抱歉,忘了提到我们使用的是Java。我们还没有使用模拟框架。
答案:好的,那么:哇。 JMockit 真是太棒了,在我的眼里,它是测试遗留代码的杀手级应用程序。在我的情况下,特别有用。非常感谢!您基本上可以像以下示例一样操作伪代码:
class AMock {
   final String foo() {
     return "myTestValue";
   }
}
class Test extends TestCase {
   A mockedA;
   B b;
   protected void setUp() {
      Mockit.redefineMethods( A.class, AMock.class );  // this "pipes" all mocked methods from A to AMock
      mockedA = new A();    // NOT new AMock()!!!
      b = new B();
   }
   public void testB() {
      assertEquals("myTestValue",mockedA.foo());
      assertEquals("myTestValue_suffix",b.methodIWantToTest(mockedA));
   }
}

这真是酷毙了,不是吗?


从大写字母看,这一定是Java。 - jop
你能告诉我们你使用的是什么语言(看起来像Java)吗?有些答案可能与语言相关,请告诉我们你使用的是哪个Mocking框架。 - Jean
3个回答

6
您可以尝试使用 JMockit 模拟库。

0
我会移除 "final",并在注释中写上 "不要重写这个方法!!"。如果你不能相信同事遵循简单的指示,那也没什么希望了。

除了我们不仅仅是在谈论同事,因为客户可以使用我们的API... - Epaga

0
以下代码也能帮助您实现它。我并不是说这是最佳实践,但这是匿名类的一个有趣应用(滥用?)。
public class Jobber {

    public final String foo() {
        return fooFactory() ;
    }

    String fooFactory() {
        return "jobber" ;
    }


    public static void main(String[] args) {

        Jobber jobber = new Jobber() { String fooFactory() { return "prefix " + super.fooFactory() ;} } ;

        System.out.println(jobber.foo() );
    }
}

mmmn. 看起来没有给出理由就打分有点严厉。我想我不应该把这些事情当作个人问题。这里有一篇有趣的文章讨论了测试对象的策略... http://www.ibm.com/developerworks/library/j-mocktest.html - David Turner

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接