コード例 #1
0
def main():
    """Execute the Kong Certificate module."""
    ansible_module = AnsibleModule(argument_spec=dict(
        kong_admin_uri=dict(required=True, type='str'),
        kong_admin_username=dict(required=False, type='str'),
        kong_admin_password=dict(required=False, type='str', no_log=True),
        snis=dict(required=True, type='list'),
        cert=dict(required=False, type='str'),
        key=dict(required=False, type='str', no_log=True),
        state=dict(required=False,
                   default="present",
                   choices=['present', 'absent'],
                   type='str'),
    ),
                                   required_if=[('state', 'present',
                                                 ['snis', 'cert', 'key'])],
                                   supports_check_mode=True)

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract arguments
    state = ansible_module.params['state']
    snis = ansible_module.params['snis']
    cert = ansible_module.params['cert']
    key = ansible_module.params['key']

    if not snis:
        ansible_module.fail_json(msg="'snis' cannot be empty")

    # First SNI in the list to use in queries.
    sni = snis[0]

    data = {'snis': snis, 'cert': cert.strip(), 'key': key.strip()}

    # Create Kong client instance.
    k = KongCertificate(url, auth_user=auth_user, auth_pass=auth_pass)
    kong_status_check(k, ansible_module)
    kong_version_check(k, ansible_module)

    # Default return values.
    result = {}
    changed = False
    resp = ''

    # Ensure the Certificate is configured.
    if state == "present":

        # Look up the first SNI in the list.
        orig = k.certificate_get(sni)
        if orig is not None:
            # Determine whether to report 'modified' or 'created'.
            certdiff = dotdiff(orig, data)
            if certdiff:
                changed = True
                result['state'] = 'modified'
        else:
            # Insert a new Certificate, set changed.
            changed = True
            result['state'] = 'created'

        if not ansible_module.check_mode and changed:
            try:
                resp = k.certificate_apply(**data)
            except requests.HTTPError as e:
                ansible_module.fail_json(
                    msg='Error applying Certificate: {}'.format(e))

    # Ensure the certificate is deleted
    if state == "absent":

        orig = k.certificate_get(sni)
        if orig:
            changed = True
            result['state'] = 'deleted'

        if not ansible_module.check_mode and orig:
            try:
                resp = k.certificate_delete(sni)
            except requests.HTTPError as e:
                ansible_module.fail_json(
                    msg='Error deleting Certificate: {}'.format(e))

    result.update(changed=changed)

    # Pass through the API response if non-empty.
    if resp:
        result['response'] = resp

    ansible_module.exit_json(**result)
コード例 #2
0
def main():

    ansible_module = AnsibleModule(
        argument_spec=dict(
            kong_admin_uri=dict(required=True, type='str'),
            kong_admin_username=dict(required=False, type='str'),
            kong_admin_password=dict(required=False, type='str', no_log=True),
            name=dict(required=True, type='str'),
            api_name=dict(required=True, type='str'),
            consumer_name=dict(required=False, type='str', default=False),
            config=dict(required=False, type='dict', default=dict()),
            state=dict(required=False, default="present", choices=['present', 'absent'], type='str'),
        ),
        supports_check_mode=True
    )

    # Initialize output dictionary
    result = {}

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract arguments
    state = ansible_module.params['state']
    name = ansible_module.params['name']
    api_name = ansible_module.params['api_name']
    consumer_name = ansible_module.params['consumer_name']
    config = ansible_module.params['config']

    # Convert consumer_name to bool if bool conversion evals to False
    if consumer_name == 'False':
        consumer_name = False

    # Create KongAPI client instance
    k = KongPlugin(url, auth_user=auth_user, auth_pass=auth_pass)

    # Contact Kong status endpoint
    kong_status_check(k, ansible_module)

    # Kong API version compatibility check
    kong_version_check(k, ansible_module, MIN_VERSION)

    # Default return values
    changed = False
    resp = ''

    # Check if the Plugin is already present
    pq = k.plugin_query(name, api_name=api_name, consumer_name=consumer_name)

    # ansible_module.fail_json(msg=pq)

    if len(pq) > 1:
        ansible_module.fail_json(
            msg='Got multiple results for Plugin query name: {}, api_name: {}, consumer_name: {}'.
                format(name, api_name, consumer_name))

    # Ensure the Plugin is installed on Kong
    if state == "present":
        if pq:
            # Extract the remote Plugin object into orig
            orig = pq[0]

            # Diff the remote Plugin object against the target data if it already exists
            plugindiff = dotdiff(orig.get('config'), config)

            # Set changed flag if there's a diff
            if plugindiff:
                # Log modified state and diff result
                changed = True
                result['state'] = 'modified'
                result['diff'] = [dict(prepared=render_list(plugindiff))]

        else:
            # We're inserting a new Plugin, set changed
            changed = True
            result['state'] = 'created'
            result['diff'] = dict(
                before_header='<undefined>', before='<undefined>\n',
                after_header=name, after={
                    'name': name,
                    'consumer_name': consumer_name,
                    'api_name': api_name,
                    'state': 'created',
                    'config': config
                }
            )

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and changed:
            try:
                resp = k.plugin_apply(name=name, config=config, api_name=api_name, consumer_name=consumer_name)
            except requests.HTTPError as e:
                ansible_module.fail_json(msg='Plugin configuration rejected by Kong.', name=name, config=config,
                                         api_name=api_name, consumer_name=consumer_name, response=e.response._content)

    # Delete the Plugin if it exists
    if state == "absent" and pq:

        # Check if the API exists
        orig = pq[0]

        # Predict a change if the Plugin exists
        changed = True
        result['state'] = 'deleted'
        result['diff'] = dict(
            before_header=name, before=orig,
            after_header='<deleted>', after='\n'
        )

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and orig:
            # Issue delete call to the Kong API
            try:
                resp = k.plugin_delete(name, api_name=api_name, consumer_name=consumer_name)
            except requests.HTTPError as e:
                app_err = "Error deleting Plugin."
                ansible_module.fail_json(msg=app_err, response=e.response._content)

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    # Prepare module output
    result.update(
        dict(
            changed=changed,
        )
    )

    ansible_module.exit_json(**result)
