Ejemplo n.º 1
0
    def get_version_data(self):
        """Gets app_versions data by pages. Pages that were already accessed would be stored in history

        Then modifies app_versions: add SinceCreated field and format DateCreated field for each version in app_versions.
        Paginates, so appends PAGE_LENGTH versions with each call

        :returns data object with two keys: environment and app_versions
        note: environment data would be None if no environment is specified
        """

        if self.list_len_left <= 0:
            return self.get_table_data()

        if self.next_token:
            response = elasticbeanstalk.get_application_versions(self.app_name, None, self.PAGE_LENGTH, self.next_token)
        else:
            response = elasticbeanstalk.get_application_versions(self.app_name, None, self.PAGE_LENGTH)

        new_page_versions = response['ApplicationVersions']
        self.next_token = None
        if u'NextToken' in response:
            self.next_token = response['NextToken']

        self.prep_version_data(new_page_versions)
        self.history.append(self.app_versions)
        self.curr_page += 1

        return self.get_table_data()
Ejemplo n.º 2
0
    def get_version_data(self):
        """
        Gets app_versions data by pages. Pages that were already accessed would be
        stored in history

        Then modifies app_versions: add SinceCreated field and format DateCreated
        field for each version in app_versions. Paginates, so appends PAGE_LENGTH
        versions with each call

        :returns data object with two keys: environment and app_versions
        note: environment data would be None if no environment is specified
        """

        if self.list_len_left <= 0:
            return self.get_table_data()

        if self.next_token:
            response = elasticbeanstalk.get_application_versions(
                self.app_name, None, self.PAGE_LENGTH, self.next_token)
        else:
            response = elasticbeanstalk.get_application_versions(
                self.app_name, None, self.PAGE_LENGTH)

        new_page_versions = response['ApplicationVersions']
        self.next_token = None
        if u'NextToken' in response:
            self.next_token = response['NextToken']

        self.prep_version_data(new_page_versions)
        self.history.append(self.app_versions)
        self.curr_page += 1

        return self.get_table_data()
Ejemplo n.º 3
0
def delete_app_version_label(app_name, version_label):

    if version_label:
        # check if version_label exists under app_name
        app_versions = elasticbeanstalk.get_application_versions(app_name)['ApplicationVersions']
        #  if the given version label does not exist at all!
        if not any(version_label == app_version['VersionLabel'] for app_version in app_versions):
            raise ValidationError(strings['appversion.delete.notfound'].format(app_name, version_label))

        envs = elasticbeanstalk.get_app_environments(app_name)

        versions_in_use = [(e.version_label, e.name) for e in envs]

        # find all the environments that are using the app version
        used_envs = [version[1] for version in versions_in_use if version[0] == version_label]

        if used_envs:
            raise ValidationError(strings['appversion.delete.deployed'].format(version_label, ','.join(used_envs)))

        try:
            io.validate_action(prompts['appversion.delete.validate'].format(version_label), "y")
            elasticbeanstalk.delete_application_version(app_name, version_label)
            io.echo('Application Version deleted successfully.')
            delete_successful = True
        except ValidationError:
            io.echo('Application Version will not be deleted.')
            delete_successful = False

        return delete_successful
    else:
        raise NotFoundError(strings['appversion.delete.none'])
Ejemplo n.º 4
0
def stream_build_configuration_app_version_creation(app_name,
                                                    app_version_label):
    # Get the CloudWatch logs link
    successfully_generated = wait_for_app_version_attribute(
        app_name, [app_version_label], 'BuildArn', timeout=1)
    app_version_response = elasticbeanstalk.get_application_versions(
        app_name, version_labels=[app_version_label])['ApplicationVersions']

    build_response = codebuild.batch_get_builds([app_version_response[0]['BuildArn']]) \
        if successfully_generated else None

    if build_response is not None and 'logs' in build_response['builds'][0]:
        log_link_text = strings['codebuild.buildlogs'].replace(
            '{logs_link}', build_response['builds'][0]['logs']['deepLink'])
        io.echo(log_link_text)
    else:
        io.log_warning("Could not retrieve CloudWatch link for CodeBuild logs")

    # Wait for the success events
    try:
        from ebcli.operations.commonops import wait_for_success_events
        wait_for_success_events(None,
                                timeout_in_minutes=5,
                                can_abort=False,
                                version_label=app_version_label)
    except ServiceError as ex:
        LOG.debug(
            "Caught service error while creating application version '{0}' "
            "deleting the created applicaiton version as it is useless now.")
        elasticbeanstalk.delete_application_version(app_name,
                                                    app_version_label)
        raise ex
