def main():
    module = KatelloEntityAnsibleModule(
        argument_spec=dict(updated_name=dict(), ),
        entity_spec=dict(
            name=dict(required=True),
            description=dict(),
        ),
    )

    entity_dict = module.clean_params()

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        entity = module.find_resource_by_name('host_collections',
                                              name=entity_dict['name'],
                                              params=scope,
                                              failsafe=True)

        if entity and 'updated_name' in entity_dict:
            entity_dict['name'] = entity_dict.pop('updated_name')

        module.ensure_entity('host_collections',
                             entity_dict,
                             entity,
                             params=scope)
def main():
    module = KatelloEntityAnsibleModule(
        argument_spec=dict(
            manifest_path=dict(type='path'),
            state=dict(default='present', choices=['absent', 'present', 'refreshed']),
            repository_url=dict(aliases=['redhat_repository_url']),
        ),
        foreman_spec=dict(
            organization=dict(type='entity', required=True, thin=False),
        ),
        required_if=[
            ['state', 'present', ['manifest_path']],
        ],
        supports_check_mode=False,
    )

    module.task_timeout = 5 * 60

    with module.api_connection():
        organization = module.lookup_entity('organization')
        scope = module.scope_for('organization')

        try:
            existing_manifest = organization['owner_details']['upstreamConsumer']
        except KeyError:
            existing_manifest = None

        if module.state == 'present':
            if 'repository_url' in module.foreman_params:
                payload = {'redhat_repository_url': module.foreman_params['repository_url']}
                org_spec = dict(id=dict(), redhat_repository_url=dict())
                organization = module.ensure_entity('organizations', payload, organization, state='present', foreman_spec=org_spec)

            try:
                with open(module.foreman_params['manifest_path'], 'rb') as manifest_file:
                    files = {'content': (module.foreman_params['manifest_path'], manifest_file, 'application/zip')}
                    params = {}
                    if 'repository_url' in module.foreman_params:
                        params['repository_url'] = module.foreman_params['repository_url']
                    params.update(scope)
                    result = module.resource_action('subscriptions', 'upload', params, files=files, record_change=False, ignore_task_errors=True)
                    for error in result['humanized']['errors']:
                        if "same as existing data" in error:
                            # Nothing changed, but everything ok
                            break
                        if "older than existing data" in error:
                            module.fail_json(msg="Manifest is older than existing data.")
                        else:
                            module.fail_json(msg="Upload of the manifest failed: %s" % error)
                    else:
                        module.set_changed()
            except IOError as e:
                module.fail_json(msg="Unable to read the manifest file: %s" % e)
        elif module.desired_absent and existing_manifest:
            module.resource_action('subscriptions', 'delete_manifest', scope)
        elif module.state == 'refreshed':
            if existing_manifest:
                module.resource_action('subscriptions', 'refresh_manifest', scope)
            else:
                module.fail_json(msg="No manifest found to refresh.")
Ejemplo n.º 3
0
def main():
    module = KatelloEntityAnsibleModule(
        argument_spec=dict(
            product=dict(required=True),
        ),
        entity_spec=dict(
            label=dict(),
            name=dict(required=True),
            content_type=dict(required=True, choices=['docker', 'ostree', 'yum', 'puppet', 'file', 'deb']),
            url=dict(),
            gpg_key=dict(type='entity'),
            ssl_ca_cert=dict(type='entity'),
            ssl_client_cert=dict(type='entity'),
            ssl_client_key=dict(type='entity'),
            download_policy=dict(choices=['background', 'immediate', 'on_demand']),
            mirror_on_sync=dict(type='bool', default=True),
            upstream_username=dict(),
            upstream_password=dict(no_log=True),
            docker_upstream_name=dict(),
            docker_tags_whitelist=dict(type='list'),
            deb_errata_url=dict(),
            deb_releases=dict(),
            deb_components=dict(),
            deb_architectures=dict(),
            state=dict(default='present', choices=['present_with_defaults', 'present', 'absent']),
        ),
    )

    entity_dict = module.clean_params()

    if entity_dict['content_type'] != 'docker':
        invalid_list = [key for key in ['docker_upstream_name', 'docker_tags_whitelist'] if key in entity_dict]
        if invalid_list:
            module.fail_json(msg="({0}) can only be used with content_type 'docker'".format(",".join(invalid_list)))

    if entity_dict['content_type'] != 'deb':
        invalid_list = [key for key in ['deb_errata_url', 'deb_releases', 'deb_components', 'deb_architectures'] if key in entity_dict]
        if invalid_list:
            module.fail_json(msg="({0}) can only be used with content_type 'deb'".format(",".join(invalid_list)))

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        entity_dict['product'] = module.find_resource_by_name('products', name=entity_dict['product'], params=scope, thin=True)

        if not module.desired_absent:
            if 'gpg_key' in entity_dict:
                entity_dict['gpg_key'] = module.find_resource_by_name('content_credentials', name=entity_dict['gpg_key'], params=scope, thin=True)
            if 'ssl_ca_cert' in entity_dict:
                entity_dict['ssl_ca_cert'] = module.find_resource_by_name('content_credentials', name=entity_dict['ssl_ca_cert'], params=scope, thin=True)
            if 'ssl_client_cert' in entity_dict:
                entity_dict['ssl_client_cert'] = module.find_resource_by_name('content_credentials',
                                                                              name=entity_dict['ssl_client_cert'], params=scope, thin=True)
            if 'ssl_client_key' in entity_dict:
                entity_dict['ssl_client_key'] = module.find_resource_by_name('content_credentials', name=entity_dict['ssl_client_key'], params=scope, thin=True)

        scope['product_id'] = entity_dict['product']['id']
        entity = module.find_resource_by_name('repositories', name=entity_dict['name'], params=scope, failsafe=True)

        module.ensure_entity('repositories', entity_dict, entity, params=scope)