コード例 #3
0
def main():
    """Execute the Kong Consumer module."""
    ansible_module = AnsibleModule(argument_spec=dict(
        kong_admin_uri=dict(required=True, type='str'),
        kong_admin_username=dict(required=False, type='str'),
        kong_admin_password=dict(required=False, type='str', no_log=True),
        username=dict(required=True, type='list'),
        custom_id=dict(required=False, type='str'),
        state=dict(required=False,
                   default="present",
                   choices=['present', 'absent'],
                   type='str'),
    ),
                                   supports_check_mode=True)

    # Initialize output dictionary
    result = {}

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract other arguments
    state = ansible_module.params['state']
    users = ansible_module.params['username']
    custom_id = ansible_module.params['custom_id']

    if len(users) > 1 and custom_id:
        ansible_module.fail_json(
            msg="custom_id can only be given when managing a single Consumer")

    # Create Kong client instance
    k = KongConsumer(url, auth_user=auth_user, auth_pass=auth_pass)
    kong_status_check(k, ansible_module)
    kong_version_check(k, ansible_module)

    # Default return values
    changed = False
    resp = ''
    diff = []

    if state == 'present':

        # Ensure the list of Consumers is created.
        for username in users:
            data = {'username': username}
            if custom_id:
                # Will only be present with a single user.
                data['custom_id'] = custom_id

            # Check if the Consumer exists.
            orig = k.consumer_get(username)
            if orig is None:
                # Insert a new Consumer.
                changed = True
                diff.append(
                    dict(before_header='<undefined>',
                         before='<undefined>\n',
                         after_header=username,
                         after=data))

            else:
                # Patch an existing Consumer.
                consumer_diff = dotdiff(orig, data)
                if consumer_diff:
                    # Log modified state and diff result.
                    changed = True
                    diff.append(dict(prepared=render_list(consumer_diff)))

            if not ansible_module.check_mode:
                try:
                    resp = k.consumer_apply(**data)
                except requests.HTTPError as e:
                    ansible_module.fail_json(msg=str(e))

    if state == 'absent':

        # Ensure the list of Consumers is deleted.
        for username in users:
            orig = k.consumer_get(username)
            if orig:
                # Delete the Consumer.
                changed = True
                diff.append(
                    dict(before_header=username,
                         before=orig,
                         after_header='<deleted>',
                         after='\n'))

            if not ansible_module.check_mode and orig:
                try:
                    resp = k.consumer_delete(username)
                except requests.HTTPError as e:
                    ansible_module.fail_json(
                        msg='Error deleting Consumer: {}'.format(e))

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    # Pass through the diff result
    if diff:
        result['diff'] = diff

    # Prepare module output
    result.update(changed=changed)

    ansible_module.exit_json(**result)
