diff --git a/pkg/aks/components/CruAks.vue b/pkg/aks/components/CruAks.vue index 45ca971d3a..9feb27e39b 100644 --- a/pkg/aks/components/CruAks.vue +++ b/pkg/aks/components/CruAks.vue @@ -37,7 +37,7 @@ import { } from '../util/aks'; import { parseTaint } from '../util/taints'; -import { diffUpstreamSpec } from '@shell/utils/kontainer'; +import { diffUpstreamSpec, syncUpstreamConfig } from '@shell/utils/kontainer'; import { requiredInCluster, clusterNameChars, @@ -144,6 +144,12 @@ export default defineComponent({ const liveNormanCluster = await this.value.findNormanCluster(); this.normanCluster = await store.dispatch(`rancher/clone`, { resource: liveNormanCluster }); + + // ensure any fields editable through this UI that have been altered in azure portal are shown here - see syncUpstreamConfig jsdoc for details + if (!this.isNewOrUnprovisioned) { + syncUpstreamConfig('aks', this.normanCluster); + } + // track original version on edit to ensure we don't offer k8s downgrades this.originalVersion = this.normanCluster?.aksConfig?.kubernetesVersion; } else { @@ -736,12 +742,14 @@ export default defineComponent({ } }, - setAuthorizedIpRanges(neu) { + setAuthorizedIPRanges(neu) { if (neu) { this.$set(this.config, 'privateCluster', false); delete this.config.managedIdentity; delete this.config.privateDnsZone; delete this.config.userAssignedIdentity; + } else { + this.$set(this.config, 'authorizedIpRanges', []); } }, diff --git a/shell/utils/kontainer.ts b/shell/utils/kontainer.ts index 10f2d5200d..1f81bacbc1 100644 --- a/shell/utils/kontainer.ts +++ b/shell/utils/kontainer.ts @@ -1,5 +1,28 @@ import { isArray } from '@shell/utils/array'; -import { set, get } from '@shell/utils/object'; +import { set, get, isEmpty } from '@shell/utils/object'; + +/** + * This function accepts a v3 cluster object and mutates its config field to sync values that were set outside Rancher (eg, when an imported cluster is created in its respective cloud provider). + * Values configured outside of rancher are not automatically propagated to the config field that the UI edits; they are reflected in the aksStatus/eksStatus/gkeStatus.upstreamSpec field. + * This function works in tandem with diffUpstreamSpec: the former runs when the edit form is initialized and the latter runs when the cluster is saved. + * @param configPrefix one of aks, eks, gke + * @param normanCluster v3 cluster object + */ +export function syncUpstreamConfig(configPrefix: string, normanCluster: {[key: string]: any}): void { + const configKey = `${ configPrefix }Config`; + const statusKey = `${ configPrefix }Status`; + + const rancherConfig = normanCluster[configKey] || {}; + const upstreamConfig = normanCluster?.[statusKey]?.upstreamSpec || {}; + + if (!isEmpty(upstreamConfig)) { + Object.keys(upstreamConfig).forEach((key) => { + if (isEmpty(rancherConfig[key]) && !isEmpty(upstreamConfig[key])) { + set(rancherConfig, key, upstreamConfig[key]); + } + }); + } +} /** * Hosted provider (aks gke eks) edit functionality differs from other k8s resources