@@ -17,6 +17,7 @@ limitations under the License.
17
17
package envtest
18
18
19
19
import (
20
+ "errors"
20
21
"fmt"
21
22
"os"
22
23
"path/filepath"
@@ -43,7 +44,6 @@ It's possible to override some defaults, by setting the following environment va
43
44
KUBEBUILDER_CONTROLPLANE_START_TIMEOUT (string supported by time.ParseDuration): timeout for test control plane to start. Defaults to 20s.
44
45
KUBEBUILDER_CONTROLPLANE_STOP_TIMEOUT (string supported by time.ParseDuration): timeout for test control plane to start. Defaults to 20s.
45
46
KUBEBUILDER_ATTACH_CONTROL_PLANE_OUTPUT (boolean): if set to true, the control plane's stdout and stderr are attached to os.Stdout and os.Stderr
46
-
47
47
*/
48
48
const (
49
49
envUseExistingCluster = "USE_EXISTING_CLUSTER"
@@ -58,18 +58,32 @@ const (
58
58
StartTimeout = 60
59
59
StopTimeout = 60
60
60
61
+ // rquired binaries to run env test
62
+ kubeApiserverBin = "kube-apiserver"
63
+ etcdBin = "etcd"
64
+ kubectlBin = "kubectl"
65
+
61
66
defaultKubebuilderControlPlaneStartTimeout = 20 * time .Second
62
67
defaultKubebuilderControlPlaneStopTimeout = 20 * time .Second
63
68
)
64
69
65
- // Default binary path for test framework
66
- func defaultAssetPath (binary string ) string {
67
- assetPath := os .Getenv (envKubebuilderPath )
68
- if assetPath == "" {
69
- assetPath = defaultKubebuilderPath
70
+ // getBinAssetPath will return the path for the required binaries
71
+ // if the KUBEBUILDER_ASSETS is not set and the Directory is not informed in the
72
+ // config as well. Then, a default fixed value will be returned
73
+ func (te * Environment ) getBinAssetPath () string {
74
+ assetPath := defaultKubebuilderPath
75
+
76
+ valueFromEnvVar := os .Getenv (envKubebuilderPath )
77
+ if strings .TrimSpace (valueFromEnvVar ) != "" {
78
+ assetPath = valueFromEnvVar
79
+ }
80
+
81
+ valueFromEnvConfig := te .BinaryDirectoryPath
82
+ if strings .TrimSpace (valueFromEnvConfig ) != "" {
83
+ assetPath = valueFromEnvConfig
70
84
}
71
- return filepath .Join (assetPath , binary )
72
85
86
+ return assetPath
73
87
}
74
88
75
89
// ControlPlane is the re-exported ControlPlane type from the internal integration package
@@ -113,6 +127,10 @@ type Environment struct {
113
127
// values are merged.
114
128
CRDDirectoryPaths []string
115
129
130
+ // BinaryDirectoryPath is the path where the binaries required for the envtest are
131
+ // locate in the environment
132
+ BinaryDirectoryPath string
133
+
116
134
// UseExisting indicates that this environments should use an
117
135
// existing kubeconfig, instead of trying to stand up a new control plane.
118
136
// This is useful in cases that need aggregated API servers and the like.
@@ -217,18 +235,24 @@ func (te *Environment) Start() (*rest.Config, error) {
217
235
}
218
236
219
237
if os .Getenv (envKubeAPIServerBin ) == "" {
220
- te .ControlPlane .APIServer .Path = defaultAssetPath ("kube-apiserver" )
238
+ te .ControlPlane .APIServer .Path = filepath .Join (te .getBinAssetPath (), kubeApiserverBin )
239
+
221
240
}
222
241
if os .Getenv (envEtcdBin ) == "" {
223
- te .ControlPlane .Etcd .Path = defaultAssetPath ("etcd" )
242
+ te .ControlPlane .Etcd .Path = filepath .Join (te .getBinAssetPath (), etcdBin )
243
+
224
244
}
225
245
if os .Getenv (envKubectlBin ) == "" {
226
246
// we can't just set the path manually (it's behind a function), so set the environment variable instead
227
- if err := os .Setenv (envKubectlBin , defaultAssetPath ( "kubectl" )); err != nil {
247
+ if err := os .Setenv (envKubectlBin , filepath . Join ( te . getBinAssetPath (), kubectlBin )); err != nil {
228
248
return nil , err
229
249
}
230
250
}
231
251
252
+ if err := te .validateRequiredBinaries (); err != nil {
253
+ return nil , err
254
+ }
255
+
232
256
if err := te .defaultTimeouts (); err != nil {
233
257
return nil , fmt .Errorf ("failed to default controlplane timeouts: %w" , err )
234
258
}
@@ -267,6 +291,22 @@ func (te *Environment) Start() (*rest.Config, error) {
267
291
return te .Config , err
268
292
}
269
293
294
+ // validateRequiredBinaries will return an error if the required binaries are not found
295
+ func (te * Environment ) validateRequiredBinaries () error {
296
+ if _ , err := os .Stat (te .ControlPlane .APIServer .Path ); os .IsNotExist (err ) {
297
+ return errors .New (fmt .Sprintf ("unable to find the %v" , te .ControlPlane .APIServer .Path ))
298
+ }
299
+
300
+ if _ , err := os .Stat (te .ControlPlane .Etcd .Path ); os .IsNotExist (err ) {
301
+ return errors .New (fmt .Sprintf ("unable to find the %v" , te .ControlPlane .Etcd .Path ))
302
+ }
303
+
304
+ if _ , err := os .Stat (os .Getenv (envKubectlBin )); os .IsNotExist (err ) {
305
+ return errors .New (fmt .Sprintf ("unable to find the %v" , os .Getenv (envKubectlBin )))
306
+ }
307
+ return nil
308
+ }
309
+
270
310
func (te * Environment ) startControlPlane () error {
271
311
numTries , maxRetries := 0 , 5
272
312
var err error
0 commit comments