Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
36a789a
support aca as target
wchigit Dec 19, 2023
b61cf55
add experimental tag
wchigit Dec 19, 2023
3ecffb5
store-to-app-config
wchigit Dec 20, 2023
1687650
add opt out command
wchigit Dec 20, 2023
5cb5f51
add tests
wchigit Dec 21, 2023
6b087e8
Merge branch 'dev' of https://github.com/wchigit/azure-cli into opt-out
wchigit Dec 21, 2023
a6f6bd1
fix error
wchigit Dec 21, 2023
b590691
fix pipeline failure
wchigit Dec 21, 2023
c18f352
support app insights
wchigit Dec 21, 2023
9f9ade2
Merge branch 'dev' of https://github.com/wchigit/azure-cli into store…
wchigit Dec 21, 2023
f823d86
fix comments except auth opt-out
wchigit Dec 22, 2023
73d8a00
fix style
wchigit Dec 25, 2023
dc9d9bb
add test
wchigit Dec 25, 2023
737af8f
add test result
wchigit Dec 25, 2023
f5dda5a
skip test that is expected to fail
wchigit Dec 25, 2023
7767933
Merge branch 'store-in-app-config' of https://github.com/wchigit/azur…
wchigit Dec 25, 2023
cb22cba
fix cred
wchigit Dec 25, 2023
7a7e2bd
add test
wchigit Dec 26, 2023
0f8cb29
check style
wchigit Dec 26, 2023
e9af5c0
Merge branch 'add-appinsight-as-target' of https://github.com/wchigit…
wchigit Dec 27, 2023
851baae
Merge branch 'store-in-app-config' of https://github.com/wchigit/azur…
wchigit Dec 27, 2023
020b4a8
resolve test conflict
wchigit Dec 27, 2023
a873315
Merge branch 'add-aca-as-target' of https://github.com/wchigit/azure-…
wchigit Dec 27, 2023
b1b02c0
Merge branch 'opt-out' of https://github.com/wchigit/azure-cli into p…
wchigit Dec 27, 2023
2477722
update sdk version
wchigit Jan 2, 2024
0039d3e
add extension whl to install
wchigit Jan 3, 2024
c056bf4
update whl
wchigit Jan 3, 2024
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
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,8 @@
SUPPORTED_CLIENT_TYPE,
TARGET_SUPPORT_SERVICE_ENDPOINT,
TARGET_SUPPORT_PRIVATE_ENDPOINT,
LOCAL_CONNECTION_PARAMS
LOCAL_CONNECTION_PARAMS,
OPT_OUT_OPTION
)
from ._addon_factory import AddonFactory
from knack.arguments import CLIArgumentType
Expand Down Expand Up @@ -191,6 +192,11 @@ def add_secret_store_argument(context):
'--vault-id'], help='The id of key vault to store secret value')


def add_configuration_store_argument(context):
context.argument('app_config_id', options_list=[
'--appconfig-id'], help='The app configuration id to store configuration')


def add_vnet_block(context, target):
if target not in TARGET_SUPPORT_SERVICE_ENDPOINT:
context.ignore('service_endpoint')
Expand Down Expand Up @@ -236,6 +242,16 @@ def add_confluent_kafka_argument(context):
help='Name of the connection', validator=validate_kafka_params)


def add_opt_out_argument(context):
context.argument('opt_out_list', options_list=['--opt-out'],
default=None, nargs='+',
arg_type=get_enum_type(OPT_OUT_OPTION),
help='Whether to disable configuration steps. '
'Add config to disbale configuration changes on source. '
'Add public-network to disable public network access configuration.'
)


def load_arguments(self, _): # pylint: disable=too-many-statements

for source in SOURCE_RESOURCES_PARAMS:
Expand Down Expand Up @@ -275,18 +291,22 @@ def load_arguments(self, _): # pylint: disable=too-many-statements
add_auth_block(c, source, target)
add_new_addon_argument(c, source, target)
add_secret_store_argument(c)
add_configuration_store_argument(c)
add_vnet_block(c, target)
add_connection_string_argument(c, source, target)
add_customized_keys_argument(c)
add_opt_out_argument(c)
with self.argument_context('{} connection update {}'.format(source.value, target.value)) as c:
add_client_type_argument(c, source, target)
add_connection_name_argument(c, source)
add_source_resource_block(c, source)
add_auth_block(c, source, target)
add_secret_store_argument(c)
add_configuration_store_argument(c)
add_vnet_block(c, target)
add_connection_string_argument(c, source, target)
add_customized_keys_argument(c)
add_opt_out_argument(c)