Ejemplo n.º 4
0
def main():
    module = KatelloEntityAnsibleModule(entity_spec=dict(
        name=dict(required=True),
        label=dict(),
        gpg_key=dict(type='entity'),
        ssl_ca_cert=dict(type='entity'),
        ssl_client_cert=dict(type='entity'),
        ssl_client_key=dict(type='entity'),
        sync_plan=dict(type='entity'),
        description=dict(),
        state=dict(default='present',
                   choices=['present_with_defaults', 'present', 'absent']),
    ), )

    entity_dict = module.clean_params()

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        entity = module.find_resource_by_name('products',
                                              name=entity_dict['name'],
                                              params=scope,
                                              failsafe=True)

        if not module.desired_absent:
            if 'gpg_key' in entity_dict:
                entity_dict['gpg_key'] = module.find_resource_by_name(
                    'content_credentials',
                    name=entity_dict['gpg_key'],
                    params=scope,
                    thin=True)
            if 'ssl_ca_cert' in entity_dict:
                entity_dict['ssl_ca_cert'] = module.find_resource_by_name(
                    'content_credentials',
                    name=entity_dict['ssl_ca_cert'],
                    params=scope,
                    thin=True)
            if 'ssl_client_cert' in entity_dict:
                entity_dict['ssl_client_cert'] = module.find_resource_by_name(
                    'content_credentials',
                    name=entity_dict['ssl_client_cert'],
                    params=scope,
                    thin=True)
            if 'ssl_client_key' in entity_dict:
                entity_dict['ssl_client_key'] = module.find_resource_by_name(
                    'content_credentials',
                    name=entity_dict['ssl_client_key'],
                    params=scope,
                    thin=True)
            if 'sync_plan' in entity_dict:
                entity_dict['sync_plan'] = module.find_resource_by_name(
                    'sync_plans',
                    name=entity_dict['sync_plan'],
                    params=scope,
                    thin=True)

        module.ensure_entity('products', entity_dict, entity, params=scope)
Ejemplo n.º 5
0
def main():
    module = KatelloEntityAnsibleModule(
        entity_spec=dict(
            name=dict(required=True),
            content_type=dict(required=True, choices=['gpg_key', 'cert']),
            content=dict(required=True),
        ),
    )

    entity_dict = module.clean_params()
    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)
        entity = module.find_resource_by_name('content_credentials', name=entity_dict['name'], params=scope, failsafe=True)

        module.ensure_entity('content_credentials', entity_dict, entity, params=scope)
