13
13
import org .slf4j .LoggerFactory ;
14
14
15
15
import io .fabric8 .kubernetes .api .model .HasMetadata ;
16
+ import io .fabric8 .kubernetes .client .LocalPortForward ;
16
17
import io .javaoperatorsdk .operator .Operator ;
17
18
import io .javaoperatorsdk .operator .api .config .ConfigurationService ;
18
19
import io .javaoperatorsdk .operator .api .config .ControllerConfigurationOverrider ;
@@ -29,11 +30,14 @@ public class OperatorExtension extends AbstractOperatorExtension {
29
30
30
31
private final Operator operator ;
31
32
private final List <ReconcilerSpec > reconcilers ;
33
+ private List <PortFowardSpec > portForwards ;
34
+ private List <LocalPortForward > localPortForwards ;
32
35
33
36
private OperatorExtension (
34
37
ConfigurationService configurationService ,
35
38
List <ReconcilerSpec > reconcilers ,
36
39
List <HasMetadata > infrastructure ,
40
+ List <PortFowardSpec > portForwards ,
37
41
Duration infrastructureTimeout ,
38
42
boolean preserveNamespaceOnError ,
39
43
boolean waitForNamespaceDeletion ,
@@ -46,6 +50,8 @@ private OperatorExtension(
46
50
preserveNamespaceOnError ,
47
51
waitForNamespaceDeletion );
48
52
this .reconcilers = reconcilers ;
53
+ this .portForwards = portForwards ;
54
+ this .localPortForwards = new ArrayList <>(portForwards .size ());
49
55
this .operator = new Operator (getKubernetesClient (), this .configurationService );
50
56
}
51
57
@@ -83,6 +89,22 @@ public <T extends Reconciler> T getControllerOfType(Class<T> type) {
83
89
protected void before (ExtensionContext context ) {
84
90
super .before (context );
85
91
92
+ final var kubernetesClient = getKubernetesClient ();
93
+
94
+ for (var ref : portForwards ) {
95
+ String podName = kubernetesClient .pods ()
96
+ .inNamespace (ref .getNamespace ())
97
+ .withLabel (ref .getLabelKey (), ref .getLabelValue ())
98
+ .list ()
99
+ .getItems ()
100
+ .get (0 )
101
+ .getMetadata ()
102
+ .getName ();
103
+
104
+ localPortForwards .add (kubernetesClient .pods ().inNamespace (ref .getNamespace ())
105
+ .withName (podName ).portForward (ref .getPort (), ref .getLocalPort ()));
106
+ }
107
+
86
108
for (var ref : reconcilers ) {
87
109
final var config = configurationService .getConfigurationFor (ref .reconciler );
88
110
final var oconfig = override (config ).settingNamespace (namespace );
@@ -95,7 +117,6 @@ protected void before(ExtensionContext context) {
95
117
ref .controllerConfigurationOverrider .accept (oconfig );
96
118
}
97
119
98
- final var kubernetesClient = getKubernetesClient ();
99
120
try (InputStream is = getClass ().getResourceAsStream (path )) {
100
121
final var crd = kubernetesClient .load (is );
101
122
crd .createOrReplace ();
@@ -127,15 +148,26 @@ protected void after(ExtensionContext context) {
127
148
} catch (Exception e ) {
128
149
// ignored
129
150
}
151
+
152
+ for (var ref : localPortForwards ) {
153
+ try {
154
+ ref .close ();
155
+ } catch (Exception e ) {
156
+ // ignored
157
+ }
158
+ }
159
+ localPortForwards .clear ();
130
160
}
131
161
132
162
@ SuppressWarnings ("rawtypes" )
133
163
public static class Builder extends AbstractBuilder <Builder > {
134
164
private final List <ReconcilerSpec > reconcilers ;
165
+ private final List <PortFowardSpec > portForwards ;
135
166
136
167
protected Builder () {
137
168
super ();
138
169
this .reconcilers = new ArrayList <>();
170
+ this .portForwards = new ArrayList <>();
139
171
}
140
172
141
173
public Builder withReconciler (
@@ -173,18 +205,62 @@ public Builder withReconciler(Class<? extends Reconciler> value) {
173
205
return this ;
174
206
}
175
207
208
+ public Builder withPortForward (String namespace , String labelKey , String labelValue , int port ,
209
+ int localPort ) {
210
+ portForwards .add (new PortFowardSpec (namespace , labelKey , labelValue , port , localPort ));
211
+ return this ;
212
+ }
213
+
176
214
public OperatorExtension build () {
177
215
return new OperatorExtension (
178
216
configurationService ,
179
217
reconcilers ,
180
218
infrastructure ,
219
+ portForwards ,
181
220
infrastructureTimeout ,
182
221
preserveNamespaceOnError ,
183
222
waitForNamespaceDeletion ,
184
223
oneNamespacePerClass );
185
224
}
186
225
}
187
226
227
+ private static class PortFowardSpec {
228
+ final String namespace ;
229
+ final String labelKey ;
230
+ final String labelValue ;
231
+ final int port ;
232
+ final int localPort ;
233
+
234
+ public PortFowardSpec (String namespace , String labelKey , String labelValue , int port ,
235
+ int localPort ) {
236
+ this .namespace = namespace ;
237
+ this .labelKey = labelKey ;
238
+ this .labelValue = labelValue ;
239
+ this .port = port ;
240
+ this .localPort = localPort ;
241
+ }
242
+
243
+ public String getNamespace () {
244
+ return namespace ;
245
+ }
246
+
247
+ public String getLabelKey () {
248
+ return labelKey ;
249
+ }
250
+
251
+ public String getLabelValue () {
252
+ return labelValue ;
253
+ }
254
+
255
+ public int getPort () {
256
+ return port ;
257
+ }
258
+
259
+ public int getLocalPort () {
260
+ return localPort ;
261
+ }
262
+ }
263
+
188
264
@ SuppressWarnings ("rawtypes" )
189
265
private static class ReconcilerSpec {
190
266
final Reconciler reconciler ;
0 commit comments