# special target resource: independent implementation
target = RESOURCE.ConfluentKafka
Expand All @@ -295,13 +315,17 @@ def load_arguments(self, _): # pylint: disable=too-many-statements
add_source_resource_block(c, source, enable_id=False)
add_confluent_kafka_argument(c)
add_secret_store_argument(c)
add_configuration_store_argument(c)
add_customized_keys_argument(c)
add_opt_out_argument(c)
with self.argument_context('{} connection update {}'.format(source.value, target.value)) as c:
add_client_type_argument(c, source, target)
add_source_resource_block(c, source, enable_id=False)
add_confluent_kafka_argument(c)
add_secret_store_argument(c)
add_configuration_store_argument(c)
add_customized_keys_argument(c)
add_opt_out_argument(c)

# local connection
with self.argument_context('connection list') as c:
Expand Down Expand Up @@ -337,13 +361,15 @@ def load_arguments(self, _): # pylint: disable=too-many-statements
add_auth_block(c, source, target)
add_new_addon_argument(c, source, target)
add_secret_store_argument(c)
add_configuration_store_argument(c)
add_vnet_block(c, target)
add_local_connection_block(c)
add_customized_keys_argument(c)
with self.argument_context('connection update {}'.format(target.value)) as c:
add_client_type_argument(c, source, target)
add_auth_block(c, source, target)
add_secret_store_argument(c)
add_configuration_store_argument(c)
add_vnet_block(c, target)
add_local_connection_block(c)
add_customized_keys_argument(c)
Expand All @@ -354,12 +380,14 @@ def load_arguments(self, _): # pylint: disable=too-many-statements
add_client_type_argument(c, source, target)
add_confluent_kafka_argument(c)
add_secret_store_argument(c)
add_configuration_store_argument(c)
add_local_connection_block(c, show_id=False)
add_customized_keys_argument(c)
with self.argument_context('connection update {}'.format(target.value)) as c:
add_client_type_argument(c, source, target)
add_confluent_kafka_argument(c)
add_secret_store_argument(c)
add_configuration_store_argument(c)
add_local_connection_block(c, show_id=False)
add_customized_keys_argument(c)
with self.argument_context('connection preview-configuration {}'.format(target.value)) as c:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,8 @@ class RESOURCE(Enum):
SignalR = 'signalr'
WebPubSub = 'webpubsub'
ConfluentKafka = 'confluent-cloud'
AppInsights = 'app-insights'
ContainerAppAsTarget = 'containerapp'

@classmethod
def value_of(cls, value):
Expand Down Expand Up @@ -143,6 +145,9 @@ class CLIENT_TYPE(Enum):
RESOURCE.SignalR: '/subscriptions/{subscription}/resourceGroups/{target_resource_group}/providers/Microsoft.SignalRService/SignalR/{signalr}',
RESOURCE.WebPubSub: '/subscriptions/{subscription}/resourceGroups/{target_resource_group}/providers/Microsoft.SignalRService/WebPubSub/{webpubsub}',
RESOURCE.ConfluentKafka: '#', # special target resource, no arm resource id
RESOURCE.AppInsights: '/subscriptions/{subscription}/resourceGroups/{target_resource_group}/providers/microsoft.insights/components/{appinsights}',

RESOURCE.ContainerAppAsTarget: '/subscriptions/{subscription}/resourceGroups/{target_resource_group}/providers/Microsoft.App/containerApps/{target_app_name}'
}


Expand Down Expand Up @@ -621,6 +626,30 @@ class CLIENT_TYPE(Enum):
'help': 'Name of the webpubsub service',
'placeholder': 'MyWebPubSub'
}
},
RESOURCE.AppInsights: {
'target_resource_group': {
'options': ['--target-resource-group', '--tg'],
'help': 'The resource group which contains the app insights',
'placeholder': 'AppInsightsRG'
},
'appinsights': {
'options': ['--app-insights'],
'help': 'Name of the app insights',
'placeholder': 'MyAppInsights'
}
},
RESOURCE.ContainerAppAsTarget: {
'target_resource_group': {
'options': ['--target-resource-group', '--tg'],
'help': 'The resource group which contains the container app as target resource',
'placeholder': 'ContainerAppAsTargetRG'
},
'target_app_name': {
'options': ['--target-app-name'],
'help': 'Name of the container app as target resource',
'placeholder': 'MyContainerAppAsTarget'
}
}
}

