Beispiel #1
0
    def test_get_user_role(self):
        assert self.user.role is None
        assert get_user_role(self.user) == DEFAULT_USER

        User.objects.update_role(self.user.email, 'test_role')
        u = User.objects.get(self.user.email)
        assert get_user_role(u) == 'test_role'
Beispiel #2
0
def get_user_info(email):
    user = User.objects.get(email=email)
    profile = Profile.objects.get_profile_by_user(email)

    info = {}
    info['email'] = email
    info['name'] = email2nickname(email)
    info[
        'contact_email'] = profile.contact_email if profile and profile.contact_email else ''
    info['login_id'] = profile.login_id if profile and profile.login_id else ''

    info['is_staff'] = user.is_staff
    info['is_active'] = user.is_active

    orgs = ccnet_api.get_orgs_by_user(email)
    try:
        if orgs:
            org_id = orgs[0].org_id
            info['org_id'] = org_id
            info['org_name'] = orgs[0].org_name
    except Exception as e:
        logger.error(e)

    info['create_time'] = timestamp_to_isoformat_timestr(user.ctime)

    if getattr(settings, 'MULTI_INSTITUTION', False):
        info['institution'] = profile.institution if profile else ''

    info['role'] = get_user_role(user)

    return info
Beispiel #3
0
    def get_info_of_users_order_by_quota_usage(self, source, direction, page,
                                               per_page):

        # get user's quota usage info
        user_usage_dict = {}
        users_with_usage = seafile_api.list_user_quota_usage()
        for user in users_with_usage:
            email = user.user
            if email not in user_usage_dict:
                user_usage_dict[email] = user.usage

        # get all users and map quota usage to user
        if source == 'db':
            users = ccnet_api.get_emailusers('DB', -1, -1)
        else:
            users = ccnet_api.get_emailusers('LDAPImport', -1, -1)

        for user in users:
            email = user.email
            user.quota_usage = user_usage_dict.get(email, -1)

        # sort
        users.sort(key=lambda item: item.quota_usage,
                   reverse=direction == 'desc')

        data = []
        MULTI_INSTITUTION = getattr(settings, 'MULTI_INSTITUTION', False)
        for user in users[(page - 1) * per_page:page * per_page]:

            info = {}
            info['email'] = user.email
            info['name'] = email2nickname(user.email)
            info['contact_email'] = email2contact_email(user.email)

            profile = Profile.objects.get_profile_by_user(user.email)
            info[
                'login_id'] = profile.login_id if profile and profile.login_id else ''

            info['is_staff'] = user.is_staff
            info['is_active'] = user.is_active
            info['create_time'] = timestamp_to_isoformat_timestr(user.ctime)

            info['quota_usage'] = user.quota_usage
            info['quota_total'] = seafile_api.get_user_quota(user.email)

            last_login_obj = UserLastLogin.objects.get_by_username(user.email)
            info['last_login'] = datetime_to_isoformat_timestr(
                last_login_obj.last_login) if last_login_obj else ''

            info['role'] = get_user_role(user)

            if MULTI_INSTITUTION:
                info['institution'] = profile.institution if profile else ''

            data.append(info)

        return data
Beispiel #4
0
def _handle_login_form_valid(request, user, redirect_to, remember_me):
    if UserOptions.objects.passwd_change_required(user.username):
        redirect_to = reverse('auth_password_change')
        request.session['force_passwd_change'] = True

    if user.permissions.role_quota():
        user_role = get_user_role(user)
        quota = get_quota_from_string(user.permissions.role_quota())
        seafile_api.set_role_quota(user_role, quota)

    # password is valid, log user in
    request.session['remember_me'] = remember_me
    return log_user_in(request, user, redirect_to)
