in src/setup.py [0:0]
def main():
CMD = namedtuple("cmd", "cmd, msg")
COLLECTD_INFO = get_collectd_info()
STOP_COLLECTD_CMD = CMD("pkill collectd", "Stopping collectd process")
START_COLLECTD_CMD = CMD(COLLECTD_INFO.exec_path, "Starting collectd process")
DOWNLOAD_PLUGIN_CMD = CMD("curl -sL https://github.com/" + GITHUB_USER_NAME + "/collectd-cloudwatch/tarball/" + GITHUB_REPO_BRANCH + " > " + TAR_FILE, "Downloading plugin")
UNTAR_PLUGIN_CMD = CMD("tar zxf " + TAR_FILE, "Extracting plugin")
COPY_CMD = "\cp -rf {source} {target}"
COPY_PLUGIN_CMD = CMD(COPY_CMD.format(source=NEW_PLUGIN_FILES, target=CollectdInfo.PLUGINS_DIR), "Moving to collectd plugins directory")
COPY_PLUGIN_INCLUDE_FILE_CMD = CMD(COPY_CMD.format(source=PLUGIN_INCLUDE_CONFIGURATION, target="/etc/"), "Copying CloudWatch plugin include file")
COPY_RECOMMENDED_COLLECTD_CONFIG_CMD = CMD(COPY_CMD.format(source=RECOMMENDED_COLLECTD_CONFIGURATION, target=COLLECTD_INFO.config_path), "Replacing collectd configuration")
BACKUP_COLLECTD_CONFIG_CMD = CMD(COPY_CMD.format(source=COLLECTD_INFO.config_path, target=COLLECTD_INFO.config_path + "." + time.strftime(TIMESTAMP_FORMAT)),
"Creating backup of the original configuration")
REPLACE_WHITELIST_CMD = CMD(COPY_CMD.format(source=RECOMMENDED_WHITELIST, target=DEFAULT_PLUGIN_CONFIGURATION_DIR), "Replacing whitelist configuration")
parser = argparse.ArgumentParser(
formatter_class=argparse.ArgumentDefaultsHelpFormatter,
description='Script for custom installation process for collectd AWS CloudWatch plugin'
)
parser.add_argument(
'-I', '--non_interactive', required=False,
help='Non interactive mode',
default=False, action='store_true'
)
parser.add_argument(
'-H', '--host_name', required=False,
help='Manual override for EC2 Instance ID and Host information propagated by collectd',
metavar='HOST_NAME', default=None
)
parser.add_argument(
'-r', '--region', required=False,
help='Manual override for region used to publish metrics',
metavar='REGION', default=None
)
parser.add_argument(
'-n', '--proxy_name', required=False,
help='Proxy server name',
metavar='NAME', default=None
)
parser.add_argument(
'-p', '--proxy_port', required=False,
help='Proxy server port',
metavar='PORT', default=None
)
parser.add_argument(
'-e', '--enable_high_resolution_metrics', required=False,
help='Enable high resolution metrics',
default=False, action='store_true'
)
parser.add_argument(
'-f', '--flush_interval', required=False,
help='Flush interval (in seconds)',
metavar='FLUSH_INTERVAL', default=None
)
parser.add_argument(
'-a', '--access_key', required=False,
help='AWS IAM user access key',
metavar='ACCESS_KEY', default=None
)
parser.add_argument(
'-s', '--secret_key', required=False,
help='AWS IAM user secret key',
metavar='SECRET_KEY', default=None
)
parser.add_argument(
'-P', '--creds_path', required=False,
help='Absolute path to AWS credentials file',
metavar='CREDENTIALS_PATH', default=None
)
parser.add_argument(
'-m', '--installation_method', required=False,
help='Choose how to install CloudWatch plugin in collectd',
choices=['recommended', 'add', 'not_modify'],
metavar='recommended|add|not_modify', default=None
)
parser.add_argument(
'-g', '--push_asg', required=False,
help='Include the Auto-Scaling Group name as a metric dimension:',
default=False, action='store_true'
)
parser.add_argument(
'-c', '--push_constant', required=False,
help='Include the FixedDimension as a metric dimension',
default=None, action='store_true'
)
parser.add_argument(
'-v', '--dimension_value', required=False,
help='FixedDimension value',
metavar='DIMENSION_VALUE', default=None
)
parser.add_argument(
'-d', '--debug', default=False,
action='store_true', help='Provides verbose logging of metrics emitted to CloudWatch'
)
parser.add_argument(
'-D', '--debug_setup', default=False,
action='store_true', help='Provides verbose logging during setup process'
)
args = parser.parse_args()
if args.proxy_port is None and args.proxy_name or args.proxy_port and args.proxy_name is None:
parser.error('To enable proxy, use both --proxy_name and --proxy_port ')
if args.access_key is None and args.secret_key or args.access_key and args.secret_key is None:
parser.error('For IAM credentials, use both --secret_key and --access_key')
if args.push_constant is None and args.dimension_value:
parser.error('To include the FixedDimension as a metric dimension, '
'use both --push_constant and --dimension_value')
if args.creds_path and args.secret_key is None and args.access_key is None:
parser.error('Credential path (--creds_path) used only with --secret_key and --access_key arguments')
non_interactive = args.non_interactive
host = args.host_name
region = args.region
proxy_name = args.proxy_name
proxy_port = args.proxy_port
enable_high_resolution_metrics = args.enable_high_resolution_metrics
flush_interval = args.flush_interval
access_key = args.access_key
secret_key = args.secret_key
creds_path = args.creds_path
installation_method = args.installation_method
push_asg = args.push_asg
push_constant = args.push_constant
dimension_value = args.dimension_value
debug_setup = args.debug_setup
debug = args.debug
def install_plugin():
try:
# "python-pip", "python-setuptools" will pull in the python2.6 runtime
# Since python with version >= 2.7 should install pip and setuptools by default, we
# can ignore the system dependencies
if not ( is_pip_installed() and is_setupTools_installed() ):
install_packages(["python-pip", "python-setuptools"])
install_python_packages(PYTHON_DEPENDENCIES)
create_directory_structure()
chdir(TEMP_DIRECTORY)
_run_command(DOWNLOAD_PLUGIN_CMD, shell=True, exit_on_failure=True)
_run_command(UNTAR_PLUGIN_CMD, exit_on_failure=True)
_run_command(COPY_PLUGIN_CMD, shell=True, exit_on_failure=True)
supply_config()
restart_collectd()
finally:
remove_temp_dir()
def create_directory_structure():
try:
make_dirs(TEMP_DIRECTORY)
make_dirs(CollectdInfo.PLUGINS_DIR)
except IOError:
raise InstallationFailedException("Cannot create required directories.")
def supply_config():
if COLLECTD_INFO.is_supported_version():
_run_command(COPY_PLUGIN_INCLUDE_FILE_CMD, shell=True)
config = PluginConfig()
_prepare_plugin_config(config)
if config.use_recommended_collectd_config:
_copy_recommended_configs()
elif config.only_add_plugin:
_inject_plugin_configuration()
else:
print Color.yellow("Please find instructions for the manual configuration of the plugin in the readme.md file.")
else:
raise InstallationFailedException("The minimum supported version of collectd is " + CollectdInfo.MIN_SUPPORTED_VERSION + \
", and your version is " + COLLECTD_INFO.version + \
". You need to upgrade collectd before proceeding with the plugin installation.")
def _prepare_plugin_config(plugin_config):
metadata_reader = MetadataReader()
InteractiveConfigurator(plugin_config, metadata_reader, COLLECTD_INFO,
non_interactive, region, host, proxy_name,
proxy_port, enable_high_resolution_metrics,
flush_interval, access_key, secret_key,
creds_path, installation_method, push_asg,
push_constant, dimension_value, debug_setup,
debug).run()
PluginConfigWriter(plugin_config).write()
def _inject_plugin_configuration():
if _is_cloudwatch_plugin_configured():
print Color.yellow("CloudWatch collectd plugin is already configured in the existing collectd.conf file.")
elif _can_safely_add_python_plugin():
with open(COLLECTD_INFO.config_path, "a") as config:
config.write(PLUGIN_CONFIGURATION_INCLUDE_LINE)
else:
print Color.yellow("Cannot add CloudWatch collectd plugin automatically to the existing collectd configuration.\n"
"Plugin must be configured manually, please find instructions in readme.md file.")
def _copy_recommended_configs():
_run_command(BACKUP_COLLECTD_CONFIG_CMD)
_run_command(COPY_RECOMMENDED_COLLECTD_CONFIG_CMD, shell=True)
_run_command(REPLACE_WHITELIST_CMD, shell=True)
def _can_safely_add_python_plugin():
configs = [COLLECTD_INFO.config_path]
configs += _find_custom_includes(COLLECTD_INFO.config_path)
return not any(_is_python_plugin_configured(config) for config in configs)
def _is_cloudwatch_plugin_configured():
with open(COLLECTD_INFO.config_path) as config:
return bool(CLOUD_WATCH_COLLECTD_DETECTION_REGEX.findall(config.read()))
def _find_custom_includes(config_path):
with open(config_path) as config:
return COLLECTD_CONFIG_INCLUDE_REGEX.findall(config.read())
def _is_python_plugin_configured(config_path):
with open(config_path) as config:
return bool(COLLECTD_PYTHON_PLUGIN_CONFIGURATION_REGEX.findall(config.read()))
def restart_collectd():
_run_command(STOP_COLLECTD_CMD)
_run_command(START_COLLECTD_CMD, exit_on_failure=True)
def remove_temp_dir():
shutil.rmtree(TEMP_DIRECTORY, ignore_errors=True)
def _run_command(command, exit_on_failure=False, shell=False):
Command(command.cmd, command.msg, shell=shell, exit_on_failure=exit_on_failure).run()
install_plugin()