Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: refacto github/gitlab clients #413

Merged
merged 9 commits into from
Jan 2, 2025
2 changes: 0 additions & 2 deletions api/v1alpha1/terraformpullrequest_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@ import (

// TerraformPullRequestSpec defines the desired state of TerraformPullRequest
type TerraformPullRequestSpec struct {
Provider string `json:"provider,omitempty"`
Branch string `json:"branch,omitempty"`
Base string `json:"base,omitempty"`
ID string `json:"id,omitempty"`
Expand All @@ -45,7 +44,6 @@ type TerraformPullRequestStatus struct {
// +kubebuilder:subresource:status
// +kubebuilder:printcolumn:name="ID",type=string,JSONPath=`.spec.id`
// +kubebuilder:printcolumn:name="State",type=string,JSONPath=`.status.state`
// +kubebuilder:printcolumn:name="Provider",type=string,JSONPath=`.spec.provider`
// +kubebuilder:printcolumn:name="Base",type=string,JSONPath=`.spec.base`
// +kubebuilder:printcolumn:name="Branch",type=string,JSONPath=`.spec.branch`
// TerraformPullRequest is the Schema for the TerraformPullRequests API
Expand Down
28 changes: 28 additions & 0 deletions deploy/charts/burrito/templates/tenant.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,34 @@ subjects:
name: {{ $serviceAccount.name }}
namespace: {{ $tenant.namespace.name }}
---
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: secret-access
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should be a ClusterRole named burrito-server-secret-access

labels:
app: burrito
namespace: {{ $tenant.namespace.name }}
rules:
- apiGroups: [""]
resources: ["secrets"]
verbs: ["get", "list", "watch"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
name: burrito-server-secret-access
labels:
app: burrito
namespace: {{ $tenant.namespace.name }}
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: secret-access
subjects:
- kind: ServiceAccount
name: burrito-server
namespace: {{ $.Release.Namespace }}
---
{{- range $additionalRoleBinding := $serviceAccount.additionalRoleBindings }}
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
Expand Down
29 changes: 3 additions & 26 deletions deploy/charts/burrito/values.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -41,20 +41,6 @@ config:
healthProbeBindAddress: ":8081"
# -- Port used to handle the Kubernetes webhook
kubernetesWebhookPort: 9443
githubConfig:
# -- Github app ID, prefer override with the BURRITO_CONTROLLER_GITHUBCONFIG_APPID environment variable
appId: ""
# -- Github app unstallation ID, prefer override with the BURRITO_CONTROLLER_GITHUBCONFIG_INSTALLATIONID environment variable
installationId: ""
# -- Github app private key, prefer override with the BURRITO_CONTROLLER_GITHUBCONFIG_PRIVATEKEY environment variable
privateKey: ""
# -- Github API token, prefer override with the BURRITO_CONTROLLER_GITHUBCONFIG_APITOKEN environment variable
apiToken: ""
gitlabConfig:
# -- Gitlab API token Prefer override with the BURRITO_CONTROLLER_GITLABCONFIG_APITOKEN environment variable
apiToken: ""
# -- Gitlab URL
url: ""
# -- Provider cache custom configuration
hermitcrab: {}
datastore:
Expand Down Expand Up @@ -84,13 +70,6 @@ config:
server:
# -- Server exposed port
addr: ":8080"
webhook:
github:
# -- Secret to validate webhook payload, prefer override with the BURRITO_SERVER_WEBHOOK_GITHUB_SECRET environment variable
secret: ""
gitlab:
# -- Secret to validate webhook payload, Prefer override with the BURRITO_SERVER_WEBHOOK_GITLAB_SECRET environment variable
secret: ""

runner:
# -- Configmap name to store the SSH known hosts in the runner
Expand Down Expand Up @@ -335,11 +314,9 @@ server:
initialDelaySeconds: 5
periodSeconds: 20
# -- Environment variables to pass to the Burrito server container
envFrom:
# -- Reference the webhook secret here, it should define a BURRITO_SERVER_WEBHOOK_GITHUB_SECRET and/or BURRITO_SERVER_WEBHOOK_GITLAB_SECRET key
- secretRef:
name: burrito-webhook-secret
optional: true
env: []
# -- Environment variables to pass to the Burrito server container
envFrom: []
# -- Additional volumes
extraVolumes: {}
# -- Additional volume mounts
Expand Down
9 changes: 9 additions & 0 deletions docs/getting-started.md
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,15 @@ This will create a new namespace, `burrito-system`, where burrito services will

Create a Kubernetes `Secret` to reference the necessary credentials to clone your IaC repository (github or gitlab)

!!! info
Supported authentication methods are:
- Username and password
- SSH private key
- GitHub App
- GitHub API token
- GitLab API token
More information on how to create a secret can be found in the [Secrets](./secrets/index.md) section.

```yaml
kind: Secret
metadata:
Expand Down
37 changes: 24 additions & 13 deletions docs/guides/pr-mr-workflow.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,34 +26,45 @@ spec:
```

You will also need to setup a [GitHub App](https://docs.github.com/en/apps/creating-github-apps/about-creating-github-apps/about-creating-github-apps) to allow Burrito to comment on your PRs/MRs. Follow the instructions in the [PR/MR workflow](../operator-manual/pr-mr-workflow.md#configuration) section of the operator manual to set up the GitHub app.
Make sure that you updated the Burrito values file to include the GitHub app ID, installation ID, and private key to the Burrito controller deployment.

!!! info
Your controller deployment should now have the following environment variables:
- `BURRITO_CONTROLLER_GITHUBCONFIG_APPID`: The App ID of your GitHub app.
- `BURRITO_CONTROLLER_GITHUBCONFIG_INSTALLATIONID`: The Installation ID of your GitHub app.
- `BURRITO_CONTROLLER_GITHUBCONFIG_PRIVATEKEY`: The private key of your GitHub app.
Make sure that you created a secret associated to your repository that include the GitHub app ID, installation ID, and private key.

!!! note
You can also use a personal access token instead of a GitHub app. Your GitHub account will be used to comment on the PRs/MRs.
The environment variable to set is `BURRITO_CONTROLLER_GITHUBCONFIG_APITOKEN`
The secret should include the personal access token in the `githubToken` key.

Now let's configure the GitHub webhook. Expose the `burrito-server` kubernetes service to the internet using the method of your choice. (for testing purposes on a local cluster, you can use `kubectl port-forward` and [ngrok](https://ngrok.com/) to expose the service to the internet).

Configure a webhook in your GitHub repository to point to the exposed `burrito-server` service. **Make sure to specify the `/api/webhook` path in the target url.** The webhook should be triggered on `push` and `pull_request` events. You can reference your webhook secret in a secret named `burrito-webhook-secret` in the controller namespace (`burrito-system` in this tutorial).
Configure a webhook in your GitHub repository to point to the exposed `burrito-server` service. **Make sure to specify the `/api/webhook` path in the target url.** The webhook should be triggered on `push` and `pull_request` events. Reference your webhook secret in the secret associated to your repository, in the `webhookSecret` key.

Your `TerraformRepository` resource and secret should look like this:
```yaml
apiVersion: config.terraform.padok.cloud/v1alpha1
kind: TerraformRepository
metadata:
name: my-repository
namespace: burrito-project
spec:
repository:
url: https://github.com/<your-github-handle>/burrito-examples
secretName: burrito-secret
terraform:
enabled: true
---
kind: Secret
metadata:
name: burrito-webhook-secret
namespace: burrito-system
namespace: burrito-project
type: Opaque
stringData:
burrito-webhook-secret: <my-webhook-secret>
githubAppId: "123456"
githubAppInstallationId: "12345678"
githubAppPrivateKey: |
-----BEGIN RSA PRIVATE KEY-----
my-private-key
-----END RSA PRIVATE KEY-----
webhookSecret: "my-webhook-secret"
```

You can also directly add the webhook secret as an environment variable of the `burrito-server` deployment. The variable name depends on your git provider. For GitHub, the environment variable is `BURRITO_SERVER_WEBHOOK_GITHUB_SECRET`.

### Experiment with the PR/MR workflow

Now that you have set up the webhook and GitHub app, you can experiment with the PR/MR workflow.
Expand Down
68 changes: 68 additions & 0 deletions docs/operator-manual/git-authentication.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
# Git Authentication

## Overview

This section will guide you through the different ways to authenticate to a git repository.
Authentication is required for:
- Cloning a private repository
- Implementing the [PR/MR workflow](./pr-mr-workflow.md)

Available authentication methods:
- Username and password (only supports cloning)
- SSH private key (only supports cloning)
- GitHub App
- GitHub API token
- GitLab API token

## Repository Secret

The `TerraformRepository` spec allows you to specify a secret that contains the credentials to authenticate to a git repository.
The secret must be created in the same namespace as the `TerraformRepository` and be referenced in `spec.repository.secretName`.

### Expected keys

To add an authentication method for a repository, the secret must contain the following keys:

Username and password:
- `username`
- `password`

SSH private key:
- `sshPrivateKey`

GitHub App:
- `githubAppId`
- `githubAppInstallationId`
- `githubAppPrivateKey`

GitHub API token:
- `githubToken`

GitLab API token:
- `gitlabToken`

For the PR/MR workflow, the Kubernetes secret must also contain the webhook secret:
- `webhookSecret`

Example of a Kubernetes secret for a GitHub repository, using authentication with a GitHub App and implementing the PR workflow:

```yaml
apiVersion: v1
kind: Secret
metadata:
name: burrito-repo
namespace: burrito-project
type: Opaque
stringData:
githubAppId: "123456"
githubAppInstallationId: "12345678"
githubAppPrivateKey: |
-----BEGIN RSA PRIVATE KEY-----
my-private-key
-----END RSA PRIVATE KEY-----
webhookSecret: "my-webhook-secret"
```

### Behavior

If multiple authentication methods are provided, the runner will try them all until one succeeds to clone the repository.
41 changes: 28 additions & 13 deletions docs/operator-manual/git-webhook.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,23 +15,38 @@ The webhook should be triggered on `push` and `pull_request` events.
GitLab triggers:
The webhook should be triggered on `Push events` from all branches and `Merge request events`.

## Reference the webhook secret in the controller
## Reference the webhook secret in the repository secret

Add the webhook secret to the secret used to authenticate to the repository. If the repository is public, create a secret in the same namespace as the `TerraformRepository` and reference it in the `spec.repository.secretName`.
Reference the webhook secret in the webhookSecret key of the Kubernetes secret.

```yaml
apiVersion: config.terraform.padok.cloud/v1alpha1
kind: TerraformRepository
metadata:
name: my-repository
namespace: burrito-project
spec:
repository:
url: https://github.com/owner/repo
secretName: burrito-repo
terraform:
enabled: true
```

Create a secret called `burrito-webhook-secret` in the controller namespace with the webhook secret.
```yaml
kind: Secret
apiVersion: v1
kind: Secret
metadata:
name: burrito-webhook-secret
namespace: burrito-system
name: burrito-repo
namespace: burrito-project
type: Opaque
stringData:
burrito-webhook-secret: <my-webhook-secret>
githubAppId: "123456"
githubAppInstallationId: "12345678"
githubAppPrivateKey: |
-----BEGIN RSA PRIVATE KEY-----
my-private-key
-----END RSA PRIVATE KEY-----
webhookSecret: "my-webhook-secret"
```

Add the webhook secret as an environment variable of the `burrito-server`. The variables depends on your git provider.

| Git provider | Environment Variable |
| :----------: | :------------------------------------: |
| GitHub | `BURRITO_SERVER_WEBHOOK_GITHUB_SECRET` |
| GitLab | `BURRITO_SERVER_WEBHOOK_GITLAB_SECRET` |
Loading
Loading