コード例 #4
0
def main():
    ansible_module = AnsibleModule(argument_spec=dict(
        kong_admin_uri=dict(required=True, type='str'),
        kong_admin_username=dict(required=False, type='str'),
        kong_admin_password=dict(required=False, type='str', no_log=True),
        sni=dict(required=True, type='str'),
        cert=dict(required=False, type='str'),
        key=dict(required=False, type='str', no_log=True),
        state=dict(required=False,
                   default="present",
                   choices=['present', 'absent'],
                   type='str'),
    ),
                                   required_if=[('state', 'present',
                                                 ['sni', 'cert', 'key'])],
                                   supports_check_mode=True)

    # Initialize output dictionary
    result = {}

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract arguments
    state = ansible_module.params['state']
    sni = ansible_module.params['sni']
    cert = ansible_module.params['cert']
    key = ansible_module.params['key']

    data = {'snis': [sni], 'cert': cert.strip(), 'key': key.strip()}

    # Create KongCertificate client instance
    k = KongCertificate(url, auth_user=auth_user, auth_pass=auth_pass)

    # Contact Kong status endpoint
    kong_status_check(k, ansible_module)

    # Kong API version compatibility check
    kong_version_check(k, ansible_module, MIN_VERSION)

    # Default return values
    changed = False
    resp = ''

    # Ensure the service is registered in Kong
    if state == "present":

        # Check if the service exists
        orig = k.certificate_get(sni)
        if orig is not None:

            # Diff the remote API object against the target data if it already exists
            certdiff = dotdiff(orig, data)

            # Set changed flag if there's a diff
            if certdiff:
                # Log modified state and diff result
                changed = True
                result['state'] = 'modified'
                result['diff'] = [dict(prepared=render_list(certdiff))]

        else:
            # We're inserting a new service, set changed
            changed = True
            result['state'] = 'created'
            result['diff'] = dict(before_header='<undefined>',
                                  before='<undefined>\n',
                                  after_header=sni,
                                  after='<hidden>')

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and changed:
            try:
                resp = k.certificate_apply(**data)
            except Exception as e:
                app_err = "Certfificate configuration rejected by Kong: '{}'. " \
                          "Please check configuration of the certificate you are trying to configure."
                ansible_module.fail_json(msg=app_err.format(e))

    # Ensure the certificate is deleted
    if state == "absent":

        # Check if the certificate exists
        orig = k.certificate_get(sni)

        # Predict a change if the certfificate exists
        if orig:
            changed = True
            result['state'] = 'deleted'
            result['diff'] = dict(before_header=sni,
                                  before='<hidden>',
                                  after_header='<deleted>',
                                  after='\n')

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and orig:
            # Issue delete call to the Kong service
            try:
                resp = k.certificate_delete(name)
            except Exception as e:
                ansible_module.fail_json(
                    msg='Error deleting certificate: {}'.format(e))

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    # Prepare module output
    result.update(dict(changed=changed, ))

    ansible_module.exit_json(**result)
コード例 #5
0
def main():
    ansible_module = AnsibleModule(
        argument_spec=dict(
            kong_admin_uri=dict(required=True, type='str'),
            kong_admin_username=dict(required=False, type='str'),
            kong_admin_password=dict(required=False, type='str', no_log=True),
            service=dict(required=True, type='str'),
            name=dict(required=True, type='str'),
            protocols=dict(required=False, default=['http', 'https'], type='list'),
            hosts=dict(required=False, type='list'),
            paths=dict(required=False, default=[], type='list'),
            methods=dict(required=False, default=[], type='list'),
            strip_path=dict(required=False, default=True, type='bool'),
            preserve_host=dict(required=False, default=False, type='bool'),
            tags=dict(required=False, type='list'),
            state=dict(required=False, default="present", choices=['present', 'absent'], type='str'),
        ),
        required_if=[
            ('state', 'present', ['service']),
            ('state', 'absent', ['service']),
        ],
        required_one_of=[
            ('hosts', 'paths', 'methods')
        ],
        supports_check_mode=True
    )

    # Initialize output dictionary
    result = {}

    # Emulates 'required_one_of' argument spec, as it cannot be made conditional
    if ansible_module.params['state'] == 'present' and \
            ansible_module.params['protocols'] is None and \
            ansible_module.params['methods'] is None and \
            ansible_module.params['hosts'] is None and \
            ansible_module.params['paths'] is None:
        ansible_module.fail_json(msg="At least one of protocols, methods, hosts or paths is required when state is 'present'")

    # Kong 0.14.x
    api_fields = [
        'name',
        'protocols',
        'methods',
        'hosts',
        'paths',
        'strip_path',
        'preserve_host',
        'tags'
    ]

    # Extract api_fields from module parameters into separate dictionary
    data = params_fields_lookup(ansible_module, api_fields)

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract other arguments
    service = ansible_module.params['service']
    state = ansible_module.params['state']
    name = ansible_module.params['name']

    # Create KongRoute client instance
    k = KongRoute(url, auth_user=auth_user, auth_pass=auth_pass)

    # Contact Kong status endpoint
    kong_status_check(k, ansible_module)

    # Default return values
    changed = False
    resp = ''

    # Ensure the Route is registered in Kong
    if state == "present":

        orig = k.route_get(name)
        if orig is not None:
            # Diff the remote Route object against the target data if it already exists
            route_diff = dotdiff(orig, data)
            # Set changed flag if there's a diff
            if route_diff:
                data['route_id'] = orig['id']
                # Log modified state and diff result
                changed = True
                result['state'] = 'modified'
                result['diff'] = [dict(prepared=render_list(route_diff))]

        else:
            # We're inserting a new Route, set changed
            data['route_id'] = None
            changed = True
            result['state'] = 'created'
            result['diff'] = dict(
                before_header='<undefined>', before='<undefined>\n',
                after_header=service, after=data
            )

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and changed:
            try:
                resp = k.route_apply(service, **data)
            except Exception as e:
                err_msg = "Route configuration rejected by Kong: '{}'. " \
                          "Please check configuration of the API you are trying to configure."
                ansible_module.fail_json(msg=err_msg.format(e))

    # Ensure the Route is deleted
    if state == "absent":

        # Check if the Route exists
        orig = k.route_get(name)

        # Predict a change if the API exists
        if orig:
            changed = True
            result['state'] = 'deleted'
            result['diff'] = dict(
                before_header=service, before=orig,
                after_header='<deleted>', after='\n'
            )

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and orig:
            # Issue delete call to the Kong API
            try:
                resp = k.route_delete(orig['id'])
            except Exception as e:
                ansible_module.fail_json(msg='Error deleting Route: {}'.format(e))

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    # Prepare module output
    result.update(
        dict(
            changed=changed,
        )
    )

    ansible_module.exit_json(**result)