def main():
    module = KatelloEntityAnsibleModule(entity_spec=dict(
        name=dict(required=True),
        label=dict(),
        description=dict(),
        prior=dict(type='entity'),
    ), )

    entity_dict = module.clean_params()

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        entity = module.find_resource_by_name('lifecycle_environments',
                                              name=entity_dict['name'],
                                              params=scope,
                                              failsafe=True)
        if not module.desired_absent:
            if 'prior' in entity_dict:
                entity_dict['prior'] = module.find_resource_by_name(
                    'lifecycle_environments',
                    entity_dict['prior'],
                    params=scope,
                    thin=True)
            # Default to 'Library' for new env with no 'prior' provided
            elif not entity:
                entity_dict['prior'] = module.find_resource_by_name(
                    'lifecycle_environments',
                    'Library',
                    params=scope,
                    thin=True)

        if entity:
            if 'label' in entity_dict and entity_dict[
                    'label'] and entity['label'] != entity_dict['label']:
                module.fail_json(
                    msg="Label cannot be updated on a lifecycle environment.")

            if 'prior' in entity_dict and entity['prior']['id'] != entity_dict[
                    'prior']['id']:
                module.fail_json(
                    msg="Prior cannot be updated on a lifecycle environment.")

        module.ensure_entity('lifecycle_environments',
                             entity_dict,
                             entity,
                             params=scope)
Ejemplo n.º 7
0
def main():
    module = KatelloEntityAnsibleModule(
        entity_spec=dict(
            content_view=dict(type='entity', required=True),
            description=dict(),
            version=dict(),
            lifecycle_environments=dict(type='list', elements='str'),
            force_promote=dict(type='bool', aliases=['force'], default=False),
            force_yum_metadata_regeneration=dict(type='bool', default=False),
            current_lifecycle_environment=dict(),
        ),
        mutually_exclusive=[['current_lifecycle_environment', 'version']],
    )

    module.task_timeout = 60 * 60

    entity_dict = module.clean_params()

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        content_view = module.find_resource_by_name(
            'content_views', name=entity_dict['content_view'], params=scope)

        if 'current_lifecycle_environment' in entity_dict:
            entity_dict[
                'current_lifecycle_environment'] = module.find_resource_by_name(
                    'lifecycle_environments',
                    name=entity_dict['current_lifecycle_environment'],
                    params=scope)
            search_scope = {
                'content_view_id':
                content_view['id'],
                'environment_id':
                entity_dict['current_lifecycle_environment']['id']
            }
            content_view_version = module.find_resource(
                'content_view_versions', search=None, params=search_scope)
        elif 'version' in entity_dict:
            search = "content_view_id={0},version={1}".format(
                content_view['id'], entity_dict['version'])
            content_view_version = module.find_resource(
                'content_view_versions', search=search, failsafe=True)
        else:
            content_view_version = None

        if module.desired_absent:
            module.ensure_entity('content_view_versions',
                                 None,
                                 content_view_version,
                                 params=scope)
        else:
            if content_view_version is None:
                payload = {
                    'id': content_view['id'],
                }
                if 'description' in entity_dict:
                    payload['description'] = entity_dict['description']
                if 'force_yum_metadata_regeneration' in entity_dict:
                    payload['force_yum_metadata_regeneration'] = entity_dict[
                        'force_yum_metadata_regeneration']
                if 'version' in entity_dict:
                    split_version = list(
                        map(int,
                            str(entity_dict['version']).split('.')))
                    payload['major'] = split_version[0]
                    payload['minor'] = split_version[1]

                response = module.resource_action('content_views',
                                                  'publish',
                                                  params=payload)
                # workaround for https://projects.theforeman.org/issues/28138
                if not module.check_mode:
                    content_view_version_id = response['output'].get(
                        'content_view_version_id') or response['input'].get(
                            'content_view_version_id')
                    content_view_version = module.show_resource(
                        'content_view_versions', content_view_version_id)
                else:
                    content_view_version = {'id': -1, 'environments': []}

            if 'lifecycle_environments' in entity_dict:
                lifecycle_environments = module.find_resources_by_name(
                    'lifecycle_environments',
                    names=entity_dict['lifecycle_environments'],
                    params=scope)
                promote_content_view_version(
                    module,
                    content_view_version,
                    lifecycle_environments,
                    force=entity_dict['force_promote'],
                    force_yum_metadata_regeneration=entity_dict[
                        'force_yum_metadata_regeneration'],
                )
