@@ -3,10 +3,11 @@ package convert_test
3
3
import (
4
4
"context"
5
5
"fmt"
6
- "github.com/operator-framework/operator-controller/internal/rukpak/convert "
6
+ "io/fs "
7
7
"os"
8
8
"strings"
9
9
"testing"
10
+ "testing/fstest"
10
11
11
12
"github.com/stretchr/testify/require"
12
13
appsv1 "k8s.io/api/apps/v1"
@@ -21,12 +22,17 @@ import (
21
22
22
23
"github.com/operator-framework/api/pkg/operators/v1alpha1"
23
24
"github.com/operator-framework/operator-registry/alpha/property"
25
+
26
+ "github.com/operator-framework/operator-controller/internal/rukpak/convert"
24
27
)
25
28
26
29
const (
27
30
olmNamespaces = "olm.targetNamespaces"
28
31
olmProperties = "olm.properties"
29
32
installNamespace = "testInstallNamespace"
33
+
34
+ bundlePathAnnotations = "metadata/annotations.yaml"
35
+ bundlePathCSV = "manifests/csv.yaml"
30
36
)
31
37
32
38
func getCsvAndService () (v1alpha1.ClusterServiceVersion , corev1.Service ) {
@@ -50,7 +56,7 @@ func getCsvAndService() (v1alpha1.ClusterServiceVersion, corev1.Service) {
50
56
func TestRegistryV1SuiteNamespaceNotAvailable (t * testing.T ) {
51
57
var targetNamespaces []string
52
58
53
- t .Log ("convert. RegistryV1 Suite Convert" )
59
+ t .Log ("RegistryV1 Suite Convert" )
54
60
t .Log ("It should set the namespaces of the object correctly" )
55
61
t .Log ("It should set the namespace to installnamespace if not available" )
56
62
@@ -81,7 +87,7 @@ func TestRegistryV1SuiteNamespaceNotAvailable(t *testing.T) {
81
87
func TestRegistryV1SuiteNamespaceAvailable (t * testing.T ) {
82
88
var targetNamespaces []string
83
89
84
- t .Log ("convert. RegistryV1 Suite Convert" )
90
+ t .Log ("RegistryV1 Suite Convert" )
85
91
t .Log ("It should set the namespaces of the object correctly" )
86
92
t .Log ("It should override namespace if already available" )
87
93
@@ -115,7 +121,7 @@ func TestRegistryV1SuiteNamespaceAvailable(t *testing.T) {
115
121
func TestRegistryV1SuiteNamespaceUnsupportedKind (t * testing.T ) {
116
122
var targetNamespaces []string
117
123
118
- t .Log ("convert. RegistryV1 Suite Convert" )
124
+ t .Log ("RegistryV1 Suite Convert" )
119
125
t .Log ("It should set the namespaces of the object correctly" )
120
126
t .Log ("It should error when object is not supported" )
121
127
t .Log ("It should error when unsupported GVK is passed" )
@@ -149,7 +155,7 @@ func TestRegistryV1SuiteNamespaceUnsupportedKind(t *testing.T) {
149
155
func TestRegistryV1SuiteNamespaceClusterScoped (t * testing.T ) {
150
156
var targetNamespaces []string
151
157
152
- t .Log ("convert. RegistryV1 Suite Convert" )
158
+ t .Log ("RegistryV1 Suite Convert" )
153
159
t .Log ("It should set the namespaces of the object correctly" )
154
160
t .Log ("It should not set ns cluster scoped object is passed" )
155
161
t .Log ("It should not error when cluster scoped obj is passed and not set its namespace" )
@@ -243,7 +249,7 @@ func getBaseCsvAndService() (v1alpha1.ClusterServiceVersion, corev1.Service) {
243
249
}
244
250
245
251
func TestRegistryV1SuiteGenerateAllNamespace (t * testing.T ) {
246
- t .Log ("convert. RegistryV1 Suite Convert" )
252
+ t .Log ("RegistryV1 Suite Convert" )
247
253
t .Log ("It should generate objects successfully based on target namespaces" )
248
254
249
255
t .Log ("It should convert into plain manifests successfully with AllNamespaces" )
@@ -276,7 +282,7 @@ func TestRegistryV1SuiteGenerateAllNamespace(t *testing.T) {
276
282
}
277
283
278
284
func TestRegistryV1SuiteGenerateMultiNamespace (t * testing.T ) {
279
- t .Log ("convert. RegistryV1 Suite Convert" )
285
+ t .Log ("RegistryV1 Suite Convert" )
280
286
t .Log ("It should generate objects successfully based on target namespaces" )
281
287
282
288
t .Log ("It should convert into plain manifests successfully with MultiNamespace" )
@@ -309,7 +315,7 @@ func TestRegistryV1SuiteGenerateMultiNamespace(t *testing.T) {
309
315
}
310
316
311
317
func TestRegistryV1SuiteGenerateSingleNamespace (t * testing.T ) {
312
- t .Log ("convert. RegistryV1 Suite Convert" )
318
+ t .Log ("RegistryV1 Suite Convert" )
313
319
t .Log ("It should generate objects successfully based on target namespaces" )
314
320
315
321
t .Log ("It should convert into plain manifests successfully with SingleNamespace" )
@@ -342,7 +348,7 @@ func TestRegistryV1SuiteGenerateSingleNamespace(t *testing.T) {
342
348
}
343
349
344
350
func TestRegistryV1SuiteGenerateOwnNamespace (t * testing.T ) {
345
- t .Log ("convert. RegistryV1 Suite Convert" )
351
+ t .Log ("RegistryV1 Suite Convert" )
346
352
t .Log ("It should generate objects successfully based on target namespaces" )
347
353
348
354
t .Log ("It should convert into plain manifests successfully with own namespace" )
@@ -375,7 +381,7 @@ func TestRegistryV1SuiteGenerateOwnNamespace(t *testing.T) {
375
381
}
376
382
377
383
func TestRegistryV1SuiteGenerateErrorMultiNamespaceEmpty (t * testing.T ) {
378
- t .Log ("convert. RegistryV1 Suite Convert" )
384
+ t .Log ("RegistryV1 Suite Convert" )
379
385
t .Log ("It should generate objects successfully based on target namespaces" )
380
386
381
387
t .Log ("It should error when multinamespace mode is supported with an empty string in target namespaces" )
@@ -399,7 +405,7 @@ func TestRegistryV1SuiteGenerateErrorMultiNamespaceEmpty(t *testing.T) {
399
405
}
400
406
401
407
func TestRegistryV1SuiteGenerateErrorSingleNamespaceDisabled (t * testing.T ) {
402
- t .Log ("convert. RegistryV1 Suite Convert" )
408
+ t .Log ("RegistryV1 Suite Convert" )
403
409
t .Log ("It should generate objects successfully based on target namespaces" )
404
410
405
411
t .Log ("It should error when single namespace mode is disabled with more than one target namespaces" )
@@ -423,7 +429,7 @@ func TestRegistryV1SuiteGenerateErrorSingleNamespaceDisabled(t *testing.T) {
423
429
}
424
430
425
431
func TestRegistryV1SuiteGenerateErrorAllNamespaceDisabled (t * testing.T ) {
426
- t .Log ("convert. RegistryV1 Suite Convert" )
432
+ t .Log ("RegistryV1 Suite Convert" )
427
433
t .Log ("It should generate objects successfully based on target namespaces" )
428
434
429
435
t .Log ("It should error when all namespace mode is disabled with target namespace containing an empty string" )
@@ -452,7 +458,7 @@ func TestRegistryV1SuiteGenerateErrorAllNamespaceDisabled(t *testing.T) {
452
458
}
453
459
454
460
func TestRegistryV1SuiteReadBundleFileSystem (t * testing.T ) {
455
- t .Log ("convert. RegistryV1 Suite Convert" )
461
+ t .Log ("RegistryV1 Suite Convert" )
456
462
t .Log ("It should generate objects successfully based on target namespaces" )
457
463
458
464
t .Log ("It should read the registry+v1 bundle filesystem correctly" )
@@ -466,8 +472,50 @@ func TestRegistryV1SuiteReadBundleFileSystem(t *testing.T) {
466
472
require .JSONEq (t , `[{"type":"from-csv-annotations-key","value":"from-csv-annotations-value"},{"type":"from-file-key","value":"from-file-value"}]` , chrt .Metadata .Annotations [olmProperties ])
467
473
}
468
474
475
+ func TestParseFSFails (t * testing.T ) {
476
+ for _ , tt := range []struct {
477
+ name string
478
+ FS fs.FS
479
+ }{
480
+ {
481
+ name : "bundle missing ClusterServiceVersion manifest" ,
482
+ FS : removePaths (newBundleFS (), bundlePathCSV ),
483
+ }, {
484
+ name : "bundle missing metadata/annotations.yaml" ,
485
+ FS : removePaths (newBundleFS (), bundlePathAnnotations ),
486
+ }, {
487
+ name : "bundle missing metadata/ directory" ,
488
+ FS : removePaths (newBundleFS (), "metadata/" ),
489
+ }, {
490
+ name : "bundle missing manifests/ directory" ,
491
+ FS : removePaths (newBundleFS (), "manifests/" ),
492
+ },
493
+ } {
494
+ t .Run (tt .name , func (t * testing.T ) {
495
+ _ , err := convert .ParseFS (context .Background (), tt .FS )
496
+ require .Error (t , err )
497
+ })
498
+ }
499
+ }
500
+
501
+ func TestRegistryV1SuiteReadBundleFileSystemFailsOnNoCSV (t * testing.T ) {
502
+ t .Log ("RegistryV1 Suite Convert" )
503
+ t .Log ("It should generate objects successfully based on target namespaces" )
504
+
505
+ t .Log ("It should read the registry+v1 bundle filesystem correctly" )
506
+ t .Log ("It should include metadata/properties.yaml and csv.metadata.annotations['olm.properties'] in chart metadata" )
507
+ fsys := os .DirFS ("testdata/combine-properties-bundle" )
508
+
509
+ chrt , err := convert .RegistryV1ToHelmChart (context .Background (), fsys , "" , nil )
510
+ require .NoError (t , err )
511
+ require .NotNil (t , chrt )
512
+ require .NotNil (t , chrt .Metadata )
513
+ require .Contains (t , chrt .Metadata .Annotations , olmProperties )
514
+ require .JSONEq (t , `[{"type":"from-csv-annotations-key","value":"from-csv-annotations-value"},{"type":"from-file-key","value":"from-file-value"}]` , chrt .Metadata .Annotations [olmProperties ])
515
+ }
516
+
469
517
func TestRegistryV1SuiteGenerateNoWebhooks (t * testing.T ) {
470
- t .Log ("convert. RegistryV1 Suite Convert" )
518
+ t .Log ("RegistryV1 Suite Convert" )
471
519
t .Log ("It should generate objects successfully based on target namespaces" )
472
520
473
521
t .Log ("It should enforce limitations" )
@@ -496,7 +544,7 @@ func TestRegistryV1SuiteGenerateNoWebhooks(t *testing.T) {
496
544
}
497
545
498
546
func TestRegistryV1SuiteGenerateNoAPISerciceDefinitions (t * testing.T ) {
499
- t .Log ("convert. RegistryV1 Suite Convert" )
547
+ t .Log ("RegistryV1 Suite Convert" )
500
548
t .Log ("It should generate objects successfully based on target namespaces" )
501
549
502
550
t .Log ("It should enforce limitations" )
@@ -543,3 +591,40 @@ func findObjectByName(name string, result []client.Object) client.Object {
543
591
}
544
592
return nil
545
593
}
594
+
595
+ func newBundleFS () fstest.MapFS {
596
+ annotationsYml := `
597
+ annotations:
598
+ operators.operatorframework.io.bundle.mediatype.v1: registry+v1
599
+ operators.operatorframework.io.bundle.package.v1: test
600
+ `
601
+
602
+ csvYml := `
603
+ apiVersion: operators.operatorframework.io/v1alpha1
604
+ kind: ClusterServiceVersion
605
+ metadata:
606
+ name: test.v1.0.0
607
+ annotations:
608
+ olm.properties: '[{"type":"from-csv-annotations-key", "value":"from-csv-annotations-value"}]'
609
+ spec:
610
+ installModes:
611
+ - type: AllNamespaces
612
+ supported: true
613
+ `
614
+
615
+ return fstest.MapFS {
616
+ bundlePathAnnotations : & fstest.MapFile {Data : []byte (strings .Trim (annotationsYml , "\n " ))},
617
+ bundlePathCSV : & fstest.MapFile {Data : []byte (strings .Trim (csvYml , "\n " ))},
618
+ }
619
+ }
620
+
621
+ func removePaths (mapFs fstest.MapFS , paths ... string ) fstest.MapFS {
622
+ for k := range mapFs {
623
+ for _ , path := range paths {
624
+ if strings .HasPrefix (k , path ) {
625
+ delete (mapFs , k )
626
+ }
627
+ }
628
+ }
629
+ return mapFs
630
+ }
0 commit comments