mirror of
https://salsa.debian.org/freeipa-team/freeipa.git
synced 2025-02-25 18:55:28 -06:00
Add add/edit/show for manager and secretary fields.
This commit is contained in:
parent
1685751b1c
commit
f881e21f7f
@ -36,9 +36,11 @@ class UserFields():
|
||||
businesscategory = widgets.TextField(name="businesscategory", label="Tags")
|
||||
description = widgets.TextField(name="description", label="Description")
|
||||
employeetype = widgets.TextField(name="employeetype", label="Employee Type")
|
||||
manager = widgets.TextField(name="manager", label="Manager")
|
||||
manager = widgets.HiddenField(name="manager", label="Manager")
|
||||
manager_cn = widgets.HiddenField(name="manager_cn", label="Manager")
|
||||
roomnumber = widgets.TextField(name="roomnumber", label="Room Number")
|
||||
secretary = widgets.TextField(name="secretary", label="Secretary")
|
||||
secretary = widgets.HiddenField(name="secretary", label="Secretary")
|
||||
secretary_cn = widgets.HiddenField(name="secretary_cn", label="Manager")
|
||||
|
||||
carlicense = widgets.TextField(name="carlicense", label="Car License")
|
||||
labeleduri = widgets.TextField(name="labeleduri", label="Home Page")
|
||||
@ -75,6 +77,10 @@ class UserNewForm(widgets.Form):
|
||||
|
||||
hidden_fields = [
|
||||
UserFields.dn_to_info_json,
|
||||
UserFields.manager,
|
||||
UserFields.manager_cn,
|
||||
UserFields.secretary,
|
||||
UserFields.secretary_cn,
|
||||
]
|
||||
|
||||
validator = UserNewValidator()
|
||||
@ -114,6 +120,10 @@ class UserEditForm(widgets.Form):
|
||||
UserFields.editprotected_hidden,
|
||||
UserFields.user_groups_data,
|
||||
UserFields.dn_to_info_json,
|
||||
UserFields.manager,
|
||||
UserFields.manager_cn,
|
||||
UserFields.secretary,
|
||||
UserFields.secretary_cn,
|
||||
]
|
||||
|
||||
validator = UserEditValidator()
|
||||
|
@ -3,6 +3,7 @@ NULL =
|
||||
appdir = $(IPA_DATA_DIR)/ipagui/static/javascript
|
||||
app_DATA = \
|
||||
dynamicedit.js \
|
||||
dynamicselect.js \
|
||||
effects.js \
|
||||
ipautil.js \
|
||||
prototype.js \
|
||||
|
53
ipa-server/ipa-gui/ipagui/static/javascript/dynamicselect.js
Normal file
53
ipa-server/ipa-gui/ipagui/static/javascript/dynamicselect.js
Normal file
@ -0,0 +1,53 @@
|
||||
/**
|
||||
* dynamicselect.js
|
||||
*
|
||||
* Shared code, data, and functions for the dynamic select lists on the
|
||||
* edit user pages.
|
||||
*
|
||||
*/
|
||||
|
||||
function enterDoSelectSearch(e, which_select) {
|
||||
var keyPressed;
|
||||
if (window.event) {
|
||||
keyPressed = window.event.keyCode;
|
||||
} else {
|
||||
keyPressed = e.which;
|
||||
}
|
||||
|
||||
if (keyPressed == 13) {
|
||||
return doSelectSearch(which_select);
|
||||
} else {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
function startSelect(which_select) {
|
||||
new Effect.Appear($(which_select + '_searcharea'), {duration: 0.25});
|
||||
new Effect.Fade($(which_select + '_links'), {duration: 0.25});
|
||||
return false;
|
||||
}
|
||||
|
||||
function doSelect(which_select, select_dn, select_cn) {
|
||||
select_dn_field = $('form_' + which_select);
|
||||
select_cn_field = $('form_' + which_select + '_cn');
|
||||
select_cn_span = $(which_select + '_select_cn');
|
||||
|
||||
select_dn_field.value = select_dn;
|
||||
select_cn_field.value = select_cn;
|
||||
select_cn_span.update(select_cn);
|
||||
|
||||
new Effect.Fade($(which_select + '_searcharea'), {duration: 0.25});
|
||||
new Effect.Appear($(which_select + '_links'), {duration: 0.25});
|
||||
}
|
||||
|
||||
function clearSelect(which_select) {
|
||||
select_dn_field = $('form_' + which_select);
|
||||
select_cn_field = $('form_' + which_select + '_cn');
|
||||
select_cn_span = $(which_select + '_select_cn');
|
||||
|
||||
select_dn_field.value = '';
|
||||
select_cn_field.value = '';
|
||||
select_cn_span.update('');
|
||||
|
||||
return false;
|
||||
}
|
@ -97,9 +97,9 @@ class UserController(IPAController):
|
||||
new_user.setValue('businesscategory', kw.get('businesscategory'))
|
||||
new_user.setValue('description', kw.get('description'))
|
||||
new_user.setValue('employeetype', kw.get('employeetype'))
|
||||
# new_user.setValue('manager', kw.get('manager'))
|
||||
new_user.setValue('manager', kw.get('manager'))
|
||||
new_user.setValue('roomnumber', kw.get('roomnumber'))
|
||||
# new_user.setValue('secretary', kw.get('secretary'))
|
||||
new_user.setValue('secretary', kw.get('secretary'))
|
||||
|
||||
new_user.setValue('carlicense', kw.get('carlicense'))
|
||||
new_user.setValue('labeleduri', kw.get('labeleduri'))
|
||||
@ -221,11 +221,33 @@ class UserController(IPAController):
|
||||
user_dict['user_orig'] = user_data
|
||||
user_dict['user_groups_data'] = user_groups_data
|
||||
|
||||
# grab manager and secretary names
|
||||
if user.manager:
|
||||
try:
|
||||
user_manager = client.get_entry_by_dn(user.manager,
|
||||
['givenname', 'sn', 'uid'])
|
||||
user_dict['manager_cn'] = "%s %s" % (
|
||||
user_manager.getValue('givenname', ''),
|
||||
user_manager.getValue('sn', ''))
|
||||
except (ipaerror.exception_for(ipaerror.LDAP_NOT_FOUND),
|
||||
ipaerror.exception_for(ipaerror.LDAP_DATABASE_ERROR)):
|
||||
pass
|
||||
if user.secretary:
|
||||
try:
|
||||
user_secretary = client.get_entry_by_dn(user.secretary,
|
||||
['givenname', 'sn', 'uid'])
|
||||
user_dict['secretary_cn'] = "%s %s" % (
|
||||
user_secretary.getValue('givenname', ''),
|
||||
user_secretary.getValue('sn', ''))
|
||||
except (ipaerror.exception_for(ipaerror.LDAP_NOT_FOUND),
|
||||
ipaerror.exception_for(ipaerror.LDAP_DATABASE_ERROR)):
|
||||
pass
|
||||
|
||||
return dict(form=user_edit_form, user=user_dict,
|
||||
user_groups=user_groups_dicts)
|
||||
except ipaerror.IPAError, e:
|
||||
turbogears.flash("User edit failed: " + str(e))
|
||||
raise turbogears.redirect('/user/show', uid=kw.get('uid'))
|
||||
raise turbogears.redirect('/user/show', uid=uid)
|
||||
|
||||
@expose()
|
||||
@identity.require(identity.not_anonymous())
|
||||
@ -286,9 +308,9 @@ class UserController(IPAController):
|
||||
new_user.setValue('businesscategory', kw.get('businesscategory'))
|
||||
new_user.setValue('description', kw.get('description'))
|
||||
new_user.setValue('employeetype', kw.get('employeetype'))
|
||||
# new_user.setValue('manager', kw.get('manager'))
|
||||
new_user.setValue('manager', kw.get('manager'))
|
||||
new_user.setValue('roomnumber', kw.get('roomnumber'))
|
||||
# new_user.setValue('secretary', kw.get('secretary'))
|
||||
new_user.setValue('secretary', kw.get('secretary'))
|
||||
|
||||
new_user.setValue('carlicense', kw.get('carlicense'))
|
||||
new_user.setValue('labeleduri', kw.get('labeleduri'))
|
||||
@ -421,16 +443,26 @@ class UserController(IPAController):
|
||||
user_reports.sort(self.sort_group_member)
|
||||
|
||||
user_manager = None
|
||||
user_secretary = None
|
||||
try:
|
||||
if user.manager:
|
||||
user_manager = client.get_entry_by_dn(user.manager,
|
||||
['givenname', 'sn', 'uid'])
|
||||
except ipaerror.exception_for(ipaerror.LDAP_NOT_FOUND):
|
||||
except (ipaerror.exception_for(ipaerror.LDAP_NOT_FOUND),
|
||||
ipaerror.exception_for(ipaerror.LDAP_DATABASE_ERROR)):
|
||||
pass
|
||||
|
||||
try:
|
||||
if user.secretary:
|
||||
user_secretary = client.get_entry_by_dn(user.secretary,
|
||||
['givenname', 'sn', 'uid'])
|
||||
except (ipaerror.exception_for(ipaerror.LDAP_NOT_FOUND),
|
||||
ipaerror.exception_for(ipaerror.LDAP_DATABASE_ERROR)):
|
||||
pass
|
||||
|
||||
return dict(user=user.toDict(), fields=ipagui.forms.user.UserFields(),
|
||||
user_groups=user_groups, user_reports=user_reports,
|
||||
user_manager=user_manager)
|
||||
user_manager=user_manager, user_secretary=user_secretary)
|
||||
except ipaerror.IPAError, e:
|
||||
turbogears.flash("User show failed: " + str(e))
|
||||
raise turbogears.redirect("/")
|
||||
@ -534,3 +566,28 @@ class UserController(IPAController):
|
||||
return email
|
||||
|
||||
return ""
|
||||
|
||||
@expose("ipagui.templates.userselectsearch")
|
||||
@identity.require(identity.not_anonymous())
|
||||
def user_select_search(self, **kw):
|
||||
"""Searches for users and displays list of results in a table.
|
||||
This method is used for the ajax search for managers
|
||||
and secrectary on the user pages."""
|
||||
client = self.get_ipaclient()
|
||||
|
||||
users = []
|
||||
users_counter = 0
|
||||
searchlimit = 100
|
||||
criteria = kw.get('criteria')
|
||||
if criteria != None and len(criteria) > 0:
|
||||
try:
|
||||
users = client.find_users(criteria.encode('utf-8'), None,
|
||||
searchlimit)
|
||||
users_counter = users[0]
|
||||
users = users[1:]
|
||||
except ipaerror.IPAError, e:
|
||||
turbogears.flash("search failed: " + str(e))
|
||||
|
||||
return dict(users=users, criteria=criteria,
|
||||
which_select=kw.get('which_select'),
|
||||
counter=users_counter)
|
||||
|
@ -28,6 +28,7 @@ app_DATA = \
|
||||
userlist.kid \
|
||||
usernewform.kid \
|
||||
usernew.kid \
|
||||
userselectsearch.kid \
|
||||
usershow.kid \
|
||||
welcome.kid \
|
||||
unhandled_exception.kid \
|
||||
|
@ -23,8 +23,13 @@ from ipagui.helpers import ipahelper
|
||||
|
||||
<script type="text/javascript" charset="utf-8"
|
||||
src="${tg.url('/static/javascript/dynamicedit.js')}"></script>
|
||||
<script type="text/javascript" charset="utf-8"
|
||||
src="${tg.url('/static/javascript/dynamicselect.js')}"></script>
|
||||
|
||||
<?python searchurl = tg.url('/user/edit_search') ?>
|
||||
<?python
|
||||
searchurl = tg.url('/user/edit_search')
|
||||
selectSearchurl = tg.url('/user/user_select_search')
|
||||
?>
|
||||
|
||||
<script type="text/javascript">
|
||||
function toggleProtectedFields(checkbox) {
|
||||
@ -68,6 +73,17 @@ from ipagui.helpers import ipahelper
|
||||
info.name + " "));
|
||||
}
|
||||
}
|
||||
|
||||
function doSelectSearch(which_select) {
|
||||
$(which_select + '_searchresults').update("Searching...");
|
||||
new Ajax.Updater(which_select + '_searchresults',
|
||||
'${selectSearchurl}',
|
||||
{ asynchronous:true,
|
||||
parameters: { criteria: $(which_select + '_criteria').value,
|
||||
which_select: which_select},
|
||||
evalScripts: true });
|
||||
return false;
|
||||
}
|
||||
</script>
|
||||
|
||||
|
||||
@ -513,22 +529,60 @@ from ipagui.helpers import ipahelper
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<th>
|
||||
<th valign="top">
|
||||
<label class="fieldlabel" for="${user.manager.field_id}"
|
||||
py:content="user.manager.label" />:
|
||||
</th>
|
||||
<td>
|
||||
TODO
|
||||
<td valign="top">
|
||||
<div>
|
||||
<span id='manager_select_cn'>${value_for(user.manager_cn)}</span>
|
||||
<span id='manager_links'>
|
||||
<a href="#" onclick="return clearSelect('manager');">clear</a>
|
||||
<a href="#" onclick="return startSelect('manager');">change</a>
|
||||
</span>
|
||||
<span py:if="tg.errors.get('manager')" class="fielderror"
|
||||
py:content="tg.errors.get('manager')" />
|
||||
</div>
|
||||
<div id="manager_searcharea" style="display:none">
|
||||
<div>
|
||||
<input id="manager_criteria" type="text"
|
||||
onkeypress="return enterDoSelectSearch(event, 'manager');" />
|
||||
<input type="button" value="Find"
|
||||
onclick="return doSelectSearch('manager');"
|
||||
/>
|
||||
</div>
|
||||
<div id="manager_searchresults">
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<th>
|
||||
<th valign="top">
|
||||
<label class="fieldlabel" for="${user.secretary.field_id}"
|
||||
py:content="user.secretary.label" />:
|
||||
</th>
|
||||
<td>
|
||||
TODO
|
||||
<td valign="top">
|
||||
<div>
|
||||
<span id='secretary_select_cn'>${value_for(user.secretary_cn)}</span>
|
||||
<span id='secretary_links'>
|
||||
<a href="#" onclick="return clearSelect('secretary');">clear</a>
|
||||
<a href="#" onclick="return startSelect('secretary');">change</a>
|
||||
</span>
|
||||
<span py:if="tg.errors.get('secretary')" class="fielderror"
|
||||
py:content="tg.errors.get('secretary')" />
|
||||
</div>
|
||||
<div id="secretary_searcharea" style="display:none">
|
||||
<div>
|
||||
<input id="secretary_criteria" type="text"
|
||||
onkeypress="return enterDoSelectSearch(event, 'secretary');" />
|
||||
<input type="button" value="Find"
|
||||
onclick="return doSelectSearch('secretary');"
|
||||
/>
|
||||
</div>
|
||||
<div id="secretary_searchresults">
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
@ -17,8 +17,13 @@ from ipagui.helpers import ipahelper
|
||||
|
||||
<script type="text/javascript" charset="utf-8"
|
||||
src="${tg.url('/static/javascript/dynamicedit.js')}"></script>
|
||||
<script type="text/javascript" charset="utf-8"
|
||||
src="${tg.url('/static/javascript/dynamicselect.js')}"></script>
|
||||
|
||||
<?python searchurl = tg.url('/user/edit_search') ?>
|
||||
<?python
|
||||
searchurl = tg.url('/user/edit_search')
|
||||
selectSearchurl = tg.url('/user/user_select_search')
|
||||
?>
|
||||
|
||||
<script type="text/javascript">
|
||||
function doSearch() {
|
||||
@ -39,6 +44,17 @@ from ipagui.helpers import ipahelper
|
||||
info.name + " "));
|
||||
}
|
||||
}
|
||||
|
||||
function doSelectSearch(which_select) {
|
||||
$(which_select + '_searchresults').update("Searching...");
|
||||
new Ajax.Updater(which_select + '_searchresults',
|
||||
'${selectSearchurl}',
|
||||
{ asynchronous:true,
|
||||
parameters: { criteria: $(which_select + '_criteria').value,
|
||||
which_select: which_select},
|
||||
evalScripts: true });
|
||||
return false;
|
||||
}
|
||||
</script>
|
||||
|
||||
<div py:for="field in hidden_fields"
|
||||
@ -501,12 +517,31 @@ from ipagui.helpers import ipahelper
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<th>
|
||||
<th valign="top">
|
||||
<label class="fieldlabel" for="${user.manager.field_id}"
|
||||
py:content="user.manager.label" />:
|
||||
</th>
|
||||
<td>
|
||||
TODO
|
||||
<td valign="top">
|
||||
<div>
|
||||
<span id='manager_select_cn'>${value_for(user.manager)}</span>
|
||||
<span id='manager_links'>
|
||||
<a href="#" onclick="return clearSelect('manager');">clear</a>
|
||||
<a href="#" onclick="return startSelect('manager');">change</a>
|
||||
</span>
|
||||
<span py:if="tg.errors.get('manager')" class="fielderror"
|
||||
py:content="tg.errors.get('manager')" />
|
||||
</div>
|
||||
<div id="manager_searcharea" style="display:none">
|
||||
<div>
|
||||
<input id="manager_criteria" type="text"
|
||||
onkeypress="return enterDoSelectSearch(event, 'manager');" />
|
||||
<input type="button" value="Find"
|
||||
onclick="return doSelectSearch('manager');"
|
||||
/>
|
||||
</div>
|
||||
<div id="manager_searchresults">
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
@ -516,7 +551,26 @@ from ipagui.helpers import ipahelper
|
||||
py:content="user.secretary.label" />:
|
||||
</th>
|
||||
<td>
|
||||
TODO
|
||||
<div>
|
||||
<span id='secretary_select_cn'>${value_for(user.secretary)}</span>
|
||||
<span id='secretary_links'>
|
||||
<a href="#" onclick="return clearSelect('secretary');">clear</a>
|
||||
<a href="#" onclick="return startSelect('secretary');">change</a>
|
||||
</span>
|
||||
<span py:if="tg.errors.get('secretary')" class="fielderror"
|
||||
py:content="tg.errors.get('secretary')" />
|
||||
</div>
|
||||
<div id="secretary_searcharea" style="display:none">
|
||||
<div>
|
||||
<input id="secretary_criteria" type="text"
|
||||
onkeypress="return enterDoSelectSearch(event, 'secretary');" />
|
||||
<input type="button" value="Find"
|
||||
onclick="return doSelectSearch('secretary');"
|
||||
/>
|
||||
</div>
|
||||
<div id="secretary_searchresults">
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
36
ipa-server/ipa-gui/ipagui/templates/userselectsearch.kid
Normal file
36
ipa-server/ipa-gui/ipagui/templates/userselectsearch.kid
Normal file
@ -0,0 +1,36 @@
|
||||
<div xmlns:py="http://purl.org/kid/ns#">
|
||||
|
||||
<?python
|
||||
from ipagui.helpers import ipahelper
|
||||
?>
|
||||
<div py:if='(users != None) and (len(users) > 0)'>
|
||||
<div id="search-results-count">
|
||||
${len(users)} results returned:
|
||||
<span py:if="counter < 0">
|
||||
(truncated)
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<div py:for="user in users">
|
||||
<?python
|
||||
user_name = "%s %s" % (user.getValue('givenName', ''),
|
||||
user.getValue('sn', ''))
|
||||
user_descr = "(%s)" % user.uid
|
||||
|
||||
user_dn_esc = ipahelper.javascript_string_escape(user.dn)
|
||||
user_name_esc = ipahelper.javascript_string_escape(user_name)
|
||||
user_descr_esc = ipahelper.javascript_string_escape(user_descr)
|
||||
which_select_esc = ipahelper.javascript_string_escape(which_select)
|
||||
?>
|
||||
|
||||
${user_name} ${user_descr}
|
||||
<a href=""
|
||||
onclick="doSelect('${which_select_esc}', '${user_dn_esc}', '${user_name_esc}');
|
||||
return false;"
|
||||
>select</a>
|
||||
</div>
|
||||
</div>
|
||||
<div py:if='(users != None) and (len(users) == 0)'>
|
||||
No results found for "${criteria}"
|
||||
</div>
|
||||
</div>
|
@ -222,18 +222,21 @@ else:
|
||||
</tr>
|
||||
<tr py:if='user_manager'>
|
||||
<th>
|
||||
Manager:
|
||||
<label class="fieldlabel" py:content="fields.manager.label" />:
|
||||
</th>
|
||||
<td>
|
||||
<a href="${tg.url('/user/show', uid=user_manager.uid)}"
|
||||
>${user_manager.givenname} ${user_manager.sn}</a>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<tr py:if='user_secretary'>
|
||||
<th>
|
||||
<label class="fieldlabel" py:content="fields.secretary.label" />:
|
||||
</th>
|
||||
<td>TODO</td>
|
||||
<td>
|
||||
<a href="${tg.url('/user/show', uid=user_secretary.uid)}"
|
||||
>${user_secretary.givenname} ${user_secretary.sn}</a>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user