-
Notifications
You must be signed in to change notification settings - Fork 385
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
WIP: Add scaffolding to stand up Trillian on k8s.
Signed-off-by: Ville Aikas <[email protected]>
- Loading branch information
Showing
17 changed files
with
704 additions
and
14 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,76 @@ | ||
name: Kind scaffolding test | ||
|
||
on: | ||
pull_request: | ||
branches: [ 'main', 'release-*' ] | ||
|
||
permissions: read-all | ||
|
||
jobs: | ||
e2e-tests: | ||
name: test tree creation with scaffolding | ||
runs-on: ubuntu-latest | ||
|
||
strategy: | ||
fail-fast: false # Keep running if one leg fails. | ||
matrix: | ||
k8s-version: | ||
- v1.22.x | ||
- v1.23.x | ||
|
||
env: | ||
REGISTRY_NAME: registry.local | ||
REGISTRY_PORT: 5000 | ||
KO_DOCKER_REPO: registry.local:5000/trillian | ||
|
||
steps: | ||
- uses: actions/checkout@2541b1294d2704b0964813337f33b291d3f8596b # v2.4.0 | ||
- uses: actions/setup-go@b22fbbc2921299758641fab08929b4ac52b32923 # v2.2.0 | ||
with: | ||
go-version: '1.17' | ||
check-latest: true | ||
|
||
- uses: imjasonh/setup-ko@2c3450ca27f6e6f2b02e72a40f2163c281a1f675 # v0.4 | ||
|
||
- name: Install yq | ||
uses: mikefarah/yq@70403375d7b96075bd68b40c434807cff1593568 # v4.25.1 | ||
|
||
- name: Setup mirror | ||
uses: chainguard-dev/actions/setup-mirror@main | ||
with: | ||
mirror: mirror.gcr.io | ||
|
||
- name: Setup kind cluster | ||
uses: chainguard-dev/actions/setup-kind@main | ||
with: | ||
k8s-version: ${{ matrix.k8s-version }} | ||
cluster-suffix: c${{ github.run_id }}.local | ||
|
||
- name: Setup knative | ||
uses: chainguard-dev/actions/setup-knative@main | ||
with: | ||
k8s-version: ${{ matrix.k8s-version }} | ||
cluster-suffix: c${{ github.run_id }}.local | ||
|
||
- name: Install Trillian | ||
run: | | ||
echo '::group:: install Trillian scaffolding' | ||
ko apply -BRf ./examples/deployment/kubernetes/scaffolding | ||
echo '::endgroup::' | ||
echo '::group:::' waiting for services to come up | ||
kubectl wait -n trillian-system --for=condition=Ready --timeout=5m ksvc --all | ||
echo '::endgroup::' | ||
- name: Create a tree on it | ||
run: | | ||
echo '::group:: install create tree job' | ||
kubectl apply -Rf ./examples/deployment/kubernetes/createtree | ||
echo '::endgroup::' | ||
echo '::group:::' waiting for job to complete' | ||
kubectl wait -n createtree --for=condition=Complete --timeout=5m jobs createtree | ||
echo '::endgroup::' | ||
kubectl -n createtree get cm trillian-tree -ojsonpath='{.data.treeID}' | ||
- name: Collect diagnostics | ||
if: ${{ failure() }} | ||
uses: chainguard-dev/actions/kind-diag@84c993eaf02da1c325854fb272a4df9184bd80fc # main |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,145 @@ | ||
// Copyright 2022 The Sigstore Authors | ||
// | ||
// Licensed under the Apache License, Version 2.0 (the "License"); | ||
// you may not use this file except in compliance with the License. | ||
// You may obtain a copy of the License at | ||
// | ||
// http://www.apache.org/licenses/LICENSE-2.0 | ||
// | ||
// Unless required by applicable law or agreed to in writing, software | ||
// distributed under the License is distributed on an "AS IS" BASIS, | ||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
// See the License for the specific language governing permissions and | ||
// limitations under the License. | ||
|
||
package main | ||
|
||
import ( | ||
"context" | ||
"flag" | ||
"fmt" | ||
"time" | ||
|
||
"github.com/google/trillian" | ||
"github.com/google/trillian/client" | ||
"github.com/google/trillian/client/rpcflags" | ||
"github.com/pkg/errors" | ||
"google.golang.org/grpc" | ||
"google.golang.org/protobuf/types/known/durationpb" | ||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" | ||
"k8s.io/client-go/kubernetes" | ||
"k8s.io/client-go/rest" | ||
"knative.dev/pkg/logging" | ||
"knative.dev/pkg/signals" | ||
"sigs.k8s.io/release-utils/version" | ||
) | ||
|
||
const ( | ||
// Key in the configmap holding the value of the tree. | ||
treeKey = "treeID" | ||
) | ||
|
||
var ( | ||
ns = flag.String("namespace", "", "Namespace where to update the configmap in") | ||
cmname = flag.String("configmap", "", "Name of the configmap where the treeID lives") | ||
adminServerAddr = flag.String("admin_server", "log-server.trillian-system.svc:80", "Address of the gRPC Trillian Admin Server (host:port)") | ||
treeState = flag.String("tree_state", trillian.TreeState_ACTIVE.String(), "State of the new tree") | ||
treeType = flag.String("tree_type", trillian.TreeType_LOG.String(), "Type of the new tree") | ||
displayName = flag.String("display_name", "", "Display name of the new tree") | ||
description = flag.String("description", "", "Description of the new tree") | ||
maxRootDuration = flag.Duration("max_root_duration", time.Hour, "Interval after which a new signed root is produced despite no submissions; zero means never") | ||
force = flag.Bool("force", false, "Force create a new tree and update configmap") | ||
) | ||
|
||
func main() { | ||
flag.Parse() | ||
ctx := signals.NewContext() | ||
if *ns == "" { | ||
logging.FromContext(ctx).Fatal("Need to specify --namespace for where to update the configmap in") | ||
} | ||
if *cmname == "" { | ||
logging.FromContext(ctx).Fatal("Need to specify --configmap for which configmap to update") | ||
} | ||
|
||
versionInfo := version.GetVersionInfo() | ||
logging.FromContext(ctx).Infof("running Version: %s GitCommit: %s BuildDate: %s", versionInfo.GitVersion, versionInfo.GitCommit, versionInfo.BuildDate) | ||
|
||
config, err := rest.InClusterConfig() | ||
if err != nil { | ||
logging.FromContext(ctx).Fatalf("Failed to get InClusterConfig: %v", err) | ||
} | ||
clientset, err := kubernetes.NewForConfig(config) | ||
if err != nil { | ||
logging.FromContext(ctx).Fatalf("Failed to get clientset: %v", err) | ||
} | ||
cm, err := clientset.CoreV1().ConfigMaps(*ns).Get(ctx, *cmname, metav1.GetOptions{}) | ||
if err != nil { | ||
logging.FromContext(ctx).Fatalf("Failed to get the configmap %s/%s: %v", *ns, *cmname, err) | ||
} | ||
|
||
if cm.Data == nil { | ||
cm.Data = make(map[string]string) | ||
} | ||
if treeID, ok := cm.Data[treeKey]; ok && !*force { | ||
logging.FromContext(ctx).Infof("Found existing TreeID: %s", treeID) | ||
return | ||
} | ||
|
||
tree, err := createTree(ctx) | ||
if err != nil { | ||
logging.FromContext(ctx).Fatalf("Failed to create the trillian tree: %v", err) | ||
} | ||
cm.Data[treeKey] = fmt.Sprint(tree.TreeId) | ||
logging.FromContext(ctx).Infof("Created a new tree %d updating configmap %s/%s", tree.TreeId, *ns, *cmname) | ||
|
||
_, err = clientset.CoreV1().ConfigMaps(*ns).Update(ctx, cm, metav1.UpdateOptions{}) | ||
if err != nil { | ||
logging.FromContext(ctx).Fatalf("Failed to update the configmap: %v", err) | ||
} | ||
} | ||
|
||
func createTree(ctx context.Context) (*trillian.Tree, error) { | ||
req, err := newRequest(ctx) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
dialOpts, err := rpcflags.NewClientDialOptionsFromFlags() | ||
if err != nil { | ||
return nil, errors.Wrap(err, "failed to determine dial options") | ||
} | ||
|
||
conn, err := grpc.Dial(*adminServerAddr, dialOpts...) | ||
if err != nil { | ||
return nil, errors.Wrap(err, "failed to dial") | ||
} | ||
defer conn.Close() | ||
|
||
adminClient := trillian.NewTrillianAdminClient(conn) | ||
logClient := trillian.NewTrillianLogClient(conn) | ||
|
||
return client.CreateAndInitTree(ctx, req, adminClient, logClient) | ||
} | ||
|
||
func newRequest(ctx context.Context) (*trillian.CreateTreeRequest, error) { | ||
ts, ok := trillian.TreeState_value[*treeState] | ||
if !ok { | ||
return nil, fmt.Errorf("unknown TreeState: %v", *treeState) | ||
} | ||
|
||
tt, ok := trillian.TreeType_value[*treeType] | ||
if !ok { | ||
return nil, fmt.Errorf("unknown TreeType: %v", *treeType) | ||
} | ||
|
||
ctr := &trillian.CreateTreeRequest{Tree: &trillian.Tree{ | ||
TreeState: trillian.TreeState(ts), | ||
TreeType: trillian.TreeType(tt), | ||
DisplayName: *displayName, | ||
Description: *description, | ||
MaxRootDuration: durationpb.New(*maxRootDuration), | ||
}} | ||
logging.FromContext(ctx).Infof("Creating Tree: %+v", ctr.Tree) | ||
|
||
return ctr, nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,65 @@ | ||
# Deploying onto Kubernetes | ||
|
||
This document guides you through the process of spinning up an example Trillian | ||
deployment on Kubernetes cluster with [Knative](https://knative.dev/docs/) | ||
installed. It's suitable for GitHub action based e2e tests | ||
as well as local testing using something like kind cluster. | ||
|
||
## Prerequisites | ||
|
||
1. You should have this repo checked out :) | ||
1. A Kubernetes cluster with [Knative](https://knative.dev/docs/) installed. One | ||
example for installing local kind cluster with Knative is | ||
[here](https://github.com/sigstore/scaffolding/blob/main/getting-started.md#running-locally-on-kind) | ||
and ignoring the sigstore parts after installing the cluster. | ||
1. [ko](https://github.com/google/ko) installed. | ||
1. You have `kubectl` installed. | ||
|
||
## Process | ||
|
||
1. Create the scaffolding parts of the Trillian system. | ||
```shell | ||
kubectl apply -Rf ./examples/deployment/kubernetes/scaffolding | ||
``` | ||
This spins up a namespace `trillian-system` where it deploys | ||
the following components: | ||
* log-signer | ||
* log-server | ||
* mysql server | ||
2. Let's make sure everything comes up ready: | ||
```shell | ||
kubectl wait -n trillian-system --for=condition=Ready --timeout=5m ksvc --all | ||
``` | ||
|
||
You should see something like this: | ||
```shell | ||
vaikas@villes-mbp scaffolding % kubectl wait -n trillian-system --for=condition=Ready --timeout=5m ksvc --all | ||
service.serving.knative.dev/log-server condition met | ||
service.serving.knative.dev/log-signer condition met | ||
``` | ||
3. Then create a tree in the Trillian: | ||
```shell | ||
ko apply -BRf ./examples/deployment/kubernetes/createtree | ||
``` | ||
|
||
And make sure it completes. | ||
|
||
```shell | ||
kubectl wait -n createtree --for=condition=Complete --timeout=5m jobs createtree | ||
``` | ||
|
||
4. Check out the tree: | ||
```shell | ||
kubectl -n createtree get cm trillian-tree -ojsonpath='{.data.treeID}' | ||
``` | ||
|
||
You should see something like this: | ||
```shell | ||
vaikas@villes-mbp scaffolding % kubectl -n createtree get cm trillian-tree -ojsonpath='{.data.treeID}' | ||
5213139395739357930% | ||
``` | ||
|
||
5. You can then use the TreeID for example to run CTLog on | ||
top of newly created Trillian. | ||
|
||
6. TODO: Add examples for talking to Trillian for other things. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,4 @@ | ||
kind: Namespace | ||
apiVersion: v1 | ||
metadata: | ||
name: createtree |
24 changes: 24 additions & 0 deletions
24
examples/deployment/kubernetes/createtree/101-binding.yaml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
apiVersion: rbac.authorization.k8s.io/v1 | ||
kind: Role | ||
metadata: | ||
namespace: createtree | ||
name: cm-operator | ||
rules: | ||
- apiGroups: [""] # "" indicates the core API group | ||
resources: ["configmaps"] | ||
resourceNames: ["trillian-tree"] | ||
verbs: ["get", "update"] | ||
--- | ||
apiVersion: rbac.authorization.k8s.io/v1 | ||
kind: RoleBinding | ||
metadata: | ||
name: role-cm-updater | ||
namespace: createtree | ||
roleRef: | ||
apiGroup: rbac.authorization.k8s.io | ||
kind: Role | ||
name: cm-operator | ||
subjects: | ||
- kind: ServiceAccount | ||
name: createtree | ||
namespace: createtree |
12 changes: 12 additions & 0 deletions
12
examples/deployment/kubernetes/createtree/101-configmap.yaml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
apiVersion: v1 | ||
kind: ConfigMap | ||
metadata: | ||
name: trillian-tree | ||
namespace: createtree | ||
data: | ||
__placeholder: | | ||
################################################################### | ||
# Just a placeholder so that reapplying this won't overwrite treeID | ||
# if it already exists. This caused grief, do not remove. | ||
################################################################### | ||
5 changes: 5 additions & 0 deletions
5
examples/deployment/kubernetes/createtree/101-service-account.yaml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
apiVersion: v1 | ||
kind: ServiceAccount | ||
metadata: | ||
name: createtree | ||
namespace: createtree |
18 changes: 18 additions & 0 deletions
18
examples/deployment/kubernetes/createtree/300-createtree.yaml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
apiVersion: batch/v1 | ||
kind: Job | ||
metadata: | ||
name: createtree | ||
namespace: createtree | ||
spec: | ||
template: | ||
spec: | ||
serviceAccountName: createtree | ||
restartPolicy: Never | ||
containers: | ||
- name: createtree | ||
image: ko://github.com/google/trillian/cmd/createtree-k8s | ||
args: [ | ||
"--namespace=createtree", | ||
"--configmap=trillian-tree", | ||
"--display_name=ctlogtree" | ||
] |
4 changes: 4 additions & 0 deletions
4
examples/deployment/kubernetes/scaffolding/log-server/100-namespace.yaml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,4 @@ | ||
kind: Namespace | ||
apiVersion: v1 | ||
metadata: | ||
name: trillian-system |
Oops, something went wrong.