Beispiel #1
0
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        api_token=dict(type='str', required=True, no_log=True),
        project=dict(type='str', required=True),
        name=dict(type='str', required=True),
        merge_access_levels=dict(type='str', default="maintainer", choices=["maintainer", "developer", "nobody"]),
        push_access_level=dict(type='str', default="maintainer", choices=["maintainer", "developer", "nobody"]),
        state=dict(type='str', default="present", choices=["absent", "present"]),
    )

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[
            ['api_username', 'api_token'],
            ['api_password', 'api_token'],
        ],
        required_together=[
            ['api_username', 'api_password'],
        ],
        required_one_of=[
            ['api_username', 'api_token']
        ],
        supports_check_mode=True
    )

    project = module.params['project']
    name = module.params['name']
    merge_access_levels = module.params['merge_access_levels']
    push_access_level = module.params['push_access_level']
    state = module.params['state']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"), exception=GITLAB_IMP_ERR)

    gitlab_version = gitlab.__version__
    if LooseVersion(gitlab_version) < LooseVersion('2.3.0'):
        module.fail_json(msg="community.general.gitlab_proteched_branch requires python-gitlab Python module >= 2.3.0 (installed version: [%s])."
                             " Please upgrade python-gitlab to version 2.3.0 or above." % gitlab_version)

    gitlab_instance = gitlabAuthentication(module)
    this_gitlab = GitlabProtectedBranch(module=module, project=project, gitlab_instance=gitlab_instance)

    p_branch = this_gitlab.protected_branch_exist(name=name)
    if not p_branch and state == "present":
        this_gitlab.create_protected_branch(name=name, merge_access_levels=merge_access_levels, push_access_level=push_access_level)
        module.exit_json(changed=True, msg="Created the proteched branch.")
    elif p_branch and state == "present":
        if not this_gitlab.compare_protected_branch(name, merge_access_levels, push_access_level):
            this_gitlab.delete_protected_branch(name=name)
            this_gitlab.create_protected_branch(name=name, merge_access_levels=merge_access_levels, push_access_level=push_access_level)
            module.exit_json(changed=True, msg="Recreated the proteched branch.")
    elif p_branch and state == "absent":
        this_gitlab.delete_protected_branch(name=name)
        module.exit_json(changed=True, msg="Deleted the proteched branch.")
    module.exit_json(changed=False, msg="No changes are needed.")
Beispiel #2
0
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(api_token=dict(type='str', required=True,
                                        no_log=True),
                         project=dict(type='str', required=True),
                         purge=dict(type='bool', required=False,
                                    default=False),
                         vars=dict(type='dict',
                                   required=False,
                                   default=dict(),
                                   no_log=True),
                         state=dict(type='str',
                                    default="present",
                                    choices=["absent", "present"]))

    module = AnsibleModule(argument_spec=argument_spec,
                           mutually_exclusive=[
                               ['api_username', 'api_token'],
                               ['api_password', 'api_token'],
                           ],
                           required_together=[
                               ['api_username', 'api_password'],
                           ],
                           required_one_of=[['api_username', 'api_token']],
                           supports_check_mode=True)

    purge = module.params['purge']
    var_list = module.params['vars']
    state = module.params['state']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"),
                         exception=GITLAB_IMP_ERR)

    gitlab_instance = gitlabAuthentication(module)

    this_gitlab = GitlabProjectVariables(module=module,
                                         gitlab_instance=gitlab_instance)

    change, return_value = native_python_main(this_gitlab, purge, var_list,
                                              state, module)

    module.exit_json(changed=change, project_variable=return_value)