Beispiel #5
0
def get_user_info(email):

    user = User.objects.get(email=email)
    profile = Profile.objects.get_profile_by_user(email)

    info = {}
    info['email'] = email
    info['name'] = email2nickname(email)
    info[
        'contact_email'] = profile.contact_email if profile and profile.contact_email else ''
    info['login_id'] = profile.login_id if profile and profile.login_id else ''

    info['is_staff'] = user.is_staff
    info['is_active'] = user.is_active
    info['reference_id'] = user.reference_id if user.reference_id else ''

    orgs = ccnet_api.get_orgs_by_user(email)
    try:
        if orgs:
            org_id = orgs[0].org_id
            info['org_id'] = org_id
            info['org_name'] = orgs[0].org_name
            info['quota_usage'] = seafile_api.get_org_user_quota_usage(
                org_id, user.email)
            info['quota_total'] = seafile_api.get_org_user_quota(
                org_id, user.email)
        else:
            info['quota_usage'] = seafile_api.get_user_self_usage(user.email)
            info['quota_total'] = seafile_api.get_user_quota(user.email)
    except Exception as e:
        logger.error(e)
        info['quota_usage'] = -1
        info['quota_total'] = -1

    info['create_time'] = timestamp_to_isoformat_timestr(user.ctime)

    info['has_default_device'] = True if default_device(user) else False
    info['is_force_2fa'] = UserOptions.objects.is_force_2fa(email)

    if getattr(settings, 'MULTI_INSTITUTION', False):
        info['institution'] = profile.institution if profile else ''

    info['role'] = get_user_role(user)

    return info
Beispiel #6
0
    def get(self, request):
        """Search user from DB, LDAPImport and Profile

        Permission checking:
        1. only admin can perform this action.
        """

        if not request.user.admin_permissions.can_manage_user():
            return api_error(status.HTTP_403_FORBIDDEN, 'Permission denied.')

        query_str = request.GET.get('query', '').lower()
        if not query_str:
            error_msg = 'query invalid.'
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        users = []

        # search user from ccnet db
        users += ccnet_api.search_emailusers('DB', query_str, 0, 10)

        # search user from ccnet ldapimport
        users += ccnet_api.search_emailusers('LDAP', query_str, 0, 10)

        ccnet_user_emails = [u.email for u in users]

        # get institution for user from ccnet
        if getattr(settings, 'MULTI_INSTITUTION', False):
            user_institution_dict = {}
            profiles = Profile.objects.filter(user__in=ccnet_user_emails)
            for profile in profiles:
                email = profile.user
                if email not in user_institution_dict:
                    user_institution_dict[email] = profile.institution

            for user in users:
                user.institution = user_institution_dict.get(user.email, '')

        # search user from profile
        searched_profile = Profile.objects.filter(
            (Q(nickname__icontains=query_str))
            | Q(contact_email__icontains=query_str))[:10]

        for profile in searched_profile:
            email = profile.user
            institution = profile.institution

            # remove duplicate emails
            if email not in ccnet_user_emails:
                try:
                    # get is_staff and is_active info
                    user = User.objects.get(email=email)
                    user.institution = institution
                    users.append(user)
                except User.DoesNotExist:
                    continue

        data = []
        for user in users:

            info = {}
            info['email'] = user.email
            info['name'] = email2nickname(user.email)
            info['contact_email'] = email2contact_email(user.email)

            info['is_staff'] = user.is_staff
            info['is_active'] = user.is_active

            info['source'] = user.source.lower()

            orgs = ccnet_api.get_orgs_by_user(user.email)
            if orgs:
                org_id = orgs[0].org_id
                info['org_id'] = org_id
                info['org_name'] = orgs[0].org_name
                info['quota_usage'] = seafile_api.get_org_user_quota_usage(
                    org_id, user.email)
                info['quota_total'] = seafile_api.get_org_user_quota(
                    org_id, user.email)
            else:
                info['quota_usage'] = seafile_api.get_user_self_usage(
                    user.email)
                info['quota_total'] = seafile_api.get_user_quota(user.email)

            info['create_time'] = timestamp_to_isoformat_timestr(user.ctime)
            last_login_obj = UserLastLogin.objects.get_by_username(user.email)
            info['last_login'] = datetime_to_isoformat_timestr(
                last_login_obj.last_login) if last_login_obj else ''
            info['role'] = get_user_role(user)

            if getattr(settings, 'MULTI_INSTITUTION', False):
                info['institution'] = user.institution

            data.append(info)

        result = {'user_list': data}
        return Response(result)
