Commit 66934ce2 by Victor Shnayder

Address Dave's comments on https://github.com/MITx/mitx/pull/1350

parent 3d303518
...@@ -8,6 +8,7 @@ from django.http import Http404 ...@@ -8,6 +8,7 @@ from django.http import Http404
import logging import logging
from courseware import courses from courseware import courses
from student.models import get_user_by_username_or_email
from .models import CourseUserGroup from .models import CourseUserGroup
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
...@@ -178,10 +179,7 @@ def add_user_to_cohort(cohort, username_or_email): ...@@ -178,10 +179,7 @@ def add_user_to_cohort(cohort, username_or_email):
CohortConflict if user already in another cohort. CohortConflict if user already in another cohort.
""" """
if '@' in username_or_email: user = get_user_by_username_or_email(username_or_email)
user = User.objects.get(email=username_or_email)
else:
user = User.objects.get(username=username_or_email)
# If user in any cohorts in this course already, complain # If user in any cohorts in this course already, complain
course_cohorts = CourseUserGroup.objects.filter( course_cohorts = CourseUserGroup.objects.filter(
......
from django_future.csrf import ensure_csrf_cookie from django_future.csrf import ensure_csrf_cookie
from django.contrib.auth.decorators import login_required from django.contrib.auth.decorators import login_required
from django.views.decorators.http import require_POST
from django.contrib.auth.models import User from django.contrib.auth.models import User
from django.core.context_processors import csrf from django.core.context_processors import csrf
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
...@@ -8,10 +9,10 @@ from django.http import HttpResponse, HttpResponseForbidden, Http404 ...@@ -8,10 +9,10 @@ from django.http import HttpResponse, HttpResponseForbidden, Http404
from django.shortcuts import redirect from django.shortcuts import redirect
import json import json
import logging import logging
import re
from courseware.courses import get_course_with_access from courseware.courses import get_course_with_access
from mitxmako.shortcuts import render_to_response, render_to_string from mitxmako.shortcuts import render_to_response, render_to_string
from string_util import split_by_comma_and_whitespace
from .models import CourseUserGroup from .models import CourseUserGroup
from . import cohorts from . import cohorts
...@@ -21,13 +22,20 @@ import track.views ...@@ -21,13 +22,20 @@ import track.views
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
def JsonHttpReponse(data): def json_http_response(data):
""" """
Return an HttpResponse with the data json-serialized and the right content type Return an HttpResponse with the data json-serialized and the right content
header. Named to look like a class. type header.
""" """
return HttpResponse(json.dumps(data), content_type="application/json") return HttpResponse(json.dumps(data), content_type="application/json")
def split_by_comma_and_whitespace(s):
"""
Split a string both by commas and whitespice. Returns a list.
"""
return re.split(r'[\s|,|]+', s)
@ensure_csrf_cookie @ensure_csrf_cookie
def list_cohorts(request, course_id): def list_cohorts(request, course_id):
""" """
...@@ -41,11 +49,12 @@ def list_cohorts(request, course_id): ...@@ -41,11 +49,12 @@ def list_cohorts(request, course_id):
all_cohorts = [{'name': c.name, 'id': c.id} all_cohorts = [{'name': c.name, 'id': c.id}
for c in cohorts.get_course_cohorts(course_id)] for c in cohorts.get_course_cohorts(course_id)]
return JsonHttpReponse({'success': True, return json_http_response({'success': True,
'cohorts': all_cohorts}) 'cohorts': all_cohorts})
@ensure_csrf_cookie @ensure_csrf_cookie
@require_POST
def add_cohort(request, course_id): def add_cohort(request, course_id):
""" """
Return json of dict: Return json of dict:
...@@ -60,22 +69,18 @@ def add_cohort(request, course_id): ...@@ -60,22 +69,18 @@ def add_cohort(request, course_id):
""" """
get_course_with_access(request.user, course_id, 'staff') get_course_with_access(request.user, course_id, 'staff')
if request.method != "POST":
raise Http404("Must POST to add cohorts")
name = request.POST.get("name") name = request.POST.get("name")
if not name: if not name:
return JsonHttpReponse({'success': False, return json_http_response({'success': False,
'msg': "No name specified"}) 'msg': "No name specified"})
try: try:
cohort = cohorts.add_cohort(course_id, name) cohort = cohorts.add_cohort(course_id, name)
except ValueError as err: except ValueError as err:
return JsonHttpReponse({'success': False, return json_http_response({'success': False,
'msg': str(err)}) 'msg': str(err)})
return JsonHttpReponse({'success': 'True', return json_http_response({'success': 'True',
'cohort': { 'cohort': {
'id': cohort.id, 'id': cohort.id,
'name': cohort.name 'name': cohort.name
...@@ -98,6 +103,8 @@ def users_in_cohort(request, course_id, cohort_id): ...@@ -98,6 +103,8 @@ def users_in_cohort(request, course_id, cohort_id):
""" """
get_course_with_access(request.user, course_id, 'staff') get_course_with_access(request.user, course_id, 'staff')
# this will error if called with a non-int cohort_id. That's ok--it
# shoudn't happen for valid clients.
cohort = cohorts.get_cohort_by_id(course_id, int(cohort_id)) cohort = cohorts.get_cohort_by_id(course_id, int(cohort_id))
paginator = Paginator(cohort.users.all(), 100) paginator = Paginator(cohort.users.all(), 100)
...@@ -118,13 +125,14 @@ def users_in_cohort(request, course_id, cohort_id): ...@@ -118,13 +125,14 @@ def users_in_cohort(request, course_id, cohort_id):
'name': '{0} {1}'.format(u.first_name, u.last_name)} 'name': '{0} {1}'.format(u.first_name, u.last_name)}
for u in users] for u in users]
return JsonHttpReponse({'success': True, return json_http_response({'success': True,
'page': page, 'page': page,
'num_pages': paginator.num_pages, 'num_pages': paginator.num_pages,
'users': user_info}) 'users': user_info})
@ensure_csrf_cookie @ensure_csrf_cookie
@require_POST
def add_users_to_cohort(request, course_id, cohort_id): def add_users_to_cohort(request, course_id, cohort_id):
""" """
Return json dict of: Return json dict of:
...@@ -140,9 +148,6 @@ def add_users_to_cohort(request, course_id, cohort_id): ...@@ -140,9 +148,6 @@ def add_users_to_cohort(request, course_id, cohort_id):
""" """
get_course_with_access(request.user, course_id, 'staff') get_course_with_access(request.user, course_id, 'staff')
if request.method != "POST":
raise Http404("Must POST to add users to cohorts")
cohort = cohorts.get_cohort_by_id(course_id, cohort_id) cohort = cohorts.get_cohort_by_id(course_id, cohort_id)
users = request.POST.get('users', '') users = request.POST.get('users', '')
...@@ -166,13 +171,14 @@ def add_users_to_cohort(request, course_id, cohort_id): ...@@ -166,13 +171,14 @@ def add_users_to_cohort(request, course_id, cohort_id):
'msg': str(err)}) 'msg': str(err)})
return JsonHttpReponse({'success': True, return json_http_response({'success': True,
'added': added, 'added': added,
'present': present, 'present': present,
'conflict': conflict, 'conflict': conflict,
'unknown': unknown}) 'unknown': unknown})
@ensure_csrf_cookie @ensure_csrf_cookie
@require_POST
def remove_user_from_cohort(request, course_id, cohort_id): def remove_user_from_cohort(request, course_id, cohort_id):
""" """
Expects 'username': username in POST data. Expects 'username': username in POST data.
...@@ -185,22 +191,19 @@ def remove_user_from_cohort(request, course_id, cohort_id): ...@@ -185,22 +191,19 @@ def remove_user_from_cohort(request, course_id, cohort_id):
""" """
get_course_with_access(request.user, course_id, 'staff') get_course_with_access(request.user, course_id, 'staff')
if request.method != "POST":
raise Http404("Must POST to add users to cohorts")
username = request.POST.get('username') username = request.POST.get('username')
if username is None: if username is None:
return JsonHttpReponse({'success': False, return json_http_response({'success': False,
'msg': 'No username specified'}) 'msg': 'No username specified'})
cohort = cohorts.get_cohort_by_id(course_id, cohort_id) cohort = cohorts.get_cohort_by_id(course_id, cohort_id)
try: try:
user = User.objects.get(username=username) user = User.objects.get(username=username)
cohort.users.remove(user) cohort.users.remove(user)
return JsonHttpReponse({'success': True}) return json_http_response({'success': True})
except User.DoesNotExist: except User.DoesNotExist:
log.debug('no user') log.debug('no user')
return JsonHttpReponse({'success': False, return json_http_response({'success': False,
'msg': "No user '{0}'".format(username)}) 'msg': "No user '{0}'".format(username)})
......
...@@ -613,7 +613,20 @@ class CourseEnrollmentAllowed(models.Model): ...@@ -613,7 +613,20 @@ class CourseEnrollmentAllowed(models.Model):
#cache_relation(User.profile) #cache_relation(User.profile)
#### Helper methods for use from python manage.py shell. #### Helper methods for use from python manage.py shell and other classes.
def get_user_by_username_or_email(username_or_email):
"""
Return a User object, looking up by email if username_or_email contains a
'@', otherwise by username.
Raises:
User.DoesNotExist is lookup fails.
"""
if '@' in username_or_email:
return User.objects.get(email=username_or_email)
else:
return User.objects.get(username=username_or_email)
def get_user(email): def get_user(email):
......
import itertools
def split_by_comma_and_whitespace(s):
"""
Split a string both by on commas and whitespice.
"""
# Note: split() with no args removes empty strings from output
lists = [x.split() for x in s.split(',')]
# return all of them
return itertools.chain(*lists)
...@@ -28,6 +28,8 @@ from django_comment_client.utils import JsonResponse, JsonError, extract, get_co ...@@ -28,6 +28,8 @@ from django_comment_client.utils import JsonResponse, JsonError, extract, get_co
from django_comment_client.permissions import check_permissions_by_view, cached_has_permission from django_comment_client.permissions import check_permissions_by_view, cached_has_permission
from django_comment_client.models import Role from django_comment_client.models import Role
log = logging.getLogger(__name__)
def permitted(fn): def permitted(fn):
@functools.wraps(fn) @functools.wraps(fn)
def wrapper(request, *args, **kwargs): def wrapper(request, *args, **kwargs):
...@@ -59,17 +61,12 @@ def ajax_content_response(request, course_id, content, template_name): ...@@ -59,17 +61,12 @@ def ajax_content_response(request, course_id, content, template_name):
'annotated_content_info': annotated_content_info, 'annotated_content_info': annotated_content_info,
}) })
def is_moderator(user, course_id):
cached_has_permission(user, "see_all_cohorts", course_id)
@require_POST @require_POST
@login_required @login_required
@permitted @permitted
def create_thread(request, course_id, commentable_id): def create_thread(request, course_id, commentable_id):
print "\n\n\n\n\n*******************" log.debug("Creating new thread in %r, id %r", course_id, commentable_id)
print commentable_id
course = get_course_with_access(request.user, course_id, 'load') course = get_course_with_access(request.user, course_id, 'load')
post = request.POST post = request.POST
...@@ -91,29 +88,23 @@ def create_thread(request, course_id, commentable_id): ...@@ -91,29 +88,23 @@ def create_thread(request, course_id, commentable_id):
'course_id' : course_id, 'course_id' : course_id,
'user_id' : request.user.id, 'user_id' : request.user.id,
}) })
#now cohort the thread if the commentable is cohorted # Cohort the thread if the commentable is cohorted.
#if the group id came in from the form, set it there, otherwise, if is_commentable_cohorted(course_id, commentable_id):
#see if the user and the commentable are cohorted user_group_id = get_cohort_id(request.user, course_id)
if is_commentable_cohorted(course_id,commentable_id): # TODO (vshnayder): once we have more than just cohorts, we'll want to
if 'group_id' in post: #if a group id was submitted in the form # change this to a single get_group_for_user_and_commentable function
posted_group_id = post['group_id'] # that can do different things depending on the commentable_id
else: if cached_has_permission(request.user, "see_all_cohorts", course_id):
post_group_id = None # admins can optionally choose what group to post as
group_id = post.get('group_id', user_group_id)
user_group_id = get_cohort_id(request.user, course_id)
if is_moderator(request.user,course_id):
if post_group_id is None:
group_id = user_group_id
else: else:
group_id = post_group_id # regular users always post with their own id.
else: group_id = user_group_id
group_id = user_group_id
thread.update_attributes(group_id=group_id)
thread.update_attributes(**{'group_id' :group_id})
thread.save() thread.save()
if post.get('auto_subscribe', 'false').lower() == 'true': if post.get('auto_subscribe', 'false').lower() == 'true':
user = cc.User.from_django_user(request.user) user = cc.User.from_django_user(request.user)
......
...@@ -17,7 +17,8 @@ from courseware.access import has_access ...@@ -17,7 +17,8 @@ from courseware.access import has_access
from urllib import urlencode from urllib import urlencode
from operator import methodcaller from operator import methodcaller
from django_comment_client.permissions import check_permissions_by_view from django_comment_client.permissions import check_permissions_by_view
from django_comment_client.utils import merge_dict, extract, strip_none, strip_blank, get_courseware_context from django_comment_client.utils import (merge_dict, extract, strip_none,
strip_blank, get_courseware_context)
import django_comment_client.utils as utils import django_comment_client.utils as utils
import comment_client as cc import comment_client as cc
...@@ -58,16 +59,17 @@ def get_threads(request, course_id, discussion_id=None, per_page=THREADS_PER_PAG ...@@ -58,16 +59,17 @@ def get_threads(request, course_id, discussion_id=None, per_page=THREADS_PER_PAG
user.default_sort_key = request.GET.get('sort_key') user.default_sort_key = request.GET.get('sort_key')
user.save() user.save()
#if the course-user is cohorted, then add the group id #if the course-user is cohorted, then add the group id
group_id = get_cohort_id(user,course_id); group_id = get_cohort_id(user,course_id)
if group_id: if group_id:
default_query_params["group_id"] = group_id; default_query_params["group_id"] = group_id
print("\n\n\n\n\n****************GROUP ID IS ")
print group_id
query_params = merge_dict(default_query_params, query_params = merge_dict(default_query_params,
strip_none(extract(request.GET, ['page', 'sort_key', 'sort_order', 'text', 'tags', 'commentable_ids']))) strip_none(extract(request.GET,
['page', 'sort_key',
'sort_order', 'text',
'tags', 'commentable_ids'])))
threads, page, num_pages = cc.Thread.search(query_params) threads, page, num_pages = cc.Thread.search(query_params)
...@@ -226,7 +228,7 @@ def single_thread(request, course_id, discussion_id, thread_id): ...@@ -226,7 +228,7 @@ def single_thread(request, course_id, discussion_id, thread_id):
# course_id, # course_id,
#) #)
annotated_content_info = utils.get_metadata_for_threads(course_id, threads, request.user, user_info) annotated_content_info = utils.get_metadata_for_threads(course_id, threads, request.user, user_info)
context = { context = {
......
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