コード例 #6
0
def main():
    """Execute the Kong Service module."""
    ansible_module = AnsibleModule(
        argument_spec=dict(
            kong_admin_uri=dict(required=True, type='str'),
            kong_admin_username=dict(required=False, type='str'),
            kong_admin_password=dict(required=False, type='str', no_log=True),
            name=dict(required=True, type='str'),
            protocol=dict(required=False, default="http",
                          choices=['http', 'https'], type='str'),
            host=dict(required=True, type='str'),
            port=dict(required=False, default=80, type='int'),
            path=dict(required=False, type='str'),
            retries=dict(required=False, default=5, type='int'),
            connect_timeout=dict(required=False, default=60000, type='int'),
            write_timeout=dict(required=False, default=60000, type='int'),
            read_timeout=dict(required=False, default=60000, type='int'),
            state=dict(required=False, default="present",
                       choices=['present', 'absent'], type='str'),
        ),
        required_if=[
            ('state', 'present', ['host', 'name'])
        ],
        supports_check_mode=True
    )

    api_fields = [
        'name',
        'protocol',
        'host',
        'port',
        'path',
        'retries',
        'connect_timeout',
        'write_timeout',
        'read_timeout'
    ]

    # Extract api_fields from module parameters into separate dictionary
    data = params_fields_lookup(ansible_module, api_fields)

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract other arguments
    state = ansible_module.params['state']
    name = ansible_module.params['name']

    # Create Kong client instance.
    k = KongService(url, auth_user=auth_user, auth_pass=auth_pass)
    kong_status_check(k, ansible_module)
    kong_version_check(k, ansible_module)

    # Default return values.
    result = {}
    changed = False
    resp = ''

    # Ensure the Service is configured.
    if state == "present":

        orig = k.service_get(name)
        if orig is not None:
            # Diff the existing object against the target data if it already exists.
            servicediff = dotdiff(orig, data)
            if servicediff:
                changed = True
                result['state'] = 'modified'
                result['diff'] = [dict(prepared=render_list(servicediff))]

        else:
            # Insert a new Service, set changed.
            changed = True
            result['state'] = 'created'
            result['diff'] = dict(
                before_header='<undefined>', before='<undefined>\n',
                after_header=name, after=data
            )

        if not ansible_module.check_mode and changed:
            try:
                resp = k.service_apply(**data)
            except requests.HTTPError as e:
                ansible_module.fail_json(
                    msg='Error applying Service: {}'.format(e))

    # Ensure the Service is deleted.
    if state == "absent":

        orig = k.service_get(name)
        if orig:
            changed = True
            result['state'] = 'deleted'
            result['diff'] = dict(
                before_header=name, before=orig,
                after_header='<deleted>', after='\n'
            )

        if not ansible_module.check_mode and orig:
            try:
                resp = k.service_delete(name)
            except requests.HTTPError as e:
                ansible_module.fail_json(
                    msg='Error deleting Service: {}'.format(e))

    # Prepare module output
    result.update(changed=changed)

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    ansible_module.exit_json(**result)
コード例 #7
0
def main():

    ansible_module = AnsibleModule(argument_spec=dict(
        kong_admin_uri=dict(required=True, type='str'),
        kong_admin_username=dict(required=False, type='str'),
        kong_admin_password=dict(required=False, type='str', no_log=True),
        name=dict(required=True, type='str'),
        upstream_url=dict(required=False, type='str'),
        hosts=dict(required=False, type='list'),
        uris=dict(required=False, type='list'),
        methods=dict(required=False, type='list'),
        strip_uri=dict(required=False, default=False, type='bool'),
        preserve_host=dict(required=False, default=False, type='bool'),
        state=dict(required=False,
                   default="present",
                   choices=['present', 'absent'],
                   type='str'),
    ),
                                   required_if=[('state', 'present',
                                                 ['upstream_url'])],
                                   supports_check_mode=True)

    # Initialize output dictionary
    result = {}

    # Emulates 'required_one_of' argument spec, as it cannot be made conditional
    if ansible_module.params['state'] == 'present' and \
        ansible_module.params['hosts'] is None and \
        ansible_module.params['uris'] is None and \
            ansible_module.params['methods'] is None:
        ansible_module.fail_json(
            msg=
            "At least one of hosts, uris or methods is required when state is 'present'"
        )

    # Kong 0.11.x
    api_fields = [
        'name', 'upstream_url', 'hosts', 'uris', 'methods', 'strip_uri',
        'preserve_host', 'retries', 'upstream_connect_timeout',
        'upstream_read_timeout', 'upstream_send_timeout', 'https_only',
        'http_if_terminated'
    ]

    # Extract api_fields from module parameters into separate dictionary
    data = params_fields_lookup(ansible_module, api_fields)

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract other arguments
    state = ansible_module.params['state']
    name = ansible_module.params['name']

    # Create KongAPI client instance
    k = KongAPI(url, auth_user=auth_user, auth_pass=auth_pass)

    # Contact Kong status endpoint
    kong_status_check(k, ansible_module)

    # Kong API version compatibility check
    kong_version_check(k, ansible_module, MIN_VERSION)

    # Default return values
    changed = False
    resp = ''

    # Ensure the API is registered in Kong
    if state == "present":

        # Check if the API exists
        orig = k.api_get(name)
        if orig is not None:

            # Diff the remote API object against the target data if it already exists
            apidiff = dotdiff(orig, data)

            # Set changed flag if there's a diff
            if apidiff:
                # Log modified state and diff result
                changed = True
                result['state'] = 'modified'
                result['diff'] = [dict(prepared=render_list(apidiff))]

        else:
            # We're inserting a new API, set changed
            changed = True
            result['state'] = 'created'
            result['diff'] = dict(before_header='<undefined>',
                                  before='<undefined>\n',
                                  after_header=name,
                                  after=data)

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and changed:
            try:
                resp = k.api_apply(**data)
            except Exception as e:
                app_err = "API configuration rejected by Kong: '{}'. " \
                          "Please check configuration of the API you are trying to configure."
                ansible_module.fail_json(msg=app_err.format(e.message))

    # Ensure the API is deleted
    if state == "absent":

        # Check if the API exists
        orig = k.api_get(name)

        # Predict a change if the API exists
        if orig:
            changed = True
            result['state'] = 'deleted'
            result['diff'] = dict(before_header=name,
                                  before=orig,
                                  after_header='<deleted>',
                                  after='\n')

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and orig:
            # Issue delete call to the Kong API
            try:
                resp = k.api_delete(name)
            except Exception as e:
                ansible_module.fail_json(
                    msg='Error deleting API: {}'.format(e.message))

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    # Prepare module output
    result.update(dict(changed=changed, ))

    ansible_module.exit_json(**result)