Beispiel #7
0
    def get(self, request):
        """List all users in DB or LDAPImport

        Permission checking:
        1. only admin can perform this action.
        """

        if not request.user.admin_permissions.can_manage_user():
            return api_error(status.HTTP_403_FORBIDDEN, 'Permission denied.')

        # parameter check
        try:
            page = int(request.GET.get('page', '1'))
            per_page = int(request.GET.get('per_page', '25'))
        except ValueError:
            page = 1
            per_page = 25

        start = (page - 1) * per_page

        source = request.GET.get('source', 'DB').lower().strip()
        if source not in ['db', 'ldapimport']:
            # source: 'DB' or 'LDAPImport', default is 'DB'
            error_msg = 'source %s invalid.' % source
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        order_by = request.GET.get('order_by', '').lower().strip()
        if order_by:
            if order_by not in ('quota_usage'):
                error_msg = 'order_by invalid.'
                return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

            direction = request.GET.get('direction', 'desc').lower().strip()
            if direction not in ('asc', 'desc'):
                error_msg = 'direction invalid.'
                return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        if source == 'db':

            total_count = ccnet_api.count_emailusers('DB') + \
                          ccnet_api.count_inactive_emailusers('DB')
            if order_by:

                if total_count > 500 and \
                        not getattr(settings, 'ALWAYS_SORT_USERS_BY_QUOTA_USAGE', False):
                    error_msg = _(
                        "There are more than 500 users, and sort is not offered."
                    )
                    return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

                try:
                    data = self.get_info_of_users_order_by_quota_usage(
                        source, direction, page, per_page)
                except Exception as e:
                    logger.error(e)
                    error_msg = 'Internal Server Error'
                    return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR,
                                     error_msg)

                result = {'data': data, 'total_count': total_count}
                return Response(result)
            else:
                users = ccnet_api.get_emailusers('DB', start, per_page)

        elif source == 'ldapimport':

            # api param is 'LDAP', but actually get count of 'LDAPImport' users
            total_count = ccnet_api.count_emailusers('LDAP') + \
                          ccnet_api.count_inactive_emailusers('LDAP')
            if order_by:

                if total_count > 500 and \
                        not getattr(settings, 'ALWAYS_SORT_USERS_BY_QUOTA_USAGE', False):
                    error_msg = _(
                        "There are more than 500 users, and sort is not offered."
                    )
                    return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

                try:
                    data = self.get_info_of_users_order_by_quota_usage(
                        source, direction, page, per_page)
                except Exception as e:
                    logger.error(e)
                    error_msg = 'Internal Server Error'
                    return api_error(status.HTTP_500_INTERNAL_SERVER_ERROR,
                                     error_msg)

                result = {'data': data, 'total_count': total_count}
                return Response(result)
            else:
                users = ccnet_api.get_emailusers('LDAPImport', start, per_page)

        data = []
        for user in users:
            profile = Profile.objects.get_profile_by_user(user.email)

            info = {}
            info['email'] = user.email
            info['name'] = email2nickname(user.email)
            info['contact_email'] = email2contact_email(user.email)
            info[
                'login_id'] = profile.login_id if profile and profile.login_id else ''

            info['is_staff'] = user.is_staff
            info['is_active'] = user.is_active

            orgs = ccnet_api.get_orgs_by_user(user.email)
            try:
                if orgs:
                    org_id = orgs[0].org_id
                    info['org_id'] = org_id
                    info['org_name'] = orgs[0].org_name
                    info['quota_usage'] = seafile_api.get_org_user_quota_usage(
                        org_id, user.email)
                    info['quota_total'] = seafile_api.get_org_user_quota(
                        org_id, user.email)
                else:
                    info['quota_usage'] = seafile_api.get_user_self_usage(
                        user.email)
                    info['quota_total'] = seafile_api.get_user_quota(
                        user.email)
            except Exception as e:
                logger.error(e)
                info['quota_usage'] = -1
                info['quota_total'] = -1

            info['create_time'] = timestamp_to_isoformat_timestr(user.ctime)
            last_login_obj = UserLastLogin.objects.get_by_username(user.email)
            info['last_login'] = datetime_to_isoformat_timestr(
                last_login_obj.last_login) if last_login_obj else ''
            info['role'] = get_user_role(user)
            if getattr(settings, 'MULTI_INSTITUTION', False):
                info['institution'] = profile.institution if profile else ''

            data.append(info)

        result = {'data': data, 'total_count': total_count}
        return Response(result)
