Adds Prow cluster deployment config and documentation
Change-Id: I3cf47da026bf8f40ee8ae4dd3fdbebc64116ce15
Google-Bug-Id: 119890379
Signed-off-by: Avi Kondareddy <avikr@google.com>
diff --git a/README.md b/README.md
index 22c3cf9..54b2c8a 100644
--- a/README.md
+++ b/README.md
@@ -169,4 +169,39 @@
signals failure akin to regular shell scripts.
## Prow Cluster Deployment
-TODO(avikr@google.com): add cluster.yaml and explain
+
+To deploy in any Kubernetes environment, first read Prow deployment
+documentation [here](https://github.com/kubernetes/test-infra/blob/master/prow/\
+getting_started_deploy.md) and for further clarification, the Kubernetes
+documentation [here](https://kubernetes.io/docs/setup/). Prow comes with several
+[components](https://github.com/kubernetes/test-infra/blob/master/prow/cmd/README.md),
+several of which are only necessary for interacting with github webhooks. We
+have included here a [deployment.yaml](deployment.yaml) which includes just the
+components needed to poll gerrit repos. For every new gerrit repo to run
+presubmits on, you will need to update the
+[Gerrit](https://github.com/kubernetes/test-infra/tree/master/prow/cmd/gerrit)
+component in the deployment accordingly.
+
+Checkout [prow/cluster/starter.yaml](
+https://github.com/kubernetes/test-infra/blob/master/prow/cluster/starter.yaml)
+for github presubmit instructions which requires oauth token authentication.
+Job configuration in config.yaml does not need to change.
+
+Succinctly, a Kubernetes deployment file specifies all the API objects needed
+for deployment. Each prow component is a container pod that is described in
+an object of kind *Deployment*, specifying a Docker image that the deployment
+will launch. *Services* specify extra-pod communication and
+*ServiceAccount*s provide an identity to the processes that run in these pods.
+*Role*s and *RoleBinding*s provide RBAC authorization for components. Read this
+[article](https://www.cncf.io/blog/2018/08/01/demystifying-rbac-in-kubernetes/)
+on RBAC in Kubernetes if documentation is not sufficient.
+*PersistentVolumeClaim* are a type of Volume used for maintaining state and
+is used for gerrit to keep track of the latest synced commit. You may also need
+to configure the *Ingress* depending on your network / deployment environment
+for all external communication.
+
+You will also need a git https cookie file to interact with your gerrit
+instances as anonymous access is not currently supported. For a token
+periodically authenticated with gcloud, see/deploy [grandmatriarch](
+https://github.com/kubernetes/test-infra/blob/master/prow/cmd/grandmatriarch/bake.sh)
+(TODO(avikr) BUG #120081009: change documentation upon gcr image update)
diff --git a/deployment.yaml b/deployment.yaml
new file mode 100644
index 0000000..bb5bc5c
--- /dev/null
+++ b/deployment.yaml
@@ -0,0 +1,505 @@
+# This file contains Kubernetes YAML files for the most important prow
+# components. Don't edit resources in this file. Instead, pull them out into
+# their own files.
+---
+apiVersion: v1
+kind: ConfigMap
+metadata:
+ name: plugins
+data:
+ plugins.yaml: ""
+---
+apiVersion: apiextensions.k8s.io/v1beta1
+kind: CustomResourceDefinition
+metadata:
+ name: prowjobs.prow.k8s.io
+spec:
+ group: prow.k8s.io
+ version: v1
+ names:
+ kind: ProwJob
+ singular: prowjob
+ plural: prowjobs
+ scope: Namespaced
+ validation:
+ openAPIV3Schema:
+ properties:
+ spec:
+ properties:
+ max_concurrency:
+ type: integer
+ minimum: 0
+ type:
+ type: string
+ enum:
+ - "presubmit"
+ - "postsubmit"
+ - "periodic"
+ - "batch"
+ status:
+ properties:
+ state:
+ type: string
+ enum:
+ - "triggered"
+ - "pending"
+ - "success"
+ - "failure"
+ - "aborted"
+ - "error"
+ anyOf:
+ - not:
+ properties:
+ state:
+ type: string
+ enum:
+ - "success"
+ - "failure"
+ - "error"
+ - "aborted"
+ - required:
+ - completionTime
+---
+apiVersion: extensions/v1beta1
+kind: Deployment
+metadata:
+ name: plank
+ labels:
+ app: plank
+spec:
+ replicas: 1 # Do not scale up.
+ template:
+ metadata:
+ labels:
+ app: plank
+ spec:
+ serviceAccountName: plank
+ containers:
+ - name: plank
+ image: gcr.io/k8s-prow/plank:v20181101-84d67de
+ args:
+ - --dry-run=false
+ - --github-token-path=
+ volumeMounts:
+ - name: config
+ mountPath: /etc/config
+ readOnly: true
+ volumes:
+ - name: config
+ configMap:
+ name: config
+---
+apiVersion: extensions/v1beta1
+kind: Deployment
+metadata:
+ name: sinker
+ labels:
+ app: sinker
+spec:
+ replicas: 1
+ template:
+ metadata:
+ labels:
+ app: sinker
+ spec:
+ serviceAccountName: sinker
+ containers:
+ - name: sinker
+ image: gcr.io/k8s-prow/sinker:v20181101-84d67de
+ volumeMounts:
+ - name: config
+ mountPath: /etc/config
+ readOnly: true
+ volumes:
+ - name: config
+ configMap:
+ name: config
+---
+apiVersion: extensions/v1beta1
+kind: Deployment
+metadata:
+ name: deck
+ labels:
+ app: deck
+spec:
+ replicas: 2
+ strategy:
+ type: RollingUpdate
+ rollingUpdate:
+ maxSurge: 1
+ maxUnavailable: 1
+ template:
+ metadata:
+ labels:
+ app: deck
+ spec:
+ serviceAccountName: deck
+ terminationGracePeriodSeconds: 30
+ containers:
+ - name: deck
+ image: gcr.io/k8s-prow/deck:v20181101-84d67de
+ ports:
+ - name: http
+ containerPort: 8080
+ volumeMounts:
+ - name: config
+ mountPath: /etc/config
+ readOnly: true
+ volumes:
+ - name: config
+ configMap:
+ name: config
+---
+apiVersion: v1
+kind: Service
+metadata:
+ name: deck
+spec:
+ selector:
+ app: deck
+ ports:
+ - port: 80
+ targetPort: 8080
+ type: NodePort
+---
+apiVersion: extensions/v1beta1
+kind: Deployment
+metadata:
+ name: horologium
+ labels:
+ app: horologium
+spec:
+ replicas: 1
+ template:
+ metadata:
+ labels:
+ app: horologium
+ spec:
+ serviceAccountName: horologium
+ terminationGracePeriodSeconds: 30
+ containers:
+ - name: horologium
+ image: gcr.io/k8s-prow/horologium:v20181101-84d67de
+ volumeMounts:
+ - name: config
+ mountPath: /etc/config
+ readOnly: true
+ volumes:
+ - name: config
+ configMap:
+ name: config
+---
+apiVersion: extensions/v1beta1
+kind: Ingress
+metadata:
+ name: ing
+spec:
+ rules:
+ - http:
+ paths:
+ - path: /*
+ backend:
+ serviceName: deck
+ servicePort: 80
+---
+# start gerrit
+kind: PersistentVolumeClaim
+apiVersion: v1
+metadata:
+ labels:
+ app: gerrit
+ name: gerrit-storage
+spec:
+ accessModes:
+ - ReadWriteOnce
+ resources:
+ requests:
+ storage: 1Gi
+ # volumeName: added automatically after volume creation
+ # See https://cloud.google.com/kubernetes-engine/docs/concepts/persistent-volumes
+---
+apiVersion: apps/v1
+kind: Deployment
+metadata:
+ name: gerrit
+ labels:
+ app: gerrit
+spec:
+ replicas: 1
+ selector:
+ matchLabels:
+ app: gerrit
+ template:
+ metadata:
+ labels:
+ app: gerrit
+ spec:
+ serviceAccountName: gerrit
+ terminationGracePeriodSeconds: 30
+ containers:
+ - name: gerrit
+ image: gcr.io/k8s-prow/gerrit:v20181101-84d67de
+ args:
+ - --config-path=/etc/config/config.yaml
+ - --cookiefile=/etc/cookies/cookies
+ - --gerrit-projects=https://kunit.googlesource.com=linux
+ - --last-sync-fallback=/store/gerrit
+ volumeMounts:
+ - name: config
+ mountPath: /etc/config
+ readOnly: true
+ - name: gerrit-volume
+ mountPath: /store
+ - name: cookies
+ mountPath: /etc/cookies
+ readOnly: true
+ volumes:
+ - name: config
+ configMap:
+ name: config
+ - name: cookies
+ secret:
+ defaultMode: 420
+ secretName: http-cookiefile
+ - name: gerrit-volume
+ persistentVolumeClaim:
+ claimName: gerrit-storage
+---
+apiVersion: extensions/v1beta1
+kind: Deployment
+metadata:
+ name: crier
+ labels:
+ app: crier
+spec:
+ replicas: 1
+ template:
+ metadata:
+ labels:
+ app: crier
+ spec:
+ serviceAccountName: crier
+ terminationGracePeriodSeconds: 30
+ containers:
+ - name: crier
+ image: gcr.io/k8s-prow/crier:v20180923-f4dcfcecf
+ args:
+ - --gerrit-workers=1
+ - --cookiefile=/etc/cookies/cookies
+ - --gerrit-projects=https://kunit.googlesource.com=linux
+ volumeMounts:
+ - name: cookies
+ mountPath: /etc/cookies
+ readOnly: true
+ volumes:
+ - name: cookies
+ secret:
+ defaultMode: 420
+ secretName: http-cookiefile
+### Cluster rbac rules
+---
+apiVersion: v1
+kind: ServiceAccount
+metadata:
+ name: "deck"
+---
+kind: Role
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "deck"
+rules:
+ - apiGroups:
+ - ""
+ resources:
+ - pods/log
+ verbs:
+ - get
+ - apiGroups:
+ - "prow.k8s.io"
+ resources:
+ - prowjobs
+ verbs:
+ - get
+ - list
+---
+kind: RoleBinding
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "deck"
+roleRef:
+ apiGroup: rbac.authorization.k8s.io
+ kind: Role
+ name: "deck"
+subjects:
+- kind: ServiceAccount
+ name: "deck"
+---
+apiVersion: v1
+kind: ServiceAccount
+metadata:
+ name: "horologium"
+---
+kind: Role
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "horologium"
+rules:
+ - apiGroups:
+ - "prow.k8s.io"
+ resources:
+ - prowjobs
+ verbs:
+ - create
+ - list
+---
+kind: RoleBinding
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "horologium"
+roleRef:
+ apiGroup: rbac.authorization.k8s.io
+ kind: Role
+ name: "horologium"
+subjects:
+- kind: ServiceAccount
+ name: "horologium"
+---
+apiVersion: v1
+kind: ServiceAccount
+metadata:
+ name: "plank"
+---
+kind: Role
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "plank"
+rules:
+ - apiGroups:
+ - ""
+ resources:
+ - pods
+ verbs:
+ - create
+ - delete
+ - list
+ - apiGroups:
+ - "prow.k8s.io"
+ resources:
+ - prowjobs
+ verbs:
+ - create
+ - list
+ - update
+---
+kind: RoleBinding
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "plank"
+roleRef:
+ apiGroup: rbac.authorization.k8s.io
+ kind: Role
+ name: "plank"
+subjects:
+- kind: ServiceAccount
+ name: "plank"
+---
+apiVersion: v1
+kind: ServiceAccount
+metadata:
+ name: "sinker"
+---
+kind: Role
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "sinker"
+rules:
+ - apiGroups:
+ - ""
+ resources:
+ - pods
+ verbs:
+ - delete
+ - list
+ - apiGroups:
+ - "prow.k8s.io"
+ resources:
+ - prowjobs
+ verbs:
+ - delete
+ - list
+---
+kind: RoleBinding
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "sinker"
+roleRef:
+ apiGroup: rbac.authorization.k8s.io
+ kind: Role
+ name: "sinker"
+subjects:
+- kind: ServiceAccount
+ name: "sinker"
+---
+apiVersion: v1
+kind: ServiceAccount
+metadata:
+ name: "gerrit"
+---
+kind: Role
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "gerrit"
+rules:
+- apiGroups:
+ - "prow.k8s.io"
+ resources:
+ - prowjobs
+ verbs:
+ - create
+ - list
+---
+kind: RoleBinding
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "gerrit"
+roleRef:
+ apiGroup: rbac.authorization.k8s.io
+ kind: Role
+ name: "gerrit"
+subjects:
+- kind: ServiceAccount
+ name: "gerrit"
+---
+kind: ServiceAccount
+apiVersion: v1
+metadata:
+ name: "crier"
+---
+kind: ClusterRole
+apiVersion: rbac.authorization.k8s.io/v1
+metadata:
+ # "namespace" omitted since ClusterRoles are not namespaced
+ name: crier
+rules:
+- apiGroups:
+ - "prow.k8s.io"
+ resources:
+ - "prowjobs"
+ verbs:
+ - "get"
+ - "watch"
+ - "list"
+---
+kind: ClusterRoleBinding
+apiVersion: rbac.authorization.k8s.io/v1beta1
+metadata:
+ name: "crier"
+ namespace: "default"
+roleRef:
+ apiGroup: rbac.authorization.k8s.io
+ kind: ClusterRole
+ name: "crier"
+subjects:
+- kind: ServiceAccount
+ name: "crier"
+ namespace: "default"