Skip to content

Commit 58844de

Browse files
[App Service] az appservice list-locations: Add --managed-instance-enabled parameter for managed instances (#32444)
1 parent 7f1ccf6 commit 58844de

File tree

8 files changed

+2261
-6
lines changed

8 files changed

+2261
-6
lines changed

src/azure-cli/azure/cli/command_modules/appservice/_params.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,8 @@ def load_arguments(self, _):
102102
help='get regions which support hosting web apps on Windows Container workers')
103103
c.argument('linux_workers_enabled', action='store_true',
104104
help='get regions which support hosting web apps on Linux workers')
105+
c.argument('managed_instance_enabled', action='store_true', is_preview=True,
106+
help='get regions which support hosting web apps on Managed Instance workers')
105107
c.argument('sku', arg_type=sku_arg_type)
106108

107109
with self.argument_context('appservice plan') as c:

src/azure-cli/azure/cli/command_modules/appservice/aaz/latest/appservice/__init__.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,3 +9,4 @@
99
# flake8: noqa
1010

1111
from .__cmd_group import *
12+
from ._list_locations import *
Lines changed: 217 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,217 @@
1+
# --------------------------------------------------------------------------------------------
2+
# Copyright (c) Microsoft Corporation. All rights reserved.
3+
# Licensed under the MIT License. See License.txt in the project root for license information.
4+
#
5+
# Code generated by aaz-dev-tools
6+
# --------------------------------------------------------------------------------------------
7+
8+
# pylint: skip-file
9+
# flake8: noqa
10+
11+
from azure.cli.core.aaz import *
12+
13+
14+
class ListLocations(AAZCommand):
15+
"""List regions where a plan sku is available
16+
"""
17+
18+
_aaz_info = {
19+
"version": "2025-03-01",
20+
"resources": [
21+
["mgmt-plane", "/subscriptions/{}/providers/microsoft.web/georegions", "2025-03-01"],
22+
]
23+
}
24+
25+
AZ_SUPPORT_PAGINATION = True
26+
27+
def _handler(self, command_args):
28+
super()._handler(command_args)
29+
return self.build_paging(self._execute_operations, self._output)
30+
31+
_args_schema = None
32+
33+
@classmethod
34+
def _build_arguments_schema(cls, *args, **kwargs):
35+
if cls._args_schema is not None:
36+
return cls._args_schema
37+
cls._args_schema = super()._build_arguments_schema(*args, **kwargs)
38+
39+
# define Arg Group ""
40+
41+
_args_schema = cls._args_schema
42+
_args_schema.custom_mode_workers_enabled = AAZBoolArg(
43+
options=["--custom-mode-workers-enabled"],
44+
help="Specify true if you want to filter to only regions that support App Service Plans with IsCustomMode set to true.",
45+
)
46+
_args_schema.linux_dynamic_workers_enabled = AAZBoolArg(
47+
options=["--linux-dynamic-workers-enabled"],
48+
help="Specify true if you want to filter to only regions that support Linux Consumption Workers.",
49+
)
50+
_args_schema.linux_workers_enabled = AAZBoolArg(
51+
options=["--linux-workers-enabled"],
52+
help="Get regions which support hosting web apps on Linux workers.",
53+
)
54+
_args_schema.sku = AAZStrArg(
55+
options=["--sku"],
56+
help="Name of SKU used to filter the regions.",
57+
enum={"Basic": "Basic", "Dynamic": "Dynamic", "ElasticIsolated": "ElasticIsolated", "ElasticPremium": "ElasticPremium", "FlexConsumption": "FlexConsumption", "Free": "Free", "Isolated": "Isolated", "IsolatedV2": "IsolatedV2", "Premium": "Premium", "PremiumContainer": "PremiumContainer", "PremiumV2": "PremiumV2", "PremiumV3": "PremiumV3", "Shared": "Shared", "Standard": "Standard"},
58+
)
59+
_args_schema.hyperv_workers_enabled = AAZBoolArg(
60+
options=["--hyperv-workers-enabled"],
61+
help="Get regions which support hosting web apps on Windows Container workers.",
62+
)
63+
return cls._args_schema
64+
65+
def _execute_operations(self):
66+
self.pre_operations()
67+
self.ListGeoRegions(ctx=self.ctx)()
68+
self.post_operations()
69+
70+
@register_callback
71+
def pre_operations(self):
72+
pass
73+
74+
@register_callback
75+
def post_operations(self):
76+
pass
77+
78+
def _output(self, *args, **kwargs):
79+
result = self.deserialize_output(self.ctx.vars.instance.value, client_flatten=True)
80+
next_link = self.deserialize_output(self.ctx.vars.instance.next_link)
81+
return result, next_link
82+
83+
class ListGeoRegions(AAZHttpOperation):
84+
CLIENT_TYPE = "MgmtClient"
85+
86+
def __call__(self, *args, **kwargs):
87+
request = self.make_request()
88+
session = self.client.send_request(request=request, stream=False, **kwargs)
89+
if session.http_response.status_code in [200]:
90+
return self.on_200(session)
91+
92+
return self.on_error(session.http_response)
93+
94+
@property
95+
def url(self):
96+
return self.client.format_url(
97+
"/subscriptions/{subscriptionId}/providers/Microsoft.Web/geoRegions",
98+
**self.url_parameters
99+
)
100+
101+
@property
102+
def method(self):
103+
return "GET"
104+
105+
@property
106+
def error_format(self):
107+
return "ODataV4Format"
108+
109+
@property
110+
def url_parameters(self):
111+
parameters = {
112+
**self.serialize_url_param(
113+
"subscriptionId", self.ctx.subscription_id,
114+
required=True,
115+
),
116+
}
117+
return parameters
118+
119+
@property
120+
def query_parameters(self):
121+
parameters = {
122+
**self.serialize_query_param(
123+
"customModeWorkersEnabled", self.ctx.args.custom_mode_workers_enabled,
124+
),
125+
**self.serialize_query_param(
126+
"linuxDynamicWorkersEnabled", self.ctx.args.linux_dynamic_workers_enabled,
127+
),
128+
**self.serialize_query_param(
129+
"linuxWorkersEnabled", self.ctx.args.linux_workers_enabled,
130+
),
131+
**self.serialize_query_param(
132+
"sku", self.ctx.args.sku,
133+
),
134+
**self.serialize_query_param(
135+
"xenonWorkersEnabled", self.ctx.args.hyperv_workers_enabled,
136+
),
137+
**self.serialize_query_param(
138+
"api-version", "2025-03-01",
139+
required=True,
140+
),
141+
}
142+
return parameters
143+
144+
@property
145+
def header_parameters(self):
146+
parameters = {
147+
**self.serialize_header_param(
148+
"Accept", "application/json",
149+
),
150+
}
151+
return parameters
152+
153+
def on_200(self, session):
154+
data = self.deserialize_http_content(session)
155+
self.ctx.set_var(
156+
"instance",
157+
data,
158+
schema_builder=self._build_schema_on_200
159+
)
160+
161+
_schema_on_200 = None
162+
163+
@classmethod
164+
def _build_schema_on_200(cls):
165+
if cls._schema_on_200 is not None:
166+
return cls._schema_on_200
167+
168+
cls._schema_on_200 = AAZObjectType()
169+
170+
_schema_on_200 = cls._schema_on_200
171+
_schema_on_200.next_link = AAZStrType(
172+
serialized_name="nextLink",
173+
flags={"read_only": True},
174+
)
175+
_schema_on_200.value = AAZListType(
176+
flags={"required": True},
177+
)
178+
179+
value = cls._schema_on_200.value
180+
value.Element = AAZObjectType()
181+
182+
_element = cls._schema_on_200.value.Element
183+
_element.id = AAZStrType(
184+
flags={"read_only": True},
185+
)
186+
_element.kind = AAZStrType()
187+
_element.name = AAZStrType(
188+
flags={"read_only": True},
189+
)
190+
_element.properties = AAZObjectType(
191+
flags={"client_flatten": True},
192+
)
193+
_element.type = AAZStrType(
194+
flags={"read_only": True},
195+
)
196+
197+
properties = cls._schema_on_200.value.Element.properties
198+
properties.description = AAZStrType(
199+
flags={"read_only": True},
200+
)
201+
properties.display_name = AAZStrType(
202+
serialized_name="displayName",
203+
flags={"read_only": True},
204+
)
205+
properties.org_domain = AAZStrType(
206+
serialized_name="orgDomain",
207+
flags={"read_only": True},
208+
)
209+
210+
return cls._schema_on_200
211+
212+
213+
class _ListLocationsHelper:
214+
"""Helper class for ListLocations"""
215+
216+
217+
__all__ = ["ListLocations"]