Ejemplo n.º 5
0
def delete_app_version_label(app_name, version_label):

    if version_label:
        # check if version_label exists under app_name
        app_versions = elasticbeanstalk.get_application_versions(app_name)['ApplicationVersions']
        #  if the given version label does not exist at all!
        if not any(version_label == app_version['VersionLabel'] for app_version in app_versions):
            raise ValidationError(strings['appversion.delete.notfound'].format(app_name, version_label))

        envs = elasticbeanstalk.get_app_environments(app_name)

        versions_in_use = [(e.version_label, e.name) for e in envs]

        # find all the environments that are using the app version
        used_envs = [version[1] for version in versions_in_use if version[0] == version_label]

        if used_envs:
            raise ValidationError(strings['appversion.delete.deployed'].format(version_label, ','.join(used_envs)))

        try:
            io.validate_action(prompts['appversion.delete.validate'].format(version_label), "y")
            elasticbeanstalk.delete_application_version(app_name, version_label)
            io.echo('Application Version deleted successfully.')
            delete_successful = True
        except ValidationError:
            io.echo('Application Version will not be deleted.')
            delete_successful = False

        return delete_successful
    else:
        raise NotFoundError(strings['appversion.delete.none'])
Ejemplo n.º 6
0
def wait_for_app_version_attribute(app_name, version_labels, timeout=5):
    io.echo('--- Waiting for Application Versions to populate attributes ---')
    versions_to_check = list(version_labels)
    found = dict.fromkeys(version_labels)
    failed = dict.fromkeys(version_labels)
    start_time = datetime.utcnow()
    timediff = timedelta(minutes=timeout)
    while versions_to_check:
        if _timeout_reached(start_time, timediff):
            io.log_error(strings['appversion.attribute.failed'].replace(
                '{app_version}', ', '.join(version_labels)))
            return False
        io.LOG.debug('Retrieving app versions.')
        app_versions = elasticbeanstalk.get_application_versions(
            app_name, versions_to_check)['ApplicationVersions']
        for version in app_versions:
            if version.get('BuildArn'):
                found[version['VersionLabel']] = True
                io.echo(strings['appversion.attribute.success'].format(
                    app_version=version['VersionLabel']))
                versions_to_check.remove(version['VersionLabel'])
            elif version.get('Status') == 'FAILED':
                failed[version['VersionLabel']] = True
                io.log_error(strings['appversion.attribute.failed'].format(
                    app_version=version['VersionLabel']))
                versions_to_check.remove(version['VersionLabel'])

        if all(found.values()):
            return True

        _sleep()

    return not any(failed.values())
Ejemplo n.º 7
0
 def interactive_list_version(self):
     """Interactive mode which allows user to see previous
     versions and allow a choice to:
     - deploy a different version.
     - delete a certain version
     Run when the user supplies no argument to the --delete flag.
     """
     app_versions = elasticbeanstalk.get_application_versions(self.app_name)['ApplicationVersions']
     appversionops.display_versions(self.app_name, self.env_name, app_versions)
Ejemplo n.º 8
0
 def interactive_list_version(self):
     """Interactive mode which allows user to see previous
     versions and allow a choice to:
     - deploy a different version.
     - delete a certain version
     Run when the user supplies no argument to the --delete flag.
     """
     app_versions = elasticbeanstalk.get_application_versions(self.app_name)['ApplicationVersions']
     appversionops.display_versions(self.app_name, self.env_name, app_versions)
