Skip to content
Merged
14 changes: 13 additions & 1 deletion src/azure-cli-core/azure/cli/core/commands/arm.py
Original file line number Diff line number Diff line change
Expand Up @@ -95,11 +95,23 @@ def build_parameters(self):
return json.loads(json.dumps(self.parameters))


def raise_subdivision_deployment_error(error_message, error_code=None):
from azure.cli.core.azclierror import InvalidTemplateError, DeploymentError

if error_code == 'InvalidTemplateDeployment':
raise InvalidTemplateError(error_message)

raise DeploymentError(error_message)


def handle_template_based_exception(ex):
try:
raise CLIError(ex.inner_exception.error.message)
except AttributeError:
raise CLIError(ex)
if hasattr(ex, 'response'):
raise_subdivision_deployment_error(ex.response.internal_response.text, ex.error.code if ex.error else None)
else:
raise CLIError(ex)


def handle_long_running_operation_exception(ex):
Expand Down
30 changes: 11 additions & 19 deletions src/azure-cli/azure/cli/command_modules/resource/custom.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
from azure.cli.core.parser import IncorrectUsageError
from azure.cli.core.util import get_file_json, read_file_content, shell_safe_json_parse, sdk_no_wait
from azure.cli.core.commands import LongRunningOperation
from azure.cli.core.commands.arm import raise_subdivision_deployment_error
from azure.cli.core.commands.client_factory import get_mgmt_service_client, get_subscription_id
from azure.cli.core.profiles import ResourceType, get_sdk, get_api_version, AZURE_API_PROFILES

Expand Down Expand Up @@ -300,15 +301,6 @@ def _remove_comments_from_json(template, preserve_order=True, file_path=None):
raise CLIError("Failed to parse the JSON data, please check whether it is a valid JSON format")


def _raise_subdivision_deployment_error(error_message, error_code=None):
from azure.cli.core.azclierror import InvalidTemplateError, DeploymentError

if error_code == 'InvalidTemplateDeployment':
raise InvalidTemplateError(error_message)

raise DeploymentError(error_message)


