From 9e23094460e43806d1ae2ef370e73c95ba917a24 Mon Sep 17 00:00:00 2001 From: Leif Johansson Date: Fri, 4 Mar 2011 23:59:48 +0100 Subject: adding users now has custom validation --- coip/apps/membership/forms.py | 9 +++++---- coip/apps/membership/views.py | 8 +++++++- coip/apps/userprofile/views.py | 15 ++++++++++++++- coip/urls.py | 4 +++- templates/apps/membership/edit.html | 26 +++++++++++++++++++++++++- templates/apps/name/name.html | 6 +++--- templates/base.html | 14 ++++++++++++++ 7 files changed, 71 insertions(+), 11 deletions(-) diff --git a/coip/apps/membership/forms.py b/coip/apps/membership/forms.py index d9f7fe8..d44bb3b 100644 --- a/coip/apps/membership/forms.py +++ b/coip/apps/membership/forms.py @@ -5,16 +5,17 @@ Created on Jun 23, 2010 ''' from coip.apps.membership.models import Membership from form_utils.forms import BetterModelForm -from django.forms.fields import ChoiceField -from django.forms.widgets import Select, TextInput +from django.forms.fields import ChoiceField, CharField +from django.forms.widgets import Select, HiddenInput class MembershipForm(BetterModelForm): type = ChoiceField(choices=(("user","I'm adding a user to the group"),("entity","I'm adding a relying party (SP or IdP) to the group")), label="", widget=Select(attrs={'class':'link'}), required=False, initial="user") + username = CharField(label="Username") class Meta: model = Membership fields = ['entity','user'] widgets = { - 'user': TextInput() + 'user': HiddenInput() } fieldsets = [('type', {'fields': ['type'], 'legend': 'Which type of member are you adding to the group?', @@ -24,7 +25,7 @@ class MembershipForm(BetterModelForm): 'legend': 'Adding a federation entity to the group', 'description': 'Select the relying party you wish to add to the group.', 'classes': ['step','submit_step']}), - ('user', {'fields': ['user'], + ('user', {'fields': ['user','username'], 'legend': 'Adding a user to the group', 'description': 'Provide the federation identifier of the user you wish to join. That user must have already logged in at least once. To add a user that has not yet logged in, send an invitation instead.', 'classes': ['step','submit_step']}) diff --git a/coip/apps/membership/views.py b/coip/apps/membership/views.py index 7c4c4e1..dd505d2 100644 --- a/coip/apps/membership/views.py +++ b/coip/apps/membership/views.py @@ -34,7 +34,13 @@ def join(request,id,membername=None): m = Membership(name=name,enabled=True) form = MembershipForm(request.POST,instance=m) if form.is_valid(): - m = form.save() + if form.cleaned_data.has_key('user'): + add_member(name,form.cleaned_data['user']) + elif form.cleaned_data.has_key('entity'): + add_member(name,form.cleaned_data['entity']) + else: + raise Exception,"Bad form state - should not happen at all!" + return HttpResponseRedirect(name.url()) else: return respond_to(request, diff --git a/coip/apps/userprofile/views.py b/coip/apps/userprofile/views.py index 4660a52..3ca4416 100644 --- a/coip/apps/userprofile/views.py +++ b/coip/apps/userprofile/views.py @@ -6,13 +6,15 @@ Created on Jul 6, 2010 from django.contrib.auth.decorators import login_required from coip.apps.userprofile.models import PKey from django.http import HttpResponseRedirect -from coip.multiresponse import respond_to +from coip.multiresponse import respond_to, json_response from coip.apps.membership.models import Membership, add_member from coip.apps.userprofile.utils import user_profile from django.core.exceptions import ObjectDoesNotExist from pprint import pformat from coip.apps.auth.utils import nonce from coip.apps.name.models import Name, NameLink, lookup +from django.contrib.auth.models import User +from django.shortcuts import get_object_or_404 @login_required def merge(request,pkey=None): @@ -54,4 +56,15 @@ def home(request): return respond_to(request, {'text/html': 'apps/userprofile/home.html'},{'memberships': memberships,'names': names}) +@login_required +def search(request): + list = [] + if request.REQUEST.has_key('term'): + term = request.REQUEST['term'] + list = [{'label': user.username,'value': user.id} for user in User.objects.filter(username__contains=term)] + return json_response(list) +@login_required +def info(request,username): + user = get_object_or_404(User,username=username) + return json_response({'username': user.username}); \ No newline at end of file diff --git a/coip/urls.py b/coip/urls.py index 6df5442..637bfa8 100644 --- a/coip/urls.py +++ b/coip/urls.py @@ -27,6 +27,8 @@ urlpatterns = patterns('', (r'^user/merge$', 'coip.apps.userprofile.views.merge'), (r'^user/home$', 'coip.apps.userprofile.views.home'), (r'^user/(.+)/groups.json$', 'coip.apps.name.views.user_groups'), + (r'^user/search.json$', 'coip.apps.userprofile.views.search'), + (r'^user/info/(.+).json$', 'coip.apps.userprofile.views.info'), # Invitations (r'^name/(?P[0-9]+)/invite$', 'coip.apps.invitation.views.invite'), (r'^invitation/(?P[0-9]+)/cancel$', 'coip.apps.invitation.views.cancel'), @@ -47,7 +49,7 @@ urlpatterns = patterns('', # ACL (r'^name/(?P[0-9]+)/acl/(?P[0-9]+)$', 'coip.apps.name.views.lsacl'), (r'^name/(?P[0-9]+)/acl/(?P[0-9]+)/add$', 'coip.apps.name.views.addacl'), - (r'^name/(?P[0-9]+)/acl/(?P[0-9]+)/copy$', 'coip.apps.name.views.copyacl'), + #(r'^name/(?P[0-9]+)/acl/(?P[0-9]+)/copy$', 'coip.apps.name.views.copyacl'), (r'^name/(?P[0-9]+)/acl/(?P[0-9]+)/remove$', 'coip.apps.name.views.rmacl'), # Links (r'^name/(?P[0-9]+)/addlink$', 'coip.apps.link.views.add'), diff --git a/templates/apps/membership/edit.html b/templates/apps/membership/edit.html index 8174aea..06d033b 100644 --- a/templates/apps/membership/edit.html +++ b/templates/apps/membership/edit.html @@ -3,6 +3,30 @@ $('#wizard').formwizard({ validationEnabled: true, focusFirstInput: true, - textSubmit: "Finish" + textSubmit: "Finish", + validationOptions: { + rules: { + username: 'validUser' + } + } + }); + $('#id_username').autocomplete({ + source: "/user/search.json", + focus: function(event, ui) { + $('#id_username').val(ui.item.label); + return false; + }, + select: function(event, ui) { + $('#id_username').val(ui.item.label); + $('#id_user').val(ui.item.value); + return false; + }, + minLength: 2, + open: function() { + $( this ).removeClass( "ui-corner-all" ).addClass( "ui-corner-top" ); + }, + close: function() { + $( this ).removeClass( "ui-corner-top" ).addClass( "ui-corner-all" ); + } }); {% endblock %} \ No newline at end of file diff --git a/templates/apps/name/name.html b/templates/apps/name/name.html index 01de064..f8d667a 100644 --- a/templates/apps/name/name.html +++ b/templates/apps/name/name.html @@ -60,13 +60,13 @@

{{m.user|lastidentifier}}

- {{m.user|userdisplay}} ({{m.user|lastidentifier}}) became a member of {{name.shortname}} {{m.timecreated|datehumanize}} - and has the following role{{m.tags|pluralize}}: + {{m.user|userdisplay}} ({{m.user|lastidentifier}}) became a member of {{name.shortname}} {{m.timecreated|datehumanize}} + {% if m.tags %}and has the following role{{m.tags|pluralize}}:
    {% for tag in m.tags %}
  • {{ tag|escape }}
  • {% endfor %} -
+ {%endif%}.
    diff --git a/templates/base.html b/templates/base.html index bb59dda..64024e4 100644 --- a/templates/base.html +++ b/templates/base.html @@ -40,6 +40,20 @@ $(input).addClass("ui-state-default"); } }); + + function validUser(value,element) { + var valid = false; + $.ajax({ + url: "/user/info/"+value+".json", + async: false, + dataType: 'json', + success: function (json) { + valid = true; + } + }); + return valid; + } + $.validator.addMethod("validUser", validUser, "Please enter a valid user."); }); {% block js %}{% endblock %} -- cgit v1.1