Ejemplo n.º 9
0
    def do_command(self):
        app_name = self.get_app_name()
        num_to_leave = self.app.pargs.num_to_leave
        older_than = self.app.pargs.older_than
        force = self.app.pargs.force

        envs = elasticbeanstalk.get_app_environments(app_name)
        versions_in_use = [e.version_label for e in envs]

        app_versions = elasticbeanstalk.get_application_versions(
            app_name)['ApplicationVersions']
        app_versions.sort(key=itemgetter('DateUpdated'), reverse=True)

        # Filter out versions currently being used
        app_versions = [
            v for v in app_versions if v['VersionLabel'] not in versions_in_use
        ]

        total_num_unused_versions = len(app_versions)

        if total_num_unused_versions < num_to_leave:
            io.echo(
                'Not enough unused application version to leave behind {0}; No application versions to delete.'
                .format(num_to_leave))
            return

        # Filter out versions newer than filter date
        app_versions = [
            v for v in app_versions if utils.get_delta_from_now_and_datetime(
                v['DateUpdated']).days > older_than
        ]

        # dont include most recent
        app_versions = app_versions[num_to_leave:]

        if app_versions:
            if not force:
                response = io.get_boolean_response(
                    '{} application versions will be deleted. '
                    'Continue?'.format(len(app_versions)))
                if not response:
                    return
        else:
            io.echo('No application versions to delete.')
            return

        for version in app_versions:
            label = version['VersionLabel']
            try:
                elasticbeanstalk.delete_application_version(app_name, label)
            except ServiceError as e:
                io.log_warning('Error deleting version {0}. Error: {1}'.format(
                    label, e.message))
Ejemplo n.º 10
0
def stream_build_configuration_app_version_creation(app_name, app_version_label, build_spec):
    # Get the CloudWatch logs link
    successfully_generated = wait_for_app_version_attribute(
        app_name,
        [app_version_label],
        timeout=1
    )
    app_version_response = elasticbeanstalk.get_application_versions(
        app_name,
        version_labels=[app_version_label]
    )['ApplicationVersions']

    build_response = codebuild.batch_get_builds([app_version_response[0]['BuildArn']]) \
        if successfully_generated else None

    codebuild_timeout = build_spec.timeout or 60
    if build_response is not None and 'logs' in build_response['builds'][0]:
        log_link_text = strings['codebuild.buildlogs'].replace(
            '{logs_link}',
            build_response['builds'][0]['logs']['deepLink']
        )
        io.echo(log_link_text)
        io.echo(
            "NOTE: The CodeBuild timeout is set to {0} minutes, so this "
            "operation may take upto '{0}' minutes to complete.".format(codebuild_timeout)
        )
    else:
        io.log_warning("Could not retrieve CloudWatch link for CodeBuild logs")

    try:
        # Need to lazy-import `ebcli.lib.commonops` because `pytest` is unable to load it
        # at module load-time using Python 2.7 and Python 3.4
        from ebcli.operations import commonops
        timeout_error_message = ' '.join([
            'The CodeBuild build timed out after {} minute(s).'.format(codebuild_timeout),
            "To increase the time limit, use the 'Timeout' option in the 'buildspec.yml' file."
        ])
        commonops.wait_for_success_events(
            app_name=app_name,
            can_abort=False,
            request_id=None,
            timeout_error_message=timeout_error_message,
            timeout_in_minutes=codebuild_timeout,
            version_label=app_version_label
        )

    except ServiceError as exception:
        LOG.debug("Caught service error while creating application version '{0}' "
                  "deleting the created application version as it is useless now.".format(app_version_label))
        elasticbeanstalk.delete_application_version(app_name, app_version_label)
        raise exception