Beispiel #3
0
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        dict(
            api_token=dict(type='str', no_log=True),
            name=dict(type='str'),
            state=dict(type='str',
                       default="present",
                       choices=["absent", "present"]),
            username=dict(type='str', required=True),
            password=dict(type='str', no_log=True),
            email=dict(type='str'),
            sshkey_name=dict(type='str'),
            sshkey_file=dict(type='str'),
            group=dict(type='str'),
            access_level=dict(type='str',
                              default="guest",
                              choices=[
                                  "developer", "guest", "maintainer", "master",
                                  "owner", "reporter"
                              ]),
            confirm=dict(type='bool', default=True),
            isadmin=dict(type='bool', default=False),
            external=dict(type='bool', default=False),
        ))

    module = AnsibleModule(argument_spec=argument_spec,
                           mutually_exclusive=[
                               ['api_username', 'api_token'],
                               ['api_password', 'api_token'],
                           ],
                           required_together=[
                               ['api_username', 'api_password'],
                           ],
                           required_one_of=[['api_username', 'api_token']],
                           supports_check_mode=True,
                           required_if=(('state', 'present',
                                         ['name', 'email', 'password']), ))

    user_name = module.params['name']
    state = module.params['state']
    user_username = module.params['username'].lower()
    user_password = module.params['password']
    user_email = module.params['email']
    user_sshkey_name = module.params['sshkey_name']
    user_sshkey_file = module.params['sshkey_file']
    group_path = module.params['group']
    access_level = module.params['access_level']
    confirm = module.params['confirm']
    user_isadmin = module.params['isadmin']
    user_external = module.params['external']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"),
                         exception=GITLAB_IMP_ERR)

    gitlab_instance = gitlabAuthentication(module)

    gitlab_user = GitLabUser(module, gitlab_instance)
    user_exists = gitlab_user.existsUser(user_username)

    if state == 'absent':
        if user_exists:
            gitlab_user.deleteUser()
            module.exit_json(changed=True,
                             msg="Successfully deleted user %s" %
                             user_username)
        else:
            module.exit_json(changed=False,
                             msg="User deleted or does not exists")

    if state == 'present':
        if gitlab_user.createOrUpdateUser(
                user_username, {
                    "name": user_name,
                    "password": user_password,
                    "email": user_email,
                    "sshkey_name": user_sshkey_name,
                    "sshkey_file": user_sshkey_file,
                    "group_path": group_path,
                    "access_level": access_level,
                    "confirm": confirm,
                    "isadmin": user_isadmin,
                    "external": user_external
                }):
            module.exit_json(
                changed=True,
                msg="Successfully created or updated the user %s" %
                user_username,
                user=gitlab_user.userObject._attrs)
        else:
            module.exit_json(changed=False,
                             msg="No need to update the user %s" %
                             user_username,
                             user=gitlab_user.userObject._attrs)
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        dict(
            api_token=dict(type='str', no_log=True),
            state=dict(type='str',
                       default="present",
                       choices=["absent", "present"]),
            project=dict(type='str', required=True),
            hook_url=dict(type='str', required=True),
            push_events=dict(type='bool', default=True),
            push_events_branch_filter=dict(type='str', default=''),
            issues_events=dict(type='bool', default=False),
            merge_requests_events=dict(type='bool', default=False),
            tag_push_events=dict(type='bool', default=False),
            note_events=dict(type='bool', default=False),
            job_events=dict(type='bool', default=False),
            pipeline_events=dict(type='bool', default=False),
            wiki_page_events=dict(type='bool', default=False),
            hook_validate_certs=dict(type='bool',
                                     default=False,
                                     aliases=['enable_ssl_verification']),
            token=dict(type='str', no_log=True),
        ))

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[['api_username', 'api_token'],
                            ['api_password', 'api_token']],
        required_together=[['api_username', 'api_password']],
        required_one_of=[['api_username', 'api_token']],
        supports_check_mode=True,
    )

    state = module.params['state']
    project_identifier = module.params['project']
    hook_url = module.params['hook_url']
    push_events = module.params['push_events']
    push_events_branch_filter = module.params['push_events_branch_filter']
    issues_events = module.params['issues_events']
    merge_requests_events = module.params['merge_requests_events']
    tag_push_events = module.params['tag_push_events']
    note_events = module.params['note_events']
    job_events = module.params['job_events']
    pipeline_events = module.params['pipeline_events']
    wiki_page_events = module.params['wiki_page_events']
    enable_ssl_verification = module.params['hook_validate_certs']
    hook_token = module.params['token']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"),
                         exception=GITLAB_IMP_ERR)

    gitlab_instance = gitlabAuthentication(module)

    gitlab_hook = GitLabHook(module, gitlab_instance)

    project = findProject(gitlab_instance, project_identifier)

    if project is None:
        module.fail_json(
            msg="Failed to create hook: project %s doesn't exists" %
            project_identifier)

    hook_exists = gitlab_hook.existsHook(project, hook_url)

    if state == 'absent':
        if hook_exists:
            gitlab_hook.deleteHook()
            module.exit_json(changed=True,
                             msg="Successfully deleted hook %s" % hook_url)
        else:
            module.exit_json(changed=False,
                             msg="Hook deleted or does not exists")

    if state == 'present':
        if gitlab_hook.createOrUpdateHook(
                project, hook_url, {
                    "push_events": push_events,
                    "push_events_branch_filter": push_events_branch_filter,
                    "issues_events": issues_events,
                    "merge_requests_events": merge_requests_events,
                    "tag_push_events": tag_push_events,
                    "note_events": note_events,
                    "job_events": job_events,
                    "pipeline_events": pipeline_events,
                    "wiki_page_events": wiki_page_events,
                    "enable_ssl_verification": enable_ssl_verification,
                    "token": hook_token
                }):

            module.exit_json(
                changed=True,
                msg="Successfully created or updated the hook %s" % hook_url,
                hook=gitlab_hook.hookObject._attrs)
        else:
            module.exit_json(changed=False,
                             msg="No need to update the hook %s" % hook_url,
                             hook=gitlab_hook.hookObject._attrs)
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        dict(api_token=dict(type='str', no_log=True),
             state=dict(type='str',
                        default="present",
                        choices=["absent", "present"]),
             project=dict(type='str', required=True),
             key=dict(type='str', required=True, no_log=False),
             can_push=dict(type='bool', default=False),
             title=dict(type='str', required=True)))

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[['api_username', 'api_token'],
                            ['api_password', 'api_token']],
        required_together=[['api_username', 'api_password']],
        required_one_of=[['api_username', 'api_token']],
        supports_check_mode=True,
    )

    state = module.params['state']
    project_identifier = module.params['project']
    key_title = module.params['title']
    key_keyfile = module.params['key']
    key_can_push = module.params['can_push']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"),
                         exception=GITLAB_IMP_ERR)

    gitlab_instance = gitlabAuthentication(module)

    gitlab_deploy_key = GitLabDeployKey(module, gitlab_instance)

    project = findProject(gitlab_instance, project_identifier)

    if project is None:
        module.fail_json(
            msg="Failed to create deploy key: project %s doesn't exists" %
            project_identifier)

    deployKey_exists = gitlab_deploy_key.existsDeployKey(project, key_title)

    if state == 'absent':
        if deployKey_exists:
            gitlab_deploy_key.deleteDeployKey()
            module.exit_json(changed=True,
                             msg="Successfully deleted deploy key %s" %
                             key_title)
        else:
            module.exit_json(changed=False,
                             msg="Deploy key deleted or does not exists")

    if state == 'present':
        if gitlab_deploy_key.createOrUpdateDeployKey(
                project, key_title, key_keyfile, {'can_push': key_can_push}):

            module.exit_json(
                changed=True,
                msg="Successfully created or updated the deploy key %s" %
                key_title,
                deploy_key=gitlab_deploy_key.deployKeyObject._attrs)
        else:
            module.exit_json(
                changed=False,
                msg="No need to update the deploy key %s" % key_title,
                deploy_key=gitlab_deploy_key.deployKeyObject._attrs)
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        dict(api_token=dict(type='str', required=True, no_log=True),
             gitlab_group=dict(type='str', required=True),
             gitlab_user=dict(type='str', required=True),
             state=dict(type='str',
                        default='present',
                        choices=['present', 'absent']),
             access_level=dict(type='str',
                               required=False,
                               choices=[
                                   'guest', 'reporter', 'developer',
                                   'maintainer', 'owner'
                               ])))

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[
            ['api_username', 'api_token'],
            ['api_password', 'api_token'],
        ],
        required_together=[
            ['api_username', 'api_password'],
        ],
        required_one_of=[
            ['api_username', 'api_token'],
        ],
        required_if=[
            ['state', 'present', ['access_level']],
        ],
        supports_check_mode=True,
    )

    if not HAS_PY_GITLAB:
        module.fail_json(msg=missing_required_lib(
            'python-gitlab',
            url='https://python-gitlab.readthedocs.io/en/stable/'),
                         exception=GITLAB_IMP_ERR)

    gitlab_group = module.params['gitlab_group']
    gitlab_user = module.params['gitlab_user']
    state = module.params['state']
    access_level = module.params['access_level']

    # convert access level string input to int
    if access_level:
        access_level_int = {
            'guest': gitlab.GUEST_ACCESS,
            'reporter': gitlab.REPORTER_ACCESS,
            'developer': gitlab.DEVELOPER_ACCESS,
            'maintainer': gitlab.MAINTAINER_ACCESS,
            'owner': gitlab.OWNER_ACCESS
        }

        access_level = access_level_int[access_level]

    # connect to gitlab server
    gl = gitlabAuthentication(module)

    group = GitLabGroup(module, gl)

    gitlab_user_id = group.get_user_id(gitlab_user)
    gitlab_group_id = group.get_group_id(gitlab_group)

    # group doesn't exist
    if not gitlab_group_id:
        module.fail_json(msg="group '%s' not found." % gitlab_group)

    # user doesn't exist
    if not gitlab_user_id:
        if state == 'absent':
            module.exit_json(
                changed=False,
                result=
                "user '%s' not found, and thus also not part of the group" %
                gitlab_user)
        else:
            module.fail_json(msg="user '%s' not found." % gitlab_user)

    members = group.get_members_in_a_group(gitlab_group_id)
    is_user_a_member = group.is_user_a_member(members, gitlab_user_id)

    # check if the user is a member in the group
    if not is_user_a_member:
        if state == 'present':
            # add user to the group
            if not module.check_mode:
                group.add_member_to_group(gitlab_user_id, gitlab_group_id,
                                          access_level)
            module.exit_json(
                changed=True,
                result="Successfully added user '%s' to the group." %
                gitlab_user)
        # state as absent
        else:
            module.exit_json(
                changed=False,
                result=
                "User, '%s', is not a member in the group. No change to report"
                % gitlab_user)
    # in case that a user is a member
    else:
        if state == 'present':
            # compare the access level
            user_access_level = group.get_user_access_level(
                members, gitlab_user_id)
            if user_access_level == access_level:
                module.exit_json(
                    changed=False,
                    result=
                    "User, '%s', is already a member in the group. No change to report"
                    % gitlab_user)
            else:
                # update the access level for the user
                if not module.check_mode:
                    group.update_user_access_level(members, gitlab_user_id,
                                                   access_level)
                module.exit_json(
                    changed=True,
                    result=
                    "Successfully updated the access level for the user, '%s'"
                    % gitlab_user)
        else:
            # remove the user from the group
            if not module.check_mode:
                group.remove_user_from_group(gitlab_user_id, gitlab_group_id)
            module.exit_json(
                changed=True,
                result="Successfully removed user, '%s', from the group" %
                gitlab_user)