コード例 #8
0
def main():
    """Execute the Kong Route module."""
    ansible_module = AnsibleModule(
        argument_spec=dict(
            kong_admin_uri=dict(required=True, type='str'),
            kong_admin_username=dict(required=False, type='str'),
            kong_admin_password=dict(required=False, type='str', no_log=True),
            service=dict(required=True, type='str'),
            name=dict(required=False, type='str'),
            protocols=dict(required=False, default=['http', 'https'],
                           choices=['http', 'https', 'tcp', 'tls'], type='list'),
            methods=dict(required=False, default=[], type='list'),
            hosts=dict(required=False, default=[], type='list'),
            paths=dict(required=False, default=[], type='list'),
            snis=dict(required=False, default=[], type='list'),
            sources=dict(required=False, default=[], type='list'),
            destinations=dict(required=False, default=[], type='list'),
            strip_path=dict(required=False, default=True, type='bool'),
            preserve_host=dict(required=False, default=False, type='bool'),
            state=dict(required=False, default="present",
                       choices=['present', 'absent'], type='str'),
        ),
        supports_check_mode=True
    )

    # Initialize output dictionary
    result = {}

    # Emulates 'required_one_of' argument spec, as it cannot be made conditional
    if ansible_module.params['state'] == 'present' and \
            not ansible_module.params['protocols'] and \
            not ansible_module.params['methods'] and \
            not ansible_module.params['hosts'] and \
            not ansible_module.params['paths'] and \
            not ansible_module.params['snis'] and \
            not ansible_module.params['sources'] and \
            not ansible_module.params['destinations']:
        ansible_module.fail_json(
            msg="At least one of protocols, methods, hosts, paths, snis, " +
                "sources or destinations is required when state is 'present'")

    api_fields = [
        'protocols',
        'hosts',
        'paths',
        'methods',
        'snis',
        'sources',
        'destinations',
        'strip_path',
        'preserve_host'
    ]

    # Extract api_fields from module parameters into separate dictionary
    data = params_fields_lookup(ansible_module, api_fields)

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract other arguments
    service = ansible_module.params['service']
    name = ansible_module.params['name']
    state = ansible_module.params['state']

    # Create Kong client instance.
    k = KongRoute(url, auth_user=auth_user, auth_pass=auth_pass)
    kong_status_check(k, ansible_module)
    kong_version_check(k, ansible_module)

    # Default return values
    changed = False
    resp = ''

    orig = None
    if name:
        # Route name is given, only manage a named object.
        orig = k.route_get(name)

        # Pass 'name' parameter to route_apply data.
        data['name'] = name
    else:
        try:
            # Check if a Route with these parameters already exists
            # without including the route name.
            rq = k.route_query(service, protocols=data['protocols'],
                               hosts=data['hosts'], paths=data['paths'], methods=data['methods'],
                               snis=data['snis'], sources=data['sources'], destinations=data['destinations'])
        except requests.HTTPError as e:
            ansible_module.fail_json(
                msg="Error querying Route: '{}'".format(e))

        if len(rq) > 1:
            ansible_module.fail_json(
                msg='Multiple results for Route query', results=rq)

        if rq:
            orig = rq[0]

    # Ensure the Route is configured.
    if state == "present":
        if orig:
            # Diff existing Route object against the target data if it already exists.
            routediff = dotdiff(orig, data)
            if routediff:
                changed = True
                result['state'] = 'modified'
                result['diff'] = [dict(prepared=render_list(routediff))]

        else:
            # Insert a new Route, set changed.
            changed = True
            result['state'] = 'created'
            result['diff'] = dict(
                before_header='<undefined>', before='<undefined>\n',
                after_header=service, after=data
            )

        if not ansible_module.check_mode and changed:
            try:
                resp = k.route_apply(service, **data)
            except requests.HTTPError as e:
                ansible_module.fail_json(
                    msg='Error applying Route: {}'.format(e))

    # Ensure the Route is deleted.
    if state == "absent":
        # Predict a change if the API exists.
        if orig:
            changed = True
            result['state'] = 'deleted'
            result['diff'] = dict(
                before_header=service, before=orig,
                after_header='<deleted>', after='\n'
            )

            if not ansible_module.check_mode:
                try:
                    resp = k.route_delete(orig['id'])
                except requests.HTTPError as e:
                    ansible_module.fail_json(
                        msg='Error deleting Route: {}'.format(e))

    # Prepare module output
    result.update(changed=changed)

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    ansible_module.exit_json(**result)
コード例 #9
0
def main():
    ansible_module = AnsibleModule(argument_spec=dict(
        kong_admin_uri=dict(required=True, type='str'),
        kong_admin_username=dict(required=False, type='str'),
        kong_admin_password=dict(required=False, type='str', no_log=True),
        username=dict(required=True, type='list'),
        tags=dict(required=False, type='list'),
        state=dict(required=False,
                   default="present",
                   choices=['present', 'absent'],
                   type='str'),
    ),
                                   supports_check_mode=True)

    # We don't support custom_id, as its use is too limited in terms of querying
    # the Kong API. The custom_id is not a primary key, cannot be used as an index
    # in many operations, though it's marked as UNIQUE.

    # Initialize output dictionary
    result = {}

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract other arguments
    state = ansible_module.params['state']
    users = ansible_module.params['username']
    tags = ansible_module.params['tags']

    api_fields = ['name', 'tags']

    # Extract api_fields from module parameters into separate dictionary
    data = params_fields_lookup(ansible_module, api_fields)

    # Create KongAPI client instance
    k = KongConsumer(url, auth_user=auth_user, auth_pass=auth_pass)

    # Contact Kong status endpoint
    kong_status_check(k, ansible_module)

    # Default return values
    changed = False
    resp = ''
    diff = []

    # Ensure the Consumer(s) are registered in Kong
    if state == "present":

        for username in users:

            orig = k.consumer_get(username)
            if orig is not None:
                # Diff the remote Consumer object against the target data if it already exists
                consumer_diff = dotdiff(orig, data)
                resp = orig
                # Set changed flag if there's a diff
                if consumer_diff:
                    data['username'] = orig['username']
                    # Log modified state and diff result
                    changed = True
                    result['state'] = 'modified'
                    result['diff'] = [
                        dict(prepared=render_list(consumer_diff))
                    ]

            else:
                # We're inserting a new Consumer, set changed
                data['username'] = username
                changed = True
                result['state'] = 'created'
                result['diff'] = dict(before_header='<undefined>',
                                      before='<undefined>\n',
                                      after_header=username,
                                      after=data)

            # Only make changes when Ansible is not run in check mode
            if not ansible_module.check_mode and changed:
                try:
                    resp = k.consumer_apply(**data)
                except Exception as e:
                    err_msg = "Consumer configuration rejected by Kong: '{}'. " \
                              "Please check configuration of the API you are trying to configure."
                    ansible_module.fail_json(msg=err_msg.format(e))

    # Ensure the Consumer is deleted
    if state == "absent":

        for username in users:
            # Check if the Consumer exists
            orig = k.consumer_get(username)

            # Predict a change if the Consumer is present
            if orig:
                changed = True
                result['state'] = 'deleted'

                diff.append(
                    dict(before_header=username,
                         before=orig,
                         after_header='<deleted>',
                         after='\n'))

            # Only make changes when Ansible is not run in check mode
            if not ansible_module.check_mode and orig:
                # Issue delete call to the Kong API
                try:
                    resp = k.consumer_delete(username)
                except Exception as e:
                    ansible_module.fail_json(
                        msg='Error deleting Consumer: {}'.format(e))

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    # Pass through the diff result
    if diff:
        result['diff'] = diff

    # Prepare module output
    result.update(dict(changed=changed, ))

    ansible_module.exit_json(**result)
