manage_harness - robjcook/sync GitHub Wiki
pipeline:
name: Terraform Harness Self-Management
identifier: terraform_harness_self_management
projectIdentifier: YOUR_HARNESS_PROJECT_FOR_THIS_PIPELINE # Replace with the project ID where this pipeline will live
orgIdentifier: YOUR_HARNESS_ORG_FOR_THIS_PIPELINE # Replace with the organization ID where this pipeline will live
tags: {}
stages:
- stage:
name: Terraform Plan
identifier: terraform_plan_stage
description: "Generates a Terraform plan for Harness resource changes."
type: Custom
spec:
skipCondition:
expression: <+pipeline.variables.skip_terraform_plan>
execution:
steps:
- step:
name: Fetch Terraform Code
identifier: fetch_terraform_code
type: GitClone
spec:
connectorRef: YOUR_GIT_CONNECTOR_ID # Replace with your Git connector ID (e.g., 'my_github_connector')
repoName: YOUR_TERRAFORM_CONFIG_REPO_NAME # Replace with the name of the repo holding main.tf
branch: main # Or the branch where your Terraform config is stored
depth: 1
- step:
name: Initialize Terraform
identifier: init_terraform
type: Run
spec:
shell: Sh
command: |-
terraform init
# Ensure Terraform CLI is available on the Delegate running this step.
# You might need to install it via the Delegate's init_script or use a custom delegate image.
- step:
name: Terraform Plan
identifier: terraform_plan
type: TerraformPlan
spec:
provisionerIdentifier: harness_resources # A unique identifier for this Terraform provisioning
configuration:
type: Inline
spec:
# Path to your Terraform files relative to the cloned repository root
workspace: default
configFiles:
store:
type: Inline
spec:
files:
- content: |
# Copy the content of your main.tf here
# For a large main.tf, it's better to use `Git` for configFiles
# or `file` function within Terraform if main.tf is in a sub-path.
# Example for Git:
# store:
# type: Git
# spec:
# connectorRef: YOUR_GIT_CONNECTOR_ID
# repoName: YOUR_TERRAFORM_CONFIG_REPO_NAME
# folderPath: /path/to/your/terraform/files
# branch: main
content: |
${file(".harness_temp_dir/main.tf")} # This is a placeholder, actual content needs to be inline or fetched from Git
# IMPORTANT: For real-world use, you would configure `configFiles` to point to your Git repo
# Example:
# configFiles:
# store:
# type: Git
# spec:
# connectorRef: YOUR_GIT_CONNECTOR_ID
# repoName: YOUR_TERRAFORM_CONFIG_REPO_NAME
# folderPath: "." # Path to your .tf files within the repo
# branch: main
# If you use the Git clone step, you can point to the local path:
# `folderPath: ./` for the repo root or `./terraform_configs` if in a subfolder.
# The values for variables will be passed as secret variables from Harness.
# These map to the `variable` blocks in your `main.tf`.
# The expression `account.harness_platform_api_key_secret` references a Harness Secret.
# Ensure this secret is created in Harness.
# The `harness_account_id_secret` should also be created as a secret.
variables:
harness_account_id: <+secrets.getValue("harness_account_id_secret")>
harness_platform_api_key: <+secrets.getValue("harness_platform_api_key_secret")>
command: Apply # Or Destroy if you want to plan for destruction
# Specify the delegate selector if you have specific delegates for Terraform execution
delegateSelectors:
- terraform-delegate # Replace with your delegate selector
- stage:
name: Approval
identifier: approval_stage
description: "Manual approval to review the Terraform plan."
type: Approval
spec:
approvalMessage: "Review the Terraform plan before applying changes to Harness resources."
inputVariables: []
timeout: 1d
approvers:
userGroups:
- YOUR_HARNESS_USER_GROUP_ID # Replace with a user group that can approve
minimumCount: 1
# Skip condition to only run approval if the plan stage was successful
skipCondition:
expression: <+pipeline.stages.terraform_plan_stage.status> != "SUCCESS"
- stage:
name: Terraform Apply
identifier: terraform_apply_stage
description: "Applies the Terraform plan to provision Harness resources."
type: Custom
spec:
execution:
steps:
- step:
name: Terraform Apply
identifier: terraform_apply
type: TerraformApply
spec:
provisionerIdentifier: harness_resources # Must match the identifier from Terraform Plan step
configuration:
type: Inline
spec:
# As in the plan step, point to your Git repo
# If you use the Git clone step before, the local path should be used
# If fetching directly here:
# configFiles:
# store:
# type: Git
# spec:
# connectorRef: YOUR_GIT_CONNECTOR_ID
# repoName: YOUR_TERRAFORM_CONFIG_REPO_NAME
# folderPath: "." # Path to your .tf files within the repo
# branch: main
content: |
${file(".harness_temp_dir/main.tf")} # Placeholder, content needs to be inline or fetched
variables:
harness_account_id: <+secrets.getValue("harness_account_id_secret")>
harness_platform_api_key: <+secrets.getValue("harness_platform_api_key_secret")>
command: Apply
# Specify the delegate selector
delegateSelectors:
- terraform-delegate # Replace with your delegate selector