forked from shaba/openuds
* Fixed current authenticators to use "real_name" instead of realName in createuser && modifyuser
* Finished (hopefully) Users add/edit
This commit is contained in:
parent
75a7a787b9
commit
fb1a367e93
@ -48,6 +48,7 @@ logger = logging.getLogger(__name__)
|
|||||||
|
|
||||||
class Authenticators(ModelHandler):
|
class Authenticators(ModelHandler):
|
||||||
model = Authenticator
|
model = Authenticator
|
||||||
|
custom_methods = ['search']
|
||||||
detail = { 'users': Users, 'groups':Groups }
|
detail = { 'users': Users, 'groups':Groups }
|
||||||
save_fields = ['name', 'comments', 'priority', 'small_name']
|
save_fields = ['name', 'comments', 'priority', 'small_name']
|
||||||
|
|
||||||
@ -90,3 +91,24 @@ class Authenticators(ModelHandler):
|
|||||||
'type': type_.type(),
|
'type': type_.type(),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# Custom "search" method
|
||||||
|
def search(self, item):
|
||||||
|
try:
|
||||||
|
type_ = self._params['type']
|
||||||
|
if type_ not in ('user', 'group'):
|
||||||
|
self.invalidRequestException()
|
||||||
|
|
||||||
|
term = self._params['term']
|
||||||
|
|
||||||
|
auth = item.getInstance()
|
||||||
|
|
||||||
|
canDoSearch = type_ == 'user' and (auth.searchUsers != auths.Authenticator.searchUsers) or (auth.searchGroups != auths.Authenticator.searchGroups)
|
||||||
|
if canDoSearch is False:
|
||||||
|
self.invalidRequestException()
|
||||||
|
|
||||||
|
if type_ == 'user':
|
||||||
|
return auth.searchUsers(term)
|
||||||
|
else:
|
||||||
|
return auth.searchGroups(term)
|
||||||
|
except:
|
||||||
|
self.invalidRequestException()
|
||||||
|
@ -96,18 +96,25 @@ class Users(DetailHandler):
|
|||||||
# Extract item db fields
|
# Extract item db fields
|
||||||
# We need this fields for all
|
# We need this fields for all
|
||||||
logger.debug('Saving user {0} / {1}'.format(parent, item))
|
logger.debug('Saving user {0} / {1}'.format(parent, item))
|
||||||
fields = self.readFieldsFromParams(['name', 'real_name', 'comments', 'state', 'staff_member', 'is_admin', 'groups'])
|
valid_fields = ['name', 'real_name', 'comments', 'state', 'staff_member', 'is_admin']
|
||||||
|
fields = self.readFieldsFromParams(valid_fields + ['groups'])
|
||||||
try:
|
try:
|
||||||
auth = parent.getInstance()
|
auth = parent.getInstance()
|
||||||
groups = fields['groups']
|
groups = fields['groups']
|
||||||
del fields['groups'] # Not update this on user dict
|
del fields['groups'] # Not update this on user dict
|
||||||
if item is None: # Create new
|
if item is None: # Create new
|
||||||
auth.createUser(fields) # this throws an exception if there is an error (for example, this auth can't create users)
|
auth.createUser(fields) # this throws an exception if there is an error (for example, this auth can't create users)
|
||||||
user = parent.users.create(**fields)
|
toSave = {}
|
||||||
|
for k in valid_fields:
|
||||||
|
toSave[k] = fields[k]
|
||||||
|
user = parent.users.create(**toSave)
|
||||||
else:
|
else:
|
||||||
auth.modifyUser(fields) # Notifies authenticator
|
auth.modifyUser(fields) # Notifies authenticator
|
||||||
|
toSave = {}
|
||||||
|
for k in valid_fields:
|
||||||
|
toSave[k] = fields[k]
|
||||||
user = parent.users.get(pk=item)
|
user = parent.users.get(pk=item)
|
||||||
user.__dict__.update(fields)
|
user.__dict__.update(toSave)
|
||||||
|
|
||||||
if auth.isExternalSource == False and user.parent == -1:
|
if auth.isExternalSource == False and user.parent == -1:
|
||||||
user.groups = Group.objects.filter(id__in=groups)
|
user.groups = Group.objects.filter(id__in=groups)
|
||||||
|
@ -319,6 +319,7 @@ class ModelHandler(BaseModelHandler):
|
|||||||
needs_staff = True
|
needs_staff = True
|
||||||
# Which model does this manage
|
# Which model does this manage
|
||||||
model = None
|
model = None
|
||||||
|
custom_methods = [] # If this model respond to "custom" methods, we will declare them here
|
||||||
# If this model has details, which ones
|
# If this model has details, which ones
|
||||||
detail = None # Dictionary containing detail routing
|
detail = None # Dictionary containing detail routing
|
||||||
# Put needed fields
|
# Put needed fields
|
||||||
@ -380,6 +381,8 @@ class ModelHandler(BaseModelHandler):
|
|||||||
path = self._path + '/'.join(args[:2])
|
path = self._path + '/'.join(args[:2])
|
||||||
detail = detailCls(self, path, self._params, *args, parent = item)
|
detail = detailCls(self, path, self._params, *args, parent = item)
|
||||||
method = getattr(detail, self._operation)
|
method = getattr(detail, self._operation)
|
||||||
|
except KeyError:
|
||||||
|
self.invalidMethodException()
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
self.invalidMethodException()
|
self.invalidMethodException()
|
||||||
|
|
||||||
@ -435,11 +438,21 @@ class ModelHandler(BaseModelHandler):
|
|||||||
if nArgs != 2:
|
if nArgs != 2:
|
||||||
self.invalidRequestException()
|
self.invalidRequestException()
|
||||||
try:
|
try:
|
||||||
item = self.model.objects.filter(pk=self._args[0])[0]
|
item = self.model.objects.get(pk=self._args[0])
|
||||||
except:
|
except:
|
||||||
self.invalidItemException()
|
self.invalidItemException()
|
||||||
return self.getLogs(item)
|
return self.getLogs(item)
|
||||||
|
|
||||||
|
# if has custom methods
|
||||||
|
if self._args[1] in self.custom_methods:
|
||||||
|
try:
|
||||||
|
operation = getattr(self, self._args[1])
|
||||||
|
item = self.model.objects.get(pk=self._args[0])
|
||||||
|
except:
|
||||||
|
self.invalidMethodException()
|
||||||
|
|
||||||
|
return operation(item)
|
||||||
|
|
||||||
# If has detail and is requesting detail
|
# If has detail and is requesting detail
|
||||||
if self.detail is not None:
|
if self.detail is not None:
|
||||||
return self.processDetail()
|
return self.processDetail()
|
||||||
|
@ -295,14 +295,14 @@ class RegexLdap(auths.Authenticator):
|
|||||||
External sources already has the user cause they are managed externally, so, it can at most test if the users exists on external source
|
External sources already has the user cause they are managed externally, so, it can at most test if the users exists on external source
|
||||||
before accepting it.
|
before accepting it.
|
||||||
Groups are only used in case of internal users (non external sources) that must know to witch groups this user belongs to
|
Groups are only used in case of internal users (non external sources) that must know to witch groups this user belongs to
|
||||||
@param usrData: Contains data received from user directly, that is, a dictionary with at least: name, realName, comments, state & password
|
@param usrData: Contains data received from user directly, that is, a dictionary with at least: name, real_name, comments, state & password
|
||||||
@return: Raises an exception (AuthException) it things didn't went fine
|
@return: Raises an exception (AuthException) it things didn't went fine
|
||||||
'''
|
'''
|
||||||
res = self.__getUser(usrData['name'])
|
res = self.__getUser(usrData['name'])
|
||||||
if res is None:
|
if res is None:
|
||||||
raise AuthenticatorException(_('Username not found'))
|
raise AuthenticatorException(_('Username not found'))
|
||||||
# Fills back realName field
|
# Fills back realName field
|
||||||
usrData['realName'] = self.__getUserRealName(res)
|
usrData['real_name'] = self.__getUserRealName(res)
|
||||||
|
|
||||||
|
|
||||||
def getRealName(self, username):
|
def getRealName(self, username):
|
||||||
|
@ -275,7 +275,7 @@ class SampleAuth(auths.Authenticator):
|
|||||||
to create new users "by hand", i mean, the "new" options from menus will dissapear.
|
to create new users "by hand", i mean, the "new" options from menus will dissapear.
|
||||||
|
|
||||||
usrData is a dictionary that contains the input parameters from user,
|
usrData is a dictionary that contains the input parameters from user,
|
||||||
with at least name, realName, comments, state & password.
|
with at least name, real_name, comments, state & password.
|
||||||
|
|
||||||
We can modify this parameters, we can modify ALL, but name is not recommended to
|
We can modify this parameters, we can modify ALL, but name is not recommended to
|
||||||
modify it unles you know what you are doing.
|
modify it unles you know what you are doing.
|
||||||
@ -283,7 +283,7 @@ class SampleAuth(auths.Authenticator):
|
|||||||
Here, we will set the state to "Inactive" and realName to the same as username, but twice :-)
|
Here, we will set the state to "Inactive" and realName to the same as username, but twice :-)
|
||||||
'''
|
'''
|
||||||
from uds.core.util.State import State
|
from uds.core.util.State import State
|
||||||
usrData['realName'] = usrData['name'] + ' ' + usrData['name']
|
usrData['real_name'] = usrData['name'] + ' ' + usrData['name']
|
||||||
usrData['state'] = State.INACTIVE
|
usrData['state'] = State.INACTIVE
|
||||||
|
|
||||||
def modifyUser(self, usrData):
|
def modifyUser(self, usrData):
|
||||||
@ -295,7 +295,7 @@ class SampleAuth(auths.Authenticator):
|
|||||||
it's valid).
|
it's valid).
|
||||||
|
|
||||||
usrData is a dictionary that contains the input parameters from user,
|
usrData is a dictionary that contains the input parameters from user,
|
||||||
with at least name, realName, comments, state & password.
|
with at least name, real_name, comments, state & password.
|
||||||
|
|
||||||
We can modify this parameters, we can modify ALL, but name is not recommended to
|
We can modify this parameters, we can modify ALL, but name is not recommended to
|
||||||
modify it unless you know what you are doing.
|
modify it unless you know what you are doing.
|
||||||
@ -303,5 +303,5 @@ class SampleAuth(auths.Authenticator):
|
|||||||
Here, we will simply update the realName of the user, and (we have to take care
|
Here, we will simply update the realName of the user, and (we have to take care
|
||||||
this this kind of things) modify the userName to a new one, the original plus '-1'
|
this this kind of things) modify the userName to a new one, the original plus '-1'
|
||||||
'''
|
'''
|
||||||
usrData['realName'] = usrData['name'] + ' ' + usrData['name']
|
usrData['real_name'] = usrData['name'] + ' ' + usrData['name']
|
||||||
usrData['name'] = usrData['name'] + '-1'
|
usrData['name'] = usrData['name'] + '-1'
|
||||||
|
@ -268,7 +268,7 @@ class SimpleLDAPAuthenticator(Authenticator):
|
|||||||
if res is None:
|
if res is None:
|
||||||
raise AuthenticatorException(_('Username not found'))
|
raise AuthenticatorException(_('Username not found'))
|
||||||
# Fills back realName field
|
# Fills back realName field
|
||||||
usrData['realName'] = self.__getUserRealName(res)
|
usrData['real_name'] = self.__getUserRealName(res)
|
||||||
|
|
||||||
def getRealName(self, username):
|
def getRealName(self, username):
|
||||||
'''
|
'''
|
||||||
|
@ -515,7 +515,7 @@ class Authenticator(Module):
|
|||||||
|
|
||||||
Args:
|
Args:
|
||||||
usrData: Contains data received from user directly, that is a dictionary
|
usrData: Contains data received from user directly, that is a dictionary
|
||||||
with at least: name, realName, comments, state & password.
|
with at least: name, real_name, comments, state & password.
|
||||||
This is an in/out parameter, so you can modify, for example,
|
This is an in/out parameter, so you can modify, for example,
|
||||||
**realName**
|
**realName**
|
||||||
|
|
||||||
@ -545,7 +545,7 @@ class Authenticator(Module):
|
|||||||
|
|
||||||
Args:
|
Args:
|
||||||
usrData: Contains data received from user directly, that is a dictionary
|
usrData: Contains data received from user directly, that is a dictionary
|
||||||
with at least: name, realName, comments, state & password.
|
with at least: name, real_name, comments, state & password.
|
||||||
This is an in/out parameter, so you can modify, for example,
|
This is an in/out parameter, so you can modify, for example,
|
||||||
**realName**
|
**realName**
|
||||||
|
|
||||||
|
@ -250,6 +250,15 @@ BasicModelRest.prototype = {
|
|||||||
});
|
});
|
||||||
|
|
||||||
},
|
},
|
||||||
|
// Search
|
||||||
|
search: function(id, type, term, success_fnc, fail_fnc) {
|
||||||
|
"use strict";
|
||||||
|
return this.get({
|
||||||
|
id: id + '/search?type=' + encodeURIComponent(type) + '&term=' + encodeURIComponent(term),
|
||||||
|
success: success_fnc,
|
||||||
|
fail: fail_fnc
|
||||||
|
});
|
||||||
|
},
|
||||||
// -------------
|
// -------------
|
||||||
// Log methods
|
// Log methods
|
||||||
// -------------
|
// -------------
|
||||||
@ -311,8 +320,6 @@ BasicModelRest.prototype = {
|
|||||||
method: 'POST'
|
method: 'POST'
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
|
|
||||||
// --------------
|
// --------------
|
||||||
// Delete
|
// Delete
|
||||||
// --------------
|
// --------------
|
||||||
|
@ -48,22 +48,49 @@ gui.authenticators.link = function(event) {
|
|||||||
|
|
||||||
|
|
||||||
// Search button event generator for user/group
|
// Search button event generator for user/group
|
||||||
var searchForm = function(modalId, model, title, searchLabel, resultsLabel, srcSelector) {
|
var searchForm = function(parentModalId, type, id, title, searchLabel, resultsLabel, srcSelector) {
|
||||||
$(modalId + ' .button-search').on('click', function() {
|
var errorModal = gui.failRequestModalFnc(gettext('Search error'));
|
||||||
|
|
||||||
|
$(parentModalId + ' .button-search').on('click', function() {
|
||||||
api.templates.get('search', function(tmpl) { // Get form template
|
api.templates.get('search', function(tmpl) { // Get form template
|
||||||
var modalId = gui.launchModal(title, api.templates.evaluate(tmpl, {
|
var modalId = gui.launchModal(title, api.templates.evaluate(tmpl, {
|
||||||
search_label : searchLabel,
|
search_label : searchLabel,
|
||||||
results_label : resultsLabel,
|
results_label : resultsLabel,
|
||||||
}), { actionButton: '<button type="button" class="btn btn-success button-accept">' + gettext('Accept') + '</button>'});
|
}), { actionButton: '<button type="button" class="btn btn-success button-accept">' + gettext('Accept') + '</button>'});
|
||||||
var searchInput = modalId + ' input[name="search"]';
|
|
||||||
var resultsInput = modalId + ' select';
|
|
||||||
|
|
||||||
$(searchInput).val($(srcSelector).val());
|
var $searchInput = $(modalId + ' input[name="search"]');
|
||||||
|
var $select = $(modalId + ' select[name="results"]');
|
||||||
|
var $searchButton = $(modalId + ' .button-do-search');
|
||||||
|
|
||||||
|
$searchInput.val($(srcSelector).val());
|
||||||
|
|
||||||
$(modalId + ' .button-accept').on('click', function(){
|
$(modalId + ' .button-accept').on('click', function(){
|
||||||
gui.doLog('Accepted');
|
var value = $select.val();
|
||||||
|
if( value ) {
|
||||||
|
$(srcSelector).val(value);
|
||||||
|
$(modalId).modal('hide');
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
$searchButton.on('click', function() {
|
||||||
|
$searchButton.addClass('disabled');
|
||||||
|
var term = $searchInput.val();
|
||||||
|
api.authenticators.search(id, type, term, function(data) {
|
||||||
|
$searchButton.removeClass('disabled');
|
||||||
|
$select.empty();
|
||||||
|
gui.doLog(data);
|
||||||
|
$.each(data, function(undefined, value) {
|
||||||
|
$select.append('<option value="' + value.id + '">' + value.id + ' (' + value.name + ')</option>');
|
||||||
|
});
|
||||||
|
}, function(jqXHR, textStatus, errorThrown) {
|
||||||
|
$searchButton.removeClass('disabled');
|
||||||
|
errorModal(jqXHR, textStatus, errorThrown);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
if( $searchInput.val() != '') {
|
||||||
|
$searchButton.click();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@ -143,8 +170,11 @@ gui.authenticators.link = function(event) {
|
|||||||
onLoad: function(k) {
|
onLoad: function(k) {
|
||||||
gui.tools.unblockUI();
|
gui.tools.unblockUI();
|
||||||
},
|
},
|
||||||
|
onRefresh : function() {
|
||||||
|
$('#users-log-placeholder').empty(); // Remove logs on detail refresh
|
||||||
|
},
|
||||||
onEdit: function(value, event, table, refreshFnc) {
|
onEdit: function(value, event, table, refreshFnc) {
|
||||||
var password = "#æð~¬~@æß”¢ß€~½¬@#~½¬@|"; // Garbage for password (to detect change)
|
var password = "#æð~¬ŋ@æß”¢€~½¬@#~þ¬@|"; // Garbage for password (to detect change)
|
||||||
gui.tools.blockUI();
|
gui.tools.blockUI();
|
||||||
api.templates.get('user', function(tmpl) { // Get form template
|
api.templates.get('user', function(tmpl) { // Get form template
|
||||||
group.rest.overview(function(groups) { // Get groups
|
group.rest.overview(function(groups) { // Get groups
|
||||||
@ -228,7 +258,7 @@ gui.authenticators.link = function(event) {
|
|||||||
|
|
||||||
gui.tools.unblockUI();
|
gui.tools.unblockUI();
|
||||||
|
|
||||||
searchForm(modalId, user, gettext('Search users'), gettext('User'), gettext('Users found'), modalId + ' input[name="name"]'); // Enable search button click, if it exist ofc
|
searchForm(modalId, 'user', id, gettext('Search users'), gettext('User'), gettext('Users found'), modalId + ' input[name="name"]'); // Enable search button click, if it exist ofc
|
||||||
|
|
||||||
$(modalId + ' .button-accept').click(function(){
|
$(modalId + ' .button-accept').click(function(){
|
||||||
var fields = gui.forms.read(modalId);
|
var fields = gui.forms.read(modalId);
|
||||||
|
@ -1,17 +1,17 @@
|
|||||||
{% load i18n %}
|
{% load i18n %}
|
||||||
{% verbatim %}
|
{% verbatim %}
|
||||||
<form role="form">
|
<form role="form" class="do-search-form">
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
<label for="id_srch_search">{{ search_label }}</label>
|
<label>{{ search_label }}</label>
|
||||||
<div class="input-group">
|
<div class="input-group">
|
||||||
<input type="text" class="form-control" name="search">
|
<input type="text" class="form-control" name="search">
|
||||||
<span class="input-group-btn">
|
<span class="input-group-btn">
|
||||||
<button class="btn btn-info" type="button"><i class="fa fa-search"></i> {% endverbatim %}{% trans 'Search' %}{% verbatim %}</button>
|
<button class="btn btn-info button-do-search" type="button"><i class="fa fa-search"></i> {% endverbatim %}{% trans 'Search' %}{% verbatim %}</button>
|
||||||
</span>
|
</span>
|
||||||
</div><!-- /input-group -->
|
</div><!-- /input-group -->
|
||||||
</div>
|
</div>
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
<label for="id_srch_search">{{ results_label }}</label>
|
<label>{{ results_label }}</label>
|
||||||
<select class="form-control" size="8" name="results">
|
<select class="form-control" size="8" name="results">
|
||||||
</select>
|
</select>
|
||||||
</div>
|
</div>
|
||||||
|
@ -7,16 +7,22 @@
|
|||||||
<label for="id_username" class="col-sm-2 control-label">{{ username_label }}</label>
|
<label for="id_username" class="col-sm-2 control-label">{{ username_label }}</label>
|
||||||
<div class="col-sm-10">
|
<div class="col-sm-10">
|
||||||
{{# if canSearchUsers }}
|
{{# if canSearchUsers }}
|
||||||
|
{{# if username }}
|
||||||
|
{{ else }}
|
||||||
<div class="input-group">
|
<div class="input-group">
|
||||||
|
{{/ if }}
|
||||||
{{/ if }}
|
{{/ if }}
|
||||||
<input name="name" value="{{ username }}" type="text" id="id_username" class="form-control modal_field_data"
|
<input name="name" value="{{ username }}" type="text" id="id_username" class="form-control modal_field_data"
|
||||||
placeholder="{% endverbatim %}{% trans 'Username' %}{% verbatim %}"{{# if username }}readonly{{/ if }}>
|
placeholder="{% endverbatim %}{% trans 'Username' %}{% verbatim %}"{{# if username }}readonly{{/ if }}>
|
||||||
{{# if canSearchUsers }}
|
{{# if canSearchUsers }}
|
||||||
|
{{# if username }}
|
||||||
|
{{ else }}
|
||||||
<span class="input-group-btn">
|
<span class="input-group-btn">
|
||||||
<button class="btn btn-info button-search" type="button"><i class="fa fa-search"></i> {% endverbatim %}{% trans 'Search' %}{% verbatim %}</button>
|
<button class="btn btn-info button-search" type="button"><i class="fa fa-search"></i> {% endverbatim %}{% trans 'Search' %}{% verbatim %}</button>
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
{{/ if }}
|
{{/ if }}
|
||||||
|
{{/ if }}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
|
@ -90,6 +90,7 @@ def createUser(credentials, usr):
|
|||||||
auth = DbAuthenticator.objects.get(pk=usr['idParent'])
|
auth = DbAuthenticator.objects.get(pk=usr['idParent'])
|
||||||
try:
|
try:
|
||||||
authInstance = auth.getInstance()
|
authInstance = auth.getInstance()
|
||||||
|
usr['real_name'] = usr['realName'] # Copy to keep this in the right place
|
||||||
authInstance.createUser(usr) # Remenber, this throws an exception if there is an error
|
authInstance.createUser(usr) # Remenber, this throws an exception if there is an error
|
||||||
staffMember = isAdmin = False
|
staffMember = isAdmin = False
|
||||||
if credentials.isAdmin is True:
|
if credentials.isAdmin is True:
|
||||||
@ -99,7 +100,7 @@ def createUser(credentials, usr):
|
|||||||
if authInstance.needsPassword is True:
|
if authInstance.needsPassword is True:
|
||||||
password = CryptoManager.manager().hash(usr['password'])
|
password = CryptoManager.manager().hash(usr['password'])
|
||||||
|
|
||||||
user = auth.users.create(name = usr['name'], real_name = usr['realName'], comments = usr['comments'], state = usr['state'],
|
user = auth.users.create(name = usr['name'], real_name = usr['real_name'], comments = usr['comments'], state = usr['state'],
|
||||||
password = password, staff_member = staffMember, is_admin = isAdmin)
|
password = password, staff_member = staffMember, is_admin = isAdmin)
|
||||||
|
|
||||||
if authInstance.isExternalSource == False:
|
if authInstance.isExternalSource == False:
|
||||||
@ -123,10 +124,11 @@ def modifyUser(credentials, usr):
|
|||||||
try:
|
try:
|
||||||
user = DbUser.objects.get(pk=usr['id'])
|
user = DbUser.objects.get(pk=usr['id'])
|
||||||
auth = user.manager.getInstance()
|
auth = user.manager.getInstance()
|
||||||
|
usr['real_name'] = usr['realName'] # Copy to keep this in the right place
|
||||||
auth.modifyUser(usr) # Notifies authenticator
|
auth.modifyUser(usr) # Notifies authenticator
|
||||||
logger.debug(usr)
|
logger.debug(usr)
|
||||||
user.name = usr['name']
|
user.name = usr['name']
|
||||||
user.real_name = usr['realName']
|
user.real_name = usr['real_name']
|
||||||
user.comments = usr['comments']
|
user.comments = usr['comments']
|
||||||
if credentials.isAdmin is True:
|
if credentials.isAdmin is True:
|
||||||
logger.debug('Is an admin')
|
logger.debug('Is an admin')
|
||||||
|
Loading…
Reference in New Issue
Block a user