github.com/redhat-appstudio/e2e-tests@v0.0.0-20240520140907-9709f6f59323/pkg/utils/tekton/bundle.go (about)

     1  package tekton
     2  
     3  import (
     4  	"context"
     5  	"fmt"
     6  	"io"
     7  	"net/http"
     8  	"os"
     9  
    10  	"github.com/google/go-containerregistry/pkg/authn"
    11  	"github.com/google/go-containerregistry/pkg/name"
    12  	remoteimg "github.com/google/go-containerregistry/pkg/v1/remote"
    13  	buildservice "github.com/redhat-appstudio/build-service/api/v1alpha1"
    14  	"github.com/tektoncd/cli/pkg/bundle"
    15  	pipeline "github.com/tektoncd/pipeline/pkg/apis/pipeline/v1"
    16  	"github.com/tektoncd/pipeline/pkg/remote/oci"
    17  	"k8s.io/apimachinery/pkg/runtime"
    18  	"k8s.io/klog"
    19  	"sigs.k8s.io/yaml"
    20  )
    21  
    22  // ExtractTektonObjectFromBundle extracts specified Tekton object from specified bundle reference
    23  func ExtractTektonObjectFromBundle(bundleRef, kind, name string) (runtime.Object, error) {
    24  	var obj runtime.Object
    25  	var err error
    26  
    27  	resolver := oci.NewResolver(bundleRef, authn.DefaultKeychain)
    28  	if obj, _, err = resolver.Get(context.Background(), kind, name); err != nil {
    29  		return nil, fmt.Errorf("failed to fetch the tekton object %s with name %s: %v", kind, name, err)
    30  	}
    31  	return obj, nil
    32  }
    33  
    34  // BuildAndPushTektonBundle builds a Tekton bundle from YAML and pushes to remote container registry
    35  func BuildAndPushTektonBundle(YamlContent []byte, ref name.Reference, remoteOption remoteimg.Option) error {
    36  	img, err := bundle.BuildTektonBundle([]string{string(YamlContent)}, os.Stdout)
    37  	if err != nil {
    38  		return fmt.Errorf("error when building a bundle %s: %v", ref.String(), err)
    39  	}
    40  
    41  	outDigest, err := bundle.Write(img, ref, remoteOption)
    42  	if err != nil {
    43  		return fmt.Errorf("error when pushing a bundle %s to a container image registry repo: %v", ref.String(), err)
    44  	}
    45  	klog.Infof("image digest for a new tekton bundle %s: %+v", ref.String(), outDigest)
    46  
    47  	return nil
    48  }
    49  
    50  // GetBundleRef returns the bundle reference from a pipelineRef
    51  func GetBundleRef(pipelineRef *pipeline.PipelineRef) string {
    52  	_, bundleRef := GetPipelineNameAndBundleRef(pipelineRef)
    53  	return bundleRef
    54  }
    55  
    56  // GetDefaultPipelineBundleRef gets the specific Tekton pipeline bundle reference from a Build pipeline selector
    57  // (in a YAML format) from a URL specified in the parameter
    58  func GetDefaultPipelineBundleRef(buildPipelineSelectorYamlURL, selectorName string) (string, error) {
    59  	request, err := http.NewRequest("GET", buildPipelineSelectorYamlURL, nil)
    60  	if err != nil {
    61  		return "", fmt.Errorf("error creating GET request: %s", err)
    62  	}
    63  
    64  	client := &http.Client{}
    65  	res, err := client.Do(request)
    66  	if err != nil {
    67  		return "", fmt.Errorf("failed to get a build pipeline selector from url %s: %v", buildPipelineSelectorYamlURL, err)
    68  	}
    69  
    70  	defer res.Body.Close()
    71  	body, err := io.ReadAll(res.Body)
    72  	if err != nil {
    73  		return "", fmt.Errorf("failed to read the body response of a build pipeline selector: %v", err)
    74  	}
    75  	ps := &buildservice.BuildPipelineSelector{}
    76  	if err = yaml.Unmarshal(body, ps); err != nil {
    77  		return "", fmt.Errorf("failed to unmarshal build pipeline selector: %v", err)
    78  	}
    79  	for i := range ps.Spec.Selectors {
    80  		s := &ps.Spec.Selectors[i]
    81  		if s.Name == selectorName {
    82  			return GetBundleRef(&s.PipelineRef), nil
    83  		}
    84  	}
    85  
    86  	return "", fmt.Errorf("could not find %s pipeline bundle in build pipeline selector fetched from %s", selectorName, buildPipelineSelectorYamlURL)
    87  }