Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
7 changes: 7 additions & 0 deletions src/azure-cli-core/azure/cli/core/cloud.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,9 @@

CLOUD_CONFIG_FILE = os.path.join(GLOBAL_CONFIG_DIR, 'clouds.config')

# Add names of clouds that don't allow telemetry data collection here such as JEDI.
CLOUDS_FORBIDDING_TELEMETRY = []


class CloudNotRegisteredException(Exception):
def __init__(self, cloud_name):
Expand Down Expand Up @@ -526,3 +529,7 @@ def remove_cloud(cli_ctx, cloud_name):
config.remove_section(cloud_name)
with open(CLOUD_CONFIG_FILE, 'w') as configfile:
config.write(configfile)


def cloud_forbid_telemetry(cli_ctx):
return get_active_cloud_name(cli_ctx) in CLOUDS_FORBIDDING_TELEMETRY
10 changes: 9 additions & 1 deletion src/azure-cli-core/azure/cli/core/telemetry.py
Original file line number Diff line number Diff line change
Expand Up @@ -204,7 +204,7 @@ def product_version(self):
def _user_agrees_to_telemetry(func):
@wraps(func)
def _wrapper(*args, **kwargs):
if not _get_config().getboolean('core', 'collect_telemetry', fallback=True):
if not is_telemetry_enabled():
return None
return func(*args, **kwargs)

Expand Down Expand Up @@ -358,6 +358,14 @@ def _add_event(event_name, properties, instrumentation_key=DEFAULT_INSTRUMENTATI
})


@decorators.suppress_all_exceptions()
def is_telemetry_enabled():
from azure.cli.core.cloud import cloud_forbid_telemetry
if cloud_forbid_telemetry(_session.application):
return False
return _get_config().getboolean('core', 'collect_telemetry', fallback=True)


# definitions

@decorators.call_once
Expand Down
18 changes: 18 additions & 0 deletions src/azure-cli-core/azure/cli/core/tests/test_telemetry.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,3 +39,21 @@ def test_extract_parameters_correctly(self):

args = ['vm', 'show', '-g', 'rg', '--name', 'vm1', '-d', '--debug']
self.assertEqual(['-g', '--name', '-d', '--debug'], AzCliCommandInvoker._extract_parameter_names(args))

def test_cloud_forbid_telemetry(self):
import mock
import azure.cli.core.telemetry as telemetry
from azure.cli.core.mock import DummyCli
from knack.completion import ARGCOMPLETE_ENV_NAME

az_cli = DummyCli()
telemetry.set_application(az_cli, ARGCOMPLETE_ENV_NAME)
# mock user turns off telemetry
with mock.patch('knack.config.CLIConfig.getboolean', return_value=False):
self.assertFalse(telemetry.is_telemetry_enabled())
# mock user turns on telemetry
with mock.patch('knack.config.CLIConfig.getboolean', return_value=True):
self.assertTrue(telemetry.is_telemetry_enabled())
# mock to add current cloud name in CLOUDS_FORBIDDING_TELEMETRY
with mock.patch('azure.cli.core.cloud.CLOUDS_FORBIDDING_TELEMETRY', [az_cli.cloud.name]):
self.assertFalse(telemetry.is_telemetry_enabled())
3 changes: 3 additions & 0 deletions src/azure-cli/azure/cli/command_modules/configure/_consts.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,9 @@
' $ az vm create --help\n' \
' $ az feedback\n'

WARNING_CLOUD_FORBID_TELEMETRY = '\nYour current cloud: %s does not allow data collection.' \
' Telemetry is disabled regardless of the configuration.'

MSG_GLOBAL_SETTINGS_LOCATION = 'Your settings can be found at {}'

MSG_HEADING_CURRENT_CONFIG_INFO = 'Your current configuration is as follows:'
Expand Down
14 changes: 11 additions & 3 deletions src/azure-cli/azure/cli/command_modules/configure/custom.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
MSG_PROMPT_TELEMETRY,
MSG_PROMPT_FILE_LOGGING,
MSG_PROMPT_CACHE_TTL,
WARNING_CLOUD_FORBID_TELEMETRY,
DEFAULT_CACHE_TTL)
from azure.cli.command_modules.configure._utils import get_default_from_config

Expand Down Expand Up @@ -96,7 +97,7 @@ def _config_env_public_azure(cli_ctx, _):
logger.error(err)


def _handle_global_configuration(config):
def _handle_global_configuration(config, cloud_forbid_telemetry):
# print location of global configuration
print(MSG_GLOBAL_SETTINGS_LOCATION.format(config.config_path))
# set up the config parsers
Expand All @@ -118,7 +119,10 @@ def _handle_global_configuration(config):
answers['output_type_prompt'] = output_index
answers['output_type_options'] = str(OUTPUT_LIST)
enable_file_logging = prompt_y_n(MSG_PROMPT_FILE_LOGGING, default='n')
allow_telemetry = prompt_y_n(MSG_PROMPT_TELEMETRY, default='y')
if cloud_forbid_telemetry:
allow_telemetry = False
else:
allow_telemetry = prompt_y_n(MSG_PROMPT_TELEMETRY, default='y')
answers['telemetry_prompt'] = allow_telemetry
cache_ttl = None
while not cache_ttl:
Expand All @@ -140,6 +144,7 @@ def _handle_global_configuration(config):

# pylint: disable=inconsistent-return-statements
def handle_configure(cmd, defaults=None, list_defaults=None, scope=None):
from azure.cli.core.cloud import cloud_forbid_telemetry, get_active_cloud_name
if defaults:
defaults_section = cmd.cli_ctx.config.defaults_section_name
with ConfiguredDefaultSetter(cmd.cli_ctx.config, scope.lower() == 'local'):
Expand All @@ -157,8 +162,11 @@ def handle_configure(cmd, defaults=None, list_defaults=None, scope=None):
# if nothing supplied, we go interactively
try:
print(MSG_INTRO)
_handle_global_configuration(cmd.cli_ctx.config)
cloud_forbid_telemetry = cloud_forbid_telemetry(cmd.cli_ctx)
_handle_global_configuration(cmd.cli_ctx.config, cloud_forbid_telemetry)
print(MSG_CLOSING)
if cloud_forbid_telemetry:
logger.warning(WARNING_CLOUD_FORBID_TELEMETRY, get_active_cloud_name(cmd.cli_ctx))
# TODO: log_telemetry('configure', **answers)
except NoTTYException:
raise CLIError('This command is interactive and no tty available.')
Expand Down