Skip to content

Commit

Permalink
[k8s-extension] Update extension CLI to v1.3.0 (#5204)
Browse files Browse the repository at this point in the history
  • Loading branch information
bavneetsingh16 authored Aug 9, 2022
1 parent a5396ef commit d4ffc41
Show file tree
Hide file tree
Showing 13 changed files with 77 additions and 49 deletions.
4 changes: 4 additions & 0 deletions src/k8s-extension/HISTORY.rst
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,10 @@
Release History
===============

1.3.0
++++++++++++++++++
* Add support for provisionedClusters

1.2.6
++++++++++++++++++
* k8s-extension new sub command group for extension types
Expand Down
7 changes: 5 additions & 2 deletions src/k8s-extension/azext_k8s_extension/_params.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,9 +29,12 @@ def load_arguments(self, _):
options_list=['--cluster-name', '-c'],
help='Name of the Kubernetes cluster')
c.argument('cluster_type',
arg_type=get_enum_type(['connectedClusters', 'managedClusters', 'appliances']),
arg_type=get_enum_type(['connectedClusters', 'managedClusters', 'appliances', 'provisionedClusters']),
options_list=['--cluster-type', '-t'],
help='Specify Arc clusters or AKS managed clusters or Arc appliances.')
help='Specify Arc clusters or AKS managed clusters or Arc appliances or provisionedClusters.')
c.argument('cluster_resource_provider',
options_list=['--cluster-resource-provider', '--cluster-rp'],
help='Cluster Resource Provider name for this clusterType (Required for provisionedClusters)')
c.argument('scope',
arg_type=get_enum_type(['cluster', 'namespace']),
help='Specify the extension scope.')
Expand Down
3 changes: 3 additions & 0 deletions src/k8s-extension/azext_k8s_extension/consts.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,16 @@
CONNECTED_CLUSTER_RP = "Microsoft.Kubernetes"
MANAGED_CLUSTER_RP = "Microsoft.ContainerService"
APPLIANCE_RP = "Microsoft.ResourceConnector"
HYBRIDCONTAINERSERVICE_RP = "microsoft.hybridcontainerservice"

CONNECTED_CLUSTER_TYPE = "connectedclusters"
MANAGED_CLUSTER_TYPE = "managedclusters"
APPLIANCE_TYPE = "appliances"
PROVISIONED_CLUSTER_TYPE = "provisionedclusters"

CONNECTED_CLUSTER_API_VERSION = "2021-10-01"
MANAGED_CLUSTER_API_VERSION = "2021-10-01"
APPLIANCE_API_VERSION = "2021-10-31-preview"
HYBRIDCONTAINERSERVICE_API_VERSION = "2022-05-01-preview"

EXTENSION_TYPE_API_VERSION = "2022-01-15-preview"
34 changes: 18 additions & 16 deletions src/k8s-extension/azext_k8s_extension/custom.py
Original file line number Diff line number Diff line change
Expand Up @@ -53,10 +53,10 @@ def ExtensionFactory(extension_name):
return extension_map.get(extension_name, DefaultExtension)()


def show_k8s_extension(client, resource_group_name, cluster_name, name, cluster_type):
def show_k8s_extension(client, resource_group_name, cluster_name, name, cluster_type, cluster_resource_provider=None):
"""Get an existing K8s Extension."""
# Determine ClusterRP
cluster_rp, _ = get_cluster_rp_api_version(cluster_type)
cluster_rp, _ = get_cluster_rp_api_version(cluster_type=cluster_type, cluster_rp=cluster_resource_provider)