コード例 #10
0
def main():
    ansible_module = AnsibleModule(
        argument_spec=dict(
            kong_admin_uri=dict(required=True, type='str'),
            kong_admin_username=dict(required=False, type='str'),
            kong_admin_password=dict(required=False, type='str', no_log=True),
            name=dict(required=True, type='str'),
            protocol=dict(required=False, default="http", choices=['http', 'https'], type='str'),
            host=dict(required=True, type='str'),
            port=dict(required=False, default=80, type='int'),
            path=dict(required=False, type='str'),
            tags=dict(required=False, type='list'),
            retries=dict(required=False, default=5, type='int'),
            connect_timeout=dict(required=False, default=60000, type='int'),
            write_timeout=dict(required=False, default=60000, type='int'),
            read_timeout=dict(required=False, default=60000, type='int'),
            state=dict(required=False, default="present", choices=['present', 'absent'], type='str'),
        ),
        required_if=[
            ('state', 'present', ['host', 'name'])
        ],
        supports_check_mode=True
    )

    # Initialize output dictionary
    result = {}

    # Kong 0.14.x
    api_fields = [
        'name',
        'protocol',
        'host',
        'port',
        'path',
        'retries',
        'connect_timeout',
        'write_timeout',
        'read_timeout',
        'tags'
    ]

    # Extract api_fields from module parameters into separate dictionary
    data = params_fields_lookup(ansible_module, api_fields)

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract other arguments
    state = ansible_module.params['state']
    name = ansible_module.params['name']

    # Create KongService client instance
    k = KongService(url, auth_user=auth_user, auth_pass=auth_pass)

    # Contact Kong status endpoint
    kong_status_check(k, ansible_module)

    # Default return values
    changed = False
    resp = ''

    # Ensure the service is registered in Kong
    if state == "present":

        # Check if the service exists
        orig = k.service_get(name)
        if orig is not None:

            # Diff the remote API object against the target data if it already exists
            servicediff = dotdiff(orig, data)

            # Set changed flag if there's a diff
            if servicediff:
                # Log modified state and diff result
                changed = True
                result['state'] = 'modified'
                result['diff'] = [dict(prepared=render_list(servicediff))]

        else:
            # We're inserting a new service, set changed
            changed = True
            result['state'] = 'created'
            result['diff'] = dict(
                before_header='<undefined>', before='<undefined>\n',
                after_header=name, after=data
            )

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and changed:
            try:
                resp = k.service_apply(**data)
            except Exception as e:
                app_err = "Service configuration rejected by Kong: '{}'. " \
                          "Please check configuration of the service you are trying to configure."
                ansible_module.fail_json(msg=app_err.format(e))

    # Ensure the service is deleted
    if state == "absent":

        # Check if the service exists
        orig = k.service_get(name)

        # Predict a change if the service exists
        if orig:
            changed = True
            result['state'] = 'deleted'
            result['diff'] = dict(
                before_header=name, before=orig,
                after_header='<deleted>', after='\n'
            )

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode and orig:
            # Issue delete call to the Kong service
            try:
                resp = k.service_delete(name)
            except Exception as e:
                ansible_module.fail_json(msg='Error deleting service: {}'.format(e))

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    # Prepare module output
    result.update(
        dict(
            changed=changed,
        )
    )

    ansible_module.exit_json(**result)
