{{/*
Expand the name of the chart.
*/}}
{{- define "bp-openclaw.name" -}}
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }}
{{- end }}

{{/*
Create a default fully qualified app name.
*/}}
{{- define "bp-openclaw.fullname" -}}
{{- if .Values.fullnameOverride }}
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- $name := default .Chart.Name .Values.nameOverride }}
{{- if contains $name .Release.Name }}
{{- .Release.Name | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" }}
{{- end }}
{{- end }}
{{- end }}

{{/*
Common labels — required by docs/BLUEPRINT-AUTHORING.md §14 and by the
Catalyst projector to track resources back to the Blueprint.
*/}}
{{- define "bp-openclaw.labels" -}}
helm.sh/chart: {{ printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
app.kubernetes.io/name: {{ include "bp-openclaw.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- if .Chart.AppVersion }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
{{- end }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
catalyst.openova.io/blueprint: bp-openclaw
{{- end }}

{{/*
Selector labels.
*/}}
{{- define "bp-openclaw.selectorLabels" -}}
app.kubernetes.io/name: {{ include "bp-openclaw.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- end }}

{{/*
ServiceAccount name.
*/}}
{{- define "bp-openclaw.serviceAccountName" -}}
{{- if .Values.serviceAccount.create }}
{{- default (include "bp-openclaw.fullname" .) .Values.serviceAccount.name }}
{{- else }}
{{- default "default" .Values.serviceAccount.name }}
{{- end }}
{{- end }}

{{/*
ConfigMap name (per-user pod template).
*/}}
{{- define "bp-openclaw.podTemplateConfigMapName" -}}
{{- printf "%s-pod-template" (include "bp-openclaw.fullname" .) | trunc 63 | trimSuffix "-" }}
{{- end }}

{{/*
Tenant namespace — falls back to .Release.Namespace if tenant.namespace
is unset, but we prefer an explicit value so the controller's RBAC scope
matches the operator's intent.
*/}}
{{- define "bp-openclaw.tenantNamespace" -}}
{{- default .Release.Namespace .Values.tenant.namespace }}
{{- end }}

{{/*
─── OIDC + LLM resolution helpers (umbrella #915) ─────────────────────

The chart's canonical config blocks are `oidc.*` and `llm.*`; legacy
overlays may still set `keycloak.*` / `newapi.*`. Helpers prefer the
canonical value and fall back to the legacy alias when unset.
*/}}
{{/*
Resolution rule: when an overlay sets a legacy key (`keycloak.*` /
`newapi.*`) AND leaves the canonical block at its placeholder default,
the legacy key wins (back-compat). When the canonical block is
explicitly set to a non-placeholder value, it always wins.
*/}}
{{- define "bp-openclaw.oidc.issuerURL" -}}
{{- $oidc := .Values.oidc.issuerURL | default "" -}}
{{- $legacy := .Values.keycloak.realmURL | default "" -}}
{{- if and $legacy (or (eq $oidc "") (eq $oidc "https://keycloak.example.local/realms/example")) -}}
{{- $legacy -}}
{{- else if $oidc -}}
{{- $oidc -}}
{{- else -}}
{{- "https://keycloak.example.local/realms/example" -}}
{{- end -}}
{{- end }}

{{- define "bp-openclaw.oidc.clientId" -}}
{{- $oidc := .Values.oidc.clientId | default "" -}}
{{- $legacy := .Values.keycloak.clientID | default "" -}}
{{- if and $legacy (or (eq $oidc "") (eq $oidc "openclaw")) -}}
{{- $legacy -}}
{{- else if $oidc -}}
{{- $oidc -}}
{{- else -}}
{{- "openclaw" -}}
{{- end -}}
{{- end }}

{{- define "bp-openclaw.oidc.clientSecretName" -}}
{{- $oidc := "" -}}
{{- if .Values.oidc.clientSecret -}}
{{- $oidc = .Values.oidc.clientSecret.name | default "" -}}
{{- end -}}
{{- $legacy := .Values.keycloak.clientSecretName | default "" -}}
{{- if and $legacy (or (eq $oidc "") (eq $oidc "openclaw-oidc")) -}}
{{- $legacy -}}
{{- else if $oidc -}}
{{- $oidc -}}
{{- else -}}
{{- "openclaw-oidc" -}}
{{- end -}}
{{- end }}

{{- define "bp-openclaw.oidc.clientSecretKey" -}}
{{- if and .Values.oidc.clientSecret .Values.oidc.clientSecret.key -}}
{{- .Values.oidc.clientSecret.key -}}
{{- else -}}
{{- "OIDC_CLIENT_SECRET" -}}
{{- end -}}
{{- end }}

{{- define "bp-openclaw.llm.baseURL" -}}
{{- $llm := .Values.llm.baseURL | default "" -}}
{{- $legacy := .Values.newapi.baseURL | default "" -}}
{{- if and $legacy (or (eq $llm "") (eq $llm "https://newapi.example.local/v1")) -}}
{{- $legacy -}}
{{- else if $llm -}}
{{- $llm -}}
{{- else -}}
{{- "https://newapi.example.local/v1" -}}
{{- end -}}
{{- end }}

{{- define "bp-openclaw.llm.apiKeySecretName" -}}
{{- if and .Values.llm.apiKey .Values.llm.apiKey.name -}}
{{- .Values.llm.apiKey.name -}}
{{- else -}}
{{- "openclaw-llm-apikey" -}}
{{- end -}}
{{- end }}

{{- define "bp-openclaw.llm.apiKeySecretKey" -}}
{{- if and .Values.llm.apiKey .Values.llm.apiKey.key -}}
{{- .Values.llm.apiKey.key -}}
{{- else -}}
{{- "NEWAPI_KEY" -}}
{{- end -}}
{{- end }}

{{- define "bp-openclaw.llm.defaultModel" -}}
{{- default "qwen3.6" .Values.llm.defaultModel -}}
{{- end }}

{{/*
Placeholder-rejection assertions. The chart ships placeholder defaults
(see values.yaml) so `helm template` smoke-renders cleanly in CI
(mirroring bp-self-sovereign-cutover's pattern); these assertions fail
loudly only when the placeholder is left in *and* the chart is being
installed for real (detected by the `bp-openclaw.assertNoPlaceholders`
flag in values, which Flux overlays set to `true` after they've
provided real values). The smoke-render path leaves the flag at its
default `false` so CI passes.

Operators MUST set every value in the "Required at install time" block
of values.yaml; the deploy-time validation hook in
catalyst-platform's reconciler also checks these against the rendered
HelmRelease.
*/}}
{{- define "bp-openclaw.assertNoPlaceholders" -}}
{{- if .Values.assertNoPlaceholders }}
{{- if eq .Values.controller.image.tag "0.1.0-placeholder" }}
{{- fail "controller.image.tag is still the placeholder — overlay must supply a SHA-pinned tag (Inviolable Principle 4)" }}
{{- end }}
{{- if eq .Values.perUserPod.image.tag "0.1.0-placeholder" }}
{{- fail "perUserPod.image.tag is still the placeholder — overlay must supply a SHA-pinned tag (Inviolable Principle 4)" }}
{{- end }}
{{- if eq (include "bp-openclaw.oidc.issuerURL" .) "https://keycloak.example.local/realms/example" }}
{{- fail "oidc.issuerURL is still the placeholder — overlay must supply the per-tenant Keycloak realm URL" }}
{{- end }}
{{- if eq (include "bp-openclaw.llm.baseURL" .) "https://newapi.example.local/v1" }}
{{- fail "llm.baseURL is still the placeholder — overlay must supply the per-tenant NewAPI OpenAI-compatible endpoint" }}
{{- end }}
{{- if eq .Values.tenant.namespace "sme-example" }}
{{- fail "tenant.namespace is still the placeholder — overlay must supply the SME tenant namespace" }}
{{- end }}
{{- if eq .Values.ingress.host "openclaw.example.local" }}
{{- fail "ingress.host is still the placeholder — overlay must supply the controller public hostname" }}
{{- end }}
{{- end }}
{{- end }}
