Mercurial > agora-palash
changeset 35:290dd9208cc4
Implement editing user profiles and fix bugs related to the login/logout buttons. Implement 403 exception
author | Jordi Gutiérrez Hermoso <jordigh@gmail.com> |
---|---|
date | Mon, 05 Jul 2010 00:31:20 -0500 |
parents | 22d514498935 |
children | bc0137b6c264 |
files | apps/bundle/views.py apps/profile/views.py middleware/__init__.py middleware/http.py settings.py templates/403.html templates/base.djhtml templates/profile/edit-user.djhtml templates/profile/user.djhtml templates/user.djhtml urls.py |
diffstat | 10 files changed, 276 insertions(+), 85 deletions(-) [+] |
line wrap: on
line diff
--- a/apps/bundle/views.py Fri Jul 02 02:18:22 2010 -0500 +++ b/apps/bundle/views.py Mon Jul 05 00:31:20 2010 -0500 @@ -1,9 +1,15 @@ from django.shortcuts import render_to_response, get_object_or_404 from agora.apps.bundle.models import * +from django.template import RequestContext def detail(request, user, bundle): b = get_object_or_404(Bundle, uploader__username=user, name=bundle) f = BundleFile.objects.filter(bundle=b) - return render_to_response('bundle/index.djhtml', {'bundle':b, - 'files': f,}) + return render_to_response('bundle/index.djhtml', + { + 'bundle':b, + 'files': f, + }, + RequestContext(request), + )
--- a/apps/profile/views.py Fri Jul 02 02:18:22 2010 -0500 +++ b/apps/profile/views.py Mon Jul 05 00:31:20 2010 -0500 @@ -1,37 +1,87 @@ from django.shortcuts import render_to_response, get_object_or_404 -from agora.apps.profile.models import Profile from django.contrib.auth.models import User -from django.http import Http404 +from django.http import Http404, HttpResponseRedirect +from django.core.urlresolvers import reverse +from django.contrib.auth.decorators import login_required +from django.template import RequestContext + from agora.apps.free_license.models import FreeLicense from agora.apps.bundle.models import Bundle from agora.apps.snippet.models import Snippet +from agora.apps.profile.models import Profile -def showprofile(request, user): +from agora.middleware.http import Http403 + +def getprofile(user): u = get_object_or_404(User, username=user) #Inactive users "don't exist" if not u.is_active: raise Http404 + #Get profile or create a default if none exists try: p = u.get_profile() - #Create a default profile if none exists except Profile.DoesNotExist: #At least one FreeLicense *must* exist. p = Profile(user=u, preferred_license=FreeLicense.objects.get(id=1)) p.save() + return [u,p] + +def showprofile(request, user): + [u,p] = getprofile(user) + if u.first_name or u.last_name: - n = u.first_name + " " + u.last_name + n = u.get_full_name() else: n = u.username b = Bundle.objects.filter(uploader=u) s = Snippet.objects.filter(uploader=u) - return render_to_response('user.djhtml', {'user' : u, - 'profile' : p, - 'bundles' : b, - 'snippets' : s, - 'name' : n, - }) + return render_to_response('profile/user.djhtml', + { + 'profile' : p, + 'bundles' : b, + 'snippets' : s, + 'name' : n, + }, + RequestContext(request) + ) + +@login_required +def editprofile(request, user): + [u,p] = getprofile(user) + + #Make sure user can only edit own profile + if request.user != u: + raise Http403 + + if request.method=='POST': + u.first_name = request.POST['first-name'] + u.last_name = request.POST['last-name'] + u.save() + + try: + p.preferred_license = \ + FreeLicense.objects.get(id=request.POST['license']) + except: + p.preferred_license = FreeLicense.objects.get(id=1) + + p.interests = request.POST['interests'] + p.blurb = request.POST['blurb'] + p.save() + return HttpResponseRedirect(reverse( + 'agora.apps.profile.views.showprofile', + args=(u,)) + ) + + licenses = FreeLicense.objects.all() + return render_to_response('profile/edit-user.djhtml', + { + 'profile' : p, + 'licenses' : licenses, + }, + RequestContext(request) + )
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/middleware/http.py Mon Jul 05 00:31:20 2010 -0500 @@ -0,0 +1,30 @@ +from django.template import RequestContext +from django.conf import settings +from django.core.exceptions import PermissionDenied +from django.http import HttpResponseForbidden +from django.template import loader + +class Http403(Exception): + pass + +def render_to_403(*args, **kwargs): + """ + Returns a HttpResponseForbidden whose content is filled with + the result of calling + django.template.loader.render_to_string() with the passed + arguments. + """ + if not isinstance(args,list): + args = [] + args.append('403.html') + + httpresponse_kwargs = {'mimetype': kwargs.pop('mimetype', None)} + response = HttpResponseForbidden(loader.render_to_string(*args, **kwargs), + **httpresponse_kwargs) + + return response + +class Http403Middleware(object): + def process_exception(self,request,exception): + if isinstance(exception,Http403): + return render_to_403(context_instance=RequestContext(request))
--- a/settings.py Fri Jul 02 02:18:22 2010 -0500 +++ b/settings.py Mon Jul 05 00:31:20 2010 -0500 @@ -97,11 +97,14 @@ ) MIDDLEWARE_CLASSES = ( - 'django.middleware.common.CommonMiddleware', - 'django.contrib.sessions.middleware.SessionMiddleware', - 'django.middleware.csrf.CsrfViewMiddleware', - 'django.contrib.auth.middleware.AuthenticationMiddleware', - 'django.contrib.messages.middleware.MessageMiddleware', + 'django.middleware.common.CommonMiddleware', + 'django.contrib.sessions.middleware.SessionMiddleware', + 'django.middleware.csrf.CsrfViewMiddleware', + 'django.contrib.auth.middleware.AuthenticationMiddleware', + 'django.contrib.messages.middleware.MessageMiddleware', + + #Agora-specific middleware + 'agora.middleware.http.Http403Middleware', ) ROOT_URLCONF = 'agora.urls'
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/templates/403.html Mon Jul 05 00:31:20 2010 -0500 @@ -0,0 +1,16 @@ +{% extends "whitebox.djhtml" %} + +{% block title %} +Access denied +{% endblock %} + +{% block boxtitle %} +Access denied +{% endblock %} + +{% block boxcontents %} +<p> + You requested access to a portion of Agora for which you don't have + permission. If you believe this is a mistake, please let us know. +</p> +{% endblock %}
--- a/templates/base.djhtml Fri Jul 02 02:18:22 2010 -0500 +++ b/templates/base.djhtml Mon Jul 05 00:31:20 2010 -0500 @@ -7,7 +7,7 @@ <title>Agora Octave — {% block title %} - Free your math! + Free your numbers! {% endblock %} </title>
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/templates/profile/edit-user.djhtml Mon Jul 05 00:31:20 2010 -0500 @@ -0,0 +1,76 @@ +{% extends "profile/user.djhtml" %} + +{% block boxtitle %} +Edit your profile +{% endblock boxtitle %} + +{% block boxcontents %} +<p class="explanation"> +You can provide some extra optional information about yourself. We +recommend that you provide us with a real name. If you do, it will be +displayed next to all of your contributions instead of your Agora +username. +</p> +<form id="userinfo" method="post" action="."> + + {% csrf_token %} + + <p class="explanation"> + We will display your name according to most Western European + conventions, your given name(s) followed by your surname(s). + </p> + <span class="userfield">Given name(s)</span> + <input type="text" + name="first-name" + id="edit-first-name" + value="{{user.first_name}}" /> <br /> + <span class="userfield">Surname(s)</span> + <input type="text" + id="edit-last-name" + name="last-name" + value="{{user.last_name}}" /> <br /> + + <p class="explanation"> + By default, all of your submissions will be under the following + license, and will be displayed next to your submissions. + <a href="/licenses"> + Here is a thorough explanation of the available licenses. + </a> + </p> + + <span class="userfield">Preferred license</span> + <select name="license" id="edit-license"> + {% for license in licenses %} + <option value="{{ license.id }}" + {% if license = profile.preferred_license %} + selected="true" + {% endif %} + /> + {{license.name}} + </option> + {% endfor %} + </select> + + <p class="explanation"> + Tell us about your research interests (e.g. <em>signal processing</em>, + <em>hyperbolic PDEs</em>). These keywords will be used when + searching for submissions. + </p> + <span class="userfield">Research interests</span> + <input type="text" + name="interests" + id="edit-interests" + value="{{profile.interests}}" /> <br /> + + <p class="explanation"> + Finally, anything else you would like to say about yourself. + </p> + + <span class="userfield">Blurb</span> + + <textarea name="blurb" id="edit-blurb">{{profile.blurb}}</textarea> + <br/> + + <input type="submit" value="Update profile" /> +</form> +{% endblock boxcontents %}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/templates/profile/user.djhtml Mon Jul 05 00:31:20 2010 -0500 @@ -0,0 +1,74 @@ +{% extends "whitebox.djhtml" %} + +{% block boxtitle %} +{{profile.user.username}} <br/> +{% if profile.user = user %} +<small> + (<a href="{% url agora.apps.profile.views.editprofile user %}"> + edit profile + </a>) +</small> +{% endif %} +{% endblock boxtitle%} + +{% block boxcontents %} +<div id="userinfo"> + {% if profile.user.first_name or profile.user.last_name %} + <span class="userfield">Name</span> + <span class="userdata">{{name}}</span> + <br /> + {% endif %} + <span class="userfield">Preferred license</span> + <span class="userdata">{{profile.preferred_license}}</span> + <br /> + {% if profile.interests %} + <h4> + Interests + </h4> + <p class="userdata"> + {{profile.interests}} + </p> + {% endif %} + + {% if profile.blurb %} + <h4> + About {{name}} + </h4> + <p class="userdata"> + {{profile.blurb}} + </p> +</div> +{% endif %} +{% endblock boxcontents %} + +{% block content-related %} +{% if bundles or snippets %} +<div id="info"> + <h3> + Contributions by {{name}} + </h3> + <div class="whitebox"> + {% if bundles %} + <h5> + Bundles + </h5> + <ul> + {% for b in bundles %} + <li> <a href="/{{profile.user.username}}/{{b.name}}">{{b.name}} </a></li> + {% endfor %} + </ul> + {% endif %} + {% if snippets %} + <h5> + Snippets + </h5> + <ul> + {% for s in snippets %} + <li><a href="/snippet/{{s}}"}{{s}}</a></li> + {% endfor %} + {% endif %} + </ul> + </div> +</div> +{% endif %} +{% endblock content-related %}
--- a/templates/user.djhtml Fri Jul 02 02:18:22 2010 -0500 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,65 +0,0 @@ -{% extends "whitebox.djhtml" %} -{% block boxtitle %} -{{user.username}} -{% endblock %} -{% block boxcontents %} -<div id="userinfo"> - {% if user.first_name or user.last_name %} - <span class="userfield">Name</span> - <span class="userdata">{{name}}</span> - <br /> - {% endif %} - <span class="userfield">Preferred license</span> - <span class="userdata">{{profile.preferred_license}}</span> - <br /> - {% if profile.interests %} - <h4> - Interests - </h4> - <p class="userdata"> - {{profile.interests}} - </p> - {% endif %} - - {% if profile.blurb %} - <h4> - About {{name}} - </h4> - <p class="userdata"> - {{profile.blurb}} - </p> -</div> -{% endif %} -{% endblock %} {# boxcontents #} - -{% block content-related %} -{% if bundles or snippets %} -<div id="info"> - <h3> - Contributions by {{name}} - </h3> - <div class="whitebox"> - {% if bundles %} - <h5> - Bundles - </h5> - <ul> - {% for b in bundles %} - <li> <a href="/{{user.username}}/{{b.name}}">{{b.name}} </a></li> - {% endfor %} - </ul> - {% endif %} - {% if snippets %} - <h5> - Snippets - </h5> - <ul> - {% for s in snippets %} - <li><a href="/snippet/{{s}}"}{{s}}</a></li> - {% endfor %} - {% endif %} - </ul> - </div> -</div> -{% endif %} -{% endblock %} {# content-related #}
--- a/urls.py Fri Jul 02 02:18:22 2010 -0500 +++ b/urls.py Mon Jul 05 00:31:20 2010 -0500 @@ -18,7 +18,8 @@ (r'^accounts/', include('registration.urls')), - (r'^(?P<user>[\w|_]*)/$', 'agora.apps.profile.views.showprofile'), + (r'^editprofile/(?P<user>\w*)/$', 'agora.apps.profile.views.editprofile'), + (r'^(?P<user>\w*)/$', 'agora.apps.profile.views.showprofile'), (r'^', include('agora.apps.bundle.urls')),