diff --git a/common/djangoapps/external_auth/views.py b/common/djangoapps/external_auth/views.py index 0425f3e158..35e59db0ca 100644 --- a/common/djangoapps/external_auth/views.py +++ b/common/djangoapps/external_auth/views.py @@ -1,3 +1,4 @@ +import functools import json import logging import random @@ -156,7 +157,7 @@ def edXauth_signup(request, eamap=None): log.debug('ExtAuth: doing signup for %s' % eamap.external_email) - return student_views.main_index(extra_context=context) + return student_views.main_index(request, extra_context=context) #----------------------------------------------------------------------------- # MIT SSL @@ -206,7 +207,7 @@ def edXauth_ssl_login(request): pass if not cert: # no certificate information - go onward to main index - return student_views.main_index() + return student_views.main_index(request) (user, email, fullname) = ssl_dn_extract_info(cert) @@ -216,4 +217,4 @@ def edXauth_ssl_login(request): credentials=cert, email=email, fullname=fullname, - retfun = student_views.main_index) + retfun = functools.partial(student_views.main_index, request)) diff --git a/common/djangoapps/student/views.py b/common/djangoapps/student/views.py index b6aa62e03d..a99b46fd13 100644 --- a/common/djangoapps/student/views.py +++ b/common/djangoapps/student/views.py @@ -68,9 +68,9 @@ def index(request): from external_auth.views import edXauth_ssl_login return edXauth_ssl_login(request) - return main_index(user=request.user) + return main_index(request, user=request.user) -def main_index(extra_context = {}, user=None): +def main_index(request, extra_context={}, user=None): ''' Render the edX main page. @@ -93,7 +93,8 @@ def main_index(extra_context = {}, user=None): entry.summary = soup.getText() # The course selection work is done in courseware.courses. - universities = get_courses_by_university(None) + universities = get_courses_by_university(None, + domain=request.META.get('HTTP_HOST')) context = {'universities': universities, 'entries': entries} context.update(extra_context) return render_to_response('index.html', context) diff --git a/lms/djangoapps/courseware/courses.py b/lms/djangoapps/courseware/courses.py index 2e74853760..f0b82a3c9c 100644 --- a/lms/djangoapps/courseware/courses.py +++ b/lms/djangoapps/courseware/courses.py @@ -2,8 +2,8 @@ from collections import defaultdict from fs.errors import ResourceNotFoundError from functools import wraps import logging -from path import path +from path import path from django.conf import settings from django.http import Http404 @@ -142,7 +142,8 @@ def get_course_info_section(course, section_key): raise KeyError("Invalid about key " + str(section_key)) -def get_courses_by_university(user): + +def get_courses_by_university(user, domain=None): ''' Returns dict of lists of courses available, keyed by course.org (ie university). Courses are sorted by course.number. @@ -152,9 +153,21 @@ def get_courses_by_university(user): courses = [c for c in modulestore().get_courses() if isinstance(c, CourseDescriptor)] courses = sorted(courses, key=lambda course: course.number) + + if domain and settings.MITX_FEATURES.get('SUBDOMAIN_COURSE_LISTINGS'): + subdomain = domain.split(".")[0] + if subdomain not in settings.COURSE_LISTINGS: + subdomain = 'default' + visible_courses = frozenset(settings.COURSE_LISTINGS[subdomain]) + else: + visible_courses = frozenset(c.id for c in courses) + universities = defaultdict(list) for course in courses: - if has_access(user, course, 'see_exists'): - universities[course.org].append(course) + if not has_access(user, course, 'see_exists'): + continue + if course.id not in visible_courses: + continue + universities[course.org].append(course) return universities diff --git a/lms/djangoapps/courseware/views.py b/lms/djangoapps/courseware/views.py index 98de50c089..2af58f3b27 100644 --- a/lms/djangoapps/courseware/views.py +++ b/lms/djangoapps/courseware/views.py @@ -63,7 +63,8 @@ def courses(request): ''' Render "find courses" page. The course selection work is done in courseware.courses. ''' - universities = get_courses_by_university(request.user) + universities = get_courses_by_university(request.user, + domain=request.META.get('HTTP_HOST')) return render_to_response("courses.html", {'universities': universities}) @@ -246,7 +247,8 @@ def university_profile(request, org_id): raise Http404("University Profile not found for {0}".format(org_id)) # Only grab courses for this org... - courses = get_courses_by_university(request.user)[org_id] + courses = get_courses_by_university(request.user, + domain=request.META.get('HTTP_HOST'))[org_id] context = dict(courses=courses, org_id=org_id) template_file = "university_profile/{0}.html".format(org_id).lower() diff --git a/lms/envs/common.py b/lms/envs/common.py index 303e73ea81..45818c0ff2 100644 --- a/lms/envs/common.py +++ b/lms/envs/common.py @@ -49,6 +49,11 @@ MITX_FEATURES = { ## Doing so will cause all courses to be released on production 'DISABLE_START_DATES': False, # When True, all courses will be active, regardless of start date + # When True, will only publicly list courses by the subdomain. Expects you + # to define COURSE_LISTINGS, a dictionary mapping subdomains to lists of + # course_ids (see dev_int.py for an example) + 'SUBDOMAIN_COURSE_LISTINGS' : False, + 'ENABLE_TEXTBOOK' : True, 'ENABLE_DISCUSSION' : True, @@ -61,6 +66,7 @@ MITX_FEATURES = { 'ACCESS_REQUIRE_STAFF_FOR_COURSE': False, 'AUTH_USE_OPENID': False, 'AUTH_USE_MIT_CERTIFICATES' : False, + } # Used for A/B testing diff --git a/lms/envs/dev_int.py b/lms/envs/dev_int.py new file mode 100644 index 0000000000..12123e12d4 --- /dev/null +++ b/lms/envs/dev_int.py @@ -0,0 +1,32 @@ +""" +This enables use of course listings by subdomain. To see it in action, point the +following domains to 127.0.0.1 in your /etc/hosts file: + + berkeley.dev + harvard.dev + mit.dev + +Note that OS X has a bug where using *.local domains is excruciatingly slow, so +use *.dev domains instead for local testing. +""" +from .dev import * + +MITX_FEATURES['SUBDOMAIN_COURSE_LISTINGS'] = True + +COURSE_LISTINGS = { + 'default' : ['BerkeleyX/CS169.1x/2012_Fall', + 'BerkeleyX/CS188.1x/2012_Fall', + 'HarvardX/CS50x/2012', + 'HarvardX/PH207x/2012_Fall', + 'MITx/3.091x/2012_Fall', + 'MITx/6.002x/2012_Fall', + 'MITx/6.00x/2012_Fall'], + + 'berkeley': ['BerkeleyX/CS169.1x/2012_Fall', + 'BerkeleyX/CS188.1x/2012_Fall'], + + 'harvard' : ['HarvardX/CS50x/2012'], + + 'mit' : ['MITx/3.091x/2012_Fall', + 'MITx/6.00x/2012_Fall'] +}