src/azure-cli/azure/cli/command_modules/appservice/custom.py

Lines changed: 29 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,8 @@
7474
get_resource_if_exists, repo_url_to_name, get_token,
7575
app_service_plan_exists, is_centauri_functionapp, is_flex_functionapp,
7676
_remove_list_duplicates, get_raw_functionapp,
77-
register_app_provider)
77+
register_app_provider,
78+
is_sku_tier_enabled_for_managed_instance)
7879
from ._create_util import (zip_contents_from_dir, get_runtime_version_details, create_resource_group, get_app_details,
7980
check_resource_group_exists, set_location, get_site_availability,
8081
get_regional_site_availability, get_profile_username,
@@ -100,6 +101,7 @@
100101
from .aaz.latest.relay.hyco.authorization_rule import List as HycoAuthoList, Create as HycoAuthoCreate
101102
from .aaz.latest.relay.hyco.authorization_rule.keys import List as HycoAuthoKeysList
102103
from .aaz.latest.relay.namespace import List as NamespaceList
104+
from .aaz.latest.appservice import ListLocations as AppServiceListLocations
103105
from .aaz.latest.appservice.plan import (Show as AppServicePlanShow, Create as AppServicePlanCreate,
104106
Update as AppServicePlanUpdate)
105107
from .aaz.latest.appservice.plan.managed_instance import (ShowRdpPassword
@@ -8125,13 +8127,18 @@ def list_flexconsumption_zone_redundant_locations(cmd):
81258127
return [{'name': x.name.lower().replace(' ', '')} for x in regions]
81268128

81278129

8128-
def list_locations(cmd, sku, linux_workers_enabled=None, hyperv_workers_enabled=None):
8130+
def list_locations(cmd, sku, linux_workers_enabled=None, hyperv_workers_enabled=None, managed_instance_enabled=None):
81298131
web_client = web_client_factory(cmd.cli_ctx)
81308132
full_sku = get_sku_tier(sku)
8131-
# Temporary fix due to regression in this specific API with 2021-03-01, should be removed with the next SDK update
8132-
web_client_geo_regions = web_client.list_geo_regions(sku=full_sku,
8133-
linux_workers_enabled=linux_workers_enabled,
8134-
xenon_workers_enabled=hyperv_workers_enabled)
8133+
8134+
if managed_instance_enabled:
8135+
# managed_instance_enabled needs to be specially handled due to requiring version 2025-03-01
8136+
# and due to additional validation needed for SKU
8137+
web_client_geo_regions = _list_managed_instance_locations(cmd, full_sku)
8138+
else:
8139+
web_client_geo_regions = web_client.list_geo_regions(sku=full_sku,
8140+
linux_workers_enabled=linux_workers_enabled,
8141+
xenon_workers_enabled=hyperv_workers_enabled)
81358142

81368143
providers_client = providers_client_factory(cmd.cli_ctx)
81378144
providers_client_locations_list = getattr(providers_client.get('Microsoft.Web'), 'resource_types', [])
@@ -8143,6 +8150,22 @@ def list_locations(cmd, sku, linux_workers_enabled=None, hyperv_workers_enabled=
81438150
return [geo_region for geo_region in web_client_geo_regions if geo_region.name in providers_client_locations_list]
81448151

81458152

8153+
def _list_managed_instance_locations(cmd, sku_tier):
8154+
from types import SimpleNamespace
8155+
8156+
if not is_sku_tier_enabled_for_managed_instance(sku_tier):
8157+
return []
8158+
8159+
# SKU is validated separately above and not passed into API call
8160+
# due to how the API handles SKU for managed instance
8161+
list_locations_cmd = AppServiceListLocations(cli_ctx=cmd.cli_ctx)
8162+
locations = list_locations_cmd(command_args={
8163+
'custom_mode_workers_enabled': True
8164+
})
8165+
8166+
return [SimpleNamespace(**location) for location in locations]
8167+
8168+
81468169
def _check_zip_deployment_status(cmd, rg_name, name, deployment_status_url, slot, timeout=None):
81478170
import requests
81488171
from azure.cli.core.util import should_disable_connection_verify

src/azure-cli/azure/cli/command_modules/appservice/linter_exclusions.yml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,11 @@
11
---
22
# exclusions for the vm module
33

4+
appservice list-locations:
5+
parameters:
6+
managed_instance_enabled:
7+
rule_exclusions:
8+
- option_length_too_long
49
appservice plan managed-instance instance connect:
510
rule_exclusions:
611
- missing_command_test_coverage

0 commit comments

Comments
 (0)