Skip to content

Commit af239f4

Browse files
authored
tests: multiple dependent resource integration test (#1268)
* fix: rename the existing custom resource * test: create IT showing multiple dependent resources
1 parent 3b24b2e commit af239f4

File tree

6 files changed

+211
-2
lines changed

6 files changed

+211
-2
lines changed
Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
package io.javaoperatorsdk.operator;
2+
3+
import java.time.Duration;
4+
import java.util.stream.IntStream;
5+
6+
import org.junit.jupiter.api.Test;
7+
import org.junit.jupiter.api.extension.RegisterExtension;
8+
9+
import io.fabric8.kubernetes.api.model.ConfigMap;
10+
import io.fabric8.kubernetes.api.model.ObjectMetaBuilder;
11+
import io.javaoperatorsdk.operator.junit.LocalOperatorExtension;
12+
import io.javaoperatorsdk.operator.sample.multipledependentresource.MultipleDependentResourceConfigMap;
13+
import io.javaoperatorsdk.operator.sample.multipledependentresource.MultipleDependentResourceCustomResource;
14+
import io.javaoperatorsdk.operator.sample.multipledependentresource.MultipleDependentResourceReconciler;
15+
16+
import static org.assertj.core.api.Assertions.assertThat;
17+
import static org.awaitility.Awaitility.await;
18+
19+
class MultipleDependentResourceIT {
20+
21+
public static final String TEST_RESOURCE_NAME = "multipledependentresource-testresource";
22+
@RegisterExtension
23+
LocalOperatorExtension operator =
24+
LocalOperatorExtension.builder().withReconciler(MultipleDependentResourceReconciler.class)
25+
.waitForNamespaceDeletion(true)
26+
.build();
27+
28+
@Test
29+
void twoConfigMapsHaveBeenCreated() {
30+
MultipleDependentResourceCustomResource customResource = createTestCustomResource();
31+
operator.create(MultipleDependentResourceCustomResource.class, customResource);
32+
33+
var reconciler = operator.getReconcilerOfType(MultipleDependentResourceReconciler.class);
34+
35+
await().pollDelay(Duration.ofMillis(300))
36+
.until(() -> reconciler.getNumberOfExecutions() <= 1);
37+
38+
IntStream.of(MultipleDependentResourceReconciler.FIRST_CONFIG_MAP_ID,
39+
MultipleDependentResourceReconciler.SECOND_CONFIG_MAP_ID).forEach(configMapId -> {
40+
ConfigMap configMap =
41+
operator.get(ConfigMap.class, customResource.getConfigMapName(configMapId));
42+
assertThat(configMap).isNotNull();
43+
assertThat(configMap.getMetadata().getName())
44+
.isEqualTo(customResource.getConfigMapName(configMapId));
45+
assertThat(configMap.getData().get(MultipleDependentResourceConfigMap.DATA_KEY))
46+
.isEqualTo(String.valueOf(configMapId));
47+
});
48+
}
49+
50+
public MultipleDependentResourceCustomResource createTestCustomResource() {
51+
MultipleDependentResourceCustomResource resource =
52+
new MultipleDependentResourceCustomResource();
53+
resource.setMetadata(
54+
new ObjectMetaBuilder()
55+
.withName(TEST_RESOURCE_NAME)
56+
.withNamespace(operator.getNamespace())
57+
.build());
58+
return resource;
59+
}
60+
61+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
package io.javaoperatorsdk.operator.sample.multipledependentresource;
2+
3+
import java.util.HashMap;
4+
import java.util.Map;
5+
6+
import io.fabric8.kubernetes.api.model.ConfigMap;
7+
import io.fabric8.kubernetes.api.model.ConfigMapBuilder;
8+
import io.javaoperatorsdk.operator.api.reconciler.Context;
9+
import io.javaoperatorsdk.operator.processing.dependent.kubernetes.CRUKubernetesDependentResource;
10+
import io.javaoperatorsdk.operator.processing.dependent.kubernetes.KubernetesDependent;
11+
12+
@KubernetesDependent
13+
public class MultipleDependentResourceConfigMap
14+
extends CRUKubernetesDependentResource<ConfigMap, MultipleDependentResourceCustomResource> {
15+
16+
public static final String DATA_KEY = "key";
17+
private final int value;
18+
19+
public MultipleDependentResourceConfigMap(int value) {
20+
super(ConfigMap.class);
21+
this.value = value;
22+
}
23+
24+
@Override
25+
protected ConfigMap desired(MultipleDependentResourceCustomResource primary,
26+
Context<MultipleDependentResourceCustomResource> context) {
27+
Map<String, String> data = new HashMap<>();
28+
data.put(DATA_KEY, String.valueOf(value));
29+
30+
return new ConfigMapBuilder()
31+
.withNewMetadata()
32+
.withName(primary.getConfigMapName(value))
33+
.withNamespace(primary.getMetadata().getNamespace())
34+
.withLabels(Map.of(MultipleDependentResourceReconciler.LABEL, String.valueOf(value)))
35+
.endMetadata()
36+
.withData(data)
37+
.build();
38+
}
39+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
package io.javaoperatorsdk.operator.sample.multipledependentresource;
2+
3+
import io.fabric8.kubernetes.api.model.Namespaced;
4+
import io.fabric8.kubernetes.client.CustomResource;
5+
import io.fabric8.kubernetes.model.annotation.Group;
6+
import io.fabric8.kubernetes.model.annotation.Kind;
7+
import io.fabric8.kubernetes.model.annotation.ShortNames;
8+
import io.fabric8.kubernetes.model.annotation.Version;
9+
10+
@Group("sample.javaoperatorsdk")
11+
@Version("v1")
12+
@Kind("MultipleDependentResourceCustomResource")
13+
@ShortNames("mdr")
14+
public class MultipleDependentResourceCustomResource
15+
extends CustomResource<Void, MultipleDependentResourceStatus>
16+
implements Namespaced {
17+
18+
public String getConfigMapName(int id) {
19+
return "configmap" + id;
20+
}
21+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
package io.javaoperatorsdk.operator.sample.multipledependentresource;
2+
3+
import java.util.Map;
4+
import java.util.concurrent.atomic.AtomicInteger;
5+
6+
import io.fabric8.kubernetes.client.KubernetesClient;
7+
import io.javaoperatorsdk.operator.api.reconciler.Context;
8+
import io.javaoperatorsdk.operator.api.reconciler.ControllerConfiguration;
9+
import io.javaoperatorsdk.operator.api.reconciler.EventSourceContext;
10+
import io.javaoperatorsdk.operator.api.reconciler.EventSourceInitializer;
11+
import io.javaoperatorsdk.operator.api.reconciler.Reconciler;
12+
import io.javaoperatorsdk.operator.api.reconciler.UpdateControl;
13+
import io.javaoperatorsdk.operator.junit.KubernetesClientAware;
14+
import io.javaoperatorsdk.operator.processing.dependent.kubernetes.KubernetesDependentResourceConfig;
15+
import io.javaoperatorsdk.operator.processing.event.source.EventSource;
16+
import io.javaoperatorsdk.operator.support.TestExecutionInfoProvider;
17+
18+
@ControllerConfiguration
19+
public class MultipleDependentResourceReconciler
20+
implements Reconciler<MultipleDependentResourceCustomResource>,
21+
TestExecutionInfoProvider, EventSourceInitializer<MultipleDependentResourceCustomResource>,
22+
KubernetesClientAware {
23+
24+
public static final int FIRST_CONFIG_MAP_ID = 1;
25+
public static final int SECOND_CONFIG_MAP_ID = 2;
26+
public static final String LABEL = "multipledependentresource";
27+
private final AtomicInteger numberOfExecutions = new AtomicInteger(0);
28+
29+
private final MultipleDependentResourceConfigMap firstDependentResourceConfigMap;
30+
private final MultipleDependentResourceConfigMap secondDependentResourceConfigMap;
31+
private KubernetesClient client;
32+
33+
public MultipleDependentResourceReconciler() {
34+
firstDependentResourceConfigMap = new MultipleDependentResourceConfigMap(FIRST_CONFIG_MAP_ID);
35+
secondDependentResourceConfigMap = new MultipleDependentResourceConfigMap(SECOND_CONFIG_MAP_ID);
36+
37+
firstDependentResourceConfigMap.configureWith(
38+
new KubernetesDependentResourceConfig()
39+
.setLabelSelector(getLabelSelector(FIRST_CONFIG_MAP_ID)));
40+
secondDependentResourceConfigMap.configureWith(
41+
new KubernetesDependentResourceConfig()
42+
.setLabelSelector(getLabelSelector(SECOND_CONFIG_MAP_ID)));
43+
}
44+
45+
private String getLabelSelector(int resourceId) {
46+
return LABEL + "=" + resourceId;
47+
}
48+
49+
@Override
50+
public UpdateControl<MultipleDependentResourceCustomResource> reconcile(
51+
MultipleDependentResourceCustomResource resource,
52+
Context<MultipleDependentResourceCustomResource> context) {
53+
numberOfExecutions.getAndIncrement();
54+
firstDependentResourceConfigMap.reconcile(resource, context);
55+
secondDependentResourceConfigMap.reconcile(resource, context);
56+
return UpdateControl.noUpdate();
57+
}
58+
59+
60+
public int getNumberOfExecutions() {
61+
return numberOfExecutions.get();
62+
}
63+
64+
@Override
65+
public Map<String, EventSource> prepareEventSources(
66+
EventSourceContext<MultipleDependentResourceCustomResource> context) {
67+
return EventSourceInitializer.nameEventSources(
68+
firstDependentResourceConfigMap.initEventSource(context),
69+
secondDependentResourceConfigMap.initEventSource(context));
70+
}
71+
72+
@Override
73+
public KubernetesClient getKubernetesClient() {
74+
return client;
75+
}
76+
77+
@Override
78+
public void setKubernetesClient(KubernetesClient kubernetesClient) {
79+
this.client = kubernetesClient;
80+
firstDependentResourceConfigMap.setKubernetesClient(kubernetesClient);
81+
secondDependentResourceConfigMap.setKubernetesClient(kubernetesClient);
82+
}
83+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
package io.javaoperatorsdk.operator.sample.multipledependentresource;
2+
3+
public class MultipleDependentResourceStatus {
4+
5+
}

operator-framework/src/test/java/io/javaoperatorsdk/operator/sample/multiplesecondaryeventsource/MultipleSecondaryEventSourceCustomResource.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,8 @@
99

1010
@Group("sample.javaoperatorsdk")
1111
@Version("v1")
12-
@Kind("MaxIntervalTestCustomResource")
13-
@ShortNames("mit")
12+
@Kind("MultipleSecondaryEventSourceCustomResource")
13+
@ShortNames("mses")
1414
public class MultipleSecondaryEventSourceCustomResource
1515
extends CustomResource<Void, MultipleSecondaryEventSourceStatus>
1616
implements Namespaced {

0 commit comments

Comments
 (0)