Beispiel #7
0
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        dict(
            api_token=dict(type='str', no_log=True),
            name=dict(type='str', required=True),
            path=dict(type='str'),
            description=dict(type='str'),
            state=dict(type='str',
                       default="present",
                       choices=["absent", "present"]),
            parent=dict(type='str'),
            visibility=dict(type='str',
                            default="private",
                            choices=["internal", "private", "public"]),
        ))

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[
            ['api_username', 'api_token'],
            ['api_password', 'api_token'],
        ],
        required_together=[
            ['api_username', 'api_password'],
        ],
        required_one_of=[['api_username', 'api_token']],
        supports_check_mode=True,
    )

    group_name = module.params['name']
    group_path = module.params['path']
    description = module.params['description']
    state = module.params['state']
    parent_identifier = module.params['parent']
    group_visibility = module.params['visibility']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"),
                         exception=GITLAB_IMP_ERR)

    gitlab_instance = gitlabAuthentication(module)

    # Define default group_path based on group_name
    if group_path is None:
        group_path = group_name.replace(" ", "_")

    gitlab_group = GitLabGroup(module, gitlab_instance)

    parent_group = None
    if parent_identifier:
        parent_group = findGroup(gitlab_instance, parent_identifier)
        if not parent_group:
            module.fail_json(
                msg="Failed create GitLab group: Parent group doesn't exists")

        group_exists = gitlab_group.existsGroup(parent_group.full_path + '/' +
                                                group_path)
    else:
        group_exists = gitlab_group.existsGroup(group_path)

    if state == 'absent':
        if group_exists:
            gitlab_group.deleteGroup()
            module.exit_json(changed=True,
                             msg="Successfully deleted group %s" % group_name)
        else:
            module.exit_json(changed=False,
                             msg="Group deleted or does not exists")

    if state == 'present':
        if gitlab_group.createOrUpdateGroup(
                group_name, parent_group, {
                    "path": group_path,
                    "description": description,
                    "visibility": group_visibility
                }):
            module.exit_json(
                changed=True,
                msg="Successfully created or updated the group %s" %
                group_name,
                group=gitlab_group.groupObject._attrs)
        else:
            module.exit_json(changed=False,
                             msg="No need to update the group %s" % group_name,
                             group=gitlab_group.groupObject._attrs)