Ejemplo n.º 11
0
def wait_for_app_version_attribute(app_name,
                                   version_labels,
                                   attribute,
                                   timeout=5):
    versions_to_check = list(version_labels)
    found = {}
    failed = {}
    io.echo('--- Waiting for Application Versions to populate attributes ---')
    for version in version_labels:
        found[version] = False
        failed[version] = False
    start_time = datetime.utcnow()
    while not all([(found[version] or failed[version])
                   for version in versions_to_check]):
        if datetime.utcnow() - start_time >= timedelta(minutes=timeout):
            io.log_error(strings['appversion.attribute.failed'].replace(
                '{app_version}', version_labels))
            return False
        io.LOG.debug('Retrieving app versions.')
        app_versions = elasticbeanstalk.get_application_versions(
            app_name, versions_to_check)['ApplicationVersions']
        for version in app_versions:
            if attribute in version:
                if version[attribute] is not None:
                    found[version['VersionLabel']] = True
                    io.echo(strings['appversion.attribute.success'].replace(
                        '{app_version}', version['VersionLabel']))
                    versions_to_check.remove(version['VersionLabel'])
            elif 'Status' in version and (version['Status'] == 'FAILED'
                                          or version['Status'] == 'FAILED'):
                failed[version['VersionLabel']] = True
                io.log_error(strings['appversion.attribute.failed'].replace(
                    '{app_version}', version['VersionLabel']))
                versions_to_check.remove(version['VersionLabel'])

        if all(found.values()):
            return True

        time.sleep(4)

    if any(failed.values()):
        return False

    return True
Ejemplo n.º 12
0
def cleanup_application_versions(app_name):
    io.echo('Removing application versions from s3.')
    versions = elasticbeanstalk.get_application_versions(
        app_name)['ApplicationVersions']
    buckets = defaultdict(list)
    for version in versions:
        bundle = version.get('SourceBundle', {})
        bucket = bundle.get('S3Bucket')
        key = bundle.get('S3Key')
        if bucket and key:
            buckets[bucket].append(key)

    for bucket, keys in six.iteritems(buckets):
        try:
            s3.delete_objects(bucket, keys)
        except NotAuthorizedError:
            io.log_warning(
                'Error deleting application versions from bucket "{0}"'.format(
                    bucket))
Ejemplo n.º 13
0
def download_source_bundle(app_name, env_name):
    env = elasticbeanstalk.get_environment(app_name=app_name,
                                           env_name=env_name)
    if env.version_label and env.version_label != 'Sample Application':
        app_version = elasticbeanstalk.get_application_versions(
            app_name,
            version_labels=[env.version_label])['ApplicationVersions'][0]

        source_bundle = app_version['SourceBundle']
        bucket_name = source_bundle['S3Bucket']
        key_name = source_bundle['S3Key']
        io.echo('Downloading application version...')
        data = s3.get_object(bucket_name, key_name)
        filename = get_filename(key_name)
    else:
        # sample app
        template = cloudformation.get_template('awseb-' + env.id + '-stack')
        try:
            url = template['TemplateBody']['Parameters']['AppSource'][
                'Default']
        except KeyError:
            raise NotFoundError('Can not find app source for environment')
        utils.get_data_from_url(url)
        io.echo('Downloading application version...')
        data = utils.get_data_from_url(url, timeout=30)
        filename = 'sample.zip'

    fileoperations.make_eb_dir('downloads/')
    location = fileoperations.get_eb_file_full_location('downloads/' +
                                                        filename)
    fileoperations.write_to_data_file(location, data)
    io.echo('Application version downloaded to:', location)

    cwd = os.getcwd()
    try:
        fileoperations._traverse_to_project_root()
        if heuristics.directory_is_empty():
            # If we dont have any project code, unzip as current project
            io.echo('Unzipping application version as project files.')
            fileoperations.unzip_folder(location, os.getcwd())
            io.echo('Done.')
    finally:
        os.chdir(cwd)
