...

Source file src/github.com/redhat-developer/odo/pkg/component/component_test.go

Documentation: github.com/redhat-developer/odo/pkg/component

     1  package component
     2  
     3  import (
     4  	"context"
     5  	"errors"
     6  	"os"
     7  	"path"
     8  	"path/filepath"
     9  	"testing"
    10  
    11  	devfilepkg "github.com/devfile/api/v2/pkg/devfile"
    12  	"github.com/devfile/library/v2/pkg/devfile/parser"
    13  	devfileCtx "github.com/devfile/library/v2/pkg/devfile/parser/context"
    14  	"github.com/devfile/library/v2/pkg/devfile/parser/data"
    15  	"github.com/devfile/library/v2/pkg/testingutil/filesystem"
    16  	dfutil "github.com/devfile/library/v2/pkg/util"
    17  	"github.com/golang/mock/gomock"
    18  	"github.com/google/go-cmp/cmp"
    19  	v12 "github.com/openshift/api/route/v1"
    20  	v1 "k8s.io/api/networking/v1"
    21  	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
    22  	"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
    23  	"k8s.io/apimachinery/pkg/runtime"
    24  	"k8s.io/apimachinery/pkg/runtime/schema"
    25  
    26  	"github.com/redhat-developer/odo/pkg/devfile"
    27  	"github.com/redhat-developer/odo/pkg/kclient"
    28  	"github.com/redhat-developer/odo/pkg/labels"
    29  	"github.com/redhat-developer/odo/pkg/libdevfile"
    30  	odocontext "github.com/redhat-developer/odo/pkg/odo/context"
    31  	"github.com/redhat-developer/odo/pkg/platform"
    32  	"github.com/redhat-developer/odo/pkg/podman"
    33  	"github.com/redhat-developer/odo/pkg/testingutil"
    34  	"github.com/redhat-developer/odo/pkg/util"
    35  
    36  	"github.com/redhat-developer/odo/pkg/api"
    37  )
    38  
    39  func TestListAllClusterComponents(t *testing.T) {
    40  	const odoVersion = "v3.0.0-beta3"
    41  	res1 := getUnstructured("dep1", "deployment", "v1", "Unknown", "", "Unknown", "my-ns")
    42  	res2 := getUnstructured("svc1", "service", "v1", "odo", odoVersion, "nodejs", "my-ns")
    43  	res3 := getUnstructured("dep1", "deployment", "v1", "Unknown", "", "Unknown", "my-ns")
    44  	res3.SetLabels(map[string]string{})
    45  
    46  	commonLabels := labels.Builder().WithComponentName("comp1").WithManager("odo").WithManagedByVersion(odoVersion)
    47  
    48  	resDev := getUnstructured("depDev", "deployment", "v1", "odo", odoVersion, "nodejs", "my-ns")
    49  	labelsDev := commonLabels.WithMode("Dev").Labels()
    50  	resDev.SetLabels(labelsDev)
    51  
    52  	resDeploy := getUnstructured("depDeploy", "deployment", "v1", "odo", odoVersion, "nodejs", "my-ns")
    53  	labelsDeploy := commonLabels.WithMode("Deploy").Labels()
    54  	resDeploy.SetLabels(labelsDeploy)
    55  
    56  	type fields struct {
    57  		kubeClient func(ctrl *gomock.Controller) kclient.ClientInterface
    58  	}
    59  	type args struct {
    60  		namespace string
    61  	}
    62  	tests := []struct {
    63  		name    string
    64  		fields  fields
    65  		args    args
    66  		want    []api.ComponentAbstract
    67  		wantErr bool
    68  	}{
    69  		{
    70  			name: "1 non-odo resource returned with Unknown",
    71  			fields: fields{
    72  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
    73  					var resources []unstructured.Unstructured
    74  					resources = append(resources, res1)
    75  					client := kclient.NewMockClientInterface(ctrl)
    76  					selector := ""
    77  					client.EXPECT().GetAllResourcesFromSelector(selector, "my-ns").Return(resources, nil)
    78  					return client
    79  				},
    80  			},
    81  			args: args{
    82  				namespace: "my-ns",
    83  			},
    84  			want: []api.ComponentAbstract{{
    85  				Name:             "dep1",
    86  				ManagedBy:        "Unknown",
    87  				ManagedByVersion: "",
    88  				RunningIn:        nil,
    89  				Type:             "Unknown",
    90  				RunningOn:        "cluster",
    91  				Platform:         "cluster",
    92  			}},
    93  			wantErr: false,
    94  		},
    95  		{
    96  			name: "0 non-odo resource without instance label is not returned",
    97  			fields: fields{
    98  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
    99  					var resources []unstructured.Unstructured
   100  					resources = append(resources, res3)
   101  					client := kclient.NewMockClientInterface(ctrl)
   102  					client.EXPECT().GetAllResourcesFromSelector(gomock.Any(), "my-ns").Return(resources, nil)
   103  					return client
   104  				},
   105  			},
   106  			args: args{
   107  				namespace: "my-ns",
   108  			},
   109  			want:    nil,
   110  			wantErr: false,
   111  		},
   112  		{
   113  			name: "1 non-odo resource returned with Unknown, and 1 odo resource returned with odo",
   114  			fields: fields{
   115  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   116  					var resources []unstructured.Unstructured
   117  					resources = append(resources, res1, res2)
   118  					client := kclient.NewMockClientInterface(ctrl)
   119  					client.EXPECT().GetAllResourcesFromSelector(gomock.Any(), "my-ns").Return(resources, nil)
   120  					return client
   121  				},
   122  			},
   123  			args: args{
   124  				namespace: "my-ns",
   125  			},
   126  			want: []api.ComponentAbstract{{
   127  				Name:             "dep1",
   128  				ManagedBy:        "Unknown",
   129  				ManagedByVersion: "",
   130  				RunningIn:        nil,
   131  				Type:             "Unknown",
   132  				RunningOn:        "cluster",
   133  				Platform:         "cluster",
   134  			}, {
   135  				Name:             "svc1",
   136  				ManagedBy:        "odo",
   137  				ManagedByVersion: "v3.0.0-beta3",
   138  				RunningIn:        nil,
   139  				Type:             "nodejs",
   140  				RunningOn:        "cluster",
   141  				Platform:         "cluster",
   142  			}},
   143  			wantErr: false,
   144  		},
   145  		{
   146  			name: "one resource in Dev and Deploy modes",
   147  			fields: fields{
   148  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   149  					var resources []unstructured.Unstructured
   150  					resources = append(resources, resDev, resDeploy)
   151  					client := kclient.NewMockClientInterface(ctrl)
   152  					client.EXPECT().GetAllResourcesFromSelector(gomock.Any(), "my-ns").Return(resources, nil)
   153  					return client
   154  				},
   155  			},
   156  			args: args{
   157  				namespace: "my-ns",
   158  			},
   159  			want: []api.ComponentAbstract{{
   160  				Name:             "comp1",
   161  				ManagedBy:        "odo",
   162  				ManagedByVersion: "v3.0.0-beta3",
   163  				RunningIn: api.RunningModes{
   164  					"dev":    true,
   165  					"deploy": true,
   166  				},
   167  				Type:      "nodejs",
   168  				RunningOn: "cluster",
   169  				Platform:  "cluster",
   170  			}},
   171  			wantErr: false,
   172  		},
   173  	}
   174  	for _, tt := range tests {
   175  		t.Run(tt.name, func(t *testing.T) {
   176  			ctrl := gomock.NewController(t)
   177  			got, err := ListAllClusterComponents(tt.fields.kubeClient(ctrl), tt.args.namespace)
   178  			if (err != nil) != tt.wantErr {
   179  				t.Errorf("ListAllClusterComponents error = %v, wantErr %v", err, tt.wantErr)
   180  				return
   181  			}
   182  			if diff := cmp.Diff(tt.want, got); diff != "" {
   183  				t.Errorf("ListAllClusterComponents() mismatch (-want +got):\n%s", diff)
   184  			}
   185  		})
   186  	}
   187  }
   188  
   189  func TestGetComponentTypeFromDevfileMetadata(t *testing.T) {
   190  	tests := []devfilepkg.DevfileMetadata{
   191  		{
   192  			Name:        "ReturnProject",
   193  			ProjectType: "Maven",
   194  			Language:    "Java",
   195  		},
   196  		{
   197  			Name:     "ReturnLanguage",
   198  			Language: "Java",
   199  		},
   200  		{
   201  			Name: "ReturnNA",
   202  		},
   203  	}
   204  	for _, tt := range tests {
   205  		t.Run(tt.Name, func(t *testing.T) {
   206  			var want string
   207  			got := GetComponentTypeFromDevfileMetadata(tt)
   208  			switch tt.Name {
   209  			case "ReturnProject":
   210  				want = tt.ProjectType
   211  			case "ReturnLanguage":
   212  				want = tt.Language
   213  			case "ReturnNA":
   214  				want = NotAvailable
   215  			}
   216  			if got != want {
   217  				t.Errorf("Incorrect component type returned; got: %q, want: %q", got, want)
   218  			}
   219  		})
   220  	}
   221  }
   222  
   223  // getUnstructured returns an unstructured.Unstructured object
   224  func getUnstructured(name, kind, apiVersion, managed, managedByVersion, componentType, namespace string) (u unstructured.Unstructured) {
   225  	u.SetName(name)
   226  	u.SetKind(kind)
   227  	u.SetAPIVersion(apiVersion)
   228  	u.SetNamespace(namespace)
   229  	u.SetLabels(labels.Builder().
   230  		WithComponentName(name).
   231  		WithManager(managed).
   232  		WithManagedByVersion(managedByVersion).
   233  		Labels())
   234  	u.SetAnnotations(labels.Builder().
   235  		WithProjectType(componentType).
   236  		Labels())
   237  	return
   238  }
   239  
   240  func TestGetRunningModes(t *testing.T) {
   241  
   242  	resourceDev1 := unstructured.Unstructured{}
   243  	resourceDev1.SetLabels(labels.Builder().WithMode(labels.ComponentDevMode).Labels())
   244  
   245  	resourceDev2 := unstructured.Unstructured{}
   246  	resourceDev2.SetLabels(labels.Builder().WithMode(labels.ComponentDevMode).Labels())
   247  
   248  	resourceDeploy1 := unstructured.Unstructured{}
   249  	resourceDeploy1.SetLabels(labels.Builder().WithMode(labels.ComponentDeployMode).Labels())
   250  
   251  	resourceDeploy2 := unstructured.Unstructured{}
   252  	resourceDeploy2.SetLabels(labels.Builder().WithMode(labels.ComponentDeployMode).Labels())
   253  
   254  	otherResource := unstructured.Unstructured{}
   255  
   256  	packageManifestResource := unstructured.Unstructured{}
   257  	packageManifestResource.SetKind("PackageManifest")
   258  	packageManifestResource.SetLabels(labels.Builder().WithMode(labels.ComponentDevMode).Labels())
   259  
   260  	type args struct {
   261  		kubeClient   func(ctrl *gomock.Controller) kclient.ClientInterface
   262  		podmanClient func(ctrl *gomock.Controller) podman.Client
   263  		name         string
   264  	}
   265  	tests := []struct {
   266  		name    string
   267  		args    args
   268  		want    func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes
   269  		wantErr bool
   270  	}{
   271  		{
   272  			name: "no kube client and no podman client",
   273  			args: args{
   274  				name: "aname",
   275  			},
   276  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   277  				return nil
   278  			},
   279  			wantErr: true,
   280  		},
   281  		{
   282  			name: "No cluster resources",
   283  			args: args{
   284  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   285  					c := kclient.NewMockClientInterface(ctrl)
   286  					c.EXPECT().GetCurrentNamespace().Return("a-namespace").AnyTimes()
   287  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return([]unstructured.Unstructured{}, nil)
   288  					return c
   289  				},
   290  				name: "aname",
   291  			},
   292  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   293  				return nil
   294  			},
   295  			wantErr: true,
   296  		},
   297  		{
   298  			name: "Only PackageManifest resources returned by cluster",
   299  			args: args{
   300  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   301  					c := kclient.NewMockClientInterface(ctrl)
   302  					c.EXPECT().GetCurrentNamespace().Return("a-namespace").AnyTimes()
   303  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return([]unstructured.Unstructured{packageManifestResource}, nil)
   304  					return c
   305  				},
   306  				name: "aname",
   307  			},
   308  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   309  				return nil
   310  			},
   311  			wantErr: true,
   312  		},
   313  		{
   314  			name: "No dev/deploy resources",
   315  			args: args{
   316  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   317  					c := kclient.NewMockClientInterface(ctrl)
   318  					c.EXPECT().GetCurrentNamespace().Return("a-namespace").AnyTimes()
   319  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(
   320  						[]unstructured.Unstructured{packageManifestResource, otherResource}, nil)
   321  					return c
   322  				},
   323  				podmanClient: func(ctrl *gomock.Controller) podman.Client {
   324  					c := podman.NewMockClient(ctrl)
   325  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(
   326  						[]unstructured.Unstructured{packageManifestResource, otherResource}, nil)
   327  					return c
   328  				},
   329  				name: "aname",
   330  			},
   331  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   332  				return map[platform.Client]api.RunningModes{
   333  					kubeClient:   {"dev": false, "deploy": false},
   334  					podmanClient: {"dev": false, "deploy": false},
   335  				}
   336  			},
   337  		},
   338  		{
   339  			name: "Only Dev cluster resources and no Podman resources",
   340  			args: args{
   341  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   342  					c := kclient.NewMockClientInterface(ctrl)
   343  					c.EXPECT().GetCurrentNamespace().Return("a-namespace").AnyTimes()
   344  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return([]unstructured.Unstructured{packageManifestResource, otherResource, resourceDev1, resourceDev2}, nil)
   345  					return c
   346  				},
   347  				podmanClient: func(ctrl *gomock.Controller) podman.Client {
   348  					c := podman.NewMockClient(ctrl)
   349  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(nil, nil)
   350  					return c
   351  				},
   352  				name: "aname",
   353  			},
   354  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   355  				return map[platform.Client]api.RunningModes{kubeClient: {"dev": true, "deploy": false}}
   356  			},
   357  		},
   358  		{
   359  			name: "Only Deploy cluster resources",
   360  			args: args{
   361  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   362  					c := kclient.NewMockClientInterface(ctrl)
   363  					c.EXPECT().GetCurrentNamespace().Return("a-namespace").AnyTimes()
   364  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return([]unstructured.Unstructured{packageManifestResource, otherResource, resourceDeploy1, resourceDeploy2}, nil)
   365  					return c
   366  				},
   367  				name: "aname",
   368  			},
   369  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   370  				return map[platform.Client]api.RunningModes{kubeClient: {"dev": false, "deploy": true}}
   371  			},
   372  		},
   373  		{
   374  			name: "Dev and Deploy cluster resources",
   375  			args: args{
   376  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   377  					c := kclient.NewMockClientInterface(ctrl)
   378  					c.EXPECT().GetCurrentNamespace().Return("a-namespace").AnyTimes()
   379  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return([]unstructured.Unstructured{packageManifestResource, otherResource, resourceDev1, resourceDev2, resourceDeploy1, resourceDeploy2}, nil)
   380  					return c
   381  				},
   382  				name: "aname",
   383  			},
   384  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   385  				return map[platform.Client]api.RunningModes{kubeClient: {"dev": true, "deploy": true}}
   386  			},
   387  		},
   388  		{
   389  			name: "Dev and Deploy cluster resources, Dev Podman resources",
   390  			args: args{
   391  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   392  					c := kclient.NewMockClientInterface(ctrl)
   393  					c.EXPECT().GetCurrentNamespace().Return("a-namespace").AnyTimes()
   394  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(
   395  						[]unstructured.Unstructured{
   396  							packageManifestResource, otherResource, resourceDev1, resourceDev2, resourceDeploy1, resourceDeploy2},
   397  						nil)
   398  					return c
   399  				},
   400  				podmanClient: func(ctrl *gomock.Controller) podman.Client {
   401  					c := podman.NewMockClient(ctrl)
   402  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(
   403  						[]unstructured.Unstructured{resourceDev1, resourceDev2}, nil)
   404  					return c
   405  				},
   406  				name: "aname",
   407  			},
   408  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   409  				return map[platform.Client]api.RunningModes{
   410  					kubeClient:   {"dev": true, "deploy": true},
   411  					podmanClient: {"dev": true, "deploy": false},
   412  				}
   413  			},
   414  		},
   415  		{
   416  			name: "Unknown",
   417  			args: args{
   418  				kubeClient: func(ctrl *gomock.Controller) kclient.ClientInterface {
   419  					c := kclient.NewMockClientInterface(ctrl)
   420  					c.EXPECT().GetCurrentNamespace().Return("a-namespace").AnyTimes()
   421  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(nil, errors.New("error"))
   422  					return c
   423  				},
   424  				name: "aname",
   425  			},
   426  			want: func(kubeClient, podmanClient platform.Client) map[platform.Client]api.RunningModes {
   427  				return nil
   428  			},
   429  		},
   430  	}
   431  	for _, tt := range tests {
   432  		t.Run(tt.name, func(t *testing.T) {
   433  			ctrl := gomock.NewController(t)
   434  			ctx := odocontext.WithApplication(context.TODO(), "app")
   435  			var kubeClient kclient.ClientInterface
   436  			if tt.args.kubeClient != nil {
   437  				kubeClient = tt.args.kubeClient(ctrl)
   438  			}
   439  			var podmanClient podman.Client
   440  			if tt.args.podmanClient != nil {
   441  				podmanClient = tt.args.podmanClient(ctrl)
   442  			}
   443  			got, err := GetRunningModes(ctx, kubeClient, podmanClient, tt.args.name)
   444  			if (err != nil) != tt.wantErr {
   445  				t.Errorf("error = %v, wantErr %v", err, tt.wantErr)
   446  				return
   447  			}
   448  			want := tt.want(kubeClient, podmanClient)
   449  			if diff := cmp.Diff(want, got); diff != "" {
   450  				t.Errorf("GetRunningModes() mismatch (-want +got):\n%s", diff)
   451  			}
   452  		})
   453  	}
   454  }
   455  
   456  func TestGatherName(t *testing.T) {
   457  	type devfileProvider func() (*parser.DevfileObj, string, error)
   458  	fakeDevfileWithNameProvider := func(name string) devfileProvider {
   459  		return func() (*parser.DevfileObj, string, error) {
   460  			dData, err := data.NewDevfileData(string(data.APISchemaVersion220))
   461  			if err != nil {
   462  				return nil, "", err
   463  			}
   464  			dData.SetMetadata(devfilepkg.DevfileMetadata{Name: name})
   465  			return &parser.DevfileObj{
   466  				Ctx:  devfileCtx.FakeContext(filesystem.NewFakeFs(), parser.OutputDevfileYamlPath),
   467  				Data: dData,
   468  			}, "", nil
   469  		}
   470  	}
   471  
   472  	fs := filesystem.DefaultFs{}
   473  	// realDevfileWithNameProvider creates a real temporary directory and writes a devfile with the given name to it.
   474  	// It is the responsibility of the caller to remove the directory.
   475  	realDevfileWithNameProvider := func(name string) devfileProvider {
   476  		return func() (*parser.DevfileObj, string, error) {
   477  			dir, err := fs.TempDir("", "Component_GatherName_")
   478  			if err != nil {
   479  				return nil, dir, err
   480  			}
   481  
   482  			originalDevfile := testingutil.GetTestDevfileObjFromFile("devfile.yaml")
   483  			originalDevfilePath := originalDevfile.Ctx.GetAbsPath()
   484  
   485  			stat, err := os.Stat(originalDevfilePath)
   486  			if err != nil {
   487  				return nil, dir, err
   488  			}
   489  			dPath := path.Join(dir, "devfile.yaml")
   490  			err = dfutil.CopyFile(originalDevfilePath, dPath, stat)
   491  			if err != nil {
   492  				return nil, dir, err
   493  			}
   494  
   495  			d, err := devfile.ParseAndValidateFromFile(dPath, "", false)
   496  			if err != nil {
   497  				return nil, dir, err
   498  			}
   499  
   500  			err = d.SetMetadataName(name)
   501  
   502  			return &d, dir, err
   503  		}
   504  	}
   505  
   506  	wantDevfileDirectoryName := func(contextDir string, d *parser.DevfileObj) string {
   507  		return util.GetDNS1123Name(filepath.Base(filepath.Dir(d.Ctx.GetAbsPath())))
   508  	}
   509  
   510  	for _, tt := range []struct {
   511  		name                string
   512  		devfileProviderFunc devfileProvider
   513  		wantErr             bool
   514  		want                func(contextDir string, d *parser.DevfileObj) string
   515  	}{
   516  		{
   517  			name:                "compliant name",
   518  			devfileProviderFunc: fakeDevfileWithNameProvider("my-component-name"),
   519  			want:                func(contextDir string, d *parser.DevfileObj) string { return "my-component-name" },
   520  		},
   521  		{
   522  			name:                "un-sanitized name",
   523  			devfileProviderFunc: fakeDevfileWithNameProvider("name with spaces"),
   524  			want:                func(contextDir string, d *parser.DevfileObj) string { return "name-with-spaces" },
   525  		},
   526  		{
   527  			name:                "all numeric name",
   528  			devfileProviderFunc: fakeDevfileWithNameProvider("123456789"),
   529  			// "x" prefix added by util.GetDNS1123Name
   530  			want: func(contextDir string, d *parser.DevfileObj) string { return "x123456789" },
   531  		},
   532  		{
   533  			name:                "no name",
   534  			devfileProviderFunc: realDevfileWithNameProvider(""),
   535  			want:                wantDevfileDirectoryName,
   536  		},
   537  		{
   538  			name:                "blank name",
   539  			devfileProviderFunc: realDevfileWithNameProvider("   "),
   540  			want:                wantDevfileDirectoryName,
   541  		},
   542  		{
   543  			name: "passing no devfile should use the context directory name",
   544  			devfileProviderFunc: func() (*parser.DevfileObj, string, error) {
   545  				dir, err := fs.TempDir("", "Component_GatherName_")
   546  				if err != nil {
   547  					return nil, dir, err
   548  				}
   549  				return nil, dir, nil
   550  			},
   551  			want: func(contextDir string, _ *parser.DevfileObj) string {
   552  				return util.GetDNS1123Name(filepath.Base(contextDir))
   553  			},
   554  		},
   555  	} {
   556  		t.Run(tt.name, func(t *testing.T) {
   557  			d, dir, dErr := tt.devfileProviderFunc()
   558  			if dir != "" {
   559  				defer func(fs filesystem.Filesystem, path string) {
   560  					if err := fs.RemoveAll(path); err != nil {
   561  						t.Logf("error while attempting to remove temporary directory %q: %v", path, err)
   562  					}
   563  				}(fs, dir)
   564  			}
   565  			if dErr != nil {
   566  				t.Errorf("error when building test Devfile object: %v", dErr)
   567  				return
   568  			}
   569  
   570  			got, err := GatherName(dir, d)
   571  			if (err != nil) != tt.wantErr {
   572  				t.Errorf("error = %v, wantErr %v", err, tt.wantErr)
   573  			}
   574  			want := tt.want(dir, d)
   575  			if diff := cmp.Diff(want, got); diff != "" {
   576  				t.Errorf("GatherName() mismatch (-want +got):\n%s", diff)
   577  			}
   578  		})
   579  	}
   580  }
   581  
   582  func TestListRoutesAndIngresses(t *testing.T) {
   583  	const (
   584  		componentName    = "nodejs-prj1-api-abhz" // hard coding from the Devfile
   585  		k8sComponentName = "my-nodejs-app"        // hard coding from the Devfile
   586  		namespace        = "my-namespace"
   587  	)
   588  	createFakeIngressFromDevfile := func(devfileObj parser.DevfileObj, ingressComponentName string, label map[string]string) *v1.Ingress {
   589  		ing := &v1.Ingress{}
   590  		uList, _ := libdevfile.GetK8sComponentAsUnstructuredList(devfileObj, ingressComponentName, "", filesystem.DefaultFs{})
   591  		// We default to the first object in the list because it is safe to do so since we have only defined one K8s resource for the Devfile K8s component
   592  		u := uList[0]
   593  		_ = runtime.DefaultUnstructuredConverter.FromUnstructured(u.UnstructuredContent(), ing)
   594  		ing.SetLabels(label)
   595  		return ing
   596  	}
   597  
   598  	createFakeRouteFromDevfile := func(devfileObj parser.DevfileObj, routeComponentName string, label map[string]string) *v12.Route {
   599  		route := &v12.Route{}
   600  		uList, _ := libdevfile.GetK8sComponentAsUnstructuredList(devfileObj, routeComponentName, "", filesystem.DefaultFs{})
   601  		// We default to the first object in the list because it is safe to do so since we have only defined one K8s resource for the Devfile K8s component
   602  		u := uList[0]
   603  		_ = runtime.DefaultUnstructuredConverter.FromUnstructured(u.UnstructuredContent(), route)
   604  		route.SetLabels(label)
   605  		return route
   606  	}
   607  
   608  	label := labels.GetLabels(componentName, "app", "", labels.ComponentDeployMode, false)
   609  	// cannot use default label to selector converter; it does not return expected result
   610  	selector := labels.GetNameSelector(componentName)
   611  
   612  	// create ingress object
   613  	devfileObjWithIngress := testingutil.GetTestDevfileObjFromFile("devfile-deploy-ingress.yaml")
   614  	ing := createFakeIngressFromDevfile(devfileObjWithIngress, "outerloop-url", label)
   615  	ingConnectionData := api.ConnectionData{
   616  		Name: k8sComponentName,
   617  		Rules: []api.Rules{
   618  			{
   619  				Host:  "nodejs.example.com",
   620  				Paths: []string{"/", "/foo"}},
   621  		},
   622  	}
   623  
   624  	// create ingresss object with default backend and no rules
   625  	devfileObjWithDefaultBackendIngress := testingutil.GetTestDevfileObjFromFile("devfile-deploy-defaultBackend-ingress.yaml")
   626  	ingDefaultBackend := createFakeIngressFromDevfile(devfileObjWithDefaultBackendIngress, "outerloop-url", label)
   627  	ingDBConnectionData := api.ConnectionData{
   628  		Name: k8sComponentName,
   629  		Rules: []api.Rules{
   630  			{
   631  				Host:  "*",
   632  				Paths: []string{"/*"}},
   633  		},
   634  	}
   635  
   636  	// create route object
   637  	devfileObjWithRoute := testingutil.GetTestDevfileObjFromFile("devfile-deploy-route.yaml")
   638  	routeGVR := schema.GroupVersionResource{
   639  		Group:    kclient.RouteGVK.Group,
   640  		Version:  kclient.RouteGVK.Version,
   641  		Resource: "routes",
   642  	}
   643  	route := createFakeRouteFromDevfile(devfileObjWithRoute, "outerloop-url", label)
   644  	routeUnstructured, _ := runtime.DefaultUnstructuredConverter.ToUnstructured(route)
   645  	routeConnectionData := api.ConnectionData{
   646  		Name: k8sComponentName,
   647  		Rules: []api.Rules{
   648  			{
   649  				Host:  "",
   650  				Paths: []string{"/foo"},
   651  			},
   652  		},
   653  	}
   654  
   655  	mockKubeClient := func(ctrl *gomock.Controller, isOCP bool, ingresses []v1.Ingress, routeUnstructured map[string]interface{}) kclient.ClientInterface {
   656  		client := kclient.NewMockClientInterface(ctrl)
   657  		client.EXPECT().GetCurrentNamespace().Return(namespace)
   658  		client.EXPECT().ListIngresses(namespace, selector).Return(&v1.IngressList{Items: ingresses}, nil)
   659  		client.EXPECT().IsProjectSupported().Return(isOCP, nil)
   660  		if isOCP {
   661  			client.EXPECT().GetGVRFromGVK(kclient.RouteGVK).Return(routeGVR, nil)
   662  			client.EXPECT().GetCurrentNamespace().Return(namespace)
   663  			client.EXPECT().ListDynamicResources(gomock.Any(), routeGVR, selector).Return(
   664  				&unstructured.UnstructuredList{Items: []unstructured.Unstructured{{Object: routeUnstructured}}}, nil)
   665  		}
   666  		return client
   667  	}
   668  	type args struct {
   669  		client        func(ctrl *gomock.Controller) kclient.ClientInterface
   670  		componentName string
   671  	}
   672  	tests := []struct {
   673  		name       string
   674  		args       args
   675  		wantIngs   []api.ConnectionData
   676  		wantRoutes []api.ConnectionData
   677  		wantErr    bool
   678  	}{
   679  		{
   680  			name: "list both ingresses and routes",
   681  			args: args{
   682  				client: func(ctrl *gomock.Controller) kclient.ClientInterface {
   683  					return mockKubeClient(ctrl, true, []v1.Ingress{*ing}, routeUnstructured)
   684  				},
   685  				componentName: componentName,
   686  			},
   687  			wantIngs:   []api.ConnectionData{ingConnectionData},
   688  			wantRoutes: []api.ConnectionData{routeConnectionData},
   689  			wantErr:    false,
   690  		},
   691  		{
   692  			name: "list only ingresses when the cluster is not ocp",
   693  			args: args{
   694  				client: func(ctrl *gomock.Controller) kclient.ClientInterface {
   695  					return mockKubeClient(ctrl, false, []v1.Ingress{*ing}, nil)
   696  				},
   697  				componentName: componentName,
   698  			},
   699  			wantIngs:   []api.ConnectionData{ingConnectionData},
   700  			wantRoutes: nil,
   701  			wantErr:    false,
   702  		},
   703  		{
   704  			name: "list ingress with default backend and no rules",
   705  			args: args{
   706  				client: func(ctrl *gomock.Controller) kclient.ClientInterface {
   707  					return mockKubeClient(ctrl, false, []v1.Ingress{*ingDefaultBackend}, nil)
   708  				},
   709  				componentName: componentName,
   710  			},
   711  			wantIngs:   []api.ConnectionData{ingDBConnectionData},
   712  			wantRoutes: nil,
   713  			wantErr:    false,
   714  		},
   715  		{
   716  			name: "skip ingress if it has an owner reference",
   717  			args: args{
   718  				client: func(ctrl *gomock.Controller) kclient.ClientInterface {
   719  					ownedIng := ing
   720  					ownedIng.SetOwnerReferences([]metav1.OwnerReference{
   721  						{
   722  							APIVersion: route.APIVersion,
   723  							Kind:       route.Kind,
   724  							Name:       route.GetName(),
   725  						},
   726  					})
   727  					return mockKubeClient(ctrl, false, []v1.Ingress{*ownedIng}, nil)
   728  				},
   729  				componentName: componentName,
   730  			},
   731  			wantIngs:   nil,
   732  			wantRoutes: nil,
   733  			wantErr:    false,
   734  		},
   735  		{
   736  			name: "skip route if it has an owner reference",
   737  			args: args{client: func(ctrl *gomock.Controller) kclient.ClientInterface {
   738  				ownedRoute := route
   739  				ownedRoute.SetOwnerReferences([]metav1.OwnerReference{
   740  					{
   741  						APIVersion: "apps/v1",
   742  						Kind:       "Deployment",
   743  						Name:       "some-deployment",
   744  					},
   745  				})
   746  				ownedRouteUnstructured, _ := runtime.DefaultUnstructuredConverter.ToUnstructured(ownedRoute)
   747  				return mockKubeClient(ctrl, true, nil, ownedRouteUnstructured)
   748  			},
   749  				componentName: componentName,
   750  			},
   751  			wantIngs:   nil,
   752  			wantRoutes: nil,
   753  			wantErr:    false,
   754  		},
   755  	}
   756  	for _, tt := range tests {
   757  		t.Run(tt.name, func(t *testing.T) {
   758  			ctrl := gomock.NewController(t)
   759  			gotIngs, gotRoutes, err := ListRoutesAndIngresses(tt.args.client(ctrl), tt.args.componentName, "app")
   760  			if (err != nil) != tt.wantErr {
   761  				t.Errorf("ListRoutesAndIngresses() error = %v, wantErr %v", err, tt.wantErr)
   762  				return
   763  			}
   764  			if diff := cmp.Diff(tt.wantIngs, gotIngs); diff != "" {
   765  				t.Errorf("ListRoutesAndIngresses() wantIngs mismatch (-want +got):\n%s", diff)
   766  			}
   767  			if diff := cmp.Diff(tt.wantRoutes, gotRoutes); diff != "" {
   768  				t.Errorf("ListRoutesAndIngresses() wantRoutes mismatch (-want +got):\n%s", diff)
   769  			}
   770  		})
   771  	}
   772  }
   773  
   774  func TestGetDevfileInfo(t *testing.T) {
   775  	const kubeNs = "a-namespace"
   776  
   777  	packageManifestResource := unstructured.Unstructured{}
   778  	packageManifestResource.SetKind("PackageManifest")
   779  	packageManifestResource.SetLabels(labels.Builder().WithMode(labels.ComponentDevMode).Labels())
   780  
   781  	type args struct {
   782  		kubeClient    func(ctx context.Context, ctrl *gomock.Controller, componentName string) kclient.ClientInterface
   783  		podmanClient  func(ctx context.Context, ctrl *gomock.Controller, componentName string) podman.Client
   784  		componentName string
   785  	}
   786  	tests := []struct {
   787  		name    string
   788  		args    args
   789  		want    func() (parser.DevfileObj, error)
   790  		wantErr bool
   791  	}{
   792  		{
   793  			name: "no kube client and no podman client",
   794  			args: args{
   795  				componentName: "aname",
   796  			},
   797  			wantErr: true,
   798  			want: func() (parser.DevfileObj, error) {
   799  				return parser.DevfileObj{}, nil
   800  			},
   801  		},
   802  		{
   803  			name: "only kube client returning an error",
   804  			args: args{
   805  				componentName: "some-name",
   806  				kubeClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) kclient.ClientInterface {
   807  					c := kclient.NewMockClientInterface(ctrl)
   808  					c.EXPECT().GetCurrentNamespace().Return(kubeNs).AnyTimes()
   809  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(nil, errors.New("error"))
   810  					return c
   811  				},
   812  			},
   813  			wantErr: true,
   814  			want: func() (parser.DevfileObj, error) {
   815  				return parser.DevfileObj{}, nil
   816  			},
   817  		},
   818  		{
   819  			name: "only kube client returning an empty list",
   820  			args: args{
   821  				componentName: "some-name",
   822  				kubeClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) kclient.ClientInterface {
   823  					c := kclient.NewMockClientInterface(ctrl)
   824  					c.EXPECT().GetCurrentNamespace().Return(kubeNs).AnyTimes()
   825  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(nil, nil)
   826  					return c
   827  				},
   828  			},
   829  			wantErr: true,
   830  			want: func() (parser.DevfileObj, error) {
   831  				return parser.DevfileObj{}, nil
   832  			},
   833  		},
   834  		{
   835  			name: "only kube client returning PackageManifest resource",
   836  			args: args{
   837  				componentName: "some-name",
   838  				kubeClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) kclient.ClientInterface {
   839  					c := kclient.NewMockClientInterface(ctrl)
   840  					c.EXPECT().GetCurrentNamespace().Return(kubeNs).AnyTimes()
   841  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(
   842  						[]unstructured.Unstructured{packageManifestResource}, nil)
   843  					return c
   844  				},
   845  			},
   846  			wantErr: true,
   847  			want: func() (parser.DevfileObj, error) {
   848  				return parser.DevfileObj{}, nil
   849  			},
   850  		},
   851  		{
   852  			name: "only podman client returning an error",
   853  			args: args{
   854  				componentName: "some-name",
   855  				podmanClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) podman.Client {
   856  					c := podman.NewMockClient(ctrl)
   857  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(nil, errors.New("error"))
   858  					return c
   859  				},
   860  			},
   861  			wantErr: true,
   862  			want: func() (parser.DevfileObj, error) {
   863  				return parser.DevfileObj{}, nil
   864  			},
   865  		},
   866  		{
   867  			name: "only podman client returning an empty list",
   868  			args: args{
   869  				componentName: "some-name",
   870  				podmanClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) podman.Client {
   871  					c := podman.NewMockClient(ctrl)
   872  					c.EXPECT().GetAllResourcesFromSelector(gomock.Any(), gomock.Any()).Return(nil, nil)
   873  					return c
   874  				},
   875  			},
   876  			wantErr: true,
   877  			want: func() (parser.DevfileObj, error) {
   878  				return parser.DevfileObj{}, nil
   879  			},
   880  		},
   881  		{
   882  			name: "kube and podman clients returning same component with mismatching labels",
   883  			args: args{
   884  				componentName: "some-name",
   885  				kubeClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) kclient.ClientInterface {
   886  					u1 := unstructured.Unstructured{}
   887  					u1.SetLabels(labels.Builder().
   888  						WithComponentName(componentName).
   889  						WithMode(labels.ComponentDevMode).
   890  						WithProjectType("spring").
   891  						Labels())
   892  					u2 := unstructured.Unstructured{}
   893  					u2.SetLabels(labels.Builder().
   894  						WithComponentName(componentName).
   895  						WithMode(labels.ComponentDeployMode).
   896  						WithProjectType("spring").
   897  						Labels())
   898  					c := kclient.NewMockClientInterface(ctrl)
   899  					c.EXPECT().GetCurrentNamespace().Return(kubeNs).AnyTimes()
   900  					selector := labels.GetNameSelector(componentName)
   901  					c.EXPECT().GetAllResourcesFromSelector(gomock.Eq(selector), gomock.Eq(kubeNs)).
   902  						Return([]unstructured.Unstructured{u1, packageManifestResource, u2}, nil)
   903  					return c
   904  				},
   905  				podmanClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) podman.Client {
   906  					u1 := unstructured.Unstructured{}
   907  					u1.SetLabels(labels.Builder().
   908  						WithComponentName(componentName).
   909  						WithMode(labels.ComponentDevMode).
   910  						WithProjectType("quarkus").
   911  						Labels())
   912  					c := podman.NewMockClient(ctrl)
   913  					selector := labels.GetNameSelector(componentName)
   914  					c.EXPECT().GetAllResourcesFromSelector(gomock.Eq(selector), gomock.Eq("")).
   915  						Return([]unstructured.Unstructured{u1}, nil)
   916  					return c
   917  				},
   918  			},
   919  			wantErr: true,
   920  			want: func() (parser.DevfileObj, error) {
   921  				return parser.DevfileObj{}, nil
   922  			},
   923  		},
   924  		{
   925  			name: "only kube client returning component",
   926  			args: args{
   927  				componentName: "some-name",
   928  				kubeClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) kclient.ClientInterface {
   929  					u1 := unstructured.Unstructured{}
   930  					u1.SetLabels(labels.Builder().
   931  						WithComponentName(componentName).
   932  						WithMode(labels.ComponentDeployMode).
   933  						WithProjectType("spring").
   934  						Labels())
   935  					c := kclient.NewMockClientInterface(ctrl)
   936  					c.EXPECT().GetCurrentNamespace().Return(kubeNs).AnyTimes()
   937  					selector := labels.GetNameSelector(componentName)
   938  					c.EXPECT().GetAllResourcesFromSelector(gomock.Eq(selector), gomock.Eq(kubeNs)).
   939  						Return([]unstructured.Unstructured{u1}, nil)
   940  					return c
   941  				},
   942  				podmanClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) podman.Client {
   943  					c := podman.NewMockClient(ctrl)
   944  					selector := labels.GetNameSelector(componentName)
   945  					c.EXPECT().GetAllResourcesFromSelector(gomock.Eq(selector), gomock.Eq("")).Return(nil, nil)
   946  					return c
   947  				},
   948  			},
   949  			wantErr: false,
   950  			want: func() (parser.DevfileObj, error) {
   951  				devfileData, err := data.NewDevfileData(string(data.APISchemaVersion200))
   952  				if err != nil {
   953  					return parser.DevfileObj{}, err
   954  				}
   955  				metadata := devfileData.GetMetadata()
   956  				metadata.Name = "some-name"
   957  				metadata.DisplayName = UnknownValue
   958  				metadata.ProjectType = "spring"
   959  				metadata.Language = UnknownValue
   960  				metadata.Version = UnknownValue
   961  				metadata.Description = UnknownValue
   962  				devfileData.SetMetadata(metadata)
   963  				return parser.DevfileObj{
   964  					Data: devfileData,
   965  				}, nil
   966  			},
   967  		},
   968  		{
   969  			name: "only podman client returning component",
   970  			args: args{
   971  				componentName: "some-name",
   972  				kubeClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) kclient.ClientInterface {
   973  					c := kclient.NewMockClientInterface(ctrl)
   974  					c.EXPECT().GetCurrentNamespace().Return(kubeNs).AnyTimes()
   975  					selector := labels.GetNameSelector(componentName)
   976  					c.EXPECT().GetAllResourcesFromSelector(gomock.Eq(selector), gomock.Eq(kubeNs)).
   977  						Return(nil, nil)
   978  					return c
   979  				},
   980  				podmanClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) podman.Client {
   981  					u1 := unstructured.Unstructured{}
   982  					u1.SetLabels(labels.Builder().
   983  						WithComponentName(componentName).
   984  						WithMode(labels.ComponentDevMode).
   985  						WithProjectType("quarkus").
   986  						Labels())
   987  					c := podman.NewMockClient(ctrl)
   988  					selector := labels.GetNameSelector(componentName)
   989  					c.EXPECT().GetAllResourcesFromSelector(gomock.Eq(selector), gomock.Eq("")).Return(
   990  						[]unstructured.Unstructured{u1}, nil)
   991  					return c
   992  				},
   993  			},
   994  			wantErr: false,
   995  			want: func() (parser.DevfileObj, error) {
   996  				devfileData, err := data.NewDevfileData(string(data.APISchemaVersion200))
   997  				if err != nil {
   998  					return parser.DevfileObj{}, err
   999  				}
  1000  				metadata := devfileData.GetMetadata()
  1001  				metadata.Name = "some-name"
  1002  				metadata.DisplayName = UnknownValue
  1003  				metadata.ProjectType = "quarkus"
  1004  				metadata.Language = UnknownValue
  1005  				metadata.Version = UnknownValue
  1006  				metadata.Description = UnknownValue
  1007  				devfileData.SetMetadata(metadata)
  1008  				return parser.DevfileObj{
  1009  					Data: devfileData,
  1010  				}, nil
  1011  			},
  1012  		},
  1013  		{
  1014  			name: "both kube and podman clients returning component",
  1015  			args: args{
  1016  				componentName: "some-name",
  1017  				kubeClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) kclient.ClientInterface {
  1018  					u1 := unstructured.Unstructured{}
  1019  					u1.SetLabels(labels.Builder().
  1020  						WithComponentName(componentName).
  1021  						WithMode(labels.ComponentDeployMode).
  1022  						WithProjectType("nodejs").
  1023  						Labels())
  1024  					c := kclient.NewMockClientInterface(ctrl)
  1025  					c.EXPECT().GetCurrentNamespace().Return(kubeNs).AnyTimes()
  1026  					selector := labels.GetNameSelector(componentName)
  1027  					c.EXPECT().GetAllResourcesFromSelector(gomock.Eq(selector), gomock.Eq(kubeNs)).
  1028  						Return([]unstructured.Unstructured{u1}, nil)
  1029  					return c
  1030  				},
  1031  				podmanClient: func(ctx context.Context, ctrl *gomock.Controller, componentName string) podman.Client {
  1032  					u1 := unstructured.Unstructured{}
  1033  					u1.SetLabels(labels.Builder().
  1034  						WithComponentName(componentName).
  1035  						WithMode(labels.ComponentDevMode).
  1036  						WithProjectType("nodejs").
  1037  						Labels())
  1038  					c := podman.NewMockClient(ctrl)
  1039  					selector := labels.GetNameSelector(componentName)
  1040  					c.EXPECT().GetAllResourcesFromSelector(gomock.Eq(selector), gomock.Eq("")).Return(
  1041  						[]unstructured.Unstructured{u1}, nil)
  1042  					return c
  1043  				},
  1044  			},
  1045  			wantErr: false,
  1046  			want: func() (parser.DevfileObj, error) {
  1047  				devfileData, err := data.NewDevfileData(string(data.APISchemaVersion200))
  1048  				if err != nil {
  1049  					return parser.DevfileObj{}, err
  1050  				}
  1051  				metadata := devfileData.GetMetadata()
  1052  				metadata.Name = "some-name"
  1053  				metadata.DisplayName = UnknownValue
  1054  				metadata.ProjectType = "nodejs"
  1055  				metadata.Language = UnknownValue
  1056  				metadata.Version = UnknownValue
  1057  				metadata.Description = UnknownValue
  1058  				devfileData.SetMetadata(metadata)
  1059  				return parser.DevfileObj{
  1060  					Data: devfileData,
  1061  				}, nil
  1062  			},
  1063  		},
  1064  	}
  1065  
  1066  	for _, tt := range tests {
  1067  		t.Run(tt.name, func(t *testing.T) {
  1068  			ctrl := gomock.NewController(t)
  1069  			ctx := odocontext.WithApplication(context.TODO(), "app")
  1070  			var kubeClient kclient.ClientInterface
  1071  			if tt.args.kubeClient != nil {
  1072  				kubeClient = tt.args.kubeClient(ctx, ctrl, tt.args.componentName)
  1073  			}
  1074  			var podmanClient podman.Client
  1075  			if tt.args.podmanClient != nil {
  1076  				podmanClient = tt.args.podmanClient(ctx, ctrl, tt.args.componentName)
  1077  			}
  1078  
  1079  			got, err := GetDevfileInfo(ctx, kubeClient, podmanClient, tt.args.componentName)
  1080  			if (err != nil) != tt.wantErr {
  1081  				t.Errorf("error = %v, wantErr %v", err, tt.wantErr)
  1082  			}
  1083  			want, err := tt.want()
  1084  			if err != nil {
  1085  				t.Errorf("GetDevfileInfo() error while building wanted DevfileObj: %v", err)
  1086  				return
  1087  			}
  1088  			if diff := cmp.Diff(want, got, cmp.AllowUnexported(devfileCtx.DevfileCtx{})); diff != "" {
  1089  				t.Errorf("GetDevfileInfo() mismatch (-want +got):\n%s", diff)
  1090  			}
  1091  		})
  1092  	}
  1093  }
  1094  

View as plain text