Beispiel #8
0
    def get(self, request):
        """List all users in DB or LDAPImport

        Permission checking:
        1. only admin can perform this action.
        """

        try:
            page = int(request.GET.get('page', '1'))
            per_page = int(request.GET.get('per_page', '25'))
        except ValueError:
            page = 1
            per_page = 25

        start = (page - 1) * per_page

        # source: 'DB' or 'LDAPImport', default is 'DB'
        source = request.GET.get('source', 'DB')
        source = source.lower()
        if source not in ['db', 'ldapimport']:
            error_msg = 'source %s invalid.' % source
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        if source == 'db':
            users = ccnet_api.get_emailusers('DB', start, per_page)
            total_count = ccnet_api.count_emailusers('DB') + \
                          ccnet_api.count_inactive_emailusers('DB')
        elif source == 'ldapimport':
            users = ccnet_api.get_emailusers('LDAPImport', start, per_page)
            # api param is 'LDAP', but actually get count of 'LDAPImport' users
            total_count = ccnet_api.count_emailusers('LDAP') + \
                          ccnet_api.count_inactive_emailusers('LDAP')

        data = []
        for user in users:
            profile = Profile.objects.get_profile_by_user(user.email)

            info = {}
            info['email'] = user.email
            info['name'] = email2nickname(user.email)
            info['contact_email'] = email2contact_email(user.email)
            info[
                'login_id'] = profile.login_id if profile and profile.login_id else ''

            info['is_staff'] = user.is_staff
            info['is_active'] = user.is_active

            orgs = ccnet_api.get_orgs_by_user(user.email)
            try:
                if orgs:
                    org_id = orgs[0].org_id
                    info['org_id'] = org_id
                    info['org_name'] = orgs[0].org_name
            except Exception as e:
                logger.error(e)

            info['create_time'] = timestamp_to_isoformat_timestr(user.ctime)
            last_login_obj = UserLastLogin.objects.get_by_username(user.email)
            info['last_login'] = datetime_to_isoformat_timestr(
                last_login_obj.last_login) if last_login_obj else ''
            info['role'] = get_user_role(user)
            info['storage_usage'] = Workspaces.objects.get_owner_total_storage(
                owner=user.email)
            if getattr(settings, 'MULTI_INSTITUTION', False):
                info['institution'] = profile.institution if profile else ''

            data.append(info)

        result = {'data': data, 'total_count': total_count}
        return Response(result)