Ejemplo n.º 14
0
def wait_for_processed_app_versions(app_name, version_labels, timeout=5):
    versions_to_check = list(version_labels)
    processed = {}
    failed = {}
    io.echo('--- Waiting for Application Versions to be pre-processed ---')
    for version in version_labels:
        processed[version] = False
        failed[version] = False
    start_time = datetime.utcnow()
    timediff = timedelta(seconds=timeout * 60)
    while not all([(processed[version] or failed[version]) for version in versions_to_check]):
        if _timeout_reached(start_time, timediff):
            io.log_error(strings['appversion.processtimeout'])
            return False
        io.LOG.debug('Retrieving app versions.')
        app_versions = elasticbeanstalk.get_application_versions(
            app_name,
            versions_to_check
        )["ApplicationVersions"]

        for v in app_versions:
            if v['Status'] == 'PROCESSED':
                processed[v['VersionLabel']] = True
                io.echo('Finished processing application version {}'
                        .format(v['VersionLabel']))
                versions_to_check.remove(v['VersionLabel'])

            elif v['Status'] == 'FAILED':
                failed[v['VersionLabel']] = True
                io.log_error(strings['appversion.processfailed'].replace('{app_version}',
                                                                         v['VersionLabel']))
                versions_to_check.remove(v['VersionLabel'])

        if all(processed.values()):
            return True

        _sleep(4)

    if any(failed.values()):
        io.log_error(strings['appversion.cannotdeploy'])
        return False
    return True
Ejemplo n.º 15
0
def get_quick_link(app_name, env_name):
    env = elasticbeanstalk.get_environment(app_name=app_name,
                                           env_name=env_name)
    settings = elasticbeanstalk.describe_configuration_settings(
        app_name, env_name)
    option_settings = settings['OptionSettings']

    environment_type = elasticbeanstalk.get_option_setting(
        option_settings, 'aws:elasticbeanstalk:environment', 'EnvironmentType')
    instance_type = elasticbeanstalk.get_option_setting(
        option_settings, 'aws:autoscaling:launchconfiguration', 'InstanceType')

    link = 'https://console.aws.amazon.com/elasticbeanstalk/home?'
    # add region
    region = aws.get_region_name()
    link += 'region=' + urllib.parse.quote(region)
    # add quicklaunch flag
    link += '#/newApplication'
    # add application name
    link += '?applicationName=' + urllib.parse.quote(app_name)
    # add solution stack
    link += '&solutionStackName=' + urllib.parse.quote(
        env.platform.platform_shorthand)
    # add
    link += '&tierName=' + env.tier.name
    if environment_type:
        link += '&environmentType=' + environment_type
    if env.version_label:
        app_version = elasticbeanstalk.get_application_versions(
            app_name,
            version_labels=[env.version_label])['ApplicationVersions'][0]
        source_bundle = app_version['SourceBundle']
        source_url = 'https://s3.amazonaws.com/' + source_bundle['S3Bucket'] + \
                     '/' + source_bundle['S3Key']
        link += '&sourceBundleUrl=' + source_url
    if instance_type:
        link += '&instanceType=' + instance_type

    link = _add_database_options(link, option_settings)
    link = _add_vpc_options(link, option_settings)

    io.echo(link)