コード例 #11
0
def main():
    """Execute the Kong Consumer Credential module."""
    ansible_module = AnsibleModule(argument_spec=dict(
        kong_admin_uri=dict(required=True, type='str'),
        kong_admin_username=dict(required=False, type='str'),
        kong_admin_password=dict(required=False, type='str', no_log=True),
        username=dict(required=True, type='str'),
        type=dict(required=True,
                  type='str',
                  choices=[
                      'acls', 'basic-auth', 'hmac-auth', 'key-auth', 'jwt',
                      'oauth2'
                  ]),
        config=dict(required=False, type='dict', default=dict()),
        state=dict(required=False,
                   type='str',
                   choices=['present', 'absent'],
                   default='present'),
    ),
                                   supports_check_mode=True)

    # Initialize output dictionary
    result = {}

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract  arguments
    state = ansible_module.params['state']
    username = ansible_module.params['username']
    auth_type = ansible_module.params['type']
    config = ansible_module.params['config']

    # Create Kong client instance.
    k = KongConsumer(url, auth_user=auth_user, auth_pass=auth_pass)
    kong_status_check(k, ansible_module)
    kong_version_check(k, ansible_module)

    # Default return values
    changed = False
    resp = ''
    diff = []

    try:
        # Check if the credential for the Consumer exists.
        cq = k.credential_query(username, auth_type, config=config)
    except ValueError as e:
        # Missing Consumer is not an error when state is 'absent'.
        if state == 'absent':
            ansible_module.exit_json(msg=str(e))

        ansible_module.fail_json(msg=str(e))
    except requests.HTTPError as e:
        ansible_module.fail_json(
            msg="Error querying credential: '{}'.".format(e))

    if len(cq) > 1:
        ansible_module.fail_json(msg='Multiple results for credential query',
                                 results=cq)

    # Ensure the credential is configured.
    if state == 'present':
        if cq:
            if not ansible_module.check_mode:
                try:
                    resp = k.credential_apply(username,
                                              auth_type,
                                              config=config)
                except requests.HTTPError as e:
                    ansible_module.fail_json(msg=str(e))

                orig = cq[0]

                # Diff the remote API object against the target data if it already exists.
                cred_diff = dotdiff(orig, resp)

                # Set changed flag if there's a diff
                if cred_diff:
                    # Log modified state and diff result
                    changed = True
                    result['state'] = 'modified'
                    result['diff'] = [dict(prepared=render_list(cred_diff))]

        # Credential does not exist, create it.
        else:
            changed = True
            result['state'] = 'created'

            # Append diff entry
            diff.append(
                dict(before_header='<undefined>',
                     before='<undefined>\n',
                     after_header='{}/{}'.format(username, auth_type),
                     after=config))

            # Only make changes when Ansible is not run in check mode
            if not ansible_module.check_mode:
                try:
                    resp = k.credential_apply(username,
                                              auth_type,
                                              config=config)

                except requests.HTTPError as e:
                    ansible_module.fail_json(msg=str(e))

    # Ensure the Consumer is deleted
    if state == 'absent' and cq:

        # Get the first (and only) element of the query
        orig = cq[0]

        # Predict a successful delete if the Consumer Plugin is present
        changed = True
        result['state'] = 'deleted'

        diff.append(
            dict(before_header='{}/{}'.format(username, auth_type),
                 before=orig,
                 after_header='<deleted>',
                 after='\n'))

        # Only make changes when Ansible is not run in check mode
        if not ansible_module.check_mode:
            # Issue delete call
            try:
                resp = k.credential_delete(consumer_idname=username,
                                           auth_type=auth_type,
                                           config=config)
            except requests.HTTPError as e:
                ansible_module.fail_json(msg=str(e))

    # Pass through the API response if non-empty
    if resp:
        result['response'] = resp

    # Pass through the diff result
    if diff:
        result['diff'] = diff

    # Prepare module output
    result.update(changed=changed)

    ansible_module.exit_json(**result)
