gpt4 book ai didi

java - 为什么方法在模拟后会被执行?

转载 作者:行者123 更新时间:2023-11-30 06:14:38 25 4
gpt4 key购买 nike

我有以下测试

public class MyclassTest extends JUnitSuite {

KubernetesClient kubeClient;

@SuppressWarnings("static-access")
@BeforeClass
public static void setup() {
system = ActorSystem.create();
KubeDeployment mockKubeDeployment = Mockito.mock(KubeDeployment.class);
KubeNamespace mockKubeNamespace = Mockito.mock(KubeNamespace.class);
Deployment deployment = Mockito.mock(Deployment.class);
Namespace namespace = Mockito.mock(Namespace.class);
KubernetesClient kubeClient = Mockito.mock(KubernetesClient.class);
Service serviceTodeploy = new Service("group","artifact","version");
DeployEnvironment deployEnvironment = new DeployEnvironment();
deployEnvironment.setName("K8sDeploymentCreatorTest");

when(mockKubeNamespace.createNamespace(kubeClient, serviceTodeploy)).thenReturn(namespace);
when(mockKubeDeployment.createDeployment(serviceTodeploy, kubeClient, namespace)).thenReturn(deployment);

}

这是真正的方法

public class KubeNamespace {
/**
* Creates a kubernetes namespace
*
* @param kubeClient
* @param namespaceName
* @param labelValue
* @return
*/
public static Namespace createNamespace(KubernetesClient kubeClient, Service serviceToDeploy) {
String namespaceName = serviceToDeploy.getDeployEnvironment().getName();
Namespace namespace = kubeClient.namespaces().createNew().withNewMetadata().withName(namespaceName)
.addToLabels(namespaceName, serviceToDeploy.getServiceCoordinates().toString()).endMetadata().done();

return namespace;
}

这会在第一个when语句处抛出一个NPE。调试后,它似乎在“createNamespace”方法内的某处引发了错误。发送到该方法的参数都不为空,有些是真实实例,有些是模拟对象。问题是,如果该方法被模拟,为什么会被执行?

经过更多调试后,看起来该方法并未被执行,因为我尝试添加另一个仅返回字符串的方法,并在规则时做出相同的操作

 when(mockKubeNamespace.someStupidMEthod(kubeClient, serviceTodeploy)).thenReturn("namespace");

以及实际方法

public static String someStupidMEthod(KubernetesClient kubeClient, Service serviceToDeploy) {
String namespaceName = serviceToDeploy.getDeployEnvironment().getName();
return namespaceName;

}

这仍然返回一个 null,有些东西告诉我它是模拟类的方式以及对这些方法的静态访问。但我理解不正确

在以下评论之后,我将静态方法更改为实例方法,并进行如下调用

when(new KubeNamespace().createNamespace(kubeClient, serviceTodeploy)).thenReturn(namespace);

仍然在同一行获取NPE

这是最终的代码

public class K8sDeploymentCreatorTest extends JUnitSuite {

static ActorSystem system;


@Before
public void setup() {
system = ActorSystem.create();
KubeDeployment mockKubeDeployment = mock(KubeDeployment.class);
KubeNamespace mockKubeNamespace = mock(KubeNamespace.class);
Deployment deployment = Mockito.mock(Deployment.class);
Namespace namespace = Mockito.mock(Namespace.class);
KubernetesClient kubeClient = Mockito.mock(KubernetesClient.class);
Service serviceTodeploy = new Service("group","artifact","version");
DeployEnvironment deployEnvironment = new DeployEnvironment();
deployEnvironment.setName("K8sDeploymentCreatorTest");
serviceTodeploy.setDeployEnvironment(deployEnvironment);
when(mockKubeNamespace.createNamespace(kubeClient, serviceTodeploy)).thenReturn(namespace);
when(mockKubeDeployment.createDeployment(serviceTodeploy, kubeClient, namespace)).thenReturn(deployment);

}


@AfterClass
public static void teardown() {
TestKit.shutdownActorSystem(system);
system = null;
}

@Test
public void testK8sDeployment() {

new TestKit(system) {
{
final Props props = Props.create(K8sDeploymentCreator.class);
final ActorRef underTest = system.actorOf(props);
KubernetesClient kubeClient = Mockito.mock(KubernetesClient.class);
DeployEnvironment deployEnvironment = new DeployEnvironment();
deployEnvironment.setName("K8sDeploymentCreatorTest");
Service serviceTodeploy = new Service("group","artifact","version");
serviceTodeploy.setDeployEnvironment(deployEnvironment);
createK8sDeployment msg = new createK8sDeployment(serviceTodeploy, kubeClient);
underTest.tell(msg, getRef());
expectMsg(K8sDeploymentComplete.class);
}
};
}

}


public class K8sDeploymentCreator extends AbstractActor {
private final LoggingAdapter log = Logging.getLogger(getContext().getSystem(), this);


@Override
public Receive createReceive() {
return receiveBuilder().match(createK8sDeployment.class, msg -> {

KubeNamespace kubenamespace = new KubeNamespace();
KubeDeployment kubeDeployment = new KubeDeployment();
Namespace namespace = kubenamespace.createNamespace(msg.kubeClient, msg.service);
Deployment deployment = kubeDeployment.createDeployment(msg.service, msg.kubeClient, namespace);
log.info("sending complete depl msg");

getSender().tell(new K8sDeploymentComplete(deployment), getSelf());
})
.matchAny(o -> log.info("received unknown message")).build();
}

最佳答案

这不是正确的方法

when(new KubeNamespace().createNamespace

因为在这里您正在创建未被模拟的新对象。将方法设置为非静态后,使用您之前创建的模拟对象( KubeNamespace mockKubeNamespace = Mockito.mock(KubeNamespace.class); )

基本上,旧的“when”语句应该在将 createNamespace 方法设为非静态后起作用。

when(mockKubeNamespace.createNamespace(kubeClient, serviceTodeploy)).thenReturn(namespace);

关于java - 为什么方法在模拟后会被执行?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49492754/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com