From 0c5399066ffb8b326a39bbb747a08eea7f1141ad Mon Sep 17 00:00:00 2001 From: Michael Nelson Date: Wed, 11 Jan 2023 18:38:45 +1100 Subject: [PATCH 1/4] Default to a custom default values if exactly one provided. Signed-off-by: Michael Nelson --- .../DeploymentForm/DeploymentForm.test.tsx | 51 +++++++++++++-- .../DeploymentForm/DeploymentForm.tsx | 21 ++++-- .../simplechart-customvalues/.helmignore | 26 ++++++++ .../simplechart-customvalues/Chart.yaml | 9 +++ .../templates/_helpers.tpl | 65 +++++++++++++++++++ .../templates/deployment.yaml | 40 ++++++++++++ .../templates/service.yaml | 18 +++++ .../templates/tests/test-connection.yaml | 14 ++++ .../values-custom.yaml | 7 ++ .../simplechart-customvalues/values.yaml | 19 ++++++ script/chart-museum.sh | 2 +- 11 files changed, 260 insertions(+), 12 deletions(-) create mode 100644 integration/charts/simplechart-customvalues/.helmignore create mode 100644 integration/charts/simplechart-customvalues/Chart.yaml create mode 100644 integration/charts/simplechart-customvalues/templates/_helpers.tpl create mode 100644 integration/charts/simplechart-customvalues/templates/deployment.yaml create mode 100644 integration/charts/simplechart-customvalues/templates/service.yaml create mode 100644 integration/charts/simplechart-customvalues/templates/tests/test-connection.yaml create mode 100644 integration/charts/simplechart-customvalues/values-custom.yaml create mode 100644 integration/charts/simplechart-customvalues/values.yaml diff --git a/dashboard/src/components/DeploymentForm/DeploymentForm.test.tsx b/dashboard/src/components/DeploymentForm/DeploymentForm.test.tsx index ec0c82294e4..0aefa937745 100644 --- a/dashboard/src/components/DeploymentForm/DeploymentForm.test.tsx +++ b/dashboard/src/components/DeploymentForm/DeploymentForm.test.tsx @@ -21,7 +21,7 @@ import * as ReactRouter from "react-router"; import { MemoryRouter, Route, Router } from "react-router-dom"; import { Kube } from "shared/Kube"; import { getStore, mountWrapper } from "shared/specs/mountWrapper"; -import { FetchError, IStoreState, PluginNames } from "shared/types"; +import { FetchError, IStoreState, IPackageState, PluginNames } from "shared/types"; import DeploymentForm from "./DeploymentForm"; import DeploymentFormBody from "./DeploymentFormBody"; @@ -44,9 +44,10 @@ const defaultSelectedPkg = { identifier: "test/test", plugin: { name: "my.plugin", version: "0.0.1" }, } as AvailablePackageReference, + defaultValues: "package: defaults", } as AvailablePackageDetail, pkgVersion: "1.2.4", - values: "bar: foo", + values: "not: used", }; const routePathParam = `/c/${defaultProps.cluster}/ns/${defaultProps.namespace}/apps/new/${defaultProps.plugin.name}/${defaultProps.plugin.version}/${defaultProps.packageCluster}/${defaultProps.packageNamespace}/${defaultProps.pkgName}/versions/${defaultProps.version}`; @@ -128,6 +129,46 @@ it("fetches the available versions", () => { ); }); +describe("default values", () => { + it("uses the available package detail default values", () => { + const wrapper = mountWrapper( + getStore({ packages: { selected: defaultSelectedPkg } } as IStoreState), + + + + + , + ); + + expect(wrapper.find(DeploymentFormBody).prop("appValues")).toBe("package: defaults"); + }); + + it("uses a custom default values file if there is only one", () => { + const wrapper = mountWrapper( + getStore({ + packages: { + selected: { + ...defaultSelectedPkg, + availablePackageDetail: { + ...defaultSelectedPkg.availablePackageDetail, + additionalDefaultValues: { + "values-custom": "custom: defaults", + }, + }, + }, + } as Partial, + } as Partial), + + + + + , + ); + + expect(wrapper.find(DeploymentFormBody).prop("appValues")).toBe("custom: defaults"); + }); +}); + describe("renders an error", () => { it("renders a custom error if the deployment failed", () => { const wrapper = mountWrapper( @@ -185,11 +226,11 @@ describe("renders an error", () => { .find(DeploymentFormBody) .prop("setValues"); act(() => { - handleValuesChange("foo: bar"); + handleValuesChange("changed: defaults"); }); wrapper.update(); - expect(wrapper.find(DeploymentFormBody).prop("appValues")).toBe("foo: bar"); + expect(wrapper.find(DeploymentFormBody).prop("appValues")).toBe("changed: defaults"); }); it("changes values if the version changes and it has not been modified", () => { @@ -201,7 +242,7 @@ describe("renders an error", () => { , ); - expect(wrapper.find(DeploymentFormBody).prop("appValues")).toBe("bar: foo"); + expect(wrapper.find(DeploymentFormBody).prop("appValues")).toBe("package: defaults"); }); it("display the service account selector", () => { diff --git a/dashboard/src/components/DeploymentForm/DeploymentForm.tsx b/dashboard/src/components/DeploymentForm/DeploymentForm.tsx index 0f325e6f2a1..1c493a16fea 100644 --- a/dashboard/src/components/DeploymentForm/DeploymentForm.tsx +++ b/dashboard/src/components/DeploymentForm/DeploymentForm.tsx @@ -14,6 +14,7 @@ import LoadingWrapper from "components/LoadingWrapper"; import PackageHeader from "components/PackageHeader/PackageHeader"; import { push } from "connected-react-router"; import { + AvailablePackageDetail, AvailablePackageReference, ReconciliationOptions, } from "gen/kubeappsapis/core/packages/v1alpha1/packages"; @@ -39,6 +40,14 @@ interface IRouteParams { packageVersion?: string; } +function defaultValues(pkg: AvailablePackageDetail) { + const additionalValues = Object.values(pkg.additionalDefaultValues || []); + if (additionalValues.length === 1) { + return additionalValues[0]; + } + return pkg.defaultValues || "" +} + export default function DeploymentForm() { const dispatch: ThunkDispatch = useDispatch(); const { @@ -58,7 +67,7 @@ export default function DeploymentForm() { const [isDeploying, setDeploying] = useState(false); const [releaseName, setReleaseName] = useState(""); - const [appValues, setAppValues] = useState(selectedPackage.values || ""); + const [appValues, setAppValues] = useState(defaultValues(selectedPackage.availablePackageDetail || {} as AvailablePackageDetail)); const [valuesModified, setValuesModified] = useState(false); const [serviceAccountList, setServiceAccountList] = useState([] as string[]); const [reconciliationOptions, setReconciliationOptions] = useState({} as ReconciliationOptions); @@ -94,7 +103,7 @@ export default function DeploymentForm() { ); // Populate the rest of packages versions dispatch(actions.availablepackages.fetchAvailablePackageVersions(packageReference)); - return () => {}; + return () => { }; }, [dispatch, packageReference, packageVersion]); useEffect(() => { @@ -107,15 +116,15 @@ export default function DeploymentForm() { dispatch(handleErrorAction(e)); }); } - return () => {}; + return () => { }; }, [dispatch, targetCluster, targetNamespace, pluginObj.name]); useEffect(() => { if (!valuesModified) { - setAppValues(selectedPackage.values || ""); + setAppValues(defaultValues(selectedPackage.availablePackageDetail || {} as AvailablePackageDetail)); } - return () => {}; - }, [selectedPackage.values, valuesModified]); + return () => { }; + }, [selectedPackage.availablePackageDetail?.defaultValues, valuesModified]); const handleValuesChange = (value: string) => { setAppValues(value); diff --git a/integration/charts/simplechart-customvalues/.helmignore b/integration/charts/simplechart-customvalues/.helmignore new file mode 100644 index 00000000000..c7bfa9cb0d5 --- /dev/null +++ b/integration/charts/simplechart-customvalues/.helmignore @@ -0,0 +1,26 @@ +# Copyright 2022 the Kubeapps contributors. +# SPDX-License-Identifier: Apache-2.0 + +# Patterns to ignore when building packages. +# This supports shell glob matching, relative path matching, and +# negation (prefixed with !). Only one pattern per line. +.DS_Store +# Common VCS dirs +.git/ +.gitignore +.bzr/ +.bzrignore +.hg/ +.hgignore +.svn/ +# Common backup files +*.swp +*.bak +*.tmp +*.orig +*~ +# Various IDEs +.project +.idea/ +*.tmproj +.vscode/ diff --git a/integration/charts/simplechart-customvalues/Chart.yaml b/integration/charts/simplechart-customvalues/Chart.yaml new file mode 100644 index 00000000000..7f89c8552a7 --- /dev/null +++ b/integration/charts/simplechart-customvalues/Chart.yaml @@ -0,0 +1,9 @@ +# Copyright 2022 the Kubeapps contributors. +# SPDX-License-Identifier: Apache-2.0 + +apiVersion: v2 +name: simplechart-customvalues +description: A simple chart for testing custom values +type: application +version: 0.1.0 +appVersion: "1.0.0" diff --git a/integration/charts/simplechart-customvalues/templates/_helpers.tpl b/integration/charts/simplechart-customvalues/templates/_helpers.tpl new file mode 100644 index 00000000000..5716d36c60f --- /dev/null +++ b/integration/charts/simplechart-customvalues/templates/_helpers.tpl @@ -0,0 +1,65 @@ +{{/* Copyright 2022 the Kubeapps contributors. */}} +{{/* SPDX-License-Identifier: Apache-2.0 */}} + +{{/* +Expand the name of the chart. +*/}} +{{- define "simplechart.name" -}} +{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }} +{{- end }} + +{{/* +Create a default fully qualified app name. +We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec). +If release name contains chart name it will be used as a full name. +*/}} +{{- define "simplechart.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 }} + +{{/* +Create chart name and version as used by the chart label. +*/}} +{{- define "simplechart.chart" -}} +{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }} +{{- end }} + +{{/* +Common labels +*/}} +{{- define "simplechart.labels" -}} +helm.sh/chart: {{ include "simplechart.chart" . }} +{{ include "simplechart.selectorLabels" . }} +{{- if .Chart.AppVersion }} +app.kubernetes.io/version: {{ .Chart.AppVersion | quote }} +{{- end }} +app.kubernetes.io/managed-by: {{ .Release.Service }} +{{- end }} + +{{/* +Selector labels +*/}} +{{- define "simplechart.selectorLabels" -}} +app.kubernetes.io/name: {{ include "simplechart.name" . }} +app.kubernetes.io/instance: {{ .Release.Name }} +{{- end }} + +{{/* +Create the name of the service account to use +*/}} +{{- define "simplechart.serviceAccountName" -}} +{{- if .Values.serviceAccount.create }} +{{- default (include "simplechart.fullname" .) .Values.serviceAccount.name }} +{{- else }} +{{- default "default" .Values.serviceAccount.name }} +{{- end }} +{{- end }} diff --git a/integration/charts/simplechart-customvalues/templates/deployment.yaml b/integration/charts/simplechart-customvalues/templates/deployment.yaml new file mode 100644 index 00000000000..bcf2b881c48 --- /dev/null +++ b/integration/charts/simplechart-customvalues/templates/deployment.yaml @@ -0,0 +1,40 @@ +# Copyright 2022 the Kubeapps contributors. +# SPDX-License-Identifier: Apache-2.0 + +apiVersion: apps/v1 +kind: Deployment +metadata: + name: {{ include "simplechart.fullname" . }} + labels: + {{- include "simplechart.labels" . | nindent 4 }} +spec: + replicas: 1 + selector: + matchLabels: + {{- include "simplechart.selectorLabels" . | nindent 6 }} + template: + metadata: + labels: + {{- include "simplechart.selectorLabels" . | nindent 8 }} + spec: + {{- with .Values.imagePullSecrets }} + imagePullSecrets: + {{- toYaml . | nindent 8 }} + {{- end }} + serviceAccountName: {{ include "simplechart.serviceAccountName" . }} + containers: + - name: {{ .Chart.Name }} + image: "{{ .Values.image.repository }}:{{ .Values.image.tag | default .Chart.AppVersion }}" + imagePullPolicy: {{ .Values.image.pullPolicy }} + ports: + - name: http + containerPort: 80 + protocol: TCP + livenessProbe: + httpGet: + path: / + port: http + readinessProbe: + httpGet: + path: / + port: http diff --git a/integration/charts/simplechart-customvalues/templates/service.yaml b/integration/charts/simplechart-customvalues/templates/service.yaml new file mode 100644 index 00000000000..1c52ad7c370 --- /dev/null +++ b/integration/charts/simplechart-customvalues/templates/service.yaml @@ -0,0 +1,18 @@ +# Copyright 2022 the Kubeapps contributors. +# SPDX-License-Identifier: Apache-2.0 + +apiVersion: v1 +kind: Service +metadata: + name: {{ include "simplechart.fullname" . }} + labels: + {{- include "simplechart.labels" . | nindent 4 }} +spec: + type: {{ .Values.service.type }} + ports: + - port: {{ .Values.service.port }} + targetPort: http + protocol: TCP + name: http + selector: + {{- include "simplechart.selectorLabels" . | nindent 4 }} diff --git a/integration/charts/simplechart-customvalues/templates/tests/test-connection.yaml b/integration/charts/simplechart-customvalues/templates/tests/test-connection.yaml new file mode 100644 index 00000000000..25ca2f6229d --- /dev/null +++ b/integration/charts/simplechart-customvalues/templates/tests/test-connection.yaml @@ -0,0 +1,14 @@ +# Copyright 2022 the Kubeapps contributors. +# SPDX-License-Identifier: Apache-2.0 + +apiVersion: v1 +kind: Pod +metadata: + name: "{{ include "simplechart.fullname" . }}-test-connection" +spec: + containers: + - name: wget + image: busybox + command: ['wget'] + args: ['{{ include "simplechart.fullname" . }}:{{ .Values.service.port }}'] + restartPolicy: Never diff --git a/integration/charts/simplechart-customvalues/values-custom.yaml b/integration/charts/simplechart-customvalues/values-custom.yaml new file mode 100644 index 00000000000..8d766b6b6f1 --- /dev/null +++ b/integration/charts/simplechart-customvalues/values-custom.yaml @@ -0,0 +1,7 @@ +# Copyright 2022 the Kubeapps contributors. +# SPDX-License-Identifier: Apache-2.0 + +image: + repository: bitnami/nginx + tag: "1.23.3-debian-11" + pullPolicy: IfNotPresent diff --git a/integration/charts/simplechart-customvalues/values.yaml b/integration/charts/simplechart-customvalues/values.yaml new file mode 100644 index 00000000000..110ed9fe9de --- /dev/null +++ b/integration/charts/simplechart-customvalues/values.yaml @@ -0,0 +1,19 @@ +# Copyright 2022 the Kubeapps contributors. +# SPDX-License-Identifier: Apache-2.0 + +image: + repository: bitnami/nginx + tag: "latest" + pullPolicy: IfNotPresent + +imagePullSecrets: [] +nameOverride: "" +fullnameOverride: "" + +serviceAccount: + create: false + name: "default" + +service: + type: ClusterIP + port: 80 diff --git a/script/chart-museum.sh b/script/chart-museum.sh index c2f66764334..6206b1bdc31 100755 --- a/script/chart-museum.sh +++ b/script/chart-museum.sh @@ -104,7 +104,7 @@ installChartMuseum() { --set persistence.enabled=true \ --set env.secret.BASIC_AUTH_USER=$CHARTMUSEUM_USER \ --set env.secret.BASIC_AUTH_PASS=$CHARTMUSEUM_PWD - info "Waiting for ChartMuseum to be ready..." + echo "Waiting for ChartMuseum to be ready..." kubectl rollout status -w deployment/chartmuseum --namespace="${CHARTMUSEUM_NS}" echo "Installing Ingress for ChartMuseum with access through host ${CHARTMUSEUM_HOSTNAME}" From 8482fc610380223772871d03a7bc8e86bdd6417c Mon Sep 17 00:00:00 2001 From: Michael Nelson Date: Wed, 11 Jan 2023 18:41:24 +1100 Subject: [PATCH 2/4] Prettier Signed-off-by: Michael Nelson --- .../components/DeploymentForm/DeploymentForm.tsx | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/dashboard/src/components/DeploymentForm/DeploymentForm.tsx b/dashboard/src/components/DeploymentForm/DeploymentForm.tsx index 1c493a16fea..73236a7c4cb 100644 --- a/dashboard/src/components/DeploymentForm/DeploymentForm.tsx +++ b/dashboard/src/components/DeploymentForm/DeploymentForm.tsx @@ -45,7 +45,7 @@ function defaultValues(pkg: AvailablePackageDetail) { if (additionalValues.length === 1) { return additionalValues[0]; } - return pkg.defaultValues || "" + return pkg.defaultValues || ""; } export default function DeploymentForm() { @@ -67,7 +67,9 @@ export default function DeploymentForm() { const [isDeploying, setDeploying] = useState(false); const [releaseName, setReleaseName] = useState(""); - const [appValues, setAppValues] = useState(defaultValues(selectedPackage.availablePackageDetail || {} as AvailablePackageDetail)); + const [appValues, setAppValues] = useState( + defaultValues(selectedPackage.availablePackageDetail || ({} as AvailablePackageDetail)), + ); const [valuesModified, setValuesModified] = useState(false); const [serviceAccountList, setServiceAccountList] = useState([] as string[]); const [reconciliationOptions, setReconciliationOptions] = useState({} as ReconciliationOptions); @@ -103,7 +105,7 @@ export default function DeploymentForm() { ); // Populate the rest of packages versions dispatch(actions.availablepackages.fetchAvailablePackageVersions(packageReference)); - return () => { }; + return () => {}; }, [dispatch, packageReference, packageVersion]); useEffect(() => { @@ -116,14 +118,16 @@ export default function DeploymentForm() { dispatch(handleErrorAction(e)); }); } - return () => { }; + return () => {}; }, [dispatch, targetCluster, targetNamespace, pluginObj.name]); useEffect(() => { if (!valuesModified) { - setAppValues(defaultValues(selectedPackage.availablePackageDetail || {} as AvailablePackageDetail)); + setAppValues( + defaultValues(selectedPackage.availablePackageDetail || ({} as AvailablePackageDetail)), + ); } - return () => { }; + return () => {}; }, [selectedPackage.availablePackageDetail?.defaultValues, valuesModified]); const handleValuesChange = (value: string) => { From 020b94d52d3b1afac7fb0fd35c5d542b585f4c00 Mon Sep 17 00:00:00 2001 From: Michael Nelson Date: Thu, 12 Jan 2023 12:41:05 +1100 Subject: [PATCH 3/4] Set default values in reducer first. Signed-off-by: Michael Nelson --- .../DeploymentForm/DeploymentForm.test.tsx | 31 +--------- .../DeploymentForm/DeploymentForm.tsx | 19 +----- .../src/reducers/availablepackages.test.ts | 58 ++++++++++++++++++- dashboard/src/reducers/availablepackages.ts | 13 ++++- 4 files changed, 75 insertions(+), 46 deletions(-) diff --git a/dashboard/src/components/DeploymentForm/DeploymentForm.test.tsx b/dashboard/src/components/DeploymentForm/DeploymentForm.test.tsx index 0aefa937745..88652a017d4 100644 --- a/dashboard/src/components/DeploymentForm/DeploymentForm.test.tsx +++ b/dashboard/src/components/DeploymentForm/DeploymentForm.test.tsx @@ -21,7 +21,7 @@ import * as ReactRouter from "react-router"; import { MemoryRouter, Route, Router } from "react-router-dom"; import { Kube } from "shared/Kube"; import { getStore, mountWrapper } from "shared/specs/mountWrapper"; -import { FetchError, IStoreState, IPackageState, PluginNames } from "shared/types"; +import { FetchError, IStoreState, PluginNames } from "shared/types"; import DeploymentForm from "./DeploymentForm"; import DeploymentFormBody from "./DeploymentFormBody"; @@ -47,7 +47,7 @@ const defaultSelectedPkg = { defaultValues: "package: defaults", } as AvailablePackageDetail, pkgVersion: "1.2.4", - values: "not: used", + values: "package: defaults", }; const routePathParam = `/c/${defaultProps.cluster}/ns/${defaultProps.namespace}/apps/new/${defaultProps.plugin.name}/${defaultProps.plugin.version}/${defaultProps.packageCluster}/${defaultProps.packageNamespace}/${defaultProps.pkgName}/versions/${defaultProps.version}`; @@ -130,7 +130,7 @@ it("fetches the available versions", () => { }); describe("default values", () => { - it("uses the available package detail default values", () => { + it("uses the selected package default values", () => { const wrapper = mountWrapper( getStore({ packages: { selected: defaultSelectedPkg } } as IStoreState), @@ -142,31 +142,6 @@ describe("default values", () => { expect(wrapper.find(DeploymentFormBody).prop("appValues")).toBe("package: defaults"); }); - - it("uses a custom default values file if there is only one", () => { - const wrapper = mountWrapper( - getStore({ - packages: { - selected: { - ...defaultSelectedPkg, - availablePackageDetail: { - ...defaultSelectedPkg.availablePackageDetail, - additionalDefaultValues: { - "values-custom": "custom: defaults", - }, - }, - }, - } as Partial, - } as Partial), - - - - - , - ); - - expect(wrapper.find(DeploymentFormBody).prop("appValues")).toBe("custom: defaults"); - }); }); describe("renders an error", () => { diff --git a/dashboard/src/components/DeploymentForm/DeploymentForm.tsx b/dashboard/src/components/DeploymentForm/DeploymentForm.tsx index 73236a7c4cb..0f325e6f2a1 100644 --- a/dashboard/src/components/DeploymentForm/DeploymentForm.tsx +++ b/dashboard/src/components/DeploymentForm/DeploymentForm.tsx @@ -14,7 +14,6 @@ import LoadingWrapper from "components/LoadingWrapper"; import PackageHeader from "components/PackageHeader/PackageHeader"; import { push } from "connected-react-router"; import { - AvailablePackageDetail, AvailablePackageReference, ReconciliationOptions, } from "gen/kubeappsapis/core/packages/v1alpha1/packages"; @@ -40,14 +39,6 @@ interface IRouteParams { packageVersion?: string; } -function defaultValues(pkg: AvailablePackageDetail) { - const additionalValues = Object.values(pkg.additionalDefaultValues || []); - if (additionalValues.length === 1) { - return additionalValues[0]; - } - return pkg.defaultValues || ""; -} - export default function DeploymentForm() { const dispatch: ThunkDispatch = useDispatch(); const { @@ -67,9 +58,7 @@ export default function DeploymentForm() { const [isDeploying, setDeploying] = useState(false); const [releaseName, setReleaseName] = useState(""); - const [appValues, setAppValues] = useState( - defaultValues(selectedPackage.availablePackageDetail || ({} as AvailablePackageDetail)), - ); + const [appValues, setAppValues] = useState(selectedPackage.values || ""); const [valuesModified, setValuesModified] = useState(false); const [serviceAccountList, setServiceAccountList] = useState([] as string[]); const [reconciliationOptions, setReconciliationOptions] = useState({} as ReconciliationOptions); @@ -123,12 +112,10 @@ export default function DeploymentForm() { useEffect(() => { if (!valuesModified) { - setAppValues( - defaultValues(selectedPackage.availablePackageDetail || ({} as AvailablePackageDetail)), - ); + setAppValues(selectedPackage.values || ""); } return () => {}; - }, [selectedPackage.availablePackageDetail?.defaultValues, valuesModified]); + }, [selectedPackage.values, valuesModified]); const handleValuesChange = (value: string) => { setAppValues(value); diff --git a/dashboard/src/reducers/availablepackages.test.ts b/dashboard/src/reducers/availablepackages.test.ts index aca02aee300..2ca8452c366 100644 --- a/dashboard/src/reducers/availablepackages.test.ts +++ b/dashboard/src/reducers/availablepackages.test.ts @@ -1,7 +1,11 @@ // Copyright 2021-2022 the Kubeapps contributors. // SPDX-License-Identifier: Apache-2.0 -import { AvailablePackageSummary, Context } from "gen/kubeappsapis/core/packages/v1alpha1/packages"; +import { + AvailablePackageDetail, + AvailablePackageSummary, + Context, +} from "gen/kubeappsapis/core/packages/v1alpha1/packages"; import { Plugin } from "gen/kubeappsapis/core/plugins/v1alpha1/plugins"; import { getType } from "typesafe-actions"; import actions from "../actions"; @@ -498,4 +502,56 @@ describe("packageReducer", () => { ...initialState, }); }); + + describe("receiveSelectedAvailablePackageDetail", () => { + const packageDetail = { + name: "test-package", + defaultValues: "default: values", + valuesSchema: "", + } as AvailablePackageDetail; + + it("uses the package default values by default", () => { + const state = packageReducer(initialState, { + type: getType(actions.availablepackages.receiveSelectedAvailablePackageDetail) as any, + payload: { + selectedPackage: packageDetail, + }, + }); + + expect(state.selected.values).toEqual("default: values"); + }); + + it("uses the package custom default values if only one custom default values", () => { + const state = packageReducer(initialState, { + type: getType(actions.availablepackages.receiveSelectedAvailablePackageDetail) as any, + payload: { + selectedPackage: { + ...packageDetail, + additionalDefaultValues: { + "values-custom": "custom: values", + }, + } as AvailablePackageDetail, + }, + }); + + expect(state.selected.values).toEqual("custom: values"); + }); + + it("uses the package default values if more than one custom default values present", () => { + const state = packageReducer(initialState, { + type: getType(actions.availablepackages.receiveSelectedAvailablePackageDetail) as any, + payload: { + selectedPackage: { + ...packageDetail, + additionalDefaultValues: { + "values-custom": "custom: values", + "values-other": "more: customdefaultvalues", + }, + } as AvailablePackageDetail, + }, + }); + + expect(state.selected.values).toEqual("default: values"); + }); + }); }); diff --git a/dashboard/src/reducers/availablepackages.ts b/dashboard/src/reducers/availablepackages.ts index a52fde2c549..9190f46822f 100644 --- a/dashboard/src/reducers/availablepackages.ts +++ b/dashboard/src/reducers/availablepackages.ts @@ -8,6 +8,7 @@ import { getType } from "typesafe-actions"; import actions from "../actions"; import { PackagesAction } from "../actions/availablepackages"; import { NamespaceAction } from "../actions/namespace"; +import { AvailablePackageDetail } from "gen/kubeappsapis/core/packages/v1alpha1/packages"; export const initialState: IPackageState = { isFetching: false, @@ -21,6 +22,16 @@ export const initialState: IPackageState = { size: 20, }; +// defaultValues determines whether the package defaults or custom default +// values should be used. +function defaultValues(pkg: AvailablePackageDetail) { + const additionalValues = Object.values(pkg.additionalDefaultValues || []); + if (additionalValues.length === 1) { + return additionalValues[0]; + } + return pkg.defaultValues || ""; +} + const selectedPackageReducer = ( state: IPackageState["selected"], action: PackagesAction | NamespaceAction, @@ -35,7 +46,7 @@ const selectedPackageReducer = ( pkgVersion: action.payload.selectedPackage.version?.pkgVersion, appVersion: action.payload.selectedPackage.version?.appVersion, readme: action.payload.selectedPackage.readme, - values: action.payload.selectedPackage.defaultValues, + values: defaultValues(action.payload.selectedPackage), schema: action.payload.selectedPackage.valuesSchema !== "" ? (JSON.parse(action.payload.selectedPackage.valuesSchema) as JSONSchemaType) From 30d1c1f77cede6289c7cea992154e64363919cdb Mon Sep 17 00:00:00 2001 From: Michael Nelson Date: Thu, 12 Jan 2023 13:20:52 +1100 Subject: [PATCH 4/4] Update yamllint ignore for new chart. Signed-off-by: Michael Nelson --- .yamllint.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.yamllint.yml b/.yamllint.yml index 5ca10bc5e12..634f5d505c1 100644 --- a/.yamllint.yml +++ b/.yamllint.yml @@ -7,6 +7,7 @@ ignore: | # Ignore folders **/chart/kubeapps/ **/integration/charts/simplechart/ + **/integration/charts/simplechart-customvalues/ **/dashboard/node_modules/ **/devel/ # Ignore files