替换实例化类的实现而不触及代码(java) [英] Replace implementation of instantiated class without touching the code (java)

查看:133
本文介绍了替换实例化类的实现而不触及代码(java)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有遗产代码我不想碰。

I have legacy code I don't want to touch.

public class LegacyCode{
    public LegacyCode() {
        Service s = new ClassA();
        s.getMessage();
    }
}

其中 ClassA 提供CORBA服务电话。

Where ClassA provides a CORBA service call.

public class ClassA implements Service{
    @Override
    public String getMessage() {
       // Make CORBA service call...
       return "Class A";
    }
}

接口服务看起来像;

public interface Service {
    String getMessage();
}

出于测试目的,我想替换服务(在 LegacyCode ClassA 实施>),带有存根。

For test purposes, I want to replace the implementation of Service (in LegacyCode implemented by ClassA) with a stub.

public class ClassB implements Service {
    @Override
    public String getMessage() {
        return "Stub Class B";
    }
}

到目前为止一切顺利。但是,在显示的遗留代码中没有任何修改就可以在<$的实例化时加载 ClassB 而不是 ClassA C $ C> ClassA的?

So far so good. But is it possible without any modifications at the shown legacy code to load ClassB instead of ClassA at the instantiation of ClassA?

// In my test workbench
new LegacyCode(); // "Stub Class B"

我尝试编写自定义类加载器并在应用程序中加载它从java vm参数开始,但只有第一个类(这里是 LegacyCode )由该加载器加载。

I've tried to write a custom classloader and load it at application start by java vm arguments but only the first class (here LegacyCode) was loaded by that loader.

谢谢你提前

推荐答案

使用 PowerMock 你可以创建一个模拟(或存根)对于构造函数代码。答案取自此链接。我将尝试将其转换为与您的用例完全匹配:

Using PowerMock you can create a mock (or stub) for a constructor code. The answer is taken from this link. I'll try to convert it to match exactly to your use case:

@RunWith(PowerMockRunner.class)
@PrepareForTest(ClassA.class)
public class LegacyTester {
    @Test
    public void testService() {
         // Inject your stub
         PowerMock.createMock(ClassA.class);
         Service stub = new MyServiceStub();
         PowerMock.expectNew(ClassA.class).andReturn(stub);
         PowerMock.replay(stub, ClassA.class);

         // Implement test logic here

         LegacyCode legacyCode = new LegacyCode();

         // Implement Test steps

        // Call verify if you want to make sure the ClassA constructor was called
        PowerMock.verify(stub, ClassA.class)
    }
}

这样你就可以在调用 ClassA 构造函数发生,而不更改遗留代码。希望这就是你所需要的。

This way you inject your stub when the call to ClassA constructor happens, without changing the legacy code. Hope that's what you needed.

这篇关于替换实例化类的实现而不触及代码(java)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