Beispiel #9
0
    def post(self, request):
        """ Import users from xlsx file

        Permission checking:
        1. admin user.
        """

        if not request.user.admin_permissions.can_manage_user():
            return api_error(status.HTTP_403_FORBIDDEN, 'Permission denied.')

        xlsx_file = request.FILES.get('file', None)
        if not xlsx_file:
            error_msg = 'file can not be found.'
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        file_type, ext = get_file_type_and_ext(xlsx_file.name)
        if ext != 'xlsx':
            error_msg = file_type_error_msg(ext, 'xlsx')
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        content = xlsx_file.read()

        try:
            fs = BytesIO(content)
            wb = load_workbook(filename=fs, read_only=True)
        except Exception as e:
            logger.error(e)

        # example file is like:
        # Email    Password Name(Optional) Role(Optional) Space Quota(MB, Optional) Login ID
        # [email protected]  a        a              default        1024                      login id a
        # [email protected]  b        b              default        2048                      login id b

        rows = wb.worksheets[0].rows
        records = []
        # skip first row(head field).
        next(rows)
        for row in rows:
            if not all(col.value is None for col in row):
                records.append([col.value for col in row])

        if user_number_over_limit(new_users=len(records)):
            error_msg = 'The number of users exceeds the limit.'
            return api_error(status.HTTP_400_BAD_REQUEST, error_msg)

        result = {}
        result['failed'] = []
        result['success'] = []
        for record in records:
            if record[0]:
                email = record[0].strip()
                if not is_valid_username(email):
                    result['failed'].append({
                        'email': email,
                        'error_msg': 'email %s invalid.' % email
                    })
                    continue
            else:
                result['failed'].append({
                    'email': '',
                    'error_msg': 'email invalid.'
                })
                continue

            if record[1]:
                password = record[1].strip()
                if not password:
                    result['failed'].append({
                        'email': email,
                        'error_msg': 'password invalid.'
                    })
                    continue
            else:
                result['failed'].append({
                    'email': email,
                    'error_msg': 'password invalid.'
                })
                continue

            try:
                User.objects.get(email=email)
                result['failed'].append({
                    'email': email,
                    'error_msg': 'user %s exists.' % email
                })
                continue
            except User.DoesNotExist:
                pass

            User.objects.create_user(email, password, is_staff=False, is_active=True)
            if config.FORCE_PASSWORD_CHANGE:
                UserOptions.objects.set_force_passwd_change(email)

            # update the user's optional info
            # update nikename
            if record[2]:
                try:
                    nickname = record[2].strip()
                    if len(nickname) <= 64 and '/' not in nickname:
                        Profile.objects.add_or_update(email, nickname, '')
                except Exception as e:
                    logger.error(e)

            # update role
            if record[3]:
                try:
                    role = record[3].strip()
                    if is_pro_version() and role in get_available_roles():
                        User.objects.update_role(email, role)
                except Exception as e:
                    logger.error(e)

            # update quota
            if record[4]:
                try:
                    space_quota_mb = int(record[4])
                    if space_quota_mb >= 0:
                        space_quota = int(space_quota_mb) * get_file_size_unit('MB')
                        seafile_api.set_user_quota(email, space_quota)
                except Exception as e:
                    logger.error(e)

            # login id
            if record[5]:
                try:
                    Profile.objects.add_or_update(email, login_id=record[5])
                except Exception as e:
                    logger.error(e)

            send_html_email_with_dj_template(email,
                                             subject=_('You are invited to join %s') % get_site_name(),
                                             dj_template='sysadmin/user_batch_add_email.html',
                                             context={
                                                 'user': email2nickname(request.user.username),
                                                 'email': email,
                                                 'password': password
                                             })

            user = User.objects.get(email=email)

            info = {}
            info['email'] = email
            info['name'] = email2nickname(email)
            info['contact_email'] = email2contact_email(email)

            info['is_staff'] = user.is_staff
            info['is_active'] = user.is_active

            info['quota_usage'] = seafile_api.get_user_self_usage(user.email)
            info['quota_total'] = seafile_api.get_user_quota(user.email)

            info['create_time'] = timestamp_to_isoformat_timestr(user.ctime)

            info['role'] = get_user_role(user)
            result['success'].append(info)

            # send admin operation log signal
            admin_op_detail = {
                "email": email,
            }
            admin_operation.send(sender=None, admin_name=request.user.username,
                                 operation=USER_ADD, detail=admin_op_detail)

        return Response(result)