コード例 #12
0
def main():
    """Execute the Kong Plugin module."""
    ansible_module = AnsibleModule(argument_spec=dict(
        kong_admin_uri=dict(required=True, type='str'),
        kong_admin_username=dict(required=False, type='str'),
        kong_admin_password=dict(required=False, type='str', no_log=True),
        name=dict(required=True, type='str'),
        service=dict(required=False, type='str'),
        route=dict(required=False, type='str'),
        consumer=dict(required=False, type='str'),
        config=dict(required=False, type='dict', default=dict()),
        state=dict(required=False,
                   default="present",
                   choices=['present', 'absent'],
                   type='str'),
    ),
                                   supports_check_mode=True)

    # Admin endpoint & auth
    url = ansible_module.params['kong_admin_uri']
    auth_user = ansible_module.params['kong_admin_username']
    auth_pass = ansible_module.params['kong_admin_password']

    # Extract arguments
    state = ansible_module.params['state']
    name = ansible_module.params['name']
    service = ansible_module.params['service']
    route = ansible_module.params['route']
    consumer = ansible_module.params['consumer']
    config = ansible_module.params['config']

    # Create KongAPI client instance
    k = KongPlugin(url, auth_user=auth_user, auth_pass=auth_pass)
    kong_status_check(k, ansible_module)
    kong_version_check(k, ansible_module)

    # Default return values
    changed = False
    resp = ''
    diff = {}
    result = {}

    try:
        pq = k.plugin_query(name=name,
                            service_name=service,
                            route_name=route,
                            consumer_name=consumer)
    except requests.HTTPError as e:
        ansible_module.fail_json(msg="Error querying plugin: '{}'.".format(e))

    if len(pq) > 1:
        ansible_module.fail_json(msg='Multiple results for Plugin query',
                                 results=pq,
                                 name=name,
                                 service=service,
                                 route=route,
                                 consumer=consumer)

    # Ensure the Plugin is configured.
    if state == "present":
        if pq:
            # Extract the remote Plugin object into orig
            orig = pq[0]

            # Diff the existing Plugin against the target data if it already exists.
            plugin_diff = dotdiff(orig.get('config'), config)
            if plugin_diff:
                # Log modified state and diff result.
                changed = True
                result['state'] = 'modified'
                diff = dict(prepared=render_list(plugin_diff))

        else:
            # Configure a new Plugin.
            changed = True
            result['state'] = 'created'
            diff = dict(before_header='<undefined>',
                        before='<undefined>\n',
                        after_header=name,
                        after={
                            'name': name,
                            'service': service,
                            'route': route,
                            'consumer': consumer,
                            'config': config,
                            'state': 'created',
                        })

        if not ansible_module.check_mode and changed:
            try:
                resp = k.plugin_apply(name=name,
                                      config=config,
                                      service_name=service,
                                      route_name=route,
                                      consumer_name=consumer)
            except requests.HTTPError as e:
                ansible_module.fail_json(msg=str(e))

    # Ensure the Plugin is deleted.
    if state == "absent" and pq:

        # Check if the API exists
        orig = pq[0]

        # Predict a change if the Plugin exists
        changed = True
        result['state'] = 'deleted'
        diff = dict(before_header=name,
                    before=orig,
                    after_header='<deleted>',
                    after='\n')

        if not ansible_module.check_mode and orig:
            try:
                resp = k.plugin_delete(name,
                                       service_name=service,
                                       route_name=route,
                                       consumer_name=consumer)
            except requests.HTTPError as e:
                err_msg = "Error deleting Plugin."
                ansible_module.fail_json(msg=err_msg,
                                         response=e.response._content)

    # Prepare module output.
    result.update(changed=changed)

    if resp:
        result['response'] = resp

    if diff:
        result['diff'] = diff

    ansible_module.exit_json(**result)