try:
extension = client.get(
Expand Down Expand Up @@ -95,6 +95,7 @@ def create_k8s_extension(
name,
cluster_type,
extension_type,
cluster_resource_provider=None,
scope=None,
auto_upgrade_minor_version=None,
release_train=None,
Expand All @@ -110,7 +111,7 @@ def create_k8s_extension(
"""Create a new Extension Instance."""

extension_type_lower = extension_type.lower()
cluster_rp, _ = get_cluster_rp_api_version(cluster_type)
cluster_rp, _ = get_cluster_rp_api_version(cluster_type=cluster_type, cluster_rp=cluster_resource_provider)

# Configuration Settings & Configuration Protected Settings
if configuration_settings is not None and configuration_settings_file is not None:
Expand Down Expand Up @@ -167,6 +168,7 @@ def create_k8s_extension(
cluster_name,
name,
cluster_type,
cluster_rp,
extension_type_lower,
scope,
auto_upgrade_minor_version,
Expand All @@ -193,7 +195,7 @@ def create_k8s_extension(
# We don't create the identity if we are in DF
if create_identity and not is_dogfood_cluster(cmd):
identity_object, location = __create_identity(
cmd, resource_group_name, cluster_name, cluster_type
cmd, resource_group_name, cluster_name, cluster_type, cluster_rp
)
if identity_object is not None and location is not None:
extension_instance.identity, extension_instance.location = (
Expand All @@ -214,8 +216,8 @@ def create_k8s_extension(
)


def list_k8s_extension(client, resource_group_name, cluster_name, cluster_type):
cluster_rp, _ = get_cluster_rp_api_version(cluster_type)
def list_k8s_extension(client, resource_group_name, cluster_name, cluster_type, cluster_resource_provider=None):
cluster_rp, _ = get_cluster_rp_api_version(cluster_type=cluster_type, cluster_rp=cluster_resource_provider)
return client.list(resource_group_name, cluster_rp, cluster_type, cluster_name)


Expand All @@ -226,6 +228,7 @@ def update_k8s_extension(
cluster_name,
name,
cluster_type,
cluster_resource_provider=None,
auto_upgrade_minor_version=None,
release_train=None,
version=None,
Expand Down Expand Up @@ -253,22 +256,21 @@ def update_k8s_extension(
user_confirmation_factory(cmd, yes, msg)

# Determine ClusterRP
cluster_rp, _ = get_cluster_rp_api_version(cluster_type)
cluster_rp, _ = get_cluster_rp_api_version(cluster_type=cluster_type, cluster_rp=cluster_resource_provider)

# We need to determine the ExtensionType to call ExtensionFactory and create Extension class
extension = show_k8s_extension(
client, resource_group_name, cluster_name, name, cluster_type
client, resource_group_name, cluster_name, name, cluster_type, cluster_rp
)
extension_type_lower = extension.extension_type.lower()

config_settings = None
config_protected_settings = None
config_settings = {}
config_protected_settings = {}
# Get Configuration Settings from file
if configuration_settings_file is not None:
config_settings = read_config_settings_file(configuration_settings_file)

if configuration_settings is not None:
config_settings = {}
for dicts in configuration_settings:
for key, value in dicts.items():
config_settings[key] = value
Expand All @@ -280,7 +282,6 @@ def update_k8s_extension(
)

if configuration_protected_settings is not None:
config_protected_settings = {}
for dicts in configuration_protected_settings:
for key, value in dicts.items():
config_protected_settings[key] = value
Expand Down Expand Up @@ -320,13 +321,14 @@ def delete_k8s_extension(
cluster_name,
name,
cluster_type,
cluster_resource_provider=None,
no_wait=False,
yes=False,
force=False,
):
"""Delete an existing Kubernetes Extension."""
# Determine ClusterRP
cluster_rp, _ = get_cluster_rp_api_version(cluster_type)
cluster_rp, _ = get_cluster_rp_api_version(cluster_type=cluster_type, cluster_rp=cluster_resource_provider)
extension = None
try:
extension = client.get(
Expand All @@ -343,7 +345,7 @@ def delete_k8s_extension(

# If there is any custom delete logic, this will call the logic
extension_class.Delete(
cmd, client, resource_group_name, cluster_name, name, cluster_type, yes
cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp, yes
)

return sdk_no_wait(
Expand Down Expand Up @@ -406,7 +408,7 @@ def show_k8s_cluster_extension_type(client, resource_group_name, cluster_type, c
raise ex


def __create_identity(cmd, resource_group_name, cluster_name, cluster_type):
def __create_identity(cmd, resource_group_name, cluster_name, cluster_type, cluster_rp):
subscription_id = get_subscription_id(cmd.cli_ctx)
resources = cf_resources(cmd.cli_ctx, subscription_id)

Expand All @@ -417,7 +419,7 @@ def __create_identity(cmd, resource_group_name, cluster_name, cluster_type):
):
return None, None

cluster_rp, parent_api_version = get_cluster_rp_api_version(cluster_type)
cluster_rp, parent_api_version = get_cluster_rp_api_version(cluster_type=cluster_type, cluster_rp=cluster_rp)

cluster_resource_id = (
"/subscriptions/{0}/resourceGroups/{1}/providers/{2}/{3}/{4}".format(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,8 @@


class AzureDefender(DefaultExtension):
def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, extension_type,
scope, auto_upgrade_minor_version, release_train, version, target_namespace,
def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp,
extension_type, scope, auto_upgrade_minor_version, release_train, version, target_namespace,
release_namespace, configuration_settings, configuration_protected_settings,
configuration_settings_file, configuration_protected_settings_file):

Expand All @@ -43,7 +43,7 @@ def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_t
'only supports cluster scope and single instance of this extension.', extension_type)
logger.warning("Defaulting to extension name '%s' and release-namespace '%s'", name, release_namespace)

_get_container_insights_settings(cmd, resource_group_name, cluster_name, configuration_settings,
_get_container_insights_settings(cmd, resource_group_name, cluster_rp, cluster_type, cluster_name, configuration_settings,
configuration_protected_settings, is_ci_extension_type)

# NOTE-2: Return a valid Extension object, Instance name and flag for Identity
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -108,8 +108,8 @@ def __init__(self):

self.OPEN_SHIFT = 'openshift'

def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, extension_type,
scope, auto_upgrade_minor_version, release_train, version, target_namespace,
def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp,
extension_type, scope, auto_upgrade_minor_version, release_train, version, target_namespace,
release_namespace, configuration_settings, configuration_protected_settings,
configuration_settings_file, configuration_protected_settings_file):
if scope == 'namespace':
Expand All @@ -126,7 +126,7 @@ def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_t

# get the arc's location
subscription_id = get_subscription_id(cmd.cli_ctx)
cluster_rp, parent_api_version = get_cluster_rp_api_version(cluster_type)
cluster_rp, parent_api_version = get_cluster_rp_api_version(cluster_type=cluster_type, cluster_rp=cluster_rp)
cluster_resource_id = '/subscriptions/{0}/resourceGroups/{1}/providers/{2}' \
'/{3}/{4}'.format(subscription_id, resource_group_name, cluster_rp, cluster_type, cluster_name)
cluster_location = ''
Expand Down Expand Up @@ -216,7 +216,7 @@ def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_t
)
return extension, name, create_identity

def Delete(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, yes):
def Delete(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp, yes):
user_confirmation_factory(cmd, yes)

def Update(self, cmd, resource_group_name, cluster_name, auto_upgrade_minor_version, release_train, version, configuration_settings,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,8 @@


class ContainerInsights(DefaultExtension):
def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, extension_type,
scope, auto_upgrade_minor_version, release_train, version, target_namespace,
def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp,
extension_type, scope, auto_upgrade_minor_version, release_train, version, target_namespace,
release_namespace, configuration_settings, configuration_protected_settings,
configuration_settings_file, configuration_protected_settings_file):
"""ExtensionType 'microsoft.azuremonitor.containers' specific validations & defaults for Create
Expand All @@ -56,7 +56,7 @@ def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_t
'only supports cluster scope and single instance of this extension.', extension_type)
logger.warning("Defaulting to extension name '%s' and release-namespace '%s'", name, release_namespace)

_get_container_insights_settings(cmd, resource_group_name, cluster_name, configuration_settings,
_get_container_insights_settings(cmd, resource_group_name, cluster_rp, cluster_type, cluster_name, configuration_settings,
configuration_protected_settings, is_ci_extension_type)

# NOTE-2: Return a valid Extension object, Instance name and flag for Identity
Expand All @@ -72,11 +72,11 @@ def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_t
)
return extension, name, create_identity

def Delete(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, yes):
def Delete(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp, yes):
# Delete DCR-A if it exists incase of MSI Auth
useAADAuth = False
isDCRAExists = False
cluster_rp, _ = get_cluster_rp_api_version(cluster_type)
cluster_rp, _ = get_cluster_rp_api_version(cluster_type=cluster_type, cluster_rp=cluster_rp)
try:
extension = client.get(resource_group_name, cluster_rp, cluster_type, cluster_name, name)
except Exception:
Expand Down Expand Up @@ -140,8 +140,8 @@ def _invoke_deployment(cmd, resource_group_name, deployment_name, template, para
return sdk_no_wait(no_wait, smc.begin_create_or_update, resource_group_name, deployment_name, deployment)


def _ensure_default_log_analytics_workspace_for_monitoring(cmd, subscription_id,
cluster_resource_group_name, cluster_name):
def _ensure_default_log_analytics_workspace_for_monitoring(cmd, subscription_id, cluster_resource_group_name,
cluster_rp, cluster_type, cluster_name):
# mapping for azure public cloud
# log analytics workspaces cannot be created in WCUS region due to capacity limits
# so mapped to EUS per discussion with log analytics team
Expand Down Expand Up @@ -236,8 +236,8 @@ def _ensure_default_log_analytics_workspace_for_monitoring(cmd, subscription_id,
cluster_location = ''
resources = cf_resources(cmd.cli_ctx, subscription_id)

cluster_resource_id = '/subscriptions/{0}/resourceGroups/{1}/providers/Microsoft.Kubernetes' \
'/connectedClusters/{2}'.format(subscription_id, cluster_resource_group_name, cluster_name)
cluster_resource_id = '/subscriptions/{0}/resourceGroups/{1}/providers//{2}/{3}/{4}'.format(
subscription_id, cluster_resource_group_name, cluster_rp, cluster_type, cluster_name)
try:
resource = resources.get_by_id(cluster_resource_id, '2020-01-01-preview')
cluster_location = resource.location.lower()
Expand Down Expand Up @@ -438,8 +438,8 @@ def _ensure_container_insights_for_monitoring(cmd, workspace_resource_id):
validate=False, no_wait=False, subscription_id=subscription_id)


def _get_container_insights_settings(cmd, cluster_resource_group_name, cluster_name, configuration_settings,
configuration_protected_settings, is_ci_extension_type):
def _get_container_insights_settings(cmd, cluster_resource_group_name, cluster_rp, cluster_type, cluster_name,
configuration_settings, configuration_protected_settings, is_ci_extension_type):

subscription_id = get_subscription_id(cmd.cli_ctx)
workspace_resource_id = ''
Expand Down Expand Up @@ -477,15 +477,15 @@ def _get_container_insights_settings(cmd, cluster_resource_group_name, cluster_n

if not workspace_resource_id:
workspace_resource_id = _ensure_default_log_analytics_workspace_for_monitoring(
cmd, subscription_id, cluster_resource_group_name, cluster_name)
cmd, subscription_id, cluster_resource_group_name, cluster_rp, cluster_type, cluster_name)
else:
if not is_valid_resource_id(workspace_resource_id):
raise InvalidArgumentValueError('{} is not a valid Azure resource ID.'.format(workspace_resource_id))

if is_ci_extension_type:
if useAADAuth:
logger.info("creating data collection rule and association")
_ensure_container_insights_dcr_for_monitoring(cmd, subscription_id, cluster_resource_group_name, cluster_name, workspace_resource_id)
_ensure_container_insights_dcr_for_monitoring(cmd, subscription_id, cluster_resource_group_name, cluster_rp, cluster_type, cluster_name, workspace_resource_id)
elif not _is_container_insights_solution_exists(cmd, workspace_resource_id):
logger.info("Creating ContainerInsights solution resource, since it doesn't exist and it is using legacy authentication")
_ensure_container_insights_for_monitoring(cmd, workspace_resource_id).result()
Expand Down Expand Up @@ -545,13 +545,13 @@ def get_existing_container_insights_extension_dcr_tags(cmd, dcr_url):
return tags


def _ensure_container_insights_dcr_for_monitoring(cmd, subscription_id, cluster_resource_group_name, cluster_name, workspace_resource_id):
def _ensure_container_insights_dcr_for_monitoring(cmd, subscription_id, cluster_resource_group_name, cluster_rp, cluster_type, cluster_name, workspace_resource_id):
from azure.core.exceptions import HttpResponseError

cluster_region = ''
resources = cf_resources(cmd.cli_ctx, subscription_id)
cluster_resource_id = '/subscriptions/{0}/resourceGroups/{1}/providers/Microsoft.Kubernetes' \
'/connectedClusters/{2}'.format(subscription_id, cluster_resource_group_name, cluster_name)
cluster_resource_id = '/subscriptions/{0}/resourceGroups/{1}/providers/{2}/{3}/{4}'.format(
subscription_id, cluster_resource_group_name, cluster_rp, cluster_type, cluster_name)
try:
resource = resources.get_by_id(cluster_resource_id, '2020-01-01-preview')
cluster_region = resource.location.lower()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@ def __init__(self):
# constants for configuration settings.
self.CLUSTER_TYPE = 'global.clusterType'

def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, extension_type,
scope, auto_upgrade_minor_version, release_train, version, target_namespace,
def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp,
extension_type, scope, auto_upgrade_minor_version, release_train, version, target_namespace,
release_namespace, configuration_settings, configuration_protected_settings,
configuration_settings_file, configuration_protected_settings_file):

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ def Create(
cluster_name,
name,
cluster_type,
cluster_rp,
extension_type,
scope,
auto_upgrade_minor_version,
Expand Down Expand Up @@ -87,7 +88,7 @@ def Update(
)

def Delete(
self, cmd, client, resource_group_name, cluster_name, name, cluster_type, yes
self, cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp, yes
):
user_confirmation_factory(cmd, yes)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,8 @@

class OpenServiceMesh(DefaultExtension):

def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, extension_type,
scope, auto_upgrade_minor_version, release_train, version, target_namespace,
def Create(self, cmd, client, resource_group_name, cluster_name, name, cluster_type, cluster_rp,
extension_type, scope, auto_upgrade_minor_version, release_train, version, target_namespace,
release_namespace, configuration_settings, configuration_protected_settings,
configuration_settings_file, configuration_protected_settings_file):
"""ExtensionType 'microsoft.openservicemesh' specific validations & defaults for Create
Expand Down
Loading

0 comments on commit d4ffc41

Please sign in to comment.