Ejemplo n.º 16
0
def stream_build_configuration_app_version_creation(app_name, app_version_label, build_spec):
    # Get the CloudWatch logs link
    successfully_generated = wait_for_app_version_attribute(app_name, [app_version_label], 'BuildArn', timeout=1)
    app_version_response = elasticbeanstalk.get_application_versions(app_name, version_labels=[app_version_label])['ApplicationVersions']

    build_response = codebuild.batch_get_builds([app_version_response[0]['BuildArn']]) \
        if successfully_generated else None

    codebuild_timeout = build_spec.timeout or 60
    if build_response is not None and 'logs' in build_response['builds'][0]:
        log_link_text = strings['codebuild.buildlogs'].replace('{logs_link}',
                                                               build_response['builds'][0]['logs']['deepLink'])
        io.echo(log_link_text)
        io.echo("NOTE: The CodeBuild timeout is set to {0} minutes, so this operation may take upto '{0}' minutes to complete.".format(codebuild_timeout))
    else:
        io.log_warning("Could not retrieve CloudWatch link for CodeBuild logs")

    # Wait for the success events
    try:
        # Need to lazy-import `ebcli.lib.commonops` because `pytest` is unable to load it
        # at module load-time using Python 2.7 and Python 3.4
        from ebcli.operations import commonops
        timeout_error_message = ' '.join([
            'The CodeBuild build timed out after {} minute(s).'.format(codebuild_timeout),
            "To increase the time limit, use the 'Timeout' option in the 'buildspec.yml' file."
        ])
        commonops.wait_for_success_events(
            app_name=app_name,
            can_abort=False,
            request_id=None,
            timeout_error_message=timeout_error_message,
            timeout_in_minutes=codebuild_timeout,
            version_label=app_version_label
        )

    except ServiceError as exception:
        LOG.debug("Caught service error while creating application version '{0}' "
                  "deleting the created application version as it is useless now.".format(app_version_label))
        elasticbeanstalk.delete_application_version(app_name, app_version_label)
        raise exception
Ejemplo n.º 17
0
def delete_app_version_label(app_name, version_label):

    if version_label:
        app_versions = elasticbeanstalk.get_application_versions(
            app_name)['ApplicationVersions']
        if not any(version_label == app_version['VersionLabel']
                   for app_version in app_versions):
            raise ValidationError(strings['appversion.delete.notfound'].format(
                app_name, version_label))

        envs = elasticbeanstalk.get_app_environments(app_name)

        versions_in_use = [(e.version_label, e.name) for e in envs]

        used_envs = [
            version[1] for version in versions_in_use
            if version[0] == version_label
        ]

        if used_envs:
            raise ValidationError(strings['appversion.delete.deployed'].format(
                version_label, ','.join(used_envs)))

        should_delete = io.get_boolean_response(
            text=prompts['appversion.delete.validate'].format(version_label),
            default=True)
        if not should_delete:
            io.echo('Application Version will not be deleted.')
            delete_successful = False
        else:
            elasticbeanstalk.delete_application_version(
                app_name, version_label)
            io.echo('Application Version deleted successfully.')
            delete_successful = True

        return delete_successful
    else:
        raise NotFoundError(strings['appversion.delete.none'])
Ejemplo n.º 18
0
def wait_for_app_version_attribute(app_name, version_labels, attribute, timeout=5):
    versions_to_check = list(version_labels)
    found = {}
    failed = {}
    io.echo('--- Waiting for Application Versions to populate attributes ---')
    for version in version_labels:
        found[version] = False
        failed[version] = False
    start_time = datetime.utcnow()
    while not all([(found[version] or failed[version]) for version in versions_to_check]):
        if datetime.utcnow() - start_time >= timedelta(minutes=timeout):
            io.log_error(strings['appversion.attribute.failed'].replace('{app_version}', version_labels))
            return False
        io.LOG.debug('Retrieving app versions.')
        app_versions = elasticbeanstalk.get_application_versions(app_name, versions_to_check)['ApplicationVersions']
        for version in app_versions:
            if attribute in version:
                if version[attribute] is not None:
                    found[version['VersionLabel']] = True
                    io.echo(strings['appversion.attribute.success'].replace('{app_version}', version['VersionLabel']))
                    versions_to_check.remove(version['VersionLabel'])
            elif 'Status' in version and (version['Status'] == 'FAILED' or version['Status'] == 'FAILED'):
                failed[version['VersionLabel']] = True
                io.log_error(strings['appversion.attribute.failed'].replace('{app_version}',
                                                                         version['VersionLabel']))
                versions_to_check.remove(version['VersionLabel'])

        if all(found.values()):
            return True

        time.sleep(4)

    if any(failed.values()):
        return False

    return True