# pylint: disable=too-many-locals, too-many-statements, too-few-public-methods
def _deploy_arm_template_core_unmodified(cmd, resource_group_name, template_file=None,
template_uri=None, deployment_name=None, parameters=None,
Expand Down Expand Up @@ -373,14 +365,14 @@ def _deploy_arm_template_core_unmodified(cmd, resource_group_name, template_file
try:
validation_poller = deployment_client.begin_validate(resource_group_name, deployment_name, deployment)
except HttpResponseError as cx:
_raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
validation_result = LongRunningOperation(cmd.cli_ctx)(validation_poller)
else:
validation_result = deployment_client.validate(resource_group_name, deployment_name, deployment)

if validation_result and validation_result.error:
err_message = _build_preflight_error_message(validation_result.error)
_raise_subdivision_deployment_error(err_message)
raise_subdivision_deployment_error(err_message)
if validate_only:
return validation_result

Expand Down Expand Up @@ -485,14 +477,14 @@ def _deploy_arm_template_at_subscription_scope(cmd,
try:
validation_poller = mgmt_client.begin_validate_at_subscription_scope(deployment_name, deployment)
except HttpResponseError as cx:
_raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
validation_result = LongRunningOperation(cmd.cli_ctx)(validation_poller)
else:
validation_result = mgmt_client.validate_at_subscription_scope(deployment_name, deployment)

if validation_result and validation_result.error:
err_message = _build_preflight_error_message(validation_result.error)
_raise_subdivision_deployment_error(err_message)
raise_subdivision_deployment_error(err_message)
if validate_only:
return validation_result

Expand Down Expand Up @@ -566,14 +558,14 @@ def _deploy_arm_template_at_resource_group(cmd,
try:
validation_poller = mgmt_client.begin_validate(resource_group_name, deployment_name, deployment)
except HttpResponseError as cx:
_raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
validation_result = LongRunningOperation(cmd.cli_ctx)(validation_poller)
else:
validation_result = mgmt_client.validate(resource_group_name, deployment_name, deployment)

if validation_result and validation_result.error:
err_message = _build_preflight_error_message(validation_result.error)
_raise_subdivision_deployment_error(err_message)
raise_subdivision_deployment_error(err_message)
if validate_only:
return validation_result

Expand Down Expand Up @@ -645,15 +637,15 @@ def _deploy_arm_template_at_management_group(cmd,
validation_poller = mgmt_client.begin_validate_at_management_group_scope(management_group_id,
deployment_name, deployment)
except HttpResponseError as cx:
_raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
validation_result = LongRunningOperation(cmd.cli_ctx)(validation_poller)
else:
validation_result = mgmt_client.validate_at_management_group_scope(management_group_id, deployment_name,
deployment)

if validation_result and validation_result.error:
err_message = _build_preflight_error_message(validation_result.error)
_raise_subdivision_deployment_error(err_message)
raise_subdivision_deployment_error(err_message)
if validate_only:
return validation_result

Expand Down Expand Up @@ -719,15 +711,15 @@ def _deploy_arm_template_at_tenant_scope(cmd,
validation_poller = mgmt_client.begin_validate_at_tenant_scope(deployment_name=deployment_name,
parameters=deployment)
except HttpResponseError as cx:
_raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
raise_subdivision_deployment_error(cx.response.internal_response.text, cx.error.code if cx.error else None)
validation_result = LongRunningOperation(cmd.cli_ctx)(validation_poller)
else:
validation_result = mgmt_client.validate_at_tenant_scope(deployment_name=deployment_name,
parameters=deployment)

if validation_result and validation_result.error:
err_message = _build_preflight_error_message(validation_result.error)
_raise_subdivision_deployment_error(err_message)
raise_subdivision_deployment_error(err_message)
if validate_only:
return validation_result

Expand Down
7 changes: 6 additions & 1 deletion src/azure-cli/azure/cli/command_modules/vm/_params.py
Original file line number Diff line number Diff line change
Expand Up @@ -578,8 +578,9 @@ def load_arguments(self, _):
for dest in scaleset_name_aliases:
c.argument(dest, vmss_name_type, id_part=None) # due to instance-ids parameter

with self.argument_context('vmss create') as c:
with self.argument_context('vmss create', operation_group='virtual_machine_scale_sets') as c:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What is the impact of operation_group='virtual_machine_scale_sets'?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To make sure the following api version take effect

'virtual_machine_scale_sets': '2021-03-01'

VirtualMachineEvictionPolicyTypes = self.get_models('VirtualMachineEvictionPolicyTypes', resource_type=ResourceType.MGMT_COMPUTE)

c.argument('name', name_arg_type)
c.argument('nat_backend_port', default=None, help='Backend port to open with NAT rules. Defaults to 22 on Linux and 3389 on Windows.')
c.argument('single_placement_group', arg_type=get_three_state_flag(), help="Limit the scale set to a single placement group."
Expand All @@ -602,6 +603,10 @@ def load_arguments(self, _):
c.argument('automatic_repairs_grace_period', min_api='2018-10-01',
help='The amount of time (in minutes, between 30 and 90) for which automatic repairs are suspended due to a state change on VM.')
c.argument('user_data', help='UserData for the virtual machines in the scale set. It can be passed in as file or string.', completer=FilesCompleter(), type=file_type, min_api='2021-03-01')
c.argument('network_api_version', is_preview=True, min_api='2021-03-01',
help="Specify the Microsoft.Network API version used when creating networking resources in the Network "
"Interface Configurations for Virtual Machine Scale Set with orchestration mode 'Flexible'. Possible "
"value is 2020-11-01.")

with self.argument_context('vmss create', arg_group='Network Balancer') as c:
LoadBalancerSkuName = self.get_models('LoadBalancerSkuName', resource_type=ResourceType.MGMT_NETWORK)
Expand Down
Loading