def main():
    module = KatelloEntityAnsibleModule(
        entity_spec=dict(
            name=dict(required=True),
            description=dict(),
            interval=dict(choices=['hourly', 'daily', 'weekly', 'custom cron'], required=True),
            enabled=dict(type='bool', required=True),
            sync_date=dict(required=True),
            cron_expression=dict(),
            state=dict(default='present', choices=['present_with_defaults', 'present', 'absent']),
        ),
        argument_spec=dict(
            products=dict(type='list', elements='str'),
        ),
        required_if=[
            ['interval', 'custom cron', ['cron_expression']],
        ],
    )

    entity_dict = module.clean_params()

    if (entity_dict['interval'] != 'custom cron') and ('cron_expression' in entity_dict):
        module.fail_json(msg='"cron_expression" cannot be combined with "interval"!="custom cron".')

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        entity = module.find_resource_by_name('sync_plans', name=entity_dict['name'], params=scope, failsafe=True)

        products = entity_dict.pop('products', None)

        sync_plan = module.ensure_entity('sync_plans', entity_dict, entity, params=scope)

        if not (module.desired_absent or module.state == 'present_with_defaults') and products is not None:
            products = module.find_resources_by_name('products', products, params=scope, thin=True)
            desired_product_ids = set(product['id'] for product in products)
            current_product_ids = set(product['id'] for product in entity['products']) if entity else set()

            module.record_before('sync_plans/products', {'id': sync_plan['id'], 'product_ids': current_product_ids})
            module.record_after('sync_plans/products', {'id': sync_plan['id'], 'product_ids': desired_product_ids})
            module.record_after_full('sync_plans/products', {'id': sync_plan['id'], 'product_ids': desired_product_ids})

            if desired_product_ids != current_product_ids:
                if not module.check_mode:
                    product_ids_to_add = desired_product_ids - current_product_ids
                    if product_ids_to_add:
                        payload = {
                            'id': sync_plan['id'],
                            'product_ids': list(product_ids_to_add),
                        }
                        payload.update(scope)
                        module.resource_action('sync_plans', 'add_products', payload)
                    product_ids_to_remove = current_product_ids - desired_product_ids
                    if product_ids_to_remove:
                        payload = {
                            'id': sync_plan['id'],
                            'product_ids': list(product_ids_to_remove),
                        }
                        payload.update(scope)
                        module.resource_action('sync_plans', 'remove_products', payload)
                else:
                    module.set_changed()
