Commit fc41ef36 authored by Giorgos Korfiatis's avatar Giorgos Korfiatis
Browse files

Add display options in user-list

Refs #3374

Add options --uuid, --displayname, --active, and --filter-by.
filter_results() is copied locally to avoid importing from cyclades.
parent 970bb88e
......@@ -36,6 +36,8 @@ from datetime import datetime
from django.utils.timesince import timesince, timeuntil
from django.contrib.auth.models import Permission
from django.contrib.contenttypes.models import ContentType
from django.core.exceptions import FieldError
from django.core.management import CommandError
from synnefo.lib.ordereddict import OrderedDict
from astakos.im.models import AstakosUser
......@@ -163,3 +165,48 @@ def shortened(s, limit, suffix=True):
return '..' + s[-display:]
else:
return s[:display] + '..'
# Copied from snf-cyclades-app/synnefo/management/common.py
# It could be moved to snf-common
def filter_results(objects, filter_by):
filter_list = filter_by.split(",")
filter_dict = {}
exclude_dict = {}
def map_field_type(query):
def fix_bool(val):
if val.lower() in ("yes", "true", "t"):
return True
if val.lower() in ("no", "false", "f"):
return False
return val
if "!=" in query:
key, val = query.split("!=")
exclude_dict[key] = fix_bool(val)
return
OP_MAP = {
">=": "__gte",
"=>": "__gte",
">": "__gt",
"<=": "__lte",
"=<": "__lte",
"<": "__lt",
"=": "",
}
for op, new_op in OP_MAP.items():
if op in query:
key, val = query.split(op)
filter_dict[key + new_op] = fix_bool(val)
return
map(lambda x: map_field_type(x), filter_list)
try:
objects = objects.filter(**filter_dict)
return objects.exclude(**exclude_dict)
except FieldError as e:
raise CommandError(e)
except Exception as e:
raise CommandError("Can not filter results: %s" % e)
......@@ -37,12 +37,14 @@ from django.core.management.base import NoArgsCommand
from astakos.im.models import AstakosUser, AstakosUserAuthProvider
from ._common import format
from ._common import format, filter_results
class Command(NoArgsCommand):
help = "List users"
FIELDS = AstakosUser._meta.get_all_field_names()
option_list = NoArgsCommand.option_list + (
make_option('-c',
action='store_true',
......@@ -59,6 +61,28 @@ class Command(NoArgsCommand):
dest='pending_send_mail',
default=False,
help="List only users who have not received activation"),
make_option('--uuid',
action='store_true',
dest='only_uuid',
default=False,
help="Only display user uuid (default)"),
make_option('--displayname',
action='store_true',
dest='displayname',
default=False,
help="Display both uuid and display name"),
make_option('--active',
action='store_true',
dest='active',
default=False,
help="Display only active users"),
make_option('--filter-by',
dest='filter_by',
help="Filter results. Comma seperated list of key `cond`"
" val pairs that displayed entries must satisfy. e.g."
" --filter-by \"is_active=True,email_verified=True\"."
" Available keys are: %s" % ", ".join(FIELDS)),
)
def handle_noargs(self, **options):
......@@ -68,17 +92,36 @@ class Command(NoArgsCommand):
elif options['pending_send_mail']:
users = users.filter(is_active=False, activation_sent=None)
active_only = options['active']
if active_only:
users = filter_results(users, "is_active=True")
filter_by = options['filter_by']
if filter_by:
users = filter_results(users, filter_by)
displayname = options['displayname']
ids = [user.id for user in users]
auths = AstakosUserAuthProvider.objects.filter(
user__in=ids, active=True)
all_auth = partition_by(lambda a: a.user_id, auths)
labels = ('id', 'email', 'real name', 'active', 'admin', 'uuid', 'providers')
columns = (3, 24, 24, 6, 5, 12, 36, 24)
labels = filter(lambda x: x is not Omit,
[('id', 3),
('display name', 24) if displayname else Omit,
('real name', 24),
('active', 6),
('admin', 5),
('uuid', 36),
('providers', 24),
])
columns = [c for (l, c) in labels]
if not options['csv']:
line = ' '.join(l.rjust(w) for l, w in zip(labels, columns))
line = ' '.join(l.rjust(w) for l, w in labels)
self.stdout.write(line + '\n')
sep = '-' * len(line)
self.stdout.write(sep + '\n')
......@@ -90,13 +133,15 @@ class Command(NoArgsCommand):
uuid = user.uuid or ''
auths = all_auth[user.id]
auth_display = ",".join(unicode(auth) for auth in auths)
fields = (format(elem) for elem in (
id,
user.email,
elems = filter(lambda x: x is not Omit,
[id,
user.username if displayname else Omit,
user.realname,
active, admin, uuid,
auth_display
))
])
fields = (format(elem) for elem in elems)
if options['csv']:
line = '|'.join(fields)
......@@ -106,6 +151,10 @@ class Command(NoArgsCommand):
self.stdout.write(line + '\n')
class Omit(object):
pass
def partition_by(f, l):
d = {}
for x in l:
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment