Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
77 commits
Select commit Hold shift + click to select a range
ca0a1b1
skip none overrides on localdns profile
Sep 19, 2025
c044f0e
update history rst
Sep 19, 2025
19c6404
refactor to process dns overrides func
Sep 22, 2025
2778aba
move overrides function to helper file
Sep 22, 2025
6d0dd1e
apply linter suggestions
Sep 22, 2025
ffa5a65
Merge branch 'main' into juanbe/feature-localdns-none-input-handling
jdbencardinop Sep 23, 2025
f9a3328
add localdnsconfig folder
saewoni Sep 23, 2025
eb1363b
add more tests
saewoni Sep 23, 2025
0fd5c83
add new json files
saewoni Sep 24, 2025
450d1b8
add default dns overrides
saewoni Sep 24, 2025
e6474f3
add more test cases
saewoni Sep 24, 2025
f11d205
move tests around, move invalid cases to another file
saewoni Sep 25, 2025
3c6153b
add back import semver
saewoni Sep 25, 2025
8d63c84
reorder the existing tests
saewoni Sep 25, 2025
5a5e8fa
delete preferred mode only
saewoni Sep 26, 2025
a77e76e
delete null.json
saewoni Sep 26, 2025
68e89e7
remove redundant json file
saewoni Sep 26, 2025
240b83e
remove redundant json file
saewoni Sep 26, 2025
0ed5860
fix the mistake at line 3349
saewoni Sep 26, 2025
3f17065
forgot that i put all the configs in data/localconfig folder
saewoni Sep 26, 2025
b43f7ad
remove unused file
saewoni Sep 26, 2025
8ac70f8
spelling error
saewoni Sep 26, 2025
8ce451e
fix default dnsOverrides check when we create agentpool with required…
saewoni Sep 29, 2025
39e0ead
restore localdnsconfig file
saewoni Sep 29, 2025
14d70aa
delete extra property case from invalid test file
saewoni Sep 29, 2025
d73d85e
add extra property cases in src/aks-preview/azext_aks_preview/tests/l…
saewoni Sep 29, 2025
9ff61c9
add extra property files
saewoni Sep 29, 2025
734ad4c
check for defaulted *dnsOverrides when making agent pool with mode: r…
saewoni Sep 29, 2025
d2e900f
Merge remote-tracking branch 'origin' into sakwa/feature-localdns-non…
saewoni Sep 29, 2025
0734db0
comment out cleanup in test_aks_nodepool_add_with_localdns_required_mode
saewoni Sep 29, 2025
1786254
add more logging for debugging
saewoni Sep 29, 2025
b747438
add print statements in src/aks-preview/azext_aks_preview/vendored_sd…
saewoni Sep 30, 2025
6a57dc3
only initialize the dictionaries if dnsoverrides are provided
saewoni Sep 30, 2025
7432a92
process dns overrides only when dns overrides are provided
saewoni Sep 30, 2025
45fb82f
consolidate duplicated build_localdns_profile function
saewoni Sep 30, 2025
7753f07
move invalid cases to line 4133
saewoni Sep 30, 2025
f08686b
update test_aks_commands.py
saewoni Oct 1, 2025
54c428d
look for vnetDnsOverrides and kubeDNSOverrides keys, case-insensitive
saewoni Oct 1, 2025
00b2fbd
fix test_aks_nodepool_add_with_localdns_required_mode_single_vnetdns
saewoni Oct 1, 2025
7f6a6e6
check for dictionary for build_override
saewoni Oct 1, 2025
61bc4d6
update failing test cases
saewoni Oct 1, 2025
af0aa93
rename from required_mode_extra_property.json -> required_mode_kubedn…
saewoni Oct 1, 2025
e121b3a
fix azdev style
saewoni Oct 1, 2025
794fc05
temporarily add self.fail statements s.t. i can see the error_message
saewoni Oct 1, 2025
8f3e3d2
change from assertTrue to assertIn with more specific error msg, dele…
saewoni Oct 2, 2025
c526128
change from print to debug
saewoni Oct 2, 2025
0504217
remove logger.debug line to print localdnsprofile
saewoni Oct 2, 2025
0af69ba
Merge remote-tracking branch 'origin' into sakwa/feature-localdns-non…
saewoni Oct 2, 2025
8f81a8f
add null config file
saewoni Oct 2, 2025
e1895b4
fix the tests
saewoni Oct 2, 2025
12e0f94
fix the tests
saewoni Oct 2, 2025
c53d6fd
update src/aks-preview/HISTORY.rst with a new note under 18.0.0b42
saewoni Oct 2, 2025
661a342
update src/aks-preview/HISTORY.rst
saewoni Oct 2, 2025
417cf30
Revert "add print statements in src/aks-preview/azext_aks_preview/ven…
saewoni Oct 2, 2025
4b66d2d
Merge branch 'main' into sakwa/feature-localdns-none-input-handling
saewoni Oct 3, 2025
28d0caf
update src/aks-preview/HISTORY.rst
saewoni Oct 3, 2025
965f69b
Revert "add more logging for debugging"
saewoni Oct 3, 2025
dac66cc
mix the casing for *dnsoverrides
saewoni Oct 3, 2025
a7afe9a
throw an exception from cli if the values of kubednsoverrides or vnet…
saewoni Oct 3, 2025
f03ba28
add tests for null and non-dict overrides
saewoni Oct 3, 2025
68d4a41
make the keys of localdnsprofile mixed-case
saewoni Oct 3, 2025
64c7b27
add required_mode_null_dnsOverrides.json and required_mode_number_dns…
saewoni Oct 3, 2025
1e4966c
correct the error message I'm looking for, for non-dict dns overrides
saewoni Oct 3, 2025
33cc65a
remove print stmt from src/aks-preview/azext_aks_preview/_helpers.py
saewoni Oct 3, 2025
c86acb5
add check for DNS override settings
saewoni Oct 4, 2025
4b00a09
update the test with dns override settings check
saewoni Oct 4, 2025
b2f8721
update assertIn msg for test_aks_nodepool_add_with_localdns_required_…
saewoni Oct 4, 2025
59a78ae
break down InvalidArgumentValueError msg into two lines
saewoni Oct 4, 2025
b2dac0c
update existing cassette files
saewoni Oct 5, 2025
55f4c50
new cassette files for new tests
saewoni Oct 5, 2025
0a3bfc5
add three additional cassette files I did not commit before
saewoni Oct 7, 2025
101f367
expect InvalidArgumentValueError when None is provided for DNS overrides
saewoni Oct 7, 2025
a2ae22c
update AKSPreviewAgentPoolUpdateDecoratorCommonTestCase.common_update…
saewoni Oct 7, 2025
9a3023d
revert the import statement for from azure.cli.command_modules.acs.te…
saewoni Oct 7, 2025
2c347c3
Add a new line
jdbencardinop Oct 7, 2025
3c32af3
Revert "Add a new line"
saewoni Oct 7, 2025
2a85b4d
update version in src/aks-preview/setup.py to align with azure-cli-ex…
saewoni Oct 8, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions src/aks-preview/HISTORY.rst
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,12 @@ To release a new version, please select a new version number (usually plus 1 to
Pending
+++++++

18.0.0b43
+++++++
* Fix `--localdns-config` parameter to handle null values and case-insensitive JSON keys in DNS override sections, preventing crashes with malformed localdns configuration files.
* Enhance `build_override` function to validate dictionary types and only initialize DNS overrides when present in localdns configuration (case-insensitive).
* Refactor `build_localdns_profile` function to eliminate code duplication between AgentPool add and update operations.

18.0.0b42
+++++++
* Fix role assignment failure when using azure-cli version >= `2.77.0`.
Expand Down
4 changes: 4 additions & 0 deletions src/aks-preview/azext_aks_preview/_helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -460,6 +460,10 @@ def process_dns_overrides(overrides_dict, target_dict, build_override_func):
:param target_dict: Target dictionary to populate with processed overrides
:param build_override_func: Function to build override objects from dict values
"""
if not isinstance(overrides_dict, dict):
raise InvalidArgumentValueError(
f"Expected a dictionary for DNS overrides, but got {type(overrides_dict).__name__}: {overrides_dict}"
)
if overrides_dict is not None:
for key, value in overrides_dict.items():
if value is not None:
Expand Down
160 changes: 74 additions & 86 deletions src/aks-preview/azext_aks_preview/agentpool_decorator.py
Original file line number Diff line number Diff line change
Expand Up @@ -940,6 +940,78 @@ def get_localdns_profile(self):
return profile
return None

def build_localdns_profile(self, agentpool: AgentPool) -> AgentPool:
"""Build local DNS profile for the AgentPool object if provided via --localdns-config."""
localdns_profile = self.get_localdns_profile()
kube_dns_overrides, vnet_dns_overrides = None, None

if localdns_profile is not None:
def find_keys_case_insensitive(dictionary, target_keys):
"""Find multiple keys case-insensitively and return a dict mapping target_key -> actual_key"""
result = {}
lowered_keys = {key.lower(): key for key in dictionary.keys()}
for target_key in target_keys:
lowered_target = target_key.lower()
if lowered_target in lowered_keys:
result[target_key] = lowered_keys[lowered_target]
else:
result[target_key] = None
return result

def build_override(override_dict):
if not isinstance(override_dict, dict):
raise InvalidArgumentValueError(
f"Expected a dictionary for DNS override settings,"
f" but got {type(override_dict).__name__}: {override_dict}"
)
camel_to_snake_case = {
"queryLogging": "query_logging",
"protocol": "protocol",
"forwardDestination": "forward_destination",
"forwardPolicy": "forward_policy",
"maxConcurrent": "max_concurrent",
"cacheDurationInSeconds": "cache_duration_in_seconds",
"serveStaleDurationInSeconds": "serve_stale_duration_in_seconds",
"serveStale": "serve_stale",
}
valid_keys = set(camel_to_snake_case.values())
filtered = {}
for k, v in override_dict.items():
if k in camel_to_snake_case:
filtered[camel_to_snake_case[k]] = v
elif k in valid_keys:
filtered[k] = v
return self.models.LocalDNSOverride(**filtered)

# Build kubeDNSOverrides and vnetDNSOverrides from the localdns_profile
key_mappings = find_keys_case_insensitive(localdns_profile, ["kubeDNSOverrides", "vnetDNSOverrides"])
actual_kube_key = key_mappings["kubeDNSOverrides"]
if actual_kube_key:
logger.debug("Found kubeDNSOverrides key as: %s", actual_kube_key)
kube_dns_overrides = {}
process_dns_overrides(
localdns_profile.get(actual_kube_key),
kube_dns_overrides,
build_override
)

actual_vnet_key = key_mappings["vnetDNSOverrides"]
if actual_vnet_key:
logger.debug("Found vnetDNSOverrides key as: %s", actual_vnet_key)
vnet_dns_overrides = {}
process_dns_overrides(
localdns_profile.get(actual_vnet_key),
vnet_dns_overrides,
build_override
)

agentpool.local_dns_profile = self.models.LocalDNSProfile(
mode=localdns_profile.get("mode"),
kube_dns_overrides=kube_dns_overrides,
vnet_dns_overrides=vnet_dns_overrides,
)
return agentpool

def get_node_count_and_enable_cluster_autoscaler_min_max_count_vms(
self,
) -> Tuple[int, bool, Union[int, None], Union[int, None]]:
Expand Down Expand Up @@ -1452,49 +1524,7 @@ def set_up_managed_system_mode(self, agentpool: AgentPool) -> AgentPool:
def set_up_localdns_profile(self, agentpool: AgentPool) -> AgentPool:
"""Set up local DNS profile for the AgentPool object if provided via --localdns-config."""
self._ensure_agentpool(agentpool)
localdns_profile = self.context.get_localdns_profile()
if localdns_profile is not None:
kube_dns_overrides = {}
vnet_dns_overrides = {}

def build_override(override_dict):
camel_to_snake_case = {
"queryLogging": "query_logging",
"protocol": "protocol",
"forwardDestination": "forward_destination",
"forwardPolicy": "forward_policy",
"maxConcurrent": "max_concurrent",
"cacheDurationInSeconds": "cache_duration_in_seconds",
"serveStaleDurationInSeconds": "serve_stale_duration_in_seconds",
"serveStale": "serve_stale",
}
valid_keys = set(camel_to_snake_case.values())
filtered = {}
for k, v in override_dict.items():
if k in camel_to_snake_case:
filtered[camel_to_snake_case[k]] = v
elif k in valid_keys:
filtered[k] = v
return self.models.LocalDNSOverride(**filtered)

# Build kubeDNSOverrides and vnetDNSOverrides from the localdns_profile
process_dns_overrides(
localdns_profile.get("kubeDNSOverrides"),
kube_dns_overrides,
build_override
)
process_dns_overrides(
localdns_profile.get("vnetDNSOverrides"),
vnet_dns_overrides,
build_override
)

agentpool.local_dns_profile = self.models.LocalDNSProfile(
mode=localdns_profile.get("mode"),
kube_dns_overrides=kube_dns_overrides,
vnet_dns_overrides=vnet_dns_overrides,
)
return agentpool
return self.context.build_localdns_profile(agentpool)

def construct_agentpool_profile_preview(self) -> AgentPool:
"""The overall controller used to construct the preview AgentPool profile.
Expand Down Expand Up @@ -1794,49 +1824,7 @@ def update_fips_image(self, agentpool: AgentPool) -> AgentPool:
def update_localdns_profile(self, agentpool: AgentPool) -> AgentPool:
"""Update local DNS profile for the AgentPool object if provided via --localdns-config."""
self._ensure_agentpool(agentpool)
localdns_profile = self.context.get_localdns_profile()
if localdns_profile is not None:
kube_dns_overrides = {}
vnet_dns_overrides = {}

def build_override(override_dict):
camel_to_snake_case = {
"queryLogging": "query_logging",
"protocol": "protocol",
"forwardDestination": "forward_destination",
"forwardPolicy": "forward_policy",
"maxConcurrent": "max_concurrent",
"cacheDurationInSeconds": "cache_duration_in_seconds",
"serveStaleDurationInSeconds": "serve_stale_duration_in_seconds",
"serveStale": "serve_stale",
}
valid_keys = set(camel_to_snake_case.values())
filtered = {}
for k, v in override_dict.items():
if k in camel_to_snake_case:
filtered[camel_to_snake_case[k]] = v
elif k in valid_keys:
filtered[k] = v
return self.models.LocalDNSOverride(**filtered)

# Build kubeDNSOverrides and vnetDNSOverrides from the localdns_profile
process_dns_overrides(
localdns_profile.get("kubeDNSOverrides"),
kube_dns_overrides,
build_override
)
process_dns_overrides(
localdns_profile.get("vnetDNSOverrides"),
vnet_dns_overrides,
build_override
)

agentpool.local_dns_profile = self.models.LocalDNSProfile(
mode=localdns_profile.get("mode"),
kube_dns_overrides=kube_dns_overrides,
vnet_dns_overrides=vnet_dns_overrides,
)
return agentpool
return self.context.build_localdns_profile(agentpool)

def update_upgrade_strategy(self, agentpool: AgentPool) -> AgentPool:
"""Update upgrade strategy for the AgentPool object.
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"mode": "Disabled"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{}
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"mode": ""
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"mode": "InvalidMode"
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"mode": "Required",
"kubeDNSOverrides": {
"kubednsoverrides": {
".": {
"cacheDurationInSeconds": 3600,
"forwardDestination": "ClusterCoreDNS",
Expand All @@ -22,7 +22,7 @@
"serveStaleDurationInSeconds": 3600
}
},
"vnetDNSOverrides": {
"VNETDNSOVERRIDES": {
".": {
"cacheDurationInSeconds": 3600,
"forwardDestination": "VnetDNS",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
{
"mode": "Required",
"extraProperty": "unexpected",
"kubeDNSOverrides": {
".": {
"cacheDurationInSeconds": 3600,
"forwardDestination": "ClusterCoreDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "PreferUDP",
"queryLogging": "Error",
"serveStale": "Verify",
"serveStaleDurationInSeconds": 3600
},
"cluster.local": {
"cacheDurationInSeconds": 3600,
"forwardDestination": "ClusterCoreDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "ForceTCP",
"queryLogging": "Error",
"serveStale": "Immediate",
"serveStaleDurationInSeconds": 3600
}
},
"vnetDNSOverrides": {
".": {
"cacheDurationInSeconds": 3600,
"forwardDestination": "VnetDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "PreferUDP",
"queryLogging": "Error",
"serveStale": "Verify",
"serveStaleDurationInSeconds": 3600
},
"cluster.local": {
"cacheDurationInSeconds": 3600,
"forwardDestination": "ClusterCoreDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "ForceTCP",
"queryLogging": "Error",
"serveStale": "Immediate",
"serveStaleDurationInSeconds": 3600
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
{
"mode": "Required",
"extraProperty": "unexpected",
"kubeDNSOverrides": {
".": {
"extraProperty": "unexpected",
"cacheDurationInSeconds": 3600,
"forwardDestination": "ClusterCoreDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "PreferUDP",
"queryLogging": "Error",
"serveStale": "Verify",
"serveStaleDurationInSeconds": 3600
},
"cluster.local": {
"extraProperty": "unexpected",
"cacheDurationInSeconds": 3600,
"forwardDestination": "ClusterCoreDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "ForceTCP",
"queryLogging": "Error",
"serveStale": "Immediate",
"serveStaleDurationInSeconds": 3600
}
},
"vnetDNSOverrides": {
".": {
"extraProperty": "unexpected",
"cacheDurationInSeconds": 3600,
"forwardDestination": "VnetDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "PreferUDP",
"queryLogging": "Error",
"serveStale": "Verify",
"serveStaleDurationInSeconds": 3600
},
"cluster.local": {
"extraProperty": "unexpected",
"cacheDurationInSeconds": 3600,
"forwardDestination": "ClusterCoreDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "ForceTCP",
"queryLogging": "Error",
"serveStale": "Immediate",
"serveStaleDurationInSeconds": 3600
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
{
"kubeDnsOverrides": {
".": {
"cacheDurationInSeconds": 3600,
"forwardDestination": "ClusterCoreDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "PreferUDP",
"queryLogging": "Error",
"serveStale": "Verify",
"serveStaleDurationInSeconds": 3600
}
},
"vnetDnsOverrides": {
".": {
"cacheDurationInSeconds": 3600,
"forwardDestination": "VnetDNS",
"forwardPolicy": "Sequential",
"maxConcurrent": 1000,
"protocol": "PreferUDP",
"queryLogging": "Error",
"serveStale": "Verify",
"serveStaleDurationInSeconds": 3600
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
null
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"mode": null
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
{
"mode": "Required",
"kubeDnsOverrides": {},
"vnetDnsOverrides": {}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"mode": "Required",
"kubeDnsOverrides": {
".": {
"invalidField": 123
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"mode": "Required",
"vnetDnsOverrides": {
".": {
"invalidField": 456
}
}
}
Loading
Loading