Expand Down Expand Up @@ -745,6 +774,7 @@ class CLIENT_TYPE(Enum):
RESOURCE.SignalR: [AUTH_TYPE.SecretAuto, AUTH_TYPE.UserAccount, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.WebPubSub: [AUTH_TYPE.SecretAuto, AUTH_TYPE.UserAccount, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.ConfluentKafka: [AUTH_TYPE.Secret],
RESOURCE.AppInsights: [AUTH_TYPE.SecretAuto]
},
RESOURCE.WebApp: {
RESOURCE.Postgres: [AUTH_TYPE.Secret, AUTH_TYPE.SystemIdentity],
Expand Down Expand Up @@ -773,6 +803,9 @@ class CLIENT_TYPE(Enum):
RESOURCE.SignalR: [AUTH_TYPE.SystemIdentity, AUTH_TYPE.SecretAuto, AUTH_TYPE.UserIdentity, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.WebPubSub: [AUTH_TYPE.SystemIdentity, AUTH_TYPE.SecretAuto, AUTH_TYPE.UserIdentity, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.ConfluentKafka: [AUTH_TYPE.Secret],
RESOURCE.AppInsights: [AUTH_TYPE.SecretAuto],

RESOURCE.ContainerAppAsTarget: [AUTH_TYPE.SecretAuto]
},
RESOURCE.SpringCloud: {
RESOURCE.Postgres: [AUTH_TYPE.Secret, AUTH_TYPE.SystemIdentity],
Expand Down Expand Up @@ -801,6 +834,9 @@ class CLIENT_TYPE(Enum):
RESOURCE.SignalR: [AUTH_TYPE.SystemIdentity, AUTH_TYPE.SecretAuto, AUTH_TYPE.UserIdentity, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.WebPubSub: [AUTH_TYPE.SystemIdentity, AUTH_TYPE.SecretAuto, AUTH_TYPE.UserIdentity, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.ConfluentKafka: [AUTH_TYPE.Secret],
RESOURCE.AppInsights: [AUTH_TYPE.SecretAuto],

RESOURCE.ContainerAppAsTarget: [AUTH_TYPE.SecretAuto],
},
RESOURCE.KubernetesCluster: {
RESOURCE.Postgres: [AUTH_TYPE.Secret],
Expand Down Expand Up @@ -829,6 +865,9 @@ class CLIENT_TYPE(Enum):
RESOURCE.SignalR: [AUTH_TYPE.SecretAuto, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.WebPubSub: [AUTH_TYPE.SecretAuto, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.ConfluentKafka: [AUTH_TYPE.Secret],
RESOURCE.AppInsights: [AUTH_TYPE.SecretAuto],

RESOURCE.ContainerAppAsTarget: [AUTH_TYPE.SecretAuto],
},
RESOURCE.ContainerApp: {
RESOURCE.Postgres: [AUTH_TYPE.Secret, AUTH_TYPE.SystemIdentity],
Expand Down Expand Up @@ -857,6 +896,9 @@ class CLIENT_TYPE(Enum):
RESOURCE.SignalR: [AUTH_TYPE.SystemIdentity, AUTH_TYPE.SecretAuto, AUTH_TYPE.UserIdentity, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.WebPubSub: [AUTH_TYPE.SystemIdentity, AUTH_TYPE.SecretAuto, AUTH_TYPE.UserIdentity, AUTH_TYPE.ServicePrincipalSecret],
RESOURCE.ConfluentKafka: [AUTH_TYPE.Secret],
RESOURCE.AppInsights: [AUTH_TYPE.SecretAuto],

RESOURCE.ContainerAppAsTarget: [AUTH_TYPE.SecretAuto],
},
}
SUPPORTED_AUTH_TYPE[RESOURCE.SpringCloudDeprecated] = SUPPORTED_AUTH_TYPE[RESOURCE.SpringCloud]
Expand Down Expand Up @@ -1094,6 +1136,28 @@ class CLIENT_TYPE(Enum):
CLIENT_TYPE.Go,
CLIENT_TYPE.SpringBoot,
CLIENT_TYPE.Blank
],
RESOURCE.AppInsights: [
CLIENT_TYPE.Dotnet,
CLIENT_TYPE.DotnetInternal,
CLIENT_TYPE.Java,
CLIENT_TYPE.Python,
CLIENT_TYPE.Nodejs,
CLIENT_TYPE.Go,
CLIENT_TYPE.Blank,
],
RESOURCE.ContainerAppAsTarget: [
CLIENT_TYPE.Dotnet,
CLIENT_TYPE.DotnetInternal,
CLIENT_TYPE.Java,
CLIENT_TYPE.Python,
CLIENT_TYPE.Nodejs,
CLIENT_TYPE.Go,
CLIENT_TYPE.Php,
CLIENT_TYPE.Ruby,
CLIENT_TYPE.Django,
CLIENT_TYPE.SpringBoot,
CLIENT_TYPE.Blank
]
}
}
Expand All @@ -1104,3 +1168,10 @@ class CLIENT_TYPE(Enum):
SUPPORTED_CLIENT_TYPE[RESOURCE.ContainerApp] = SUPPORTED_CLIENT_TYPE[RESOURCE.WebApp]
SUPPORTED_CLIENT_TYPE[RESOURCE.Local] = SUPPORTED_CLIENT_TYPE[RESOURCE.WebApp]
SUPPORTED_CLIENT_TYPE[RESOURCE.FunctionApp] = SUPPORTED_CLIENT_TYPE[RESOURCE.WebApp]


# The dict defines the options for opt-out
class OPT_OUT_OPTION(Enum):
PUBLIC_NETWORK = 'public-network'
CONFIGURATION_INFO = 'configinfo'
# AUTHENTICATION = 'auth'
Original file line number Diff line number Diff line change
Expand Up @@ -333,6 +333,50 @@ def get_auth_if_no_valid_key_vault_connection_for_containerapp(key_vault_connect
return {'authType': auth_type}


def create_app_config_connection_if_not_exist(cmd, client, source_id, app_config_id,
scope=None): # Resource.ContainerApp
from ._validators import get_source_resource_name

logger.warning('looking for valid app configuration connections')
for connection in client.list(resource_uri=source_id):
connection = todict(connection)
if connection.get('targetService', dict()).get('id') == app_config_id:
logger.warning('Valid app configuration connection found.')
return

logger.warning('no valid app configuration connection found. Creating with system identity...')

from ._resource_config import (
CLIENT_TYPE
)

connection_name = generate_random_string(prefix='appconfig_')
parameters = {
'target_service': {
"type": "AzureResource",
"id": app_config_id
},
'auth_info': {
'authType': 'systemAssignedIdentity'
},
# Container App container name
'scope': scope,
'client_type': CLIENT_TYPE.Blank,
}

source_name = get_source_resource_name(cmd)
if source_name == RESOURCE.KubernetesCluster:
parameters['target_service']['resource_properties'] = {
'type': 'KeyVault',
'connect_as_kubernetes_csi_driver': True,
}

return auto_register(client.begin_create_or_update,
resource_uri=source_id,
linker_name=connection_name,
parameters=parameters)


def is_packaged_installed(package_name):
import pkg_resources
installed_packages = pkg_resources.working_set
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,9 @@ def load_command_table(self, _): # pylint: disable=too-many-statements
if target in TARGET_RESOURCES_DEPRECATED:
ig.custom_command(target.value, 'connection_create', deprecate_info=self.deprecate(hide=False),
supports_no_wait=True, transform=transform_linker_properties)
elif target == RESOURCE.ContainerAppAsTarget:
ig.custom_command(target.value, 'connection_create', is_experimental=True,
supports_no_wait=True, transform=transform_linker_properties)
else:
ig.custom_command(target.value, 'connection_create',
supports_no_wait=True, transform=transform_linker_properties)
Expand All @@ -74,6 +77,9 @@ def load_command_table(self, _): # pylint: disable=too-many-statements
if target in TARGET_RESOURCES_DEPRECATED:
ig.custom_command(target.value, 'connection_update', deprecate_info=self.deprecate(hide=False),
supports_no_wait=True, transform=transform_linker_properties)
elif target == RESOURCE.ContainerAppAsTarget:
ig.custom_command(target.value, 'connection_update', is_experimental=True,
supports_no_wait=True, transform=transform_linker_properties)
else:
ig.custom_command(target.value, 'connection_update',
supports_no_wait=True, transform=transform_linker_properties)
Expand Down
Loading