def main():
    module = KatelloEntityAnsibleModule(
        entity_spec=dict(
            name=dict(required=True),
            description=dict(),
            composite=dict(type='bool', default=False),
            auto_publish=dict(type='bool', default=False),
            components=dict(type='nested_list', entity_spec=cvc_entity_spec),
            repositories=dict(type='entity_list',
                              elements='dict',
                              options=dict(
                                  name=dict(required=True),
                                  product=dict(required=True),
                              )),
        ),
        argument_spec=dict(state=dict(
            default='present',
            choices=['present_with_defaults', 'present', 'absent']), ),
        mutually_exclusive=[['repositories', 'components']],
    )

    entity_dict = module.clean_params()

    # components is None when we're managing a CCV but don't want to adjust its components
    components = entity_dict.pop('components', None)
    if components:
        for component in components:
            if not component['latest'] and component.get(
                    'content_view_version') is None:
                module.fail_json(
                    msg=
                    "Content View Component must either have latest=True or provide a Content View Version."
                )

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        if not module.desired_absent:
            if 'repositories' in entity_dict:
                if entity_dict['composite']:
                    module.fail_json(
                        msg=
                        "Repositories cannot be parts of a Composite Content View."
                    )
                else:
                    repositories = []
                    for repository in entity_dict['repositories']:
                        product = module.find_resource_by_name(
                            'products',
                            repository['product'],
                            params=scope,
                            thin=True)
                        repositories.append(
                            module.find_resource_by_name(
                                'repositories',
                                repository['name'],
                                params={'product_id': product['id']},
                                thin=True))
                    entity_dict['repositories'] = repositories

        entity = module.find_resource_by_name('content_views',
                                              name=entity_dict['name'],
                                              params=scope,
                                              failsafe=True)

        content_view_entity = module.ensure_entity('content_views',
                                                   entity_dict,
                                                   entity,
                                                   params=scope)

        # only update CVC's of newly created or updated CV's that are composite if components are specified
        update_dependent_entities = (module.state == 'present' or
                                     (module.state == 'present_with_defaults'
                                      and module.changed))
        if update_dependent_entities and content_view_entity[
                'composite'] and components is not None:
            if not module.changed:
                content_view_entity['content_view_components'] = entity[
                    'content_view_components']
            current_cvcs = content_view_entity.get('content_view_components',
                                                   [])

            # only record a subset of data
            current_cvcs_record = [{
                "id":
                cvc['id'],
                "content_view_id":
                cvc['content_view']['id'],
                "content_view_version_id":
                cvc['content_view_version']['id'],
                "latest":
                cvc['latest']
            } for cvc in current_cvcs]
            module.record_before(
                'content_views/components', {
                    'composite_content_view_id': content_view_entity['id'],
                    'content_view_components': current_cvcs_record
                })
            final_cvcs_record = copy.deepcopy(current_cvcs_record)

            components_to_add = []
            ccv_scope = {
                'composite_content_view_id': content_view_entity['id']
            }
            for component in components:
                cvc = {
                    'content_view':
                    module.find_resource_by_name(
                        'content_views',
                        name=component['content_view'],
                        params=scope),
                    'latest':
                    component['latest'],
                }
                cvc_matched = next(
                    (item for item in current_cvcs
                     if item['content_view']['id'] == cvc['content_view']['id']
                     ), None)
                if not cvc['latest']:
                    search = "content_view_id={0},version={1}".format(
                        cvc['content_view']['id'],
                        component['content_view_version'])
                    cvc['content_view_version'] = module.find_resource(
                        'content_view_versions', search=search, thin=True)
                    cvc['latest'] = False
                    if cvc_matched and cvc_matched['latest']:
                        # When changing to latest=False & version is the latest we must send 'content_view_version' to the server
                        # Let's fake, it wasn't there...
                        cvc_matched.pop('content_view_version', None)
                        cvc_matched.pop('content_view_version_id', None)
                if cvc_matched:
                    module.ensure_entity('content_view_components',
                                         cvc,
                                         cvc_matched,
                                         state='present',
                                         entity_spec=cvc_entity_spec,
                                         params=ccv_scope)
                    current_cvcs.remove(cvc_matched)
                else:
                    cvc['content_view_id'] = cvc.pop('content_view')['id']
                    if 'content_view_version' in cvc:
                        cvc['content_view_version_id'] = cvc.pop(
                            'content_view_version')['id']
                    components_to_add.append(cvc)

            if components_to_add:
                payload = {
                    'composite_content_view_id': content_view_entity['id'],
                    'components': components_to_add,
                }
                module.resource_action('content_view_components',
                                       'add_components', payload)

                final_cvcs_record.extend(components_to_add)

            # desired cvcs have already been updated and removed from `current_cvcs`
            components_to_remove = [item['id'] for item in current_cvcs]
            if components_to_remove:
                payload = {
                    'composite_content_view_id': content_view_entity['id'],
                    'component_ids': components_to_remove,
                }
                module.resource_action('content_view_components',
                                       'remove_components', payload)

                final_cvcs_record = [
                    item for item in final_cvcs_record
                    if item['id'] not in components_to_remove
                ]

            module.record_after(
                'content_views/components', {
                    'composite_content_view_id': content_view_entity['id'],
                    'content_view_components': final_cvcs_record
                })
            module.record_after_full(
                'content_views/components', {
                    'composite_content_view_id': content_view_entity['id'],
                    'content_view_components': final_cvcs_record
                })
