The Diagrid Dapr Injector is a Helm library chart designed to inject the Dapr sidecar into your Kubernetes application workloads (e.g., Deployments, StatefulSets). This chart is based on the dapr/dapr project but functions as a library chart rather than a standalone installation.
- Kubernetes cluster
- Helm 3.x
This chart is not intended for standalone use. Instead, incorporate it as a dependency in your existing Helm charts.
In your Helm chart's Chart.yaml file, add the following dependency:
dependencies:
- name: diagrid-dapr-injector
version: 1.0.0
repository: oci://public.ecr.aws/diagrid/d3e-charts
alias: diagrid_dapr_injectorUpdate your Helm chart:
helm dependency updateIn your values.yaml file, add any necessary overrides for the injector:
dapr:
image:
tag: "1.15.6-d3e.1"
ha:
enabled: true
controlPlaneNamespace: dapr-system
controlPlaneTrustDomain: cluster.local
podAnnotations:
dapr.io/enabled: "true"
dapr.io/app-id: "myapp"
dapr.io/app-port: "5000"Modify your workload templates (e.g., templates/deployment.yaml) to include the Dapr sidecar:
apiVersion: apps/v1
kind: Deployment
metadata:
name: {{ .Release.Name }}-deployment
labels:
app: {{ .Release.Name }}
spec:
replicas: 1
selector:
matchLabels:
app: {{ .Release.Name }}
template:
metadata:
labels:
app: {{ .Release.Name }}
annotations:
{{ toYaml .Values.podAnnotations | nindent 8 | trim}}
spec:
containers:
- name: {{ .Chart.Name }}
image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}"
imagePullPolicy: {{ .Values.image.pullPolicy }}
{{ include "diagrid-dapr-injector.sidecar" (dict "podAnnotations" .Values.podAnnotations "helmCtx" .) | nindent 6 }}
volumes:
{{ include "diagrid-dapr-injector.volumes" . | nindent 8 }}
{{- include "diagrid.dapr.resources-volumes" . | indent 6 }}
{{- if .Values.diagrid_dapr_injector.injectDaprResources }}
{{- include "diagrid.dapr.resources-volumes" (dict "podAnnotations" .Values.podAnnotations "helmCtx" .) | indent 6 }}
{{- end }}The default values are defined in the templates/_helpers.tpl file. Key configuration options include:
dapr.image: Dapr sidecar image settingsdapr.controlPlaneNamespace: Namespace for the Dapr control planedapr.controlPlaneTrustDomain: Trust domain for the clusterdapr.actors: Actor service configurationdapr.reminders: Reminder service configurationdapr.scheduler: Scheduler settingsdapr.ha: High availability settingsdapr.mtls: mTLS configurationdapr.prometheus: Prometheus metrics settingsdapr.mode: Dapr mode (standalone or kubernetes)dapr.injectDaprResources: Enable Dapr without CRDsdapr.configurationFiles: List of configuration files to be injected into the sidecar
For a complete list of configuration options, refer to the templates/_helpers.tpl file in the chart.
This Helm library chart enables the use of Dapr without CRDs. To enable this feature, set the injectDaprResources flag to true in your values file:
diagrid_dapr_injector:
mode: "standalone"
injectDaprResources: true
configurationFiles:
- config.yamlIn standalone mode, the injector automatically mounts Dapr configurations, components, HTTP endpoints, resiliencies, and subscriptions into the workload. To enable this, ensure that all necessary resource files are placed in resources/{type} and listed in your confifuration files listed:
diagrid_dapr_injector:
configurationFiles:
- config.yamlThe injector then converts these files into ConfigMaps and mounts them into the Dapr sidecar via the --config and --resources-path arguments.
You need to manually create the required ConfigMaps in the same namespace as the workload. Below are examples of how to generate ConfigMaps for different Dapr resources using the dapr.resource template.
{{- include "dapr.resource" (dict "namespace" .Release.Namespace "files" (.Files.Glob "resources/configurations/*") "name" "dapr-configurations") }}
---
{{- include "dapr.resource" (dict "namespace" .Release.Namespace "files" (.Files.Glob "resources/components/*") "name" "dapr-components") }}
---
{{- include "dapr.resource" (dict "namespace" .Release.Namespace "files" (.Files.Glob "resources/httpendpoints/*") "name" "dapr-httpendpoints") }}
---
{{- include "dapr.resource" (dict "namespace" .Release.Namespace "files" (.Files.Glob "resources/resiliencies/*") "name" "dapr-resiliencies") }}
---
{{- include "dapr.resource" (dict "namespace" .Release.Namespace "files" (.Files.Glob "resources/subscriptions/*") "name" "dapr-subscriptions") }}When running daprd in standalone mode, app services must be explicitly injected, as this is typically handled by the Dapr operator in Kubernetes.
To ensure proper service discovery, the name resolution component in the global configuration must be set to target Kubernetes:
nameResolution:
component: kubernetesAfter configuring name resolution, you need to define the necessary services using the following Helm template:
{{- include "diagrid.dapr.service" (dict "appId" "APP_ID_A" "podAnnotations" .Values.podAnnotationsPub "namespace" .Release.Namespace) }}
---
{{- include "diagrid.dapr.service" (dict "appId" "APP_ID_B" "podAnnotations" .Values.podAnnotationsSub "namespace" .Release.Namespace) }}Replace APP_ID with the appropriate application ID. This ensures that Dapr can correctly resolve and communicate with the injected services.
When running Dapr in Kubernetes mode, you need to configure a secret store and explicitly reference it in your components. This is required for securely retrieving sensitive values like Redis passwords, API tokens, or connection strings from Kubernetes secrets.
This component tells Dapr to use Kubernetes as the secret store. Apply the following YAML in your application's namespace:
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: kubernetes-secret-store
namespace: d3e-sample
spec:
type: secretstores.kubernetes
version: v1In each Dapr component that needs to use secrets, add the auth.secretStore field pointing to the secret store defined above:
auth:
secretStore: kubernetes-secret-storeIf your Dapr enabled apps are using components that fetch secrets from non-default namespaces, please follow this guide here
Trust anchors are essential for verifying the authenticity of the Dapr control plane.
By default, this sidecar injector library does not require explicit trust anchor configuration when the Dapr control plane and the workload are in the same namespace. In this scenario, the sidecar injector automatically utilizes the default trust anchors for the control plane via the Kubernetes downward API.
However, manual configuration of trust anchors is necessary when the Dapr control plane operates in a different namespace than the workload.
In this situation, you must manually supply the trust anchors to the sidecar injector through the dapr.trustAnchors field in your values file or Helm command.
To retrieve the trust anchors from the Dapr control plane namespace within a Kubernetes cluster, run the following command:
kubectl get secret -n dapr-system dapr-trust-bundle -o jsonpath="{.data['ca\.crt']}" | base64 -d | tee /tmp/trust-anchors.crtIf the workload is in a different namespace than the Dapr control plane, you can pass the trust anchors to the Dapr sidecar injector by setting the dapr.trustAnchors field in the values.yaml file:
dapr:
trustAnchors: |
-----BEGIN CERTIFICATE-----
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA5+1q1Qy9X/PvO8Vc0P9M
...
-----END CERTIFICATE-----Alternatively, you can pass the trust anchors via the Helm install/upgrade set command. For example, if you saved the trust anchors to a file /tmp/trust-anchors.crt, you can pass it to the Dapr sidecar injector as follows:
# also showing passing the image tag, custom control plane namespace, and the trust anchors from a file
helm template --set dapr.controlPlaneNamespace=dapr-system-3 --set "dapr.image.tag=1.15.6-d3e.1" --set-file dapr.trustAnchors=/tmp/trust-anchors.crt -n dapr-system-3 deploy-sample D3E versions 1.14.5-d3e.1 and 1.15.6-d3e.1 introduce a new feature for managing service account tokens in the Dapr Sentry component:
global.rbac.sentry.serviceAccount.automount: Controls whether the service account token is automatically mounted.global.rbac.sentry.serviceAccount.create: Determines whether a service account is created (replaces the deprecatedcreateServiceAccountfield).
When global.rbac.sentry.serviceAccount.automount is set to false:
- A Kubernetes ServiceAccount (KSA) is created with
automountServiceAccountToken=false. - A corresponding secret is created with the default name
dapr-sentry-token. - You can override the service account name using
global.rbac.sentry.serviceAccount.name.
To enable Kubernetes API access for Sentry, include the following volume mounts in your values.yaml:
extraVolumeMounts:
sentry:
- name: kube-api-access
mountPath: /var/run/secrets/kubernetes.io/serviceaccount
readOnly: true
extraVolumes:
sentry:
- name: kube-api-access
secret:
secretName: dapr-sentry-tokenAn example configuration for a standalone D3E deployment with automount disabled is available at:
For complex D3E deployments, this project includes configuration templates in the d3e-configs/ directory:
minimal-with-crds.yaml: Basic deployment with CRDs and cluster-wide RBACstandalone-no-crds.yaml: Standalone mode without CRDs (namespaced RBAC only)standalone-no-crds-automount-sentry-disabled.yaml: Standalone mode without CRDs and with Sentry automount disabledd3e-with-crds-no-cluster-roles.yaml: Hybrid approach with CRDs but namespaced RBAC
These templates help simplify the complex Helm values required for different deployment scenarios. See d3e-configs/README.md for detailed usage instructions and configuration comparisons.
For issues, feature requests, or questions, please file an issue in the GitHub repository.
By using D3E in your applications you are agreeing to comply with the Diagrid D3E Software License Agreement as described here.