Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

find (and remove) member from all GitLab projects (that I own)

Tags:

gitlab

Is there a way to search all GitLab groups and associated projects (that I own or administer) for a specific user (with the intent of removing that user)? I know how if they are a member of the group itself, but if the group has many projects and some projects have users added individually, then it's tedious to search each project one-by-one.

like image 574
crimson-egret Avatar asked May 17 '18 17:05

crimson-egret


People also ask

How do I remove myself from a GitLab project?

On projects page select the project. On top right corner select settings button. Then select members. Finally you'll see LEAVE button here.

What is the GitLab Ghost user?

When a user is deleted from a GitLab instance, some associated records are left behind and attributed to Ghost User. The user itself is removed from the users table, disposing of identifiable information. For meeting requirements like GDPR's right to be forgotten, this is good.


1 Answers

I have not found such functionality in GitLab UI, so I developed python script using GitLab API.

Here is the link to repo with source code of my script and docs: https://gitlab.com/CVisionLab/gitlab-tools/

Just download the gitlab-delete-members.py script and run in bash command line. Usage example:

$ gitlab-delete-members.py --query johndoe123 --token Abcdefg123
šŸ’¬ Auth at https://gitlab.com
Project "MyGroupSpam / my-project-foo" (id=11111111) : no users to delete
Project "MyGroupSpam / my-project-bar" (id=11111112) : delete johndoe123 (id=3333333) : šŸŸ¢ ok
Project "NotMyGroupEggs / not-my-project-baz" (id=11111113) : delete johndoe123 (id=3333333) : šŸ”“ fail
šŸ’¬ 1 members deleted in 2 repositories

Just in case I provide full source of the script here:

#!/usr/bin/env python3

# -*- coding: utf-8 -*-

"""Handy script for searching and deleting members from Gitlab projects.
Built on top of GitLab Python API: https://python-gitlab.readthedocs.io/
"""

import argparse
import gitlab


def parse_args():
    parser = argparse.ArgumentParser(
        description='Delete member from all accessible gitlab projects.')
    parser.add_argument('--query', required=True,
                        help='Gitlab query string that defines users '
                        'to be deleted (username is recommended)')
    parser.add_argument('--token', required=True,
                        help='Gitlab token of your user')
    parser.add_argument('--url', default='https://gitlab.com',
                        help='Gitlab URL')
    parser.add_argument('--visibility', default='private',
                        help='Gitlab projects visibility')
    parser.add_argument('--dry', action='store_true',
                        help='dry run')
    return parser.parse_args()


def print_ok():
    print('šŸŸ¢ ok')


def print_fail():
    print('šŸ”“ fail')


def print_skip():
    print('šŸŸ” skip')


def main():
    # Greeting and args parsing.
    args = parse_args()

    # Initialize Gitlab API.
    print(f'šŸ’¬ Auth to {args.url} : ', end='')
    gl = gitlab.Gitlab(args.url, private_token=args.token)
    try:
        gl.auth()
        print_ok()
    except:  # noqa
        print_fail()
        return

    # Iterate over projects.
    projects = gl.projects.list(all=True, visibility=args.visibility)
    del_members_count = 0
    del_projects_count = 0
    for p in projects:
        print(f'Project "{p.name_with_namespace}" (id={p.id}) :',
              end='')

        # Query members.
        members = p.members.list(query=args.query)

        # Delete members.
        if len(members) == 0:
            print(' no users to delete')
        else:
            del_projects_count += 1
            for m in members:
                print(f' delete {m.username} (id={m.id}) : ', end='')
                if not args.dry:
                    try:
                        m.delete()
                        print_ok()
                        del_members_count += 1
                    except:  # noqa
                        print_fail()
                else:
                    print_skip()

    # Statistics.
    print(f'šŸ’¬ {del_members_count} members deleted '
          f'in {del_projects_count} repositories')


if __name__ == '__main__':
    main()

If you want to know which GitLab API functions are used, here is the short list:

  • gl = gitlab.Gitlab(...) ā€“ create API object
  • gl.auth() - authenticate
  • projects = gl.projects.list(...) - get list of projects
  • members = p.members.list(...) - list members of the certain project that matches query
  • m.delete() - delete member from project
like image 130
Vlad Avatar answered Oct 24 '22 15:10

Vlad