Ejemplo n.º 10
0
def main():
    module = KatelloEntityAnsibleModule(
        entity_spec=dict(
            name=dict(required=True),
            new_name=dict(),
            lifecycle_environment=dict(type='entity',
                                       flat_name='environment_id'),
            content_view=dict(type='entity'),
            host_collections=dict(type='entity_list'),
            auto_attach=dict(type='bool'),
            release_version=dict(),
            service_level=dict(
                choices=['Self-Support', 'Standard', 'Premium']),
            max_hosts=dict(type='int'),
            unlimited_hosts=dict(type='bool'),
            purpose_usage=dict(),
            purpose_role=dict(),
            purpose_addons=dict(type='list', elements='str'),
        ),
        argument_spec=dict(
            subscriptions=dict(
                type='list',
                elements='dict',
                options=dict(
                    name=dict(),
                    pool_id=dict(),
                ),
                required_one_of=[['name', 'pool_id']],
                mutually_exclusive=[['name', 'pool_id']],
            ),
            content_overrides=dict(
                type='list',
                elements='dict',
                options=dict(
                    label=dict(required=True),
                    override=dict(required=True,
                                  choices=['enabled', 'disabled', 'default']),
                )),
            state=dict(default='present',
                       choices=[
                           'present', 'present_with_defaults', 'absent',
                           'copied'
                       ]),
        ),
        required_if=[
            ['state', 'copied', ['new_name']],
            ['unlimited_hosts', False, ['max_hosts']],
        ],
    )

    entity_dict = module.clean_params()

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        if not module.desired_absent:
            if 'lifecycle_environment' in entity_dict:
                entity_dict[
                    'lifecycle_environment'] = module.find_resource_by_name(
                        'lifecycle_environments',
                        entity_dict['lifecycle_environment'],
                        params=scope,
                        thin=True)

            if 'content_view' in entity_dict:
                entity_dict['content_view'] = module.find_resource_by_name(
                    'content_views',
                    entity_dict['content_view'],
                    params=scope,
                    thin=True)

        entity = module.find_resource_by_name('activation_keys',
                                              name=entity_dict['name'],
                                              params=scope,
                                              failsafe=True)

        if module.state == 'copied':
            new_entity = module.find_resource_by_name(
                'activation_keys',
                name=entity_dict['new_name'],
                params=scope,
                failsafe=True)
            if new_entity is not None:
                module.warn("Activation Key '{0}' already exists.".format(
                    entity_dict['new_name']))
                module.exit_json()

        subscriptions = entity_dict.pop('subscriptions', None)
        content_overrides = entity_dict.pop('content_overrides', None)
        host_collections = entity_dict.pop('host_collections', None)
        activation_key = module.ensure_entity('activation_keys',
                                              entity_dict,
                                              entity,
                                              params=scope)

        # only update subscriptions of newly created or updated AKs
        # copied keys inherit the subscriptions of the origin, so one would not have to specify them again
        # deleted keys don't need subscriptions anymore either
        if module.state == 'present' or (
                module.state == 'present_with_defaults' and module.changed):
            # the auto_attach, release_version and service_level parameters can only be set on an existing AK with an update,
            # not during create, so let's force an update. see https://projects.theforeman.org/issues/27632 for details
            if any(key in entity_dict for key in [
                    'auto_attach', 'release_version', 'service_level'
            ]) and module.changed:
                activation_key = module.ensure_entity('activation_keys',
                                                      entity_dict,
                                                      activation_key,
                                                      params=scope)

            ak_scope = {'activation_key_id': activation_key['id']}
            if subscriptions is not None:
                desired_subscriptions = []
                for subscription in subscriptions:
                    if subscription['name'] is not None and subscription[
                            'pool_id'] is None:
                        desired_subscriptions.append(
                            module.find_resource_by_name('subscriptions',
                                                         subscription['name'],
                                                         params=scope,
                                                         thin=True))
                    if subscription['pool_id'] is not None:
                        desired_subscriptions.append(
                            module.find_resource_by_id('subscriptions',
                                                       subscription['pool_id'],
                                                       params=scope,
                                                       thin=True))
                desired_subscription_ids = set(
                    item['id'] for item in desired_subscriptions)
                current_subscriptions = module.list_resource(
                    'subscriptions', params=ak_scope) if entity else []
                current_subscription_ids = set(
                    item['id'] for item in current_subscriptions)

                if desired_subscription_ids != current_subscription_ids:
                    module.record_before(
                        'activation_keys/subscriptions', {
                            'id': activation_key['id'],
                            'subscriptions': current_subscription_ids
                        })
                    module.record_after(
                        'activation_keys/subscriptions', {
                            'id': activation_key['id'],
                            'subscriptions': desired_subscription_ids
                        })
                    module.record_after_full(
                        'activation_keys/subscriptions', {
                            'id': activation_key['id'],
                            'subscriptions': desired_subscription_ids
                        })

                    ids_to_remove = current_subscription_ids - desired_subscription_ids
                    if ids_to_remove:
                        payload = {
                            'id':
                            activation_key['id'],
                            'subscriptions': [{
                                'id': item
                            } for item in ids_to_remove],
                        }
                        payload.update(scope)
                        module.resource_action('activation_keys',
                                               'remove_subscriptions', payload)

                    ids_to_add = desired_subscription_ids - current_subscription_ids
                    if ids_to_add:
                        payload = {
                            'id':
                            activation_key['id'],
                            'subscriptions': [{
                                'id': item,
                                'quantity': 1
                            } for item in ids_to_add],
                        }
                        payload.update(scope)
                        module.resource_action('activation_keys',
                                               'add_subscriptions', payload)

            if content_overrides is not None:
                if entity:
                    product_content = module.resource_action(
                        'activation_keys',
                        'product_content',
                        params={
                            'id': activation_key['id'],
                            'content_access_mode_all': True
                        },
                        ignore_check_mode=True,
                    )
                else:
                    product_content = {'results': []}
                current_content_overrides = {
                    product['content']['label']:
                    product['enabled_content_override']
                    for product in product_content['results']
                    if product['enabled_content_override'] is not None
                }
                desired_content_overrides = {
                    product['label']: override_to_boolnone(product['override'])
                    for product in content_overrides
                }
                changed_content_overrides = []

                module.record_before(
                    'activation_keys/content_overrides', {
                        'id': activation_key['id'],
                        'content_overrides': current_content_overrides.copy()
                    })
                module.record_after(
                    'activation_keys/content_overrides', {
                        'id': activation_key['id'],
                        'content_overrides': desired_content_overrides
                    })
                module.record_after_full(
                    'activation_keys/content_overrides', {
                        'id': activation_key['id'],
                        'content_overrides': desired_content_overrides
                    })

                for label, override in desired_content_overrides.items():
                    if override is not None and override != current_content_overrides.pop(
                            label, None):
                        changed_content_overrides.append({
                            'content_label': label,
                            'value': override
                        })
                for label in current_content_overrides.keys():
                    changed_content_overrides.append({
                        'content_label': label,
                        'remove': True
                    })

                if changed_content_overrides:
                    payload = {
                        'id': activation_key['id'],
                        'content_overrides': changed_content_overrides,
                    }
                    module.resource_action('activation_keys',
                                           'content_override', payload)

            if host_collections is not None:
                if not entity:
                    current_host_collection_ids = set()
                elif 'host_collection_ids' in activation_key:
                    current_host_collection_ids = set(
                        activation_key['host_collection_ids'])
                else:
                    current_host_collection_ids = set(
                        item['id']
                        for item in activation_key['host_collections'])
                desired_host_collections = module.find_resources_by_name(
                    'host_collections',
                    host_collections,
                    params=scope,
                    thin=True)
                desired_host_collection_ids = set(
                    item['id'] for item in desired_host_collections)

                if desired_host_collection_ids != current_host_collection_ids:
                    module.record_before(
                        'activation_keys/host_collections', {
                            'id': activation_key['id'],
                            'host_collections': current_host_collection_ids
                        })
                    module.record_after(
                        'activation_keys/host_collections', {
                            'id': activation_key['id'],
                            'host_collections': desired_host_collection_ids
                        })
                    module.record_after_full(
                        'activation_keys/host_collections', {
                            'id': activation_key['id'],
                            'host_collections': desired_host_collection_ids
                        })

                    ids_to_remove = current_host_collection_ids - desired_host_collection_ids
                    if ids_to_remove:
                        payload = {
                            'id': activation_key['id'],
                            'host_collection_ids': list(ids_to_remove),
                        }
                        module.resource_action('activation_keys',
                                               'remove_host_collections',
                                               payload)

                    ids_to_add = desired_host_collection_ids - current_host_collection_ids
                    if ids_to_add:
                        payload = {
                            'id': activation_key['id'],
                            'host_collection_ids': list(ids_to_add),
                        }
                        module.resource_action('activation_keys',
                                               'add_host_collections', payload)