Beispiel #8
0
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        dict(
            api_token=dict(type='str', no_log=True),
            group=dict(type='str'),
            name=dict(type='str', required=True),
            path=dict(type='str'),
            description=dict(type='str'),
            issues_enabled=dict(type='bool', default=True),
            merge_requests_enabled=dict(type='bool', default=True),
            merge_method=dict(type='str',
                              default='merge',
                              choices=["merge", "rebase_merge", "ff"]),
            wiki_enabled=dict(type='bool', default=True),
            snippets_enabled=dict(default=True, type='bool'),
            visibility=dict(type='str',
                            default="private",
                            choices=["internal", "private", "public"],
                            aliases=["visibility_level"]),
            import_url=dict(type='str'),
            state=dict(type='str',
                       default="present",
                       choices=["absent", "present"]),
        ))

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[
            ['api_username', 'api_token'],
            ['api_password', 'api_token'],
        ],
        required_together=[
            ['api_username', 'api_password'],
        ],
        required_one_of=[['api_username', 'api_token']],
        supports_check_mode=True,
    )

    group_identifier = module.params['group']
    project_name = module.params['name']
    project_path = module.params['path']
    project_description = module.params['description']
    issues_enabled = module.params['issues_enabled']
    merge_requests_enabled = module.params['merge_requests_enabled']
    merge_method = module.params['merge_method']
    wiki_enabled = module.params['wiki_enabled']
    snippets_enabled = module.params['snippets_enabled']
    visibility = module.params['visibility']
    import_url = module.params['import_url']
    state = module.params['state']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"),
                         exception=GITLAB_IMP_ERR)

    gitlab_instance = gitlabAuthentication(module)

    # Set project_path to project_name if it is empty.
    if project_path is None:
        project_path = project_name.replace(" ", "_")

    gitlab_project = GitLabProject(module, gitlab_instance)

    if group_identifier:
        group = findGroup(gitlab_instance, group_identifier)
        if group is None:
            module.fail_json(
                msg="Failed to create project: group %s doesn't exists" %
                group_identifier)

        namespace = gitlab_instance.namespaces.get(group.id)
        project_exists = gitlab_project.existsProject(namespace, project_path)
    else:
        user = gitlab_instance.users.list(
            username=gitlab_instance.user.username)[0]
        namespace = gitlab_instance.namespaces.get(user.id)
        project_exists = gitlab_project.existsProject(namespace, project_path)

    if state == 'absent':
        if project_exists:
            gitlab_project.deleteProject()
            module.exit_json(changed=True,
                             msg="Successfully deleted project %s" %
                             project_name)
        else:
            module.exit_json(changed=False,
                             msg="Project deleted or does not exists")

    if state == 'present':
        if gitlab_project.createOrUpdateProject(
                project_name, namespace, {
                    "path": project_path,
                    "description": project_description,
                    "issues_enabled": issues_enabled,
                    "merge_requests_enabled": merge_requests_enabled,
                    "merge_method": merge_method,
                    "wiki_enabled": wiki_enabled,
                    "snippets_enabled": snippets_enabled,
                    "visibility": visibility,
                    "import_url": import_url
                }):

            module.exit_json(
                changed=True,
                msg="Successfully created or updated the project %s" %
                project_name,
                project=gitlab_project.projectObject._attrs)
        else:
            module.exit_json(changed=False,
                             msg="No need to update the project %s" %
                             project_name,
                             project=gitlab_project.projectObject._attrs)
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        dict(
            api_token=dict(type='str', no_log=True),
            description=dict(type='str', required=True, aliases=["name"]),
            active=dict(type='bool', default=True),
            tag_list=dict(type='list', default=[]),
            run_untagged=dict(type='bool', default=True),
            locked=dict(type='bool', default=False),
            access_level=dict(type='str',
                              default='ref_protected',
                              choices=["not_protected", "ref_protected"]),
            maximum_timeout=dict(type='int', default=3600),
            registration_token=dict(type='str', required=True),
            state=dict(type='str',
                       default="present",
                       choices=["absent", "present"]),
        ))

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[
            ['api_username', 'api_token'],
            ['api_password', 'api_token'],
        ],
        required_together=[
            ['api_username', 'api_password'],
        ],
        required_one_of=[
            ['api_username', 'api_token'],
        ],
        supports_check_mode=True,
    )

    state = module.params['state']
    runner_description = module.params['description']
    runner_active = module.params['active']
    tag_list = module.params['tag_list']
    run_untagged = module.params['run_untagged']
    runner_locked = module.params['locked']
    access_level = module.params['access_level']
    maximum_timeout = module.params['maximum_timeout']
    registration_token = module.params['registration_token']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"),
                         exception=GITLAB_IMP_ERR)

    gitlab_instance = gitlabAuthentication(module)

    gitlab_runner = GitLabRunner(module, gitlab_instance)
    runner_exists = gitlab_runner.existsRunner(runner_description)

    if state == 'absent':
        if runner_exists:
            gitlab_runner.deleteRunner()
            module.exit_json(changed=True,
                             msg="Successfully deleted runner %s" %
                             runner_description)
        else:
            module.exit_json(changed=False,
                             msg="Runner deleted or does not exists")

    if state == 'present':
        if gitlab_runner.createOrUpdateRunner(
                runner_description, {
                    "active": runner_active,
                    "tag_list": tag_list,
                    "run_untagged": run_untagged,
                    "locked": runner_locked,
                    "access_level": access_level,
                    "maximum_timeout": maximum_timeout,
                    "registration_token": registration_token
                }):
            module.exit_json(
                changed=True,
                runner=gitlab_runner.runnerObject._attrs,
                msg="Successfully created or updated the runner %s" %
                runner_description)
        else:
            module.exit_json(changed=False,
                             runner=gitlab_runner.runnerObject._attrs,
                             msg="No need to update the runner %s" %
                             runner_description)
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(dict(
        api_token=dict(type='str', no_log=True),
        group=dict(type='str'),
        name=dict(type='str', required=True),
        path=dict(type='str'),
        description=dict(type='str'),
        issues_enabled=dict(type='bool', default=True),
        merge_requests_enabled=dict(type='bool', default=True),
        merge_method=dict(type='str', default='merge', choices=["merge", "rebase_merge", "ff"]),
        wiki_enabled=dict(type='bool', default=True),
        snippets_enabled=dict(default=True, type='bool'),
        visibility=dict(type='str', default="private", choices=["internal", "private", "public"], aliases=["visibility_level"]),
        import_url=dict(type='str'),
        state=dict(type='str', default="present", choices=["absent", "present"]),
        lfs_enabled=dict(default=False, type='bool'),
        username=dict(type='str'),
        allow_merge_on_skipped_pipeline=dict(type='bool'),
        only_allow_merge_if_all_discussions_are_resolved=dict(type='bool'),
        only_allow_merge_if_pipeline_succeeds=dict(type='bool'),
        packages_enabled=dict(type='bool'),
        remove_source_branch_after_merge=dict(type='bool'),
        squash_option=dict(type='str', choices=['never', 'always', 'default_off', 'default_on']),
        ci_config_path=dict(type='str'),
        shared_runners_enabled=dict(type='bool'),
    ))

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[
            ['api_username', 'api_token'],
            ['api_password', 'api_token'],
            ['group', 'username'],
        ],
        required_together=[
            ['api_username', 'api_password'],
        ],
        required_one_of=[
            ['api_username', 'api_token']
        ],
        supports_check_mode=True,
    )

    group_identifier = module.params['group']
    project_name = module.params['name']
    project_path = module.params['path']
    project_description = module.params['description']
    issues_enabled = module.params['issues_enabled']
    merge_requests_enabled = module.params['merge_requests_enabled']
    merge_method = module.params['merge_method']
    wiki_enabled = module.params['wiki_enabled']
    snippets_enabled = module.params['snippets_enabled']
    visibility = module.params['visibility']
    import_url = module.params['import_url']
    state = module.params['state']
    lfs_enabled = module.params['lfs_enabled']
    username = module.params['username']
    allow_merge_on_skipped_pipeline = module.params['allow_merge_on_skipped_pipeline']
    only_allow_merge_if_all_discussions_are_resolved = module.params['only_allow_merge_if_all_discussions_are_resolved']
    only_allow_merge_if_pipeline_succeeds = module.params['only_allow_merge_if_pipeline_succeeds']
    packages_enabled = module.params['packages_enabled']
    remove_source_branch_after_merge = module.params['remove_source_branch_after_merge']
    squash_option = module.params['squash_option']
    ci_config_path = module.params['ci_config_path']
    shared_runners_enabled = module.params['shared_runners_enabled']

    if not HAS_GITLAB_PACKAGE:
        module.fail_json(msg=missing_required_lib("python-gitlab"), exception=GITLAB_IMP_ERR)

    gitlab_instance = gitlabAuthentication(module)

    # Set project_path to project_name if it is empty.
    if project_path is None:
        project_path = project_name.replace(" ", "_")

    gitlab_project = GitLabProject(module, gitlab_instance)

    namespace = None
    namespace_id = None
    if group_identifier:
        group = findGroup(gitlab_instance, group_identifier)
        if group is None:
            module.fail_json(msg="Failed to create project: group %s doesn't exists" % group_identifier)

        namespace_id = group.id
    else:
        if username:
            namespace = gitlab_instance.namespaces.list(search=username)[0]
        else:
            namespace = gitlab_instance.namespaces.list(search=gitlab_instance.user.username)[0]
        namespace_id = namespace.id

    if not namespace_id:
        module.fail_json(msg="Failed to find the namespace or group ID which is required to look up the namespace")

    try:
        namespace = gitlab_instance.namespaces.get(namespace_id)
    except gitlab.exceptions.GitlabGetError as e:
        module.fail_json(msg="Failed to find the namespace for the given user: %s" % to_native(e))

    if not namespace:
        module.fail_json(msg="Failed to find the namespace for the project")
    project_exists = gitlab_project.existsProject(namespace, project_path)

    if state == 'absent':
        if project_exists:
            gitlab_project.deleteProject()
            module.exit_json(changed=True, msg="Successfully deleted project %s" % project_name)
        module.exit_json(changed=False, msg="Project deleted or does not exists")

    if state == 'present':

        if gitlab_project.createOrUpdateProject(project_name, namespace, {
                                                "path": project_path,
                                                "description": project_description,
                                                "issues_enabled": issues_enabled,
                                                "merge_requests_enabled": merge_requests_enabled,
                                                "merge_method": merge_method,
                                                "wiki_enabled": wiki_enabled,
                                                "snippets_enabled": snippets_enabled,
                                                "visibility": visibility,
                                                "import_url": import_url,
                                                "lfs_enabled": lfs_enabled,
                                                "allow_merge_on_skipped_pipeline": allow_merge_on_skipped_pipeline,
                                                "only_allow_merge_if_all_discussions_are_resolved": only_allow_merge_if_all_discussions_are_resolved,
                                                "only_allow_merge_if_pipeline_succeeds": only_allow_merge_if_pipeline_succeeds,
                                                "packages_enabled": packages_enabled,
                                                "remove_source_branch_after_merge": remove_source_branch_after_merge,
                                                "squash_option": squash_option,
                                                "ci_config_path": ci_config_path,
                                                "shared_runners_enabled": shared_runners_enabled,
                                                }):

            module.exit_json(changed=True, msg="Successfully created or updated the project %s" % project_name, project=gitlab_project.projectObject._attrs)
        module.exit_json(changed=False, msg="No need to update the project %s" % project_name, project=gitlab_project.projectObject._attrs)
