> For the complete documentation index, see [llms.txt](https://developer.harness.io/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://developer.harness.io/continuous-delivery/use-continuous-delivery/deploy-services-on-different-platforms/helm/native-helm-sops-overrides-service-hooks.md).

# SOPS and values overrides in Native Helm service hooks

Decrypt SOPS-encrypted Helm values overrides using Native Helm service hooks, with per-task override directories and optional custom override files.

{% hint style="info" %}
This feature is in Beta[^1] and requires enablement. [View all early access features.](/release-notes/features.md)

{% @harness-feature-flag-access/request-feature-flag-access module="continuous-delivery" pagePath="continuous-delivery/use-continuous-delivery/deploy-services-on-different-platforms/helm/native-helm-sops-overrides-service-hooks" featureFlags="%5B%7B%22name%22%3A%22Native%20Helm%20improved%20SOPS%20support%20for%20service%20hooks%22%2C%22key%22%3A%22CDS\_HELM\_IMPROVED\_SOPS\_SUPPORT\_FOR\_SERVICE\_HOOKS%22%2C%22status%22%3A%22BETA%22%2C%22description%22%3A%22Writes%20Helm%20values%20override%20files%20to%20a%20per-task%20directory%20before%20Fetch%20files%20post-hooks%20run%2C%20so%20hooks%20can%20reliably%20decrypt%20SOPS-encrypted%20overrides%20in%20place.%22%7D%5D" %}
{% endhint %}

For **Native Helm** deployments, Harness writes Helm values override files to a **per-task directory** before your **Fetch files** post-hooks run. This lets your service hooks decrypt overrides, for example with [Mozilla SOPS](https://github.com/mozilla/sops), before Helm template, install, and upgrade commands consume them.

Previously, Harness wrote Native Helm overrides to a shared delegate directory with hash-based filenames, and hooks ran before those files existed. That made it unreliable to decrypt service-defined overrides with SOPS inside a hook.

{% hint style="info" %}
**Native Helm improved SOPS support for service hooks**

This feature is behind the feature flag `CDS_HELM_IMPROVED_SOPS_SUPPORT_FOR_SERVICE_HOOKS`. Contact [Harness Support](mailto:support@harness.io) to enable it.

Minimum delegate version: `26.03.88700` or later.
{% endhint %}

## What you will learn from this topic

* How the [override workflow](#how-the-override-workflow-works) writes and exposes override files to your service hooks.
* The [environment variables](#environment-variables) available to locate and supply override files.
* How to [decrypt overrides in place](#example-decrypt-harness-overrides-in-place) or [supply extra override files](#example-supply-extra-override-files-with-overridefiles).

### How the override workflow works <a href="#how-the-override-workflow-works" id="how-the-override-workflow-works"></a>

* **Write-once overrides:** Harness writes override files once, after preparing the chart and **before** the **Fetch files** post-hook executes. It reuses the same file paths for every subsequent Helm operation in that task, so in-place decryption is never overwritten.
* **Per-task isolation:** Overrides live under the deployment working directory instead of a global shared folder, eliminating cross-deployment contention and producing predictable paths.
* **Hook-visible paths:** Your service hooks can read, modify, and even replace the Harness-written files. Hooks can also supply additional override files through an environment variable (see [OVERRIDE\_FILES](#override_files) below).

### Environment variables <a href="#environment-variables" id="environment-variables"></a>

### VALUES\_OVERRIDE\_DIRECTORY <a href="#valuesoverridedirectory" id="valuesoverridedirectory"></a>

Points to the directory where Harness places override YAML files. Harness names them sequentially: `override-0.yaml`, `override-1.yaml`, and so on.

Use this variable in **Fetch files** post-hooks to locate and decrypt the overrides (for example, `sops -d -i $VALUES_OVERRIDE_DIRECTORY/override-0.yaml`).

### MANIFEST\_FILES\_DIRECTORY and values-overrides <a href="#manifestfilesdirectory-and-values-overrides" id="manifestfilesdirectory-and-values-overrides"></a>

You can also reference the override directory as `$MANIFEST_FILES_DIRECTORY/values-overrides` when your task layout supports it. Prefer `$VALUES_OVERRIDE_DIRECTORY` when available, so your scripts stay aligned with the delegate implementation.

### OVERRIDE\_FILES <a href="#overridefiles" id="overridefiles"></a>

After your hook completes, Harness reads the **`OVERRIDE_FILES`** environment variable, a comma-separated list of additional YAML override file paths, and passes them to Helm alongside the Harness-written overrides.

**Path rules:**

* **Absolute paths:** Harness uses them as-is.
* **Relative paths:** Harness resolves them against the task working directory (not necessarily `$MANIFEST_FILES_DIRECTORY`).
* **Delimiter:** Comma only. Paths cannot contain commas.
* **No pre-validation:** Harness does not check whether the files exist before running Helm. Missing files surface as Helm errors.

Use `OVERRIDE_FILES` when you want decrypted copies in separate files instead of in-place decryption, or when your hook generates overrides dynamically.

### Example: decrypt Harness overrides in place <a href="#example-decrypt-harness-overrides-in-place" id="example-decrypt-harness-overrides-in-place"></a>

This **Fetch files** post-hook iterates over the override directory and decrypts any SOPS-encrypted files in place. Adjust the SOPS backend and key configuration for your environment:

```yaml
hooks:
  - postHook:
      identifier: decrypt_sops
      storeType: Inline
      actions:
        - FetchFiles
      store:
        content: |-
          VALUES_DIRECTORY="${VALUES_OVERRIDE_DIRECTORY:-$MANIFEST_FILES_DIRECTORY/values-overrides}"
          if [ ! -d "$VALUES_DIRECTORY" ]; then
            echo "Error: Directory $VALUES_DIRECTORY not found."
            exit 1
          fi
          for file in "$VALUES_DIRECTORY"/*.yaml "$VALUES_DIRECTORY"/*.yml; do
            [ -e "$file" ] || continue
            if grep -q "sops:" "$file" && grep -q "ENC\[AES256_GCM" "$file"; then
              echo "Decrypting SOPS file $file..."
              sops -d -i "$file"
            else
              echo "Skipping $file (no SOPS metadata found)."
            fi
          done
```

### Example: supply extra override files with OVERRIDE\_FILES <a href="#example-supply-extra-override-files-with-overridefiles" id="example-supply-extra-override-files-with-overridefiles"></a>

Service hooks run in the delegate task working directory. Use `$(pwd)` or an explicit path such as `/tmp` for generated files:

```yaml
hooks:
  - postHook:
      identifier: decrypt_sops
      storeType: Inline
      actions:
        - FetchFiles
      store:
        content: |-
          WORK_DIR="$(pwd)"
          cat > "$WORK_DIR/override-file1.yaml" <<EOF
          override: "override-value-1"
          EOF
          cat > "$WORK_DIR/override-file2.yaml" <<EOF
          override: "override-value-2"
          EOF
          export OVERRIDE_FILES="$WORK_DIR/override-file1.yaml,$WORK_DIR/override-file2.yaml"
```

Avoid spaces after commas in `OVERRIDE_FILES`. Use a tight comma-separated list unless your paths intentionally include leading spaces.

### Backward compatibility <a href="#backward-compatibility" id="backward-compatibility"></a>

When the feature flag is **disabled**, Native Helm follows the previous behavior for writing override files. Your existing pipelines continue to work without changes.

***

## Next steps

* [Service hooks](/continuous-delivery/use-continuous-delivery/deploy-services-on-different-platforms/kubernetes/cd-kubernetes-category/service-hooks.md): Configure pre- and post-hooks for your service.
* [Deploy Native Helm using Harness](/continuous-delivery/use-continuous-delivery/deploy-services-on-different-platforms/helm/native-helm-quickstart.md): Set up a Native Helm deployment.
* [Deploy Helm charts](/continuous-delivery/use-continuous-delivery/deploy-services-on-different-platforms/helm/deploy-helm-charts.md): Configure SOPS and encrypted values for the **Kubernetes** (Harness-managed Helm) deployment type. The encryption concepts are similar, but the deployment flow and override mechanics differ from Native Helm.

{% @harness-feedback/feedback %}

[^1]: Beta features are feature-complete but still being validated. Available on request.