def main():
    module = KatelloEntityAnsibleModule(
        entity_spec=dict(
            name=dict(required=True),
            updated_name=dict(),
            login=dict(),
            scc_account_password=dict(no_log=True, flat_name='password'),
            base_url=dict(),
            sync_date=dict(),
            interval=dict(choices=['never', 'daily', 'weekly', 'monthly']),
            state=dict(default='present',
                       choices=['present', 'absent', 'synced']),
        ),
        argument_spec=dict(test_connection=dict(type='bool', default=False), ),
    )

    entity_dict = module.clean_params()

    module.task_timeout = 4 * 60

    with module.api_connection():
        entity_dict, scope = module.handle_organization_param(entity_dict)

        failsafe = (module.state != 'synced')

        entity = module.find_resource_by_name('scc_accounts',
                                              name=entity_dict['name'],
                                              params=scope,
                                              failsafe=failsafe)

        if not module.desired_absent:
            if not entity:
                if 'login' not in entity_dict:
                    module.fail_json(msg="scc account login not provided")
                if 'scc_account_password' not in entity_dict:
                    module.fail_json(msg="Scc account password not provided")

            if entity_dict['test_connection']:
                scc_account_credentials = {}
                if entity:
                    scc_account_credentials['id'] = entity['id']
                if 'login' in entity_dict:
                    scc_account_credentials['login'] = entity_dict['login']
                if 'scc_account_password' in entity_dict:
                    scc_account_credentials['password'] = entity_dict[
                        'scc_account_password']
                if 'base_url' in entity_dict:
                    scc_account_credentials['base_url'] = entity_dict[
                        'base_url']
                module.resource_action('scc_accounts',
                                       'test_connection',
                                       scc_account_credentials,
                                       ignore_check_mode=True)

        if 'updated_name' in entity_dict:
            entity_dict['name'] = entity_dict.pop('updated_name')

        if module.state == 'synced':
            module.resource_action('scc_accounts', 'sync',
                                   {'id': entity['id']})
        else:
            module.ensure_entity('scc_accounts',
                                 entity_dict,
                                 entity,
                                 params=scope)