def main():
    argument_spec = basic_auth_argument_spec()
    argument_spec.update(
        dict(
            api_token=dict(type='str', required=True, no_log=True),
            project=dict(type='str', required=True),
            gitlab_user=dict(type='list', elements='str'),
            state=dict(type='str',
                       default='present',
                       choices=['present', 'absent']),
            access_level=dict(
                type='str',
                choices=['guest', 'reporter', 'developer', 'maintainer']),
            purge_users=dict(
                type='list',
                elements='str',
                choices=['guest', 'reporter', 'developer', 'maintainer']),
            gitlab_users_access=dict(type='list',
                                     elements='dict',
                                     options=dict(
                                         name=dict(type='str', required=True),
                                         access_level=dict(type='str',
                                                           choices=[
                                                               'guest',
                                                               'reporter',
                                                               'developer',
                                                               'maintainer'
                                                           ],
                                                           required=True),
                                     )),
        ))

    module = AnsibleModule(
        argument_spec=argument_spec,
        mutually_exclusive=[
            ['api_username', 'api_token'],
            ['api_password', 'api_token'],
            ['gitlab_user', 'gitlab_users_access'],
            ['access_level', 'gitlab_users_access'],
        ],
        required_together=[
            ['api_username', 'api_password'],
            ['gitlab_user', 'access_level'],
        ],
        required_one_of=[
            ['api_username', 'api_token'],
            ['gitlab_user', 'gitlab_users_access'],
        ],
        required_if=[
            [
                'state', 'present', ['access_level', 'gitlab_users_access'],
                True
            ],
        ],
        supports_check_mode=True,
    )

    if not HAS_PY_GITLAB:
        module.fail_json(msg=missing_required_lib(
            'python-gitlab',
            url='https://python-gitlab.readthedocs.io/en/stable/'),
                         exception=GITLAB_IMP_ERR)

    access_level_int = {
        'guest': gitlab.GUEST_ACCESS,
        'reporter': gitlab.REPORTER_ACCESS,
        'developer': gitlab.DEVELOPER_ACCESS,
        'maintainer': gitlab.MAINTAINER_ACCESS,
    }

    gitlab_project = module.params['project']
    state = module.params['state']
    access_level = module.params['access_level']
    purge_users = module.params['purge_users']

    if purge_users:
        purge_users = [access_level_int[level] for level in purge_users]

    # connect to gitlab server
    gl = gitlabAuthentication(module)

    project = GitLabProjectMembers(module, gl)

    gitlab_project_id = project.get_project(gitlab_project)

    # project doesn't exist
    if not gitlab_project_id:
        module.fail_json(msg="project '%s' not found." % gitlab_project)

    members = []
    if module.params['gitlab_user'] is not None:
        gitlab_users_access = []
        gitlab_users = module.params['gitlab_user']
        for gl_user in gitlab_users:
            gitlab_users_access.append({
                'name':
                gl_user,
                'access_level':
                access_level_int[access_level] if access_level else None
            })
    elif module.params['gitlab_users_access'] is not None:
        gitlab_users_access = module.params['gitlab_users_access']
        for user_level in gitlab_users_access:
            user_level['access_level'] = access_level_int[
                user_level['access_level']]

    if len(gitlab_users_access) == 1 and not purge_users:
        # only single user given
        members = [
            project.get_member_in_a_project(
                gitlab_project_id,
                project.get_user_id(gitlab_users_access[0]['name']))
        ]
        if members[0] is None:
            members = []
    elif len(gitlab_users_access) > 1 or purge_users:
        # list of users given
        members = project.get_members_in_a_project(gitlab_project_id)
    else:
        module.exit_json(
            changed='OK',
            result=
            "Nothing to do, please give at least one user or set purge_users true.",
            result_data=[])

    changed = False
    error = False
    changed_users = []
    changed_data = []

    for gitlab_user in gitlab_users_access:
        gitlab_user_id = project.get_user_id(gitlab_user['name'])

        # user doesn't exist
        if not gitlab_user_id:
            if state == 'absent':
                changed_users.append(
                    "user '%s' not found, and thus also not part of the project"
                    % gitlab_user['name'])
                changed_data.append({
                    'gitlab_user':
                    gitlab_user['name'],
                    'result':
                    'OK',
                    'msg':
                    "user '%s' not found, and thus also not part of the project"
                    % gitlab_user['name']
                })
            else:
                error = True
                changed_users.append("user '%s' not found." %
                                     gitlab_user['name'])
                changed_data.append({
                    'gitlab_user':
                    gitlab_user['name'],
                    'result':
                    'FAILED',
                    'msg':
                    "user '%s' not found." % gitlab_user['name']
                })
            continue

        is_user_a_member = project.is_user_a_member(members, gitlab_user_id)

        # check if the user is a member in the project
        if not is_user_a_member:
            if state == 'present':
                # add user to the project
                try:
                    if not module.check_mode:
                        project.add_member_to_project(
                            gitlab_user_id, gitlab_project_id,
                            gitlab_user['access_level'])
                    changed = True
                    changed_users.append(
                        "Successfully added user '%s' to project" %
                        gitlab_user['name'])
                    changed_data.append({
                        'gitlab_user':
                        gitlab_user['name'],
                        'result':
                        'CHANGED',
                        'msg':
                        "Successfully added user '%s' to project" %
                        gitlab_user['name']
                    })
                except (gitlab.exceptions.GitlabCreateError) as e:
                    error = True
                    changed_users.append(
                        "Failed to updated the access level for the user, '%s'"
                        % gitlab_user['name'])
                    changed_data.append({
                        'gitlab_user':
                        gitlab_user['name'],
                        'result':
                        'FAILED',
                        'msg':
                        "Not allowed to add the access level for the member, %s: %s"
                        % (gitlab_user['name'], e)
                    })
            # state as absent
            else:
                changed_users.append(
                    "User, '%s', is not a member in the project. No change to report"
                    % gitlab_user['name'])
                changed_data.append({
                    'gitlab_user':
                    gitlab_user['name'],
                    'result':
                    'OK',
                    'msg':
                    "User, '%s', is not a member in the project. No change to report"
                    % gitlab_user['name']
                })
        # in case that a user is a member
        else:
            if state == 'present':
                # compare the access level
                user_access_level = project.get_user_access_level(
                    members, gitlab_user_id)
                if user_access_level == gitlab_user['access_level']:
                    changed_users.append(
                        "User, '%s', is already a member in the project. No change to report"
                        % gitlab_user['name'])
                    changed_data.append({
                        'gitlab_user':
                        gitlab_user['name'],
                        'result':
                        'OK',
                        'msg':
                        "User, '%s', is already a member in the project. No change to report"
                        % gitlab_user['name']
                    })
                else:
                    # update the access level for the user
                    try:
                        if not module.check_mode:
                            project.update_user_access_level(
                                members, gitlab_user_id,
                                gitlab_user['access_level'])
                        changed = True
                        changed_users.append(
                            "Successfully updated the access level for the user, '%s'"
                            % gitlab_user['name'])
                        changed_data.append({
                            'gitlab_user':
                            gitlab_user['name'],
                            'result':
                            'CHANGED',
                            'msg':
                            "Successfully updated the access level for the user, '%s'"
                            % gitlab_user['name']
                        })
                    except (gitlab.exceptions.GitlabUpdateError) as e:
                        error = True
                        changed_users.append(
                            "Failed to updated the access level for the user, '%s'"
                            % gitlab_user['name'])
                        changed_data.append({
                            'gitlab_user':
                            gitlab_user['name'],
                            'result':
                            'FAILED',
                            'msg':
                            "Not allowed to update the access level for the member, %s: %s"
                            % (gitlab_user['name'], e)
                        })
            else:
                # remove the user from the project
                try:
                    if not module.check_mode:
                        project.remove_user_from_project(
                            gitlab_user_id, gitlab_project_id)
                    changed = True
                    changed_users.append(
                        "Successfully removed user, '%s', from the project" %
                        gitlab_user['name'])
                    changed_data.append({
                        'gitlab_user':
                        gitlab_user['name'],
                        'result':
                        'CHANGED',
                        'msg':
                        "Successfully removed user, '%s', from the project" %
                        gitlab_user['name']
                    })
                except (gitlab.exceptions.GitlabDeleteError) as e:
                    error = True
                    changed_users.append(
                        "Failed to removed user, '%s', from the project" %
                        gitlab_user['name'])
                    changed_data.append({
                        'gitlab_user':
                        gitlab_user['name'],
                        'result':
                        'FAILED',
                        'msg':
                        "Failed to remove user, '%s' from the project: %s" %
                        (gitlab_user['name'], e)
                    })

    # if state = present and purge_users set delete users which are in members having give access level but not in gitlab_users
    if state == 'present' and purge_users:
        uppercase_names_in_gitlab_users_access = []
        for name in gitlab_users_access:
            uppercase_names_in_gitlab_users_access.append(name['name'].upper())

        for member in members:
            if member.access_level in purge_users and member.username.upper(
            ) not in uppercase_names_in_gitlab_users_access:
                try:
                    if not module.check_mode:
                        project.remove_user_from_project(
                            member.id, gitlab_project_id)
                    changed = True
                    changed_users.append(
                        "Successfully removed user '%s', from project. Was not in given list"
                        % member.username)
                    changed_data.append({
                        'gitlab_user':
                        member.username,
                        'result':
                        'CHANGED',
                        'msg':
                        "Successfully removed user '%s', from project. Was not in given list"
                        % member.username
                    })
                except (gitlab.exceptions.GitlabDeleteError) as e:
                    error = True
                    changed_users.append(
                        "Failed to removed user, '%s', from the project" %
                        gitlab_user['name'])
                    changed_data.append({
                        'gitlab_user':
                        gitlab_user['name'],
                        'result':
                        'FAILED',
                        'msg':
                        "Failed to remove user, '%s' from the project: %s" %
                        (gitlab_user['name'], e)
                    })

    if len(gitlab_users_access) == 1 and error:
        # if single user given and an error occurred return error for list errors will be per user
        module.fail_json(msg="FAILED: '%s '" % changed_users[0],
                         result_data=changed_data)
    elif error:
        module.fail_json(
            msg='FAILED: At least one given user/permission could not be set',
            result_data=changed_data)

    module.exit_json(changed=changed,
                     msg='Successfully set memberships',
                     result="\n".join(changed_users),
                     result_data=changed_data)