func TestUnpushableBuild(t *testing.T) { // Unconfigured internal registry g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/unpushable-build.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) imageedges.AddAllImageStreamImageRefEdges(g) markers := FindUnpushableBuildConfigs(g, osgraph.DefaultNamer) if e, a := 2, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } if got, expected := markers[0].Key, MissingRequiredRegistryErr; got != expected { t.Fatalf("expected marker key %q, got %q", expected, got) } actualBC := osgraph.GetTopLevelContainerNode(g, markers[0].Node) expectedBC1 := g.Find(osgraph.UniqueName("BuildConfig|example/ruby-hello-world")) expectedBC2 := g.Find(osgraph.UniqueName("BuildConfig|example/ruby-hello-world-2")) if e1, e2, a := expectedBC1.ID(), expectedBC2.ID(), actualBC.ID(); e1 != a && e2 != a { t.Errorf("expected either %v or %v, got %v", e1, e2, a) } actualIST := markers[0].RelatedNodes[0] expectedIST := g.Find(osgraph.UniqueName("ImageStreamTag|example/ruby-hello-world:latest")) if e, a := expectedIST.ID(), actualIST.ID(); e != a { t.Errorf("expected %v, got %v: \n%v", e, a, g) } // Missing image stream g, _, err = osgraphtest.BuildGraph("../../../api/graph/test/unpushable-build-2.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) imageedges.AddAllImageStreamImageRefEdges(g) markers = FindUnpushableBuildConfigs(g, osgraph.DefaultNamer) if e, a := 1, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } if got, expected := markers[0].Key, MissingOutputImageStreamErr; got != expected { t.Fatalf("expected marker key %q, got %q", expected, got) } }
func TestUnpushableBuild(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/unpushable-build.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) markers := FindUnpushableBuildConfigs(g) if e, a := 1, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } actualBC := osgraph.GetTopLevelContainerNode(g, markers[0].Node) expectedBC := g.Find(osgraph.UniqueName("BuildConfig|/ruby-hello-world")) if e, a := expectedBC.ID(), actualBC.ID(); e != a { t.Errorf("expected %v, got %v", e, a) } actualIST := markers[0].RelatedNodes[0] expectedIST := g.Find(osgraph.UniqueName("ImageStreamTag|/ruby-hello-world:latest")) if e, a := expectedIST.ID(), actualIST.ID(); e != a { t.Errorf("expected %v, got %v: \n%v", e, a, g) } }
func TestPendingImageStreamTag(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/unpushable-build.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) buildedges.AddAllBuildEdges(g) imageedges.AddAllImageStreamRefEdges(g) imageedges.AddAllImageStreamImageRefEdges(g) // Drop the build to showcase a TagNotAvailable warning (should happen when no // build is new, pending, or running currently) nodeFn := osgraph.NodesOfKind(imagegraph.ImageStreamTagNodeKind, buildgraph.BuildConfigNodeKind) edgeFn := osgraph.EdgesOfKind(buildedges.BuildInputImageEdgeKind, buildedges.BuildOutputEdgeKind) g = g.Subgraph(nodeFn, edgeFn) markers := FindPendingTags(g, osgraph.DefaultNamer) if e, a := 1, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } if got, expected := markers[0].Key, TagNotAvailableWarning; got != expected { t.Fatalf("expected marker key %q, got %q", expected, got) } }
func (d *ProjectStatusDescriber) MakeGraph(namespace string) (osgraph.Graph, sets.String, error) { g := osgraph.New() loaders := []GraphLoader{ &serviceLoader{namespace: namespace, lister: d.K}, &serviceAccountLoader{namespace: namespace, lister: d.K}, &secretLoader{namespace: namespace, lister: d.K}, &rcLoader{namespace: namespace, lister: d.K}, &podLoader{namespace: namespace, lister: d.K}, // TODO check swagger for feature enablement and selectively add bcLoader and buildLoader // then remove errors.TolerateNotFoundError method. &bcLoader{namespace: namespace, lister: d.C}, &buildLoader{namespace: namespace, lister: d.C}, &isLoader{namespace: namespace, lister: d.C}, &dcLoader{namespace: namespace, lister: d.C}, &routeLoader{namespace: namespace, lister: d.C}, } loadingFuncs := []func() error{} for _, loader := range loaders { loadingFuncs = append(loadingFuncs, loader.Load) } forbiddenResources := sets.String{} if errs := parallel.Run(loadingFuncs...); len(errs) > 0 { actualErrors := []error{} for _, err := range errs { if kapierrors.IsForbidden(err) { forbiddenErr := err.(*kapierrors.StatusError) if (forbiddenErr.Status().Details != nil) && (len(forbiddenErr.Status().Details.Kind) > 0) { forbiddenResources.Insert(forbiddenErr.Status().Details.Kind) } continue } actualErrors = append(actualErrors, err) } if len(actualErrors) > 0 { return g, forbiddenResources, utilerrors.NewAggregate(actualErrors) } } for _, loader := range loaders { loader.AddToGraph(g) } kubeedges.AddAllExposedPodTemplateSpecEdges(g) kubeedges.AddAllExposedPodEdges(g) kubeedges.AddAllManagedByRCPodEdges(g) kubeedges.AddAllRequestedServiceAccountEdges(g) kubeedges.AddAllMountableSecretEdges(g) kubeedges.AddAllMountedSecretEdges(g) buildedges.AddAllInputOutputEdges(g) buildedges.AddAllBuildEdges(g) deployedges.AddAllTriggerEdges(g) deployedges.AddAllDeploymentEdges(g) imageedges.AddAllImageStreamRefEdges(g) routeedges.AddAllRouteEdges(g) return g, forbiddenResources, nil }
func (d *ProjectStatusDescriber) MakeGraph(namespace string) (osgraph.Graph, error) { g := osgraph.New() svcs, err := d.K.Services(namespace).List(labels.Everything()) if err != nil { return g, err } iss, err := d.C.ImageStreams(namespace).List(labels.Everything(), fields.Everything()) if err != nil { return g, err } bcs, err := d.C.BuildConfigs(namespace).List(labels.Everything(), fields.Everything()) if err != nil { return g, err } dcs, err := d.C.DeploymentConfigs(namespace).List(labels.Everything(), fields.Everything()) if err != nil { return g, err } builds := &buildapi.BuildList{} if len(bcs.Items) > 0 { if b, err := d.C.Builds(namespace).List(labels.Everything(), fields.Everything()); err == nil { builds = b } } rcs, err := d.K.ReplicationControllers(namespace).List(labels.Everything()) if err != nil { rcs = &kapi.ReplicationControllerList{} } for i := range iss.Items { imagegraph.EnsureImageStreamNode(g, &iss.Items[i]) imagegraph.EnsureAllImageStreamTagNodes(g, &iss.Items[i]) } for i := range bcs.Items { build := buildgraph.EnsureBuildConfigNode(g, &bcs.Items[i]) buildedges.AddInputOutputEdges(g, build) buildedges.JoinBuilds(build, builds.Items) } for i := range dcs.Items { deploy := deploygraph.EnsureDeploymentConfigNode(g, &dcs.Items[i]) deployedges.AddTriggerEdges(g, deploy) deployedges.JoinDeployments(deploy, rcs.Items) } for i := range svcs.Items { service := kubegraph.EnsureServiceNode(g, &svcs.Items[i]) kubeedges.AddExposedPodTemplateSpecEdges(g, service) } imageedges.AddAllImageStreamRefEdges(g) return g, nil }
func TestPushableBuild(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/pushable-build.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) if e, a := false, hasUnresolvedImageStreamTag(g); e != a { t.Errorf("expected %v, got %v", e, a) } }
func TestPushableBuild(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/pushable-build.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) if e, a := 0, len(FindUnpushableBuildConfigs(g, osgraph.DefaultNamer)); e != a { t.Errorf("expected %v, got %v", e, a) } }
func TestImageStreamPresent(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/prereq-image-present.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) imageedges.AddAllImageStreamImageRefEdges(g) if e, a := 0, len(FindMissingInputImageStreams(g, osgraph.DefaultNamer)); e != a { t.Errorf("expected %v, got %v", e, a) } }
func TestLatestBuildFailed(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/failed-build.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) buildedges.AddAllBuildEdges(g) imageedges.AddAllImageStreamRefEdges(g) markers := FindPendingTags(g, osgraph.DefaultNamer) if e, a := 1, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } if got, expected := markers[0].Key, LatestBuildFailedErr; got != expected { t.Fatalf("expected marker key %q, got %q", expected, got) } }
func TestMissingReadinessProbe(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/unpushable-build-2.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) deployedges.AddAllTriggerEdges(g) imageedges.AddAllImageStreamRefEdges(g) markers := FindDeploymentConfigReadinessWarnings(g, osgraph.DefaultNamer, "command probe") if e, a := 1, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } if got, expected := markers[0].Key, MissingReadinessProbeWarning; got != expected { t.Fatalf("expected marker key %q, got %q", expected, got) } }
func TestMissingImageStreamTag(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/missing-istag.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) deployedges.AddAllTriggerEdges(g) imageedges.AddAllImageStreamRefEdges(g) markers := FindDeploymentConfigTriggerErrors(g, osgraph.DefaultNamer) if e, a := 1, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } if got, expected := markers[0].Key, MissingImageStreamTagWarning; got != expected { t.Fatalf("expected marker key %q, got %q", expected, got) } }
func TestSyntheticImageStreamTag(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/unpushable-build.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) deployedges.AddAllTriggerEdges(g) imageedges.AddAllImageStreamRefEdges(g) markers := FindDeploymentConfigTriggerErrors(g) if e, a := 1, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } if got, expected := markers[0].Key, ImageStreamTagNotAvailableInfo; got != expected { t.Fatalf("expected marker key %q, got %q", expected, got) } }
func TestAllBCImageInputs(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/prereq-image-present.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) imageedges.AddAllImageStreamImageRefEdges(g) coveredNodes := IntSet{} bareBCPipelines, coveredByBCs := AllImagePipelinesFromBuildConfig(g, coveredNodes) coveredNodes.Insert(coveredByBCs.List()...) if e, a := 4, len(bareBCPipelines); e != a { t.Errorf("expected %v, got %v", e, a) } }
func TestImageStreamTagMissing(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/prereq-image-present-notag.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) imageedges.AddAllImageStreamImageRefEdges(g) markers := FindMissingInputImageStreams(g, osgraph.DefaultNamer) if e, a := 4, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } var actualImportOrBuild, actualImportOnly, actualSpecificHex int expectedImportOrBuild := 2 expectedImportOnly := 1 expectedSpecificHex := 1 for _, marker := range markers { if got, expected1, expected2 := marker.Key, MissingImageStreamImageWarning, MissingImageStreamTagWarning; got != expected1 && got != expected2 { t.Fatalf("expected marker key %q or %q, got %q", expected1, expected2, got) } else { if strings.Contains(marker.Suggestion.String(), "oc start-build") { actualImportOrBuild++ } if strings.Contains(marker.Suggestion.String(), "needs to be imported.") { actualImportOnly++ } if strings.Contains(marker.Suggestion.String(), "hexadecimal ID") { actualSpecificHex++ } } } if actualImportOnly != expectedImportOnly { t.Fatalf("expected %d import only suggestions but got %d", expectedImportOnly, actualImportOnly) } if actualImportOrBuild != expectedImportOrBuild { t.Fatalf("expected %d import or build suggestions but got %d", expectedImportOrBuild, actualImportOrBuild) } if actualSpecificHex != expectedSpecificHex { t.Fatalf("expected %d import specific image suggestions but got %d", expectedSpecificHex, actualSpecificHex) } }
func TestImageStreamTagMissing(t *testing.T) { g, _, err := osgraphtest.BuildGraph("../../../api/graph/test/prereq-image-present-notag.yaml") if err != nil { t.Fatalf("unexpected error: %v", err) } buildedges.AddAllInputOutputEdges(g) imageedges.AddAllImageStreamRefEdges(g) imageedges.AddAllImageStreamImageRefEdges(g) markers := FindMissingInputImageStreams(g, osgraph.DefaultNamer) if e, a := 4, len(markers); e != a { t.Fatalf("expected %v, got %v", e, a) } for _, marker := range markers { if got, expected1, expected2 := marker.Key, MissingImageStreamImageWarning, MissingImageStreamTagWarning; got != expected1 && got != expected2 { t.Fatalf("expected marker key %q or %q, got %q", expected1, expected2, got) } } }
func (d *ProjectStatusDescriber) MakeGraph(namespace string) (osgraph.Graph, error) { g := osgraph.New() loaders := []GraphLoader{ &serviceLoader{namespace: namespace, lister: d.K}, &serviceAccountLoader{namespace: namespace, lister: d.K}, &secretLoader{namespace: namespace, lister: d.K}, &rcLoader{namespace: namespace, lister: d.K}, &podLoader{namespace: namespace, lister: d.K}, &bcLoader{namespace: namespace, lister: d.C}, &buildLoader{namespace: namespace, lister: d.C}, &isLoader{namespace: namespace, lister: d.C}, &dcLoader{namespace: namespace, lister: d.C}, } loadingFuncs := []func() error{} for _, loader := range loaders { loadingFuncs = append(loadingFuncs, loader.Load) } if errs := parallel.Run(loadingFuncs...); len(errs) > 0 { return g, utilerrors.NewAggregate(errs) } for _, loader := range loaders { loader.AddToGraph(g) } kubeedges.AddAllExposedPodTemplateSpecEdges(g) kubeedges.AddAllExposedPodEdges(g) kubeedges.AddAllManagedByRCPodEdges(g) kubeedges.AddAllRequestedServiceAccountEdges(g) kubeedges.AddAllMountableSecretEdges(g) kubeedges.AddAllMountedSecretEdges(g) buildedges.AddAllInputOutputEdges(g) buildedges.AddAllBuildEdges(g) deployedges.AddAllTriggerEdges(g) deployedges.AddAllDeploymentEdges(g) imageedges.AddAllImageStreamRefEdges(g) return g, nil }
func (d *ProjectStatusDescriber) MakeGraph(namespace string) (osgraph.Graph, error) { g := osgraph.New() loadingFuncs := []GraphLoadingFunc{loadServices, loadBuildConfigs, loadImageStreams, loadDeploymentConfigs, loadBuilds, loadReplicationControllers} listingWaitGroup := sync.WaitGroup{} graphLock := sync.Mutex{} errorChannel := make(chan error, len(loadingFuncs)) for _, loadingFunc := range loadingFuncs { listingWaitGroup.Add(1) go func(loadingFunc GraphLoadingFunc) { defer listingWaitGroup.Done() if err := loadingFunc(g, graphLock, namespace, d.K, d.C); err != nil { errorChannel <- err } }(loadingFunc) } listingWaitGroup.Wait() close(errorChannel) // if we had an error. Aggregate them and return them errlist := []error{} for err := range errorChannel { errlist = append(errlist, err) } if len(errlist) > 0 { return g, utilerrors.NewAggregate(errlist) } kubeedges.AddAllExposedPodTemplateSpecEdges(g) buildedges.AddAllInputOutputEdges(g) buildedges.AddAllBuildEdges(g) deployedges.AddAllTriggerEdges(g) deployedges.AddAllDeploymentEdges(g) imageedges.AddAllImageStreamRefEdges(g) return g, nil }