Ejemplo n.º 12
0
def main():
    module = KatelloEntityAnsibleModule(
        argument_spec=dict(
            name=dict(),
            product=dict(),
            label=dict(),
            repositories=dict(type='list',
                              elements='dict',
                              options=dict(
                                  basearch=dict(),
                                  releasever=dict(),
                              )),
            all_repositories=dict(type='bool'),
            state=dict(default='enabled', choices=['disabled', 'enabled']),
        ),
        required_one_of=[
            ['label', 'name'],
            ['repositories', 'all_repositories'],
        ],
        required_if=[
            ['all_repositories', False, ['repositories']],
            ['repositories', [], ['all_repositories']],
        ],
    )

    module_params = module.clean_params()

    with module.api_connection():
        module_params, scope = module.handle_organization_param(module_params)

        record_data = {}
        if 'product' in module_params:
            module_params['product'] = module.find_resource_by_name(
                'products',
                name=module_params['product'],
                params=scope,
                thin=True)
            scope['product_id'] = module_params['product']['id']
            record_data['product'] = module_params['product']

        if 'label' in module_params:
            search = 'label="{0}"'.format(module_params['label'])
            repo_set = module.find_resource('repository_sets',
                                            search=search,
                                            params=scope)
            record_data['label'] = module_params['label']
        else:
            repo_set = module.find_resource_by_name('repository_sets',
                                                    name=module_params['name'],
                                                    params=scope)
            record_data['name'] = module_params['name']

        repo_set_scope = {
            'id': repo_set['id'],
            'product_id': repo_set['product']['id']
        }
        repo_set_scope.update(scope)

        available_repos = module.resource_action('repository_sets',
                                                 'available_repositories',
                                                 params=repo_set_scope,
                                                 ignore_check_mode=True)
        available_repos = available_repos['results']
        current_repos = repo_set['repositories']
        if not module_params.get('all_repositories', False):
            desired_repos = get_desired_repos(module_params['repositories'],
                                              available_repos)
        else:
            desired_repos = available_repos[:]

        available_repo_names = set(
            map(lambda repo: repo['repo_name'], available_repos))
        current_repo_names = set(map(lambda repo: repo['name'], current_repos))
        desired_repo_names = set(
            map(lambda repo: repo['repo_name'], desired_repos))

        if not module_params.get('all_repositories', False) and len(
                module_params['repositories']) != len(desired_repo_names):
            repo_set_identification = ' '.join(
                ['{0}: {1}'.format(k, v) for (k, v) in record_data.items()])

            error_msg = "Desired repositories are not available on the repository set {0}.\nSearched: {1}\nFound: {2}\nAvailable: {3}".format(
                repo_set_identification, module_params['repositories'],
                desired_repo_names, available_repo_names)

            module.fail_json(msg=error_msg)

        if module.state == 'enabled':
            for repo in desired_repo_names - current_repo_names:
                repo_to_enable = next(
                    (r for r in available_repos if r['repo_name'] == repo))
                repo_change_params = repo_to_enable['substitutions'].copy()
                repo_change_params.update(repo_set_scope)

                record_repository_set_state(module, record_data, repo,
                                            'disabled', 'enabled')

                module.resource_action('repository_sets',
                                       'enable',
                                       params=repo_change_params)
        elif module.state == 'disabled':
            for repo in current_repo_names & desired_repo_names:
                repo_to_disable = next(
                    (r for r in available_repos if r['repo_name'] == repo))
                repo_change_params = repo_to_disable['substitutions'].copy()
                repo_change_params.update(repo_set_scope)

                record_repository_set_state(module, record_data, repo,
                                            'enabled', 'disabled')

                module.resource_action('repository_sets',
                                       'disable',
                                       params=repo_change_params)