## 1. Project Overview & Quickstart (tektoncd/workspaces)

# workspaces

Open-source repository tektoncd/workspaces

### Repository Details
- **Repository:** [tektoncd/workspaces](https://github.com/tektoncd/workspaces)
- **Primary Language:** Code

*Note: High-volume repository documentation is actively indexed and synchronized by YakaAI.*

## 2. Official Technical Reference & Guides (tektoncd/website)

## File: README.md

# TektonCD Website

This repo contains the code behind [the Tekton org's](https://github.com/tektoncd)
website at [tekton.dev](https://tekton.dev).

For more information on the Tekton Project, see
[the community repo](https://github.com/tektoncd/community).

For more information on contributing to the website see:

* [CONTRIBUTING.md](CONTRIBUTING.md)
* [DEVELOPMENT.md](DEVELOPMENT.md)

---

## File: asciinema/README.md

This directory includes the configuration for rendering the asciinema
panel in the tekton.dev homepage.

A rendered panel (an asciinema cast) has been included at
`../static/asciinema/demo.cast`. To rebuild the cast, run the commands below:

```bash
./run.sh
rm -f ../static/asciinema/demo.cast
mv ./demo.cast ../static/asciinema/demo.cast
```

---

## File: content/en/blog/2022/graduation/index.md

---
title: Tekton Graduation
linkTitle: Tekton Graduation
date: 2022-10-26
author: "Andrea Frittoli"
  From founding project to graduated, a brief history of Tekton
---

We're very happy to announce that Tekton has reached graduated status within the
Continuous Delivery Foundation (CDF). The CDF Technical Oversight Committee
(TOC) conducted public [voting][voting-email] to decide on the graduation status
for Tekton, and the result was unanimously positive. The Tekton community is
very proud of the results of the vote and will continue working to make Tekton
better and safer for its users.

In this blog post I will explore a bit of the history of Tekton, its "road to
graduation" and what this milestone means for the project.

## Early Days

The Tekton project has its roots in [Knative][knative], where it was initially
called "Knative Build" and later "Knative Pipeline". The project was spun off in
August 2018, when it got it's current name and a new home on GitHub as
["tektoncd/pipeline"][pipeline-repo]. Here's one of the project's very first
commits:

```git
commit 49d2316d71e8c315e0a8fd76008bc2920f56b3c3
Author: Christie Wilson 
Date:   Fri Aug 31 17:15:35 2018 -0700

Add pipeline strawman example

@dlorenc @ImJasonH @tejal29 @aaron-prindle and I have been working on a
strawman proposal for adding a Pipeline CRD and also for possibly
envolving the Build CRD into a slightly more generic Task CRD.

This PR demonstrates some paper prototype examples of what it could look
like to define pipelines using the CRDs described in the README.
```

A few months later, in March 2019, [Tekton was donated][cdf-creation-blog] to
the newly formed [Continuos Delivery Foundation (CDF)][cdf].

## Growing the community

Since then the project has thrived thanks to a rich community of contributors.
One of earlier repositories to be created was the [community][community-repo]
one, where the project documented its governance, code of conduct and
contributing guidelines.

At the end of 2019 Tekton the number of repositories had grown to eleven. A
regular monthly release cadence was established - Pipeline had 9 releases and in
March 2020 the beta version of the Tekton Pipeline API was
[released][pipeline-beta-release]. During this time, we also implemented the
project's release automation using Tekton itself.

The "results" and "chains" project were started in spring 2020, and in August
the Tekton Hub was [officially launched][tekton-hub-launch].

The Tekton community kept growing thanks to Tekton adopters and end-users
contributing features, ideas and issues.

{{< imgproc contributions Fit 700x500 >}} Contributions and contributors to
Tekton Projects over time. Source [devstats](https://tekton.devstats.cd.foundation/d/74/contributions-chart?orgId=1&from=1540938487786&to=1666996087786&var-period=m&var-metric=contributions&var-repogroup_name=All&var-country_name=All&var-company_name=All&var-company=all&viewPanel=5&theme=light&kiosk=).
{{< /imgproc >}}

## Focus on security

One year later, it's now 2021, Tekton had matured considerably, while remaining
true to its nature of having a small footprint and giving users full flexibility
in how they setup their CI/CD system through Tekton.

This very flexibility has enabled Tekton to become the base for the
implementation of more opinionated services on top, ranging from open source
projects, and cloud services as well as end-user platforms for DevOps services.

It was then prime time to focus more thoroughly on security! In July 2021 the
Tekton Vulnerability Team was formed. Tekton pipelines release v0.29 was the
first one to be signed through Tekton chains, with the provenance Rekor UUID
included in the release notes.

End user adoption shows how Tekton, with the help of Tekton Chains, can help
solve software supply chain security challenges.

Very excited to see SolarWinds Trebuchet really exploring the full potential of Tekton!! 😻 [#SupplyChainSecurityCon](https://twitter.com/hashtag/SupplyChainSecurityCon?src=hash&amp;ref_src=twsrc%5Etfw) [#KubeCon](https://twitter.com/hashtag/KubeCon?src=hash&amp;ref_src=twsrc%5Etfw) [https://t.co/IFJKvED1q7](https://t.co/IFJKvED1q7) [pic.twitter.com/bS1UuBGuxh](https://t.co/bS1UuBGuxh)&mdash; tektoncd (@tektoncd) [October 11, 2021](https://twitter.com/tektoncd/status/1447608787737538560?ref_src=twsrc%5Etfw) <script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>

In March 2022, thanks to the the sponsorship of the CDF, Tekton completed an
[independent security audit][security-audit].

Later that year, Tekton achieved the [OpenSSF Best Practices
badges][openssf-badge] for its six core components.

## Long Term Support 

In October 2022 the Tekton community defined its [policy for long term support
(LTS)][lts-policy]:

> The Tekton project maintains four release branches for each project, created
one every three months, which results in a overall support window of
approximately one year for each of these releases.

These releases are called LTS, and throughout the support period, patch releases
may be created to resolve:

- CVEs (under the advisement of the Tekton Vulnerability Team)
- dependency issues (including base image updates)
- critical core component issues

The community-wide policy can be extended by each project. Pipeline continuous
with its monthly cadence, and it selects four releases a year for LTS.

{{< imgproc releases Fit 700x500 >}} Tekton Pipeline Releases and their support
window. {{< /imgproc >}}

## Graduation

The Graduated Stage for projects under the CD Foundation umbrella is when they
have reached their growth goals and are now on a sustaining cycle of
development, maintenance, and long-term support. Graduated Stage projects are
used commonly in enterprise production environments and have large,
well-established project communities.

More specifically, the Technical Oversight Committee (TOC) [defines
graduation][graduation-charter] as a set of requirements about project maturity,
best practices, security stance and adoption. 

Tekton is the second project to graduate from the CD Foundation, after Jenkins.
All the details about the twelve graduation criteria be found in the [graduation
proposal][graduation-proposal].

{{< imgproc banner Fit 700x500 >}}{{< /imgproc >}}

## What's Next

Graduation is a great milestone for the project and a great responsibility too.
The community will continue to work on improving Tekton, while keeping the
project stable and secure.

We are working on several security features like trusted resources and trusted
workloads, as well as releasing the v1 version of the API.

## Acknowledgments

The graduation has been the result of the years long work of the Tekton
community. Congratulations and thank you to all the Tekton contributors who made
it possible!

Thank you for the the CDF for hosting the project and supporting it, especially
through the security audit. Thank you to the TOC and its chair Oleg for their
support and sponsorship as well as to the CDF team, Fatih, Jesse and Roxanne for
their great work with marketing and organizing the [press
release][press-release].

[knative]: https://knative.dev
[cdf-creation-blog]:
    https://cd.foundation/blog/2019/03/12/introducing-the-continuous-delivery-foundation-the-new-home-for-tekton-jenkins-jenkins-x-and-spinnaker/
[cdf]: https://cd.foundation
[tekton-hub-launch]:
    https://cd.foundation/blog/2020/08/10/introducing-tekton-hub/
[pipeline-repo]: https://github.com/tektoncd/pipeline
[pipeline-beta-release]:
    https://github.com/tektoncd/pipeline/releases/tag/v0.11.0
[security-audit]:
    https://cd.foundation/blog/2022/08/26/tekton-security-review-completed/
[graduation-charter]:
    https://github.com/cdfoundation/toc/blob/b4844654fe5d355496481bed1bff3166889584ed/PROJECT_LIFECYCLE.md#graduated-stage
[graduation-proposal]:
    https://github.com/cdfoundation/toc/blob/main/proposals/tekton/graduation.md
[lts-policy]:
    https://github.com/tektoncd/community/blob/main/releases.md#support-policy
[openssf-badge]: https://bestpractices.coreinfrastructure.org/en
[press-release]:
    https://cd.foundation/announcement/2022/10/25/cd-foundation-welcomes-new-software-supply-chain-security-project-pyrsia-announces-tekton-graduation-and-cdevents-release/
[voting-email]: https://lists.cd.foundation/g/cdf-toc/topic/94265202#861
[community-repo]: https://github.com/tektoncd/community

---

## File: content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/README.md

# Speed Up Container Image Builds in Tekton Pipelines

This repo contains example assets to test different ways to improve build speed on Tekton pipelines.

---

## File: content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/index.md

---
title: Speeding Up Container Image Builds in Tekton Pipelines
linkTitle: Speeding Up Container Image Builds in Tekton Pipelines
date: 2023-11-02
author: "Giovanni Galloro, Google"
  Various caching approaches to speed container builds in Tekton
---


## Overview

When DevOps or developer teams evaluate the move from a persistent CI server (or a CI server using persistent workers) to a system using non-persistent workers backed by Kubernetes pods, such as Tekton Pipelines, they might also wonder how to speed up container image building using cached layers. While using cached layers is relatively easy when builds always run on the same server where layers can be stored locally, it is more challenging in an environment where the builds are run in non-persistent containers on Kubernetes. This article will show how to use Kaniko caching capabilities to speed up builds in your Tekton Pipeline. 





## Tekton Pipelines

[Tekton](https://tekton.dev/) is a powerful and flexible, open source, cloud-native framework for creating CI/CD systems, allowing developers to build, test, and deploy across cloud providers and on-premise systems.

Tekton consists of multiple projects. Among them is [Tekton Pipelines](https://tekton.dev/docs/pipelines/pipelines/), which provides the basic building blocks, in the form of Kubernetes CRDs, for creating CI/CD pipelines, whose tasks run as pods managed and orchestrated by Kubernetes. 

The main building blocks are:



* **Step**: smaller execution unit of a pipeline, is a Kubernetes container specification and includes the container image and all the info you need to run it, as the command or environment variables. It defines a step of your pipeline as “mvn package” or “docker build”. It is defined inside the Task Kubernetes custom resource.
* **Task**: Kubernetes custom resource, defines a sequence of Steps running in sequential order on a single pod in the same Kubernetes node.
* **Pipeline**: A group of tasks that you can configure to run in parallel or in sequence, it represents your CI/CD pipeline.
* **TaskRun**: Specific instance of a Task, linking it to parameters related to a specific environment or application. (For example: git repository, target container image to build, or target environment to deploy to.)
* **PipelineRun**: Specific instance of a Pipeline associating it to parameters.

You will find more information and tutorials in the [Tekton Documentation](https://tekton.dev/docs/) 


## Speeding up container image builds on Tekton

Running build steps as containers in Kubernetes has multiple advantages like portability, reusability, and the possibility to leverage all the capabilities of the underlying Kubernetes platform, but since these containers aren’t persistent by nature, optimizing the build execution through caching would need some additional actions compared to what you were used to do in a standalone CI server.

In the following sections, you will see some examples of how to use caching to speed up image builds in Tekton pipelines using Kaniko. [Kaniko](https://github.com/GoogleContainerTools/kaniko) is an open source tool that can be used to build container images from a Dockerfile. It doesn’t require a Docker daemon to run, which makes it ideal for building images in environments where Docker daemons aren’t available or can’t be run, such as Kubernetes clusters.

To run through the examples you will need a Kubernetes cluster with [Tekton Pipelines installed](https://tekton.dev/docs/installation/pipelines/), a git-based Source Code Management (SCM), and a container registry with permissions to push artifacts. I used a GKE cluster on Google Cloud, a GitHub repository, and Artifact Registry, but steps are reproducible on any standard Kubernetes platform, git based SCM, and container registry with null or minimal modifications.

Example code and assets are available in the: [tekton-speed-builds](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds) folder of the [Tekton CD Website repo](https://github.com/tektoncd/website)

To follow along you need to clone the [Tekton CD Website repo](https://github.com/tektoncd/website) locally and then copy and activate the [tekton-speed-builds](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds) folder as a new repo in your personal GitHub account or other git-based SCM if different.


### Experiment the default behavior

After you have your copy of the example repository clone it locally and look at its content:

* The [sample-app](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/sample-app) folder contains source code, Maven project files, and a Dockerfile for an example Spring Boot Java app. Look at the [Dockerfile](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/sample-app/Dockerfile): it’s multi-staged using the `maven` base image for packaging your code and the `eclipse-temurin:19-jdk-alpine` one to run your application:

```
FROM maven as build
COPY mvnw .
COPY pom.xml .
COPY src src
RUN mvn package -Dmaven.test.skip=true


FROM eclipse-temurin:19-jdk-alpine
COPY --from=build /target/demo-0.0.1-SNAPSHOT.jar app.jar
CMD ["java", "-jar", "app.jar"]

```


* The [tekton-assets](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/tekton-assets) folders contain resource manifests for the Tekton assets used in this article:
    * [pipeline.yaml](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/tekton-assets/pipeline.yaml) defines a pipeline running 2 Tasks:
        * [git-clone.yaml](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/tekton-assets/git-clone.yaml) clones the example repo to the source Tekton workspace 
        * [image-build.yaml](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/tekton-assets/image-build.yaml) runs Kaniko to build a container image from the source code cloned in the workspace and push it to the target container registry
    * [source-pvc.yaml](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/tekton-assets/source-pvc.yaml) is the manifest for the source-pvc persistent volume claim that will be used as persistent storage for the source Tekton workspace. The storage class is intentionally not defined to make it portable so it will use whatever is the default on your cluster, you can modify the manifest to use your preferred storage class.
* The [kaniko-basecache](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/kaniko-basecache), [kaniko-cache](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/kaniko-cache), and [m2cache](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/m2cache) folders contain example resources useful to implement the various caching options.

Let’s create the needed Tekton resources and run our pipeline. From your locally cloned repository, apply the resources in the tekton-assets folder to your cluster:


```
kubectl apply -f tekton-assets
```


This will create the pvc, tasks, and pipeline described above.

Now let’s start our pipeline manually. Depending on your configuration you may need to specify, using the -s parameter, a Service Account to authenticate to the registry to push the image, check [this section](https://tekton.dev/docs/how-to-guides/kaniko-build-push/#container-registry-authentication) of the Tekton docs for more info. 

Type the following command to start the pipeline


```
tkn pipeline start pipeline-clone-and-build --workspace name=source,claimName=source-pvc --showlog
```


When prompted for the value of the `git-url` parameter, type your git repository url.

When prompted for the value of the `image-name` parameter, type your container image url including the repo and image name.

Here’s an example configuration:


```
➜  ~ tkn pipeline start pipeline-clone-and-build --workspace name=source,claimName=source-pvc --showlog
? Value for param `git-url` of type `string`? https://github.com/ggalloro/tekton-speed-builds
? Value for param `image-name` of type `string`? europe-west1-docker.pkg.dev/galloro-demos/tektoncd/javasample
```


The pipeline will start and you will see the output of the steps executed.

If your pipeline run is successful the last step of the image-build task will print your image url in the console and you will have your image pushed to your target registry:


```
[image-build : write-url] europe-west1-docker.pkg.dev/galloro-demos/tektoncd/javasample:457848d
```


The pipeline execution created 2 TaskRun resources to execute the 2 tasks, type the following command to see the TaskRun information:


```
tkn tr ls
```


You will get an output similar to the one below:


```
NAME                                             STARTED          DURATION   STATUS
pipeline-clone-and-build-run-68hjg-image-build   4 minutes ago    50s        Succeeded
pipeline-clone-and-build-run-68hjg-git-clone     4 minutes ago    11s        Succeeded
```


Since your build will always run in a new container, if you change just a line in your source code your build will always need to download the base images and the Maven dependencies and can’t leverage any cache, let’s try that.

Change the text in line 25 of the [index.html](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/sample-app/src/main/resources/templates/index.html) file in [sample-app/src/main/resources/templates](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/sample-app/src/main/resources/templates) to “Hello, Slow Builder!”

Commit your change and push it to your remote repository:


```
git add .
git commit -m "change to index.html"
git push
```


Start your pipeline again following the same instructions given above.

After the Pipeline run completes look at your TasRuns info again:


```
NAME                                             STARTED          DURATION   STATUS
pipeline-clone-and-build-run-fnzxj-image-build   55 seconds ago   49s        Succeeded
pipeline-clone-and-build-run-fnzxj-git-clone     1 minute ago     12s        Succeeded
pipeline-clone-and-build-run-68hjg-image-build   4 minutes ago    50s        Succeeded
pipeline-clone-and-build-run-68hjg-git-clone     4 minutes ago    11s        Succeeded
```


As you can see, even if you change just one line of code, the build needs approximately the same time to execute. In the next sections, we will explore the options to optimize build speed through caching.


### Caching layers in a container registry

Kaniko can cache layers created by RUN and COPY commands in a remote repository. Before running a command, Kaniko checks the cache for the layer. If the layer exists in the cache, Kaniko will pull and extract it instead of running the command. If the layer doesn’t exist in the cache, Kaniko will run the command and then push the newly created layer to the cache.

This can help speed up builds in Tekton.

To use Kaniko cache you must add the `--cache=true` flag to Kaniko in our image-build Task so the build-and-push step reads as follows:


```
- name: build-and-push
      workingDir: $(workspaces.source.path)/sample-app/
      image: gcr.io/kaniko-project/executor:latest
      args:
        - --dockerfile=$(params.DOCKERFILE)
        - --context=$(params.CONTEXT) # The user does not need to care the workspace and the source.
        - --destination=$(params.IMAGE):$(params.commit)
        - --digest-file=$(results.IMAGE_DIGEST.path)
        - --cache=true
      securityContext:
        runAsUser: 0
```


To do that you can apply the modified [image-build-cache.yaml](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/kaniko-cache/image-build-cache.yaml) in the [kaniko-cache](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/kaniko-cache) folder to update the image-build Task:


```
kubectl apply -f kaniko-cache/image-build-cache.yaml
```


To leverage Kaniko layer caching capabilities you should also properly configure your Dockerfile to move the directives that are unlikely to change between builds to the top and the ones that are likely to change to the bottom.

Let’s edit the Dockerfile in the sample-app directory to separate the Maven dependency download from the code build so the dependencies are cached in a separate layer from the software artifact and any change to the code won’t cause the dependencies to be downloaded again. Add the `RUN mvn dependency:go-offline` line to your Dockerfile so it reads as follows:


```
FROM maven as build
COPY mvnw .
COPY pom.xml .
RUN mvn dependency:go-offline
COPY src src
RUN mvn package -Dmaven.test.skip=true


FROM eclipse-temurin:19-jdk-alpine
COPY --from=build /target/demo-0.0.1-SNAPSHOT.jar app.jar
CMD ["java", "-jar", "app.jar"]
```


Once you changed your Dockerfile you need to commit and push your changes so your build will use it:


```
git add .
git commit -m "update to Dockerfile"
git push
```


Now run your pipeline again as you did before, the first execution output should be similar to the previous run, and all the dependencies will be downloaded.

Let’s look at the TaskRun info. The build duration should be similar to the previous as well (although it might be  a bit longer due to the upload of layers to the registry):


```
NAME                                             STARTED          DURATION   STATUS
pipeline-clone-and-build-run-gsgwx-image-build   1 minute ago     58s        Succeeded
pipeline-clone-and-build-run-gsgwx-git-clone     1 minute ago     17s        Succeeded
pipeline-clone-and-build-run-fnzxj-image-build   55 seconds ago   49s        Succeeded
pipeline-clone-and-build-run-fnzxj-git-clone     1 minute ago     12s        Succeeded
pipeline-clone-and-build-run-68hjg-image-build   4 minutes ago    50s        Succeeded
pipeline-clone-and-build-run-68hjg-git-clone     4 minutes ago    11s        Succeeded

```


The image layers have been uploaded to your registry, as you can see in the picture below for Artifact Registry (javasample/cache folder):





Now let’s update the code (use “Hello, Fast Builder!” this time), commit your changes, and run the pipeline again following the instructions from the previous section. From the output log, you should note that the bulk of dependencies will not be downloaded again and the cached layer should be used:






The image-build TaskRun execution should be faster compared to the previous execution (42 vs 58 sec in this example): 


```
NAME                                             STARTED         DURATION   STATUS
pipeline-clone-and-build-run-5s87p-image-build   1 minute ago     42s        Succeeded
pipeline-clone-and-build-run-5s87p-git-clone     1 minute ago     17s        Succeeded
pipeline-clone-and-build-run-gsgwx-image-build   7 minutes ago    58s        Succeeded
pipeline-clone-and-build-run-gsgwx-git-clone     7 minutes ago    17s        Succeeded
pipeline-clone-and-build-run-fnzxj-image-build   18 minutes ago   49s        Succeeded
pipeline-clone-and-build-run-fnzxj-git-clone     18 minutes ago   12s        Succeeded
pipeline-clone-and-build-run-68hjg-image-build   21 minutes ago   50s        Succeeded
pipeline-clone-and-build-run-68hjg-git-clone     22 minutes ago   11s        Succeeded
```


You have experienced how enabling caching layers to a container registry can improve your build speed on Tekton, the effective speed gain would depend on various factors such as project configuration and connection to your registry.


### Caching base images on a persistent disk

In addition to cache layers on your container registry, Kaniko can use a persistent volume to store cached base images. By default, Kaniko will look for cached base images in the `/cache` folder but you can customize that with the `--cache-dir` flag. 

The persistent volume must be populated before usage, Kaniko provides an image for doing that: `gcr.io/kaniko-project/warmer`

Let’s add a volume mount mapping the `/cache` path to a PVC named `basechache-pvc` to our build-image Task:


```
- name: build-and-push
      workingDir: $(workspaces.source.path)/sample-app/
      image: gcr.io/kaniko-project/executor:latest
      args:
        - --dockerfile=$(params.DOCKERFILE)
        - --context=$(params.CONTEXT) # The user does not need to care the workspace and the source.
        - --destination=$(params.IMAGE):$(params.commit)
        - --digest-file=$(results.IMAGE_DIGEST.path)
        - --cache=true
      # kaniko assumes it is running as root, which means this example fails on platforms
      # that default to run containers as random uid (like OpenShift). Adding this securityContext
      # makes it explicit that it needs to run as root.
      securityContext:
        runAsUser: 0
      volumeMounts:
        - name: basecache
          mountPath: /cache
    - name: write-url
      image: docker.io/library/bash:5.1.4@sha256:b208215a4655538be652b2769d82e576bc4d0a2bb132144c060efc5be8c3f5d6
      script: |
        set -e
        image="$(params.IMAGE):$(params.commit)"
        echo -n "${image}" | tee "$(results.IMAGE_URL.path)"
  volumes:
    - name: basecache
      persistentVolumeClaim:
        claimName: basecache-pvc
```


To do that you can apply the modified [image-build-basecache.yaml](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/kaniko-basecache/image-build-basecache.yaml) in the [kaniko-basecache](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/kaniko-basecachespeed-builds/tree/main/kaniko-cache) folder to update the image-build Task:


```
kubectl apply -f kaniko-basecache/image-build-basecache.yaml
```


Now let’s create the basecache-pvc PVC:


```
kubectl apply -f kaniko-basecache/pvc-basecache.yaml
```


Then, run the `kaniko-warmer` pod to populate the disk:


```
kubectl apply -f kaniko-basecache/kaniko-warmer.yaml
```


Check the `kaniko-warmer` pod logs:


```
kubectl logs -f kaniko-warmer
```


Until you get the output confirming that the 2 base images have been downloaded


```
INFO[0000] Retrieving image manifest maven              
INFO[0000] Retrieving image maven from registry index.docker.io 
INFO[0004] Retrieving image manifest eclipse-temurin:19-jdk-alpine 
INFO[0004] Retrieving image eclipse-temurin:19-jdk-alpine from registry index.docker.io
```


When done you can make a change to your code again (“Hello, Base Builder!”) commit it and start your pipeline again as done in the previous tests.

This execution will leverage cached layers as the previous one and, in addition to that, will use the base images from your `basecache-pvc` persistent volume, as you can see in the output:





Even in this case, the speed improvement will depend on various factors such as how big your  base images are, storage performance, and your registry connection.


### Caching dependencies on a persistent disk

Another option to speed up builds is to cache dependencies locally. In our example Maven project we can leverage the fact that by default, maven caches the dependency modules into $HOME/.m2 directory. This possibility depends on the language and build tools you are using.

In this example, we will add another persistent volume to the build-image task and map it to the /root/.m2 folder to persist the Maven cache between builds.

Let’s apply the modified [image-build-m2cache.yaml](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/m2cache/image-build-m2cache.yaml) in the [m2cache](https://github.com/tektoncd/website/tree/main/content/en/blog/2023/speeding-up-container-image-builds-in-tekton-pipelines/tekton-speed-builds/m2cache) folder to update the image-build Task:


```
kubectl apply -f m2cache/image-build-m2cache.yaml
```


Now let’s create the `m2cache-pvc` PVC:


```
kubectl apply -f m2cache/pvc-m2cache.yaml
```


Since we don’t need to cache Maven dependencies in an image layer anymore, let’s remove the `RUN mvn dependency:go-offline `line` `from our Dockerfile and revert to its original structure. Commit and push your changes after that.

Now run your pipeline again as you did before, Maven will download your dependencies again when the `mvn package` is run since your previously cached layer is not referenced anymore in your Dockerfile. Duration should be similar to our initial test.

Make a change to your code again (“Hello, Very Fast Builder”), commit it, and start your pipeline again as done in the previous tests.

This execution will leverage cached layers as the previous one and, in addition to that, will use the base images from your basecache-pvc persistent volume and cached dependencies.

Even in this case, if you look at your TaskRun list, you should see a speed improvement compared to the first run:


```
NAME                                             STARTED          DURATION   STATUS
pipeline-clone-and-build-run-lk8x2-image-build   1 minute ago     46s        Succeeded
pipeline-clone-and-build-run-lk8x2-git-clone     1 minute ago     14s        Succeeded
pipeline-clone-and-build-run-w7sd5-image-build   3 minutes ago    59s        Succeeded
pipeline-clone-and-build-run-w7sd5-git-clone     3 minutes ago    12s        Succeeded
```



# Summary

You saw multiple options to leverage different types of caching to speed up image builds in Tekton using Kaniko:



* How to cache layers in your container registry
* How to use cached base images in a persistent volume
* How to host your local dependencies cache on a persistent volume 

Now, you are ready to speed up your build in Tekton !

### Note
This blog was originally posted in the [Continuous Delivery Foundation Blog](https://cd.foundation/blog/2023/10/12/speed-up-container-image-builds-tekton-pipelines/)

---

## File: content/en/blog/2023/slsa-2/index.md

---
title: Getting To SLSA Level 2 with Tekton and Tekton Chains
linkTitle: Getting To SLSA Level 2 with Tekton and Tekton Chains
date: 2023-04-19
author: "Prakash Jagatheesan and Brandon Lum, Google Software Engineers"
  Tekton SLSA Integrations
---
# Overview
As application developers, we achieve amazing results quickly by leveraging a rich ecosystem of freely available libraries, modules and frameworks that provide ready-to-use capabilities and abstract away from underlying complexity. This is so foundational to how we work that we'll nonchalantly build and publish an app that pulls in hundreds of dependencies without even thinking about it. And it's only fairly recently, in the wake of some very high profile and high impact compromises, that we've started to reckon with the fact that this wonderful ecosystem is also a security quagmire. All of the dependencies that feed into your build make up your software supply chain, and supply chains need to be secured. In this post, we'll show how an increasingly popular open source CI/CD system, Tekton, implements the [OpenSSF SLSA][slsa] framework to provide you with supply chain security guarantees.

# Software Supply Chain Security
A software supply chain is anything that goes into or affects your code from development, through your CI/CD pipeline, until it gets deployed into production. Increasingly, the software supply chain has become a vector for attacks. The recent Log4j, SolarWinds, Kaseya, and Codecov hacks highlight vulnerable surface areas exposed by an insecure software supply chain.

Between 2020 and 2021, there has been a [650% Surge][650] in OSS supply chain attacks, and [Gartner projects][gartner-projects] that 45% of organizations worldwide will have experienced software supply chain attacks by 2025.

# Supply Chains Levels for Software Artifacts (SLSA)
The Supply chain Levels for Software Artifacts (SLSA) framework is a check-list of controls to prevent tampering, improve integrity, and increase security in the packages and infrastructure used by projects, businesses or enterprises. SLSA formalizes criteria around software supply chain integrity to help the industry and open source ecosystem secure the software development life cycle at all stages.

As part of the framework, SLSA has multiple levels of assurances. These levels contain industry-recognized best practices to create four levels of increasing assurance.



SLSA provides a [set of requirements][slsa-l1] that needs to be met for an artifact to be considered for a particular SLSA level.

# Tekton + Tekton Chains
Tekton is a powerful and flexible, open source, cloud-native framework for creating CI/CD systems, allowing developers to build, test, and deploy across cloud providers and on-premise systems. Tekton consists of several subprojects which are relevant to SLSA:

* Pipelines: A system that allows one to define a pipeline of CI/CD tasks and
  have it be orchestrated by the Tekton controller.
* Chains: A standalone system which observes Pipelines and generates provenance
  for the artifacts built by Pipelines.  Tekton build processes are defined as
  tasks and pipelines. A Task is a collection of Steps that are defined and
  arranged in a specific order of execution as part of a continuous integration
  flow.

A Pipeline is a collection of Tasks defined and arranged in a specific order of execution as part of a continuous integration flow.

A TaskRun is an instantiation of a Task with specific inputs, outputs and execution parameters while a PipelineRun is an instantiation of a Pipeline.

A Task/Pipeline can define a set of Results. TaskRuns and PipelineRuns create Results as defined in the Task/Pipeline. Results are used to communicate to Tekton Chains run specifics like the uri and the digest of the built artifact.

Tasks, Pipelines, TaskRuns and PipelineRuns are defined through yaml files. The entire build is defined by the set of yaml files which define Tekton Tasks, Pipelines, TaskRuns and PipelineRuns. These yaml files can be checked in as code and run directly from the code repository.

# Getting to SLSA L1: Automation + Provenance
For an artifact to be [SLSA L1][slsa-l1] compliant it should satisfy the following:

1. [Scripted build][scripted]: All build steps are fully defined in some sort of
   “build script”. The only manual command, if any, is to invoke the build
   script.
1. [Provenance][available]: The provenance is available to the consumer in a
   format that the consumer accepts. The format SHOULD be in-toto SLSA
   Provenance, but another format MAY be used if both producer and consumer
   agree and it meets all the other requirements.

Tekton Tasks, TaskRuns, Pipelines and PipelineRuns are specified in yaml files. These yaml files can be considered as scripts and can even be checked in into a code repository. These could also be run from code repositories. Tekton Chains provides a way to generate provenance in in-toto SLSA format. As such, Tekton can easily make builds which satisfy the SLSA L1 requirements.

{{% alert title="Note" color="primary" %}}
The linked example demonstrates SLSA level 2 on Google Cloud, but the same
principles are applicable to any build environment.
{{% /alert %}}

Let's follow through with [an example][example-repo], which has the following files:

* `setup.sh`: Sets up Google cloud to run an instance of the build specified in
  `pipeline_run.yaml`. It also installs Tekton Pipeline and Tekton Chains. In the
  production environment, this would be run once to set up the environment and
  all builds would use the same environment.
* `pipeline_run.yaml`: This file is the actual build file that is run by Tekton
  Pipelines. The build here first clones a Github repo, builds the container
  specified in the source and uploads it to a Docker repository.



The build script `pipeline.yaml` is the definition of the script while
`pipeline_run.yaml` defines an instance of the build. It provides instance
specific parameters for the build. Though both `pipeline_run.yaml` and
`pipeline.yaml` are in source control for this example, the build definition is
in `pipeline.yaml` and as such `pipeline.yaml` being in source control would
satisfy the requirement of a source controlled build script.

```bash
kubectl create -f
    https://raw.githubusercontent.com/tektoncd/chains/main/docs/vendor/gcp/slsa-2/pipeline_run.yaml
```

# Tekton Chains for Provenance Generation

Provenance is metadata about how an artifact was built, including the build
process, top-level source, and dependencies. Knowing the provenance allows
software consumers to make risk-based security decisions.

Tekton Chains observes TaskRuns and PipelineRuns in a Kubernetes cluster. Once
the runs are done, Chains collects information (provenance) about the Run or the
build process and the artifact created by the Run. It signs [the
provenance][provenance] and stores the signed provenance. The provenance
generated for the example build complies to the SLSA provenance schema and is
explained further below.

Note that every step of the build has been recorded and can be reconstructed by following the steps in the provenance.

# Next Steps: CI/CD @ SLSA L2

[SLSA requires][slsa-requires] that for a build to be SLSA L2 compliant it should satisfy the following

1. [Every change][slsa-r1] to the source is tracked in a version control system
1. [All build steps][slsa-r2] were fully defined in some sort of “build script”. The only manual command, if any, was to invoke the build script.
1. [All build steps][slsa-r3] ran using some build service, not on a developer’s workstation.
1. [The provenance is available][slsa-r4] to the consumer in a format that the consumer accepts. The format SHOULD be in-toto SLSA Provenance, but another format MAY be used if both producer and consumer agree and it meets all the other requirements.
1. [The provenance’s authenticity][slsa-r5] and integrity can be verified by the consumer. This SHOULD be through a digital signature from a private key accessible only to the service generating the provenance.
1. [The data in the provenance][slsa-r6] MUST be obtained from the build service (either because the generator is the build service or because the provenance generator reads the data directly from the build service). Regular users of the service MUST NOT be able to inject or alter the contents.

## [Every change][slsa-r1] to the source is tracked in a version control system

Tekton does not explicitly enforce that the source is version controlled. Tekton users can enforce that the source is version controlled by writing an appropriate Task which will check for version control. The source should also be communicated by Tekton Pipelines to Tekton Chains through a [result variable][result-variable] that is suffixed with `-ARTIFACT_INPUTS`.

## [All build steps][slsa-r2] were fully defined in some sort of “build script”. The only manual command, if any, was to invoke the build script.

This is a requirement for SLSA L1 as well and as explained above, Tekton provides a way to script the build through yaml files. The build is defined as a Pipeline (or Task) which can be saved as a yaml file and submitted into source control. The build instance which is defined as a PipelineRun (or TaskRun) can resolve the Pipeline (or Task) yaml from source control and use it for the current instance of the build.

## [All build steps][slsa-r3] ran using some build service, not on a developer’s workstation.

Tekton can be hosted on a cloud provider or on a hosted Kubernetes cluster and run as a build service. The build scripts can be submitted into source control (like GitHub) and Tekton can read the scripts directly from source control.

## Provenance should be [available][slsa-r4]

This is a requirement for SLSA L1 and as explained above Tekton Chains provides build provenance.

## Provenance should be [signed and Authenticated][slsa-r5]

As can be seen in the example, Tekton Chains creates and signs the build
provenance. The signature can be verified anytime to ensure that the provenance
has not been tampered after the build and the provenance is really created by
the build process that claims to have built it. The signing is done according to
the [SLSA specification][attestation] using the [DSSE format][dsse].

Tekton Chains creates the provenance and signs it using a secure private key.
Chains then uploads the signed provenance to a user-specified location, one of
which is Google Cloud’s Container Analysis, which implements the open standard
[Grafeas API][grafeas] for storing provenance.



## Provenance should be [generated by a Service][slsa-r6]

Note that the provenance in the example is generated by the Tekton Chains service and it cannot be modified after it has been generated, which is guaranteed by the signature.

# [SLSA requirements][provenance-requirements] for the contents of the provenance, for the build to be considered L2.
All images below are extracted from the provenance of the example build. These can be verified by re-running the example.

1. Identifies artifact: The provenance MUST identify the output artifact via at
   least one cryptographic hash. The subject field in the SLSA provenance
   captures the location of the built artifact and the cryptographic hash
   associated with it. To be able to capture the artifact, Tekton Pipelines
   should populate the result variable `-ARTIFACT_OUTPUTS` with the location and
   the digest of the artifact.



2. Identifies builder: The provenance identifies the entity that performed the
   build and generated the provenance. The `builder.id` field captures the builder
   that built the artifact.



3. Identifies build instructions: The provenance identifies the top-level
   instructions used to execute the build. In our example, the build script is
   in source control. Recording the repo, the path in the repo and the commit
   hash will uniquely identify the build instructions used to build the
   artifact.



4. Identifies source code: The provenance identifies the repository origin(s)
   for the source code used in the build. The materials field records all the
   dependencies used to build the artifact, one of which is the source code. In
   the example the source used is in a GitHub repo, and as such the repo name
   and the commit hash will uniquely identify the source code.



# Conclusion

SLSA aims to secure the software supply chain by providing guidelines on how the
software build should be done. Tekton pipelines and Tekton chains implement
those guidelines and help in securing the software supply chain.

{{% alert title="Note" color="primary" %}}
This blog post was first published on the
[Google Open Source Blog](https://opensource.googleblog.com/2023/03/getting-to-slsa-level-2-with-tekton-and-tekton-chains.html).
{{% /alert %}}




[slsa]: https://slsa.dev/
[650]: https://www.sonatype.com/resources/state-of-the-software-supply-chain-2021
[gartner-projects]: https://www.gartner.com/en/documents/4003625
[slsa-l1]: https://slsa.dev/spec/v0.1/requirements
[scripted]: https://slsa.dev/spec/v0.1/requirements#scripted-build
[available]: https://slsa.dev/spec/v0.1/requirements#available
[example-repo]: https://github.com/tektoncd/chains/tree/main/docs/vendor/gcp/slsa-2
[provenance]: https://slsa.dev/provenance/v0.2
[slsa-requires]: https://slsa.dev/spec/v0.1/requirements
[slsa-r1]: https://slsa.dev/spec/v0.1/requirements#version-controlled
[slsa-r2]: https://slsa.dev/spec/v0.1/requirements#scripted-build
[slsa-r3]: https://slsa.dev/spec/v0.1/requirements#build-service
[slsa-r4]: https://slsa.dev/spec/v0.1/requirements#available
[slsa-r5]: https://slsa.dev/spec/v0.1/requirements#authenticated
[slsa-r6]: https://slsa.dev/spec/v0.1/requirements#service-generated
[result-variable]: https://github.com/tektoncd/chains/blob/82c213c172a99329d6571d76499ad816755a9069/docs/intoto.md#structured-result-type-hinting
[attestation]: https://slsa.dev/attestation-model
[dsse]: https://github.com/secure-systems-lab/dsse/blob/master/envelope.md
[grafeas]: https://github.com/grafeas/grafeas
[provenance-requirements]: https://slsa.dev/spec/v0.1/requirements#provenance-requirements

---

## File: content/en/blog/2023/distributed-traces-for-testing-with-tekton-pipelines-and-tracetest/index.md

---
title: Distributed Traces for Testing with Tekton Pipelines and Tracetest
linkTitle: Distributed Traces for Testing with Tekton Pipelines and Tracetest
date: 2023-08-15
author: "Adnan Rahic"
  How to automate Tracetest test runs with Tekton
---

[Tekton](https://tekton.dev/) is an [open-source framework](https://github.com/tektoncd/pipeline) for creating efficient CI/CD systems. This empowers developers to seamlessly construct, test, and deploy applications across various cloud environments and on-premise setups.

[Tracetest](https://tracetest.io), an [open-source testing tool](https://github.com/kubeshop/tracetest) that uses [OpenTelemetry](https://opentelemetry.io/) traces for testing, offers a sophisticated test harness for distributed cloud-native apps. It empowers users to test their apps by harnessing data from distributed traces produced by OpenTelemetry. This enables creating test specs and assertions that validate whether an application aligns with the intended behavior, as defined by pre-established test parameters.

## Why use distributed traces for testing?

The rationale behind integrating Tracetest with Tekton is compelling. Tracetest [uses pre-existing OpenTelemetry instrumentation](https://tracetest.io/features) to execute assertions against every part of an HTTP transaction.

[Combining Tracetest and Tekton](https://docs.tracetest.io/ci-cd-automation/tekton-pipeline) enables adding trace-based testing into CI/CD pipelines within your Kubernetes cluster. This integration not only furnishes the capability to initiate planned test cycles and synthetic testing but also preserves the core tenets of trace-based testing. It empowers exhaustive and in-depth assertions with trace data.

## Infrastructure Overview

The following is a high level sequence diagram on how Tekton and Tracetest interact with the different pieces of the system.



## 1. Install Tekton Pipelines, Triggers, and Dashboard

```bash
kubectl apply --filename \
https://storage.googleapis.com/tekton-releases/pipeline/latest/release.yaml

kubectl apply --filename \
https://storage.googleapis.com/tekton-releases/triggers/latest/release.yaml

kubectl apply --filename \
https://storage.googleapis.com/tekton-releases/triggers/latest/interceptors.yaml

kubectl apply --filename \
https://storage.googleapis.com/tekton-releases/dashboard/latest/release.yaml
```

## 2. Install Tracetest CLI

Install Tracetest CLI by following [these instructions](https://docs.tracetest.io/getting-started/installation) for your OS.

{{< tabs >}}

{{< tab header="MacOS" lang="bash" >}}
brew install kubeshop/tracetest/tracetest
{{< /tab >}}

{{< tab header="Linux" lang="bash" >}}
curl -L https://raw.githubusercontent.com/kubeshop/tracetest/main/install-cli.sh | bash
{{< /tab >}}

{{< tab header="Windows" lang="bash" >}}
choco source add --name=kubeshop_repo --source=https://chocolatey.kubeshop.io/chocolatey ; choco install tracetest
{{< /tab >}}

{{< /tabs >}}

## 3. Install Tracetest in Your Kubernetes Cluster

```bash
tracetest server install

[Output]
How do you want to run TraceTest? [type to search]:
  Using Docker Compose
> Using Kubernetes
```

Select `Using Kubernetes`.

```text
[Output]
Do you have OpenTelemetry based tracing already set up, or would you like us to install a demo tracing environment and app? [type to search]:
  I have a tracing environment already. Just install Tracetest
> Just learning tracing! Install Tracetest, OpenTelemetry Collector and the sample app.
```

Select `Just learning tracing! Install Tracetest, OpenTelemetry Collector and the sample app.`.

Confirm that Tracetest is running:

```bash
kubectl get all -n tracetest

[Output]
NAME                                  READY   STATUS    RESTARTS        AGE
pod/otel-collector-7f4d87489f-vp6zn   1/1     Running   0               5m41s
pod/tracetest-78b9c84c57-t4prx        1/1     Running   3 (4m15s ago)   5m29s
pod/tracetest-postgresql-0            1/1     Running   0               5m42s

NAME                              TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)               AGE
service/otel-collector            ClusterIP   10.96.173.226   <none>        4317/TCP              5m46s
service/tracetest                 ClusterIP   10.96.248.146   <none>        11633/TCP,4317/TCP   5m42s
service/tracetest-postgresql      ClusterIP   10.96.155.147   <none>        5432/TCP              5m42s
service/tracetest-postgresql-hl   ClusterIP   None            <none>        5432/TCP              5m42s

NAME                             READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/otel-collector   1/1     1            1           5m46s
deployment.apps/tracetest        1/1     1            1           5m42s

NAME                                        DESIRED   CURRENT   READY   AGE
replicaset.apps/otel-collector-7f4d87489f   1         1         1       5m46s
replicaset.apps/tracetest-78b9c84c57        1         1         1       5m42s

NAME                                    READY   AGE
statefulset.apps/tracetest-postgresql   1/1     5m42s
```

By default, Tracetest is installed in the `tracetest` namespace.

To explore the Tracetest Web UI, run the command:

```bash
kubectl --kubeconfig /.kube/config --context <your-cluster-context> --namespace tracetest port-forward svc/tracetest 11633
```



## 4. Create a Test in Tracetest

Start by clicking `Create` > `Create New Test` > `HTTP Request` > `Next` > `Choose Example` (dropdown) > `Pokeshop - List` (generates a sample test from the Tracetest demo) > `Next` > `URL` is prefilled with `http://demo-pokemon-api.demo/pokemon?take=20&skip=0` > `Create & Run`.

This will trigger the test and display a distributed trace in the `Trace` tab to run assertions against.



Proceed to add a test spec to assert all database queries return within 500 ms. Click the `Test` tab and proceed to click the `Add Test Spec` button.

In the span selector make sure to add this selector:

```css
span[tracetest.span.type="database"]
```

In the assertion field add:

```css
attr:tracetest.span.duration < 500ms
```

Save the test spec and publish the test.



The database spans that are returning in less than `500ms` are labeled in green.



This is an example of a trace-based test that asserts against every single part of an HTTP transaction, including all interactions with the database.

Let's introduce how Tekton makes it possible to run this test as part of your CI/CD pipeline.

## 5. Create a Task in Tekton

Click the `Automate` tab.



This contains both a YAML definition for the test run and a guide how to run the test with the Tracetest CLI.

Save this into a file called `test-api.yaml`:

```yaml
# test-api.yaml

type: Test
spec:
  id: L7wr5xeVR
  name: Pokeshop - List
  trigger:
    type: http
    httpRequest:
      method: GET
      url: http://demo-pokemon-api.demo/pokemon?take=20&skip=0
      headers:
      - key: Content-Type
        value: application/json
  specs:
  - selector: span[tracetest.span.type="database"]
    name: Database queries less than 500ms
    assertions:
    - attr:tracetest.span.duration < 500ms
```

Note that you'll use this CLI command to run the test:

```bash
tracetest run test --file test-api.yaml --required-gates test-specs --output pretty
```

It set's the required gates to pass the test by only validating the test specs.

Create another YAML file, name it `install-and-run-tracetest.yaml`.
This contains the Tekton `Task` definition.

```yaml
# install-and-run-tracetest.yaml

apiVersion: tekton.dev/v1beta1
kind: Task
metadata:
  name: install-and-run-tracetest
spec:
  steps:
    - name: create-test-files
      image: ubuntu
      script: |
        #!/usr/bin/env bash
        cat <<EOF >/workspace/test-api.yaml
        type: Test
        spec:
          id: L7wr5xeVR
          name: Pokeshop - List
          trigger:
            type: http
            httpRequest:
              method: GET
              url: http://demo-pokemon-api.demo/pokemon?take=20&skip=0
              headers:
              - key: Content-Type
                value: application/json
          specs:
          - selector: span[tracetest.span.type="database"]
            name: Database queries less than 500ms
            assertions:
            - attr:tracetest.span.duration < 500ms
        EOF
      volumeMounts:
      - name: custom
        mountPath: /workspace
    - name: install-and-run-tracetest
      image: kubeshop/tracetest:v0.13.3
      # The official Tracetest image comes with the Tracetest CLI installed
      script: |
        # Configure and Run Tracetest CLI
        tracetest configure -g --endpoint http://tracetest.tracetest.svc.cluster.local:11633/
        tracetest run test --file /workspace/test-api.yaml --required-gates test-specs --output pretty
      volumeMounts:
      - name: custom
        mountPath: /workspace
  volumes:
  - name: custom
    emptyDir: {}
```

```bash
kubectl apply -f ./install-and-run-tracetest.yaml
```

Make sure to use the Tracetest service as the endpoint for your [`tracetest configure` command](https://docs.tracetest.io/cli/reference/tracetest_configure/). This may vary depending on your installation.

```bash
http://tracetest.tracetest.svc.cluster.local:11633/
```

## 6. Run the Tracetest Trace-based Test in Tekton with a TaskRun

Finally, to run the test, create a `TaskRun`.

Create a file called `install-and-run-tracetest-run.yaml`.

```yaml
# install-and-run-tracetest-run.yaml

apiVersion: tekton.dev/v1beta1
kind: TaskRun
metadata:
  name: install-and-run-tracetest-run
spec:
  taskRef:
    name: install-and-run-tracetest
```

```bash
kubectl apply -f ./install-and-run-tracetest-run.yaml
```

Here's how to check the logs:

```bash
kubectl logs --selector=tekton.dev/taskRun=install-and-run-tracetest-run
```

You can also trigger a Task with the [Tekton CLI](https://tekton.dev/docs/cli/).

```bash
tkn task start install-and-run-tracetest

[Output]
TaskRun started: install-and-run-tracetest-run-xmhfg
```

In order to track the TaskRun progress run:

```bash
tkn taskrun logs install-and-run-tracetest-run-gccjk -f -n default

[Output]
[install-and-run-tracetest] ✔ Pokeshop - List (http://tracetest.tracetest.svc.cluster.local:11633/test/RUkKQ_aVR/run/3/test) - trace id: 0549641531d3221ded696f2fd3b20ce6
[install-and-run-tracetest] 	✔ Database queries less than 500 ms
[install-and-run-tracetest]
```

To preview which tasks failed or succeeded, use this command:

```bash
tkn taskrun list

[Output]
NAME                                  STARTED          DURATION   STATUS
install-and-run-tracetest-run         3 minutes ago    23s        Succeeded
install-and-run-tracetest-run-nmptn   7 minutes ago    33s        Failed
install-and-run-tracetest-run-bhf7v   20 minutes ago   23s        Succeeded
install-and-run-tracetest-run-wm8bj   21 minutes ago   22s        Succeeded
install-and-run-tracetest-run-dbrbt   23 minutes ago   24s        Failed
```

## 7. Trigger Trace-based Tests with an EventListener

By using Tektons's [triggers](https://tekton.dev/docs/getting-started/triggers/), you can trigger tests via an [eventlistener](https://tekton.dev/docs/getting-started/triggers/#create-an-eventlistener).

### Create a TriggerTemplate and TriggerBinding

```yaml
# install-and-run-tracetest-trigger-binding.yaml

apiVersion: triggers.tekton.dev/v1beta1
kind: TriggerTemplate
metadata:
  name: install-and-run-tracetest-template
spec:
  resourcetemplates:
  - apiVersion: tekton.dev/v1beta1
    kind: TaskRun
    metadata:
      generateName: install-and-run-tracetest-run-
    spec:
      taskRef:
        name: install-and-run-tracetest
```

```yaml
# install-and-run-tracetest-trigger-template.yaml

apiVersion: triggers.tekton.dev/v1beta1
kind: TriggerBinding
metadata:
  name: install-and-run-tracetest-binding
spec:
  params:
  - name: run
    value: $(body.run)
```

```bash
kubectl apply -f install-and-run-tracetest-trigger-binding.yaml
kubectl apply -f install-and-run-tracetest-trigger-template.yaml
```

### Create an EventListener

```yaml
# install-and-run-tracetest-event-listener.yaml

apiVersion: triggers.tekton.dev/v1beta1
kind: EventListener
metadata:
  name: install-and-run-tracetest-event-listener
spec:
  serviceAccountName: tekton-robot
  triggers:
    - name: install-and-run-tracetest-trigger 
      bindings:
      - ref: install-and-run-tracetest-binding
      template:
        ref: install-and-run-tracetest-template
```

The EventListener requires a service account to run. To create the service account for this example create a file named `tekton-robot-rbac.yaml` and add the following:

```yaml
# tekton-robot-rbac.yaml

apiVersion: v1
kind: ServiceAccount
metadata:
  name: tekton-robot
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: triggers-example-eventlistener-binding
subjects:
- kind: ServiceAccount
  name: tekton-robot
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: tekton-triggers-eventlistener-roles
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: triggers-example-eventlistener-clusterbinding
subjects:
- kind: ServiceAccount
  name: tekton-robot
  namespace: default
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: tekton-triggers-eventlistener-clusterroles
```

```bash
kubectl apply -f tekton-robot-rbac.yaml
kubectl apply -f install-and-run-tracetest-event-listener.yaml
```

Enable port forwarding.

```bash
kubectl port-forward service/el-install-and-run-tracetest-event-listener 8080
```

Hitting the port forwarded endpoint will trigger the task.

```text
curl -v \
   -H 'content-Type: application/json' \
   -d '{"run":true}' \
   http://localhost:8080
```

Checking the `taskruns` will confirm this.

```bash
tkn taskrun list

[Output]
NAME                                  STARTED          DURATION   STATUS
install-and-run-tracetest-run-69zrz   4 seconds ago    ---        Running(Pending)
```

Finally, check the logs:

```bash
tkn taskrun logs -f install-and-run-tracetest-run-69zrz

[Output]
[install-and-run-tracetest] ✔ Pokeshop - List (http://tracetest.tracetest.svc.cluster.local:11633/test/RUkKQ_aVR/run/5/test)
[install-and-run-tracetest] 	✔ Database queries less than 500 ms
```

## 8. Preview Trace-based Tests with Tekton Dashboard

Start by port forwarding the Tekton Dashboard.

```bash
kubectl --namespace tekton-pipelines port-forward svc/tekton-dashboard 9097:9097
```

Open it up in your browser at `http://localhost:9097`. Navigate to the TaskRuns. Open the TaskRun you ran above.



This lets you easily preview the Tracetest test runs by copying the link to the Tracetest instance. However, because you're using an internal service for Tracetest, make sure to use the port forwarded link to access the Tracetest Dashboard.

Replace:

```text
http://tracetest.tracetest.svc.cluster.local:11633/test/RUkKQ_aVR/run/4/test
```

With:

```text
http://localhost:11633/test/RUkKQ_aVR/run/4/test
```



Alternatively, you can use the Deep Link feature to trigger a new test run directly via the browser like this:

```text
http://localhost:11633/test/RUkKQ_aVR/run?
```

## Conclusion

To sum up, the partnership between Tekton and Tracetest offers a powerful approach to testing Kubernetes with distributed tracing. Tekton provides a framework for building efficient CI/CD pipelines. Tracetest utilizes OpenTelemetry traces for testing, making it a valuable tool for testing cloud-native apps.

By combining Tracetest and Tekton, developers gain the ability to integrate trace-based testing into Kubernetes clusters. This integration allows for scheduled test cycles, synthetic tests, and thorough assertions using trace data. This cohesive approach ensures that applications align with intended behavior, improving overall reliability and functionality. As cloud-native apps continue to evolve, this integration showcases how to enhance testing as well.

## Next Steps

To explore more options that Tracetest gives you, check out [the docs](https://docs.tracetest.io/) to learn more!

If you like what the [Tekton](https://github.com/tektoncd/pipeline) and [Tracetest](https://github.com/kubeshop/tracetest) communities are doing, please leave a ⭐️ in GitHub.

---

## File: content/en/blog/2023/cdcon-gitopscon/index.md

---
title: Meet with Tekton Community at cdCon + GitOpsCon 2023
linkTitle: Meet with Tekton Community at cdCon + GitOpsCon 2023
date: 2023-04-14
author: "CD Foundation"
  List of talks given by Tekton community members at cdCon + GitOpsCon 2023
---
{{< imgproc banner Fit 700x500 >}}{{< /imgproc >}}

The [Continuous Delivery Foundation (CDF)][cdf-website] is happy to host its
fourth flagship event, cdCon, taking place on May 8–9, 2023 in Vancouver,
Canada as [cdCon + GitOpsCon][cdcon-gitopscon-website], co-organized with the
[Cloud Native Computing Foundation (CNCF)][cncf-website], making it the
must-attend event for anyone who is involved in CD, DevOps, and GitOps.

By combining the two events, cdCon + GitOpsCon aims to bring their communities
together to collaborate and build the future of GitOps and CD. The program
committees reviewed more than 250 submissions and selected over 60 sessions
that will span topics from technical challenges and deep dives, to end-user
stories and introductory content.

The [cdCon + GitOpsCon program][cdcon-gitopscon-program] contains sessions from
the most widely used CI/CD and GitOps technologies. The Tekton Community will
be there with project updates and various talks from our community members and
users. Here are some of the sessions you don’t want to miss.

- [Operating Tekton with Secure Defaults][tekton-talk-1] - Christie Wilson Warwick & Wendy Dembowski, Google
- [Tekton Project Update and Roadmap][tekton-talk-2] - Andrea Frittoli, IBM
- [Save Your Pipelines (and Clusters!) with Tekton Results][tekton-talk-3] - Adam Kaplan, Red Hat & Dibyo Mukherjee, Google
- [Tekton Supply Chain Security][tekton-talk-4] - Billy Lynch, Chainguard

In addition to these sessions, Andrea Frittoli of IBM, a member of the Tekton
Governance Committee and maintainer will take part in [the Graduated Projects
Keynote Panel][graduated-projects-panel], discussing Tekton Community’s
experiences with graduation and sharing his thoughts on why graduation matters
for the community and users of Tekton.

We look forward to an awesome event and we hope to see you there!

[cdf-website]: https://cd.foundation
[cncf-website]: https://cncf.io/
[cdcon-gitopscon-website]: https://events.linuxfoundation.org/cdcon-gitopscon/
[cdcon-gitopscon-program]: https://events.linuxfoundation.org/cdcon-gitopscon/program/schedule/
[tekton-talk-1]: https://sched.co/1Jp8P
[tekton-talk-2]: https://sched.co/1KDgj
[tekton-talk-3]: https://sched.co/1JpAX
[tekton-talk-4]: https://sched.co/1KDTf
[graduated-projects-panel]: https://sched.co/1Js9F

---

## File: content/en/blog/2025/tekton-pipeline-v1.0.0/index.md

---
title: "Tekton Pipelines Reaches 1.0: Stability Today, Innovation Tomorrow"
linkTitle: "Tekton Pipelines Reaches 1.0: Stability Today, Innovation Tomorrow"
date: 2025-05-23
author: "Vincent Demeester, Red Hat"
  Tekton Pipeline component v1.0.0 release announcement.
---

We're thrilled to announce the official 1.0 release of the Tekton Pipelines component ([`tektoncd/pipeline`](https://github.com/tektoncd/pipeline) repository) ! While this marks a significant milestone for the project, it's important to note that the stability you've come to rely on with the v1 API has been a reality for over two years. This release solidifies that foundation while paving the way for even more exciting changes in the Tekton ecosystem.

The version 1.0 brings several key updates, reinforcing the project's commitment to stability and a streamlined user experience. Notably, the `StepAction` feature has graduated to General Availability (GA), signifying its maturity and readiness for production use.
Furthermore, this release includes significant enhancements and bug fixes for the Git resolver, improving its reliability and performance. We've also seen the recent introduction and ongoing development of the HTTP resolver, offering greater flexibility in how your pipelines fetch tasks and other resources. You can learn more about resolvers and their capabilities in the [Tekton documentation](https://tekton.dev/docs/pipelines/resolution/).
Finally, the deprecated `ClusterTask` resource has been removed, encouraging the adoption of the more flexible and namespaced `Task` resource or the use of the cluster resolver.

The 1.0 release is not the finish line; it's a significant step forward on an exciting journey and one we could or should have done a while ago. Looking ahead, we'll be focused on stability, performance and user experience.

- Graduate `StepAction` to the v1 API, ensuring long-term stability and support for this powerful feature.
- Working towards a `v2` of the resolvers, with a strong focus on improving both usability and performance.
- Investing in better observability and metrics to provide users with clearer insights into their Pipeline executions.

Our goal is to make Tekton Pipelines even more intuitive and efficient for developers and operators alike.

Independently of the release, we are also making a significant step in the evolution of the Tekton project as we transition to the Cloud Native Computing Foundation (CNCF). You can follow the progress of this transition in the [CNCF TOC issue](https://github.com/cncf/toc/issues/1310). Joining the CNCF will provide Tekton with a neutral home and access to a vibrant and supportive ecosystem. This move will foster even greater collaboration, expand our community reach, and ensure the long-term sustainability and growth of Tekton Pipelines for the benefit of all cloud-native practitioners.

We invite you to explore the 1.0 release, engage with our growing community, and contribute to the future of cloud-native CI/CD. The best is yet to come!

---

## File: content/en/blog/2025/protect-signing-secrets-for-tekton-chains-using-confidential-computing/index.md

---
title: Protect Signing Secrets for Tekton Chains using Confidential Computing
linkTitle: Protect Signing Secrets for Tekton Chains using Confidential Computing
date: 2025-04-23
author: "Puneet Punamiya and Pradipta Banerjee, Red Hat"
  Integrating Tekton pipelines and chains with confidential computing
---


## What is Tekton Chains?

[Tekton Chains](https://github.com/tektoncd/chains/blob/main/README.md), a part of the Tekton project, provides tools to generate, store, and sign provenance for artifacts built with Tekton Pipelines.

Technically it's a Kubernetes Custom Resource Definition (CRD) controller that allows you to manage your supply chain security in Tekton.  Chains observes Tekton Pipelines and generates provenance for the artifacts built the Pipelines.


The following diagram from the Tekton Chains [tutorial](https://github.com/tektoncd/chains/blob/main/docs/tutorials/getting-started-tutorial.md) shows the Tekton Chains workflow



Src: https://tekton.dev/docs/chains/getting-started-tutorial/


To summarise, here are the steps in Tekton Chains provenance signing

1. Create signing secret (eg. cosign key-pair - cosign.pub, cosign.key, cosign.password)
2. Save the signing secret as K8s secret - named signing-secrets
in tekton-chains ns
3. Create the pipelineRun object (execute your pipeline)
4. Chains controller watches for pipelineRun completion and creates a snapshot
5. Sign the snapshot using the private part of the signing secret (eg. cosign.key)
6. As a consumer, verify the provenance by by checking the signature using the public part of the signing secret (eg. cosign.pub)

## What is Confidential Computing?

Confidential computing protects your workload and data from unauthorised entities — the host or hypervisor, system administrators, service providers, other virtual machines (VMs) and processes on the host.

Confidential computing protects the data in use, completing the data security triad — securing data at rest, in-transit, and in-use. Only the data owner has access to the data. 



This key functionality gives you the additional confidence to run your sensitive workloads in untrusted infrastructure (e.g. third-party data-centers, public cloud) and reap the benefits of scale and cost-efficiency.



A Trusted Execution Environment (TEE) is at the heart of a confidential computing solution. TEEs are secure and isolated environments provided by confidential computing (CC) enabled hardware that prevents unauthorised access or modification of applications and data while in use. You’ll also hear the terms “enclaves” or “secure enclaves”. “TEEs” and “enclaves” are used interchangeably.

So to reap the benefits of confidential computing, your application needs to run inside a TEE (secure enclave) for it to be protected.


## How can you leverage Confidential Computing in the Kubernetes ecosystem?

In the Kubernetes world, there are two broad ways for you to use confidential computing:

**Confidential Cluster**: The entire Kubernetes cluster is running inside a confidential environment. The cluster nodes are confidential VMs, and any workload deployed on these cluster nodes benefits from confidentiality.

**Confidential Container**: The Kubernetes pod is running inside a confidential environment. This approach is more granular, where confidentiality is available to the workload of your choice.



Both confidential Kubernetes clusters and containers aim to enhance data security and privacy of Kubernetes workloads by leveraging hardware-based encryption and attestations for trust.

## Tekton Chains and Confidential Computing

In order to secure Tekton Chains code and the signing secrets from threats by privileged admins, you can leverage confidential computing.

We have used the confidential container (CoCo) approach to secure Tekton chains.


## Confidential Containers (CoCo)
Confidential Containers (CoCo) refers to a pod running inside the TEE.

The CNCF Confidential Containers (CoCo) project is leading the effort to standardise confidential computing at the pod level and simplify its consumption in Kubernetes. This enables Kubernetes users to deploy confidential container workloads using familiar workflows and tools without extensive knowledge of the underlying confidential computing technologies.

## Confidential Containers (CoCo) building blocks

Following is a high level architecture of a typical CoCo deployment in Kubernetes.



As shown in the diagram, CoCo uses Linux Confidential Virtual Machine (CVM) executing inside a TEE as the foundation. Using CVM as the foundation enables lift-and-shift of existing container workloads.

The container images are downloaded and kept inside the enclave and can be either signed and/or encrypted.

The components inside the CVM, namely image-rs, kata-agent, confidential data hub (CDH), attestation agent (AA) are collectively referred to as the enclave software stack.  The enclave software stack is measured, which means that a trusted cryptographic algorithm is used to measure these entities running within the CVM. These measurements can be used for attestation purposes. Access to secrets—including encryption keys to decrypt the container image itself or to unlock a database used by the workload—can be controlled, released only when the enclave is attested to be valid.

Attestation is the process of verifying that an enclave measurement meets some specified criteria set by the workload or data owner (mentioned as Relying party in the diagram). The attestation agent is responsible for initiating attestation and fetching of the secrets from the key broker service (KBS).  For detailed information refer to the following documentation.


The CNCF CoCo project provides the following components
  - Enclave software stack - https://github.com/confidential-containers/guest-components
  - Relying Party Services -  https://github.com/confidential-containers/trustee
  - CoCo operator - https://github.com/confidential-containers/operator
  - Trustee operator - https://github.com/confidential-containers/trustee-operator
  - CoCo enablement for Kata containers local hypervisor - https://github.com/kata-containers/kata-containers
  - CoCo enablement for Kata containers remote hypervisor - https://github.com/confidential-containers/cloud-api-adaptor 


### Tekton Chains and Confidential Containers (CoCo)

Recall from Tekton Chains [signing workflow](https://docs.google.com/document/d/1ivTjtZ1D_gjSBeaDqn4FGwIoBDid2xt3u4knVknDzzo/edit?tab=t.0#bookmark=id.7m33px6pnidl), the signing secret is stored as Kubernetes secret accessible to any cluster admin.  If you are using third party services, you would want to protect the signing secret even from the cluster admin. CoCo allows you to do that, by ensuring that the signing secret is only available inside the TEE with no access to the cluster admin.


In the following sections we'll see how the signing secrets can be protected using CoCo.

### Setup
For the purpose of this blog, we'll be using CoCo in AWS leveraging the Kata containers remote hypervisor setup provided via the CoCo cloud-api-adaptor project.

Instructions to set up CoCo on AWS - https://confidentialcontainers.org/docs/examples/aws-simple.

KBS setup details are described in the following [blog](https://confidentialcontainers.org/blog/2024/06/10/deploy-trustee-in-kubernetes/).

For other environments refer to the CoCo documentation - https://confidentialcontainers.org/docs/getting-started

### Tekton Chains Setup

Instructions to install Tekton Chains Installation -  https://github.com/tektoncd/chains?tab=readme-ov-file#installation

#### Signing Secrets for Tekton Chains

We'll be using the `sealed secrets` functionality of CoCo. A sealed secret is a way to encapsulate confidential data such that it can be accessed only inside a Trusted Execution Environment (TEE) after verification of the TEE environment.
There are two types of sealed secrets in CoCo - envelope and vault.

We'll be using the `vault` type. A vault secret is a pointer to a secret that is stored remotely in a KMS. In the CoCo environment this is managed by the Compute attestation operator as shown previously.
When deploying a workload as CoCo, the CoCo runtime components inside the TEE will retrieve the actual secret from the remote provider and make it available to the workload. This happens transparently.


Let's see an example of a vault type sealed secret.
The first step is to create a json file containing the location of the secret in a specified format.

An example json file `secret.json` is shown below. Note the `name` and the `provider`. This defines the location of the actual secret `secret`.

```bash
cat secret.json

{
    "version": "0.1.0",
    "type": "vault",
    "name": "kbs:///default/mysecret/secret",
    "provider": "kbs",
    "provider_settings": {},
    "annotations": {}
}
```


The sealed secret is of the form - `sealed.JWS header.JWS body (secret content).signature`

For using sealed secrets in K8s, we use the following:
`sealed.fakejwsheader.base64url(secret content).fakesignature`

Continuing with `secret.json` example, the sealed secret will be the following:

```bash
cat secret.json | basenc --base64url -w0

ewogICAgInZlcnNpb24iOiAiMC4xLjAiLAogICAgInR5cGUiOiAidmF1bHQiLAogICAgIm5hbWUiOiAia2JzOi8vL2RlZmF1bHQvbXlzZWNyZXQvc2VjcmV0IiwKICAgICJwcm92aWRlciI6ICJrYnMiLAogICAgInByb3ZpZGVyX3NldHRpbmdzIjoge30sCiAgICAiYW5ub3RhdGlvbnMiOiB7fQp9Cgo=

sealed_secret=sealed.fakejwsheader.ewogICAgInZlcnNpb24iOiAiMC4xLjAiLAogICAgInR5cGUiOiAidmF1bHQiLAogICAgIm5hbWUiOiAia2JzOi8vL2RlZmF1bHQvbXlzZWNyZXQvc2VjcmV0IiwKICAgICJwcm92aWRlciI6ICJrYnMiLAogICAgInByb3ZpZGVyX3NldHRpbmdzIjoge30sCiAgICAiYW5ub3RhdGlvbnMiOiB7fQp9Cgo=.fakesignature
```

Now let's see how we can use this approach to protect the signing secrets for Tekton Chains.

As mentioned previously, a CoCo deployment uses a trusted environment to store the secrets and releases it to the workload. The actual secret will be in the trusted environment whereas the sealed secret will be used in the untrusted environment running Tekton Chains.

Generate cosign key-pairs - cosign.pub, cosign.key, cosign.password

```bash
cosign generate-key-pair
```

Store the keys in the KBS. In my setup the cosign are stored under `default/cosign-secrets/{cosign.key,cosign.pub,cosign.password}`

Create sealed secrets to be used by the Tekton chains controller


### `cosign.key.json`
```json
{
    "version": "0.1.0",
    "type": "vault",
    "name": "kbs:///default/cosign-secrets/cosign.key",
    "provider": "kbs",
    "provider_settings": {},
    "annotations": {}
}
```

**Sealed secret**  
```sealed.fakejwsheader.ewogICAgInZlcnNpb24iOiAiMC4xLjAiLAogICAgInR5cGUiOiAidmF1bHQiLAogICAgIm5hbWUiOiAia2JzOi8vL2RlZmF1bHQvY29zaWduLXNlY3JldHMvY29zaWduLmtleSIsCiAgICAicHJvdmlkZXIiOiAia2JzIiwKICAgICJwcm92aWRlcl9zZXR0aW5ncyI6IHt9LAogICAgImFubm90YXRpb25zIjoge30KfQo=.fakesignature```

---

### `cosign.pub.json`
```json
{
    "version": "0.1.0",
    "type": "vault",
    "name": "kbs:///default/cosign-secrets/cosign.pub",
    "provider": "kbs",
    "provider_settings": {},
    "annotations": {}
}
```

**Sealed secret**  
`sealed.fakejwsheader.ewogICAgInZlcnNpb24iOiAiMC4xLjAiLAogICAgInR5cGUiOiAidmF1bHQiLAogICAgIm5hbWUiOiAia2JzOi8vL2RlZmF1bHQvY29zaWduLXNlY3JldHMvY29zaWduLnB1YiIsCiAgICAicHJvdmlkZXIiOiAia2JzIiwKICAgICJwcm92aWRlcl9zZXR0aW5ncyI6IHt9LAogICAgImFubm90YXRpb25zIjoge30KfQo=.fakesignature`

---

### `cosign.password.json`
```json
{
    "version": "0.1.0",
    "type": "vault",
    "name": "kbs:///default/cosign-secrets/cosign.password",
    "provider": "kbs",
    "provider_settings": {},
    "annotations": {}
}
```

**Sealed secret**  
`sealed.fakejwsheader.ewogICAgInZlcnNpb24iOiAiMC4xLjAiLAogICAgInR5cGUiOiAidmF1bHQiLAogICAgIm5hbWUiOiAia2JzOi8vL2RlZmF1bHQvY29zaWduLXNlY3JldHMvY29zaWduLnBhc3N3b3JkIiwKICAgICJwcm92aWRlciI6ICJrYnMiLAogICAgInByb3ZpZGVyX3NldHRpbmdzIjoge30sCiAgICAiYW5ub3RhdGlvbnMiOiB7fQp9Cg==.fakesignature`

---

#### The `signing-secrets` looks like this

```yaml
apiVersion: v1
data:
  cosign.key: c2VhbGVkLmZha2Vqd3NoZWFkZXIuZXdvZ0lDQWdJblpsY25OcGIyNGlPaUFpTUM0eExqQWlMQW9nSUNBZ0luUjVjR1VpT2lBaWRtRjFiSFFpTEFvZ0lDQWdJbTVoYldVaU9pQWlhMkp6T2k4dkwyUmxabUYxYkhRdlkyOXphV2R1TFhObFkzSmxkSE12WTI5emFXZHVMbXRsZVNJc0NpQWdJQ0FpY0hKdmRtbGtaWElpT2lBaWEySnpJaXdLSUNBZ0lDSndjbTkyYVdSbGNsOXpaWFIwYVc1bmN5STZJSHQ5TEFvZ0lDQWdJbUZ1Ym05MFlYUnBiMjV6SWpvZ2UzMEtmUW89LmZha2VzaWduYXR1cmUK
  cosign.password: c2VhbGVkLmZha2Vqd3NoZWFkZXIuZXdvZ0lDQWdJblpsY25OcGIyNGlPaUFpTUM0eExqQWlMQW9nSUNBZ0luUjVjR1VpT2lBaWRtRjFiSFFpTEFvZ0lDQWdJbTVoYldVaU9pQWlhMkp6T2k4dkwyUmxabUYxYkhRdlkyOXphV2R1TFhObFkzSmxkSE12WTI5emFXZHVMbkJoYzNOM2IzSmtJaXdLSUNBZ0lDSndjbTkyYVdSbGNpSTZJQ0pyWW5NaUxBb2dJQ0FnSW5CeWIzWnBaR1Z5WDNObGRIUnBibWR6SWpvZ2UzMHNDaUFnSUNBaVlXNXViM1JoZEdsdmJuTWlPaUI3ZlFwOUNnPT0uZmFrZXNpZ25hdHVyZQo=
  cosign.pub: c2VhbGVkLmZha2Vqd3NoZWFkZXIuZXdvZ0lDQWdJblpsY25OcGIyNGlPaUFpTUM0eExqQWlMQW9nSUNBZ0luUjVjR1VpT2lBaWRtRjFiSFFpTEFvZ0lDQWdJbTVoYldVaU9pQWlhMkp6T2k4dkwyUmxabUYxYkhRdlkyOXphV2R1TFhObFkzSmxkSE12WTI5emFXZHVMbkIxWWlJc0NpQWdJQ0FpY0hKdmRtbGtaWElpT2lBaWEySnpJaXdLSUNBZ0lDSndjbTkyYVdSbGNsOXpaWFIwYVc1bmN5STZJSHQ5TEFvZ0lDQWdJbUZ1Ym05MFlYUnBiMjV6SWpvZ2UzMEtmUW89LmZha2VzaWduYXR1cmUK
immutable: true
kind: Secret
metadata:
  name: signing-secrets
  namespace: tekton-chains
type: Opaque
```

---

## ⚙️ Custom Tekton Chains Deployment

Update the `TektonConfig` CR:

📖 [Tekton Operator Deployment Options](https://github.com/tektoncd/operator/blob/main/docs/TektonConfig.md#deployments)

```yaml
chain:
  options:
    deployments:
      tekton-chains-controller:
        spec:
          template:
            spec:
              containers:
              - name: tekton-chains-controller
                runtimeClassName: kata-remote
```

---

## 🚀 Run the Pipeline

Now you can run your pipeline and let Tekton chains sign the provenance using secrets that are only available inside the confidential environment.


We'll use the following sample from the getting started guide - https://github.com/tektoncd/chains/blob/main/docs/tutorials/getting-started-tutorial.md


```bash
kubectl create -f pipelinerun.yaml

tkn pr list

tkn pr describe

export PR_UID=$(tkn pr describe --last -o jsonpath='{.metadata.uid}')

tkn pr describe --last \
  -o jsonpath="{.metadata.annotations.chains\.tekton\.dev/signature-pipelinerun-$PR_UID}" \
  | base64 -d > metadata.json
```

---

## ✅ Cosign Verification

```bash
cosign verify-blob-attestation --insecure-ignore-tlog \
  --key cosign.pub --signature metadata.json \
  --type slsaprovenance --check-claims=false /dev/null
```

```
WARNING: Skipping tlog verification is an insecure practice that lacks of transparency and auditability verification for the blob attestation.
Verified OK
```

---

## 🔍 Confidentiality Verification

The following output is from the controller container.

As you can see the actual secrets are available in the volume mount path. Also the secrets are in memory.



```bash
cat /sealed/signing-secrets/cosign.pub
```

```
/* Detailed source-code truncated for AI context efficiency. */
```

---

The following screenshot shows the CVM running the container workload - `podvm-tekton-chains-controller-....` using an `"r6a"` instance type which is an AMD SNP confidential compute instance.





### References

https://github.com/tektoncd/chains

https://tekton.dev/docs/getting-started/supply-chain-security/

https://github.com/confidential-containers/guest-components/blob/main/confidential-data-hub/docs/SEALED_SECRET.md

https://opensource.googleblog.com/2023/03/getting-to-slsa-level-2-with-tekton-and-tekton-chains.html

https://github.com/tektoncd/operator/pull/2441