Add the ability to set expiration dates on course modes.
This commit is contained in:
@@ -0,0 +1,36 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
import datetime
|
||||
from south.db import db
|
||||
from south.v2 import SchemaMigration
|
||||
from django.db import models
|
||||
|
||||
|
||||
class Migration(SchemaMigration):
|
||||
|
||||
def forwards(self, orm):
|
||||
# Adding field 'CourseMode.expiration_date'
|
||||
db.add_column('course_modes_coursemode', 'expiration_date',
|
||||
self.gf('django.db.models.fields.DateField')(default=None, null=True),
|
||||
keep_default=False)
|
||||
|
||||
|
||||
def backwards(self, orm):
|
||||
# Deleting field 'CourseMode.expiration_date'
|
||||
db.delete_column('course_modes_coursemode', 'expiration_date')
|
||||
|
||||
|
||||
models = {
|
||||
'course_modes.coursemode': {
|
||||
'Meta': {'unique_together': "(('course_id', 'mode_slug', 'currency'),)", 'object_name': 'CourseMode'},
|
||||
'course_id': ('django.db.models.fields.CharField', [], {'max_length': '255', 'db_index': 'True'}),
|
||||
'currency': ('django.db.models.fields.CharField', [], {'default': "'usd'", 'max_length': '8'}),
|
||||
'expiration_date': ('django.db.models.fields.DateField', [], {'default': 'None', 'null': 'True'}),
|
||||
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
|
||||
'min_price': ('django.db.models.fields.IntegerField', [], {'default': '0'}),
|
||||
'mode_display_name': ('django.db.models.fields.CharField', [], {'max_length': '255'}),
|
||||
'mode_slug': ('django.db.models.fields.CharField', [], {'max_length': '100'}),
|
||||
'suggested_prices': ('django.db.models.fields.CommaSeparatedIntegerField', [], {'default': "''", 'max_length': '255', 'blank': 'True'})
|
||||
}
|
||||
}
|
||||
|
||||
complete_apps = ['course_modes']
|
||||
@@ -1,9 +1,13 @@
|
||||
"""
|
||||
Add and create new modes for running courses on this particular LMS
|
||||
"""
|
||||
import pytz
|
||||
from datetime import datetime
|
||||
|
||||
from django.db import models
|
||||
from collections import namedtuple
|
||||
from django.utils.translation import ugettext as _
|
||||
from django.db.models import Q
|
||||
|
||||
Mode = namedtuple('Mode', ['slug', 'name', 'min_price', 'suggested_prices', 'currency'])
|
||||
|
||||
@@ -32,6 +36,9 @@ class CourseMode(models.Model):
|
||||
# the currency these prices are in, using lower case ISO currency codes
|
||||
currency = models.CharField(default="usd", max_length=8)
|
||||
|
||||
# turn this mode off after the given expiration date
|
||||
expiration_date = models.DateField(default=None, null=True)
|
||||
|
||||
DEFAULT_MODE = Mode('honor', _('Honor Code Certificate'), 0, '', 'usd')
|
||||
DEFAULT_MODE_SLUG = 'honor'
|
||||
|
||||
@@ -42,11 +49,14 @@ class CourseMode(models.Model):
|
||||
@classmethod
|
||||
def modes_for_course(cls, course_id):
|
||||
"""
|
||||
Returns a list of the modes for a given course id
|
||||
Returns a list of the non-expired modes for a given course id
|
||||
|
||||
If no modes have been set in the table, returns the default mode
|
||||
"""
|
||||
found_course_modes = cls.objects.filter(course_id=course_id)
|
||||
now = datetime.now(pytz.UTC)
|
||||
found_course_modes = cls.objects.filter(Q(course_id=course_id) &
|
||||
Q(expiration_date__isnull=True) |
|
||||
Q(expiration_date__gte=now))
|
||||
modes = ([Mode(mode.mode_slug, mode.mode_display_name, mode.min_price, mode.suggested_prices, mode.currency)
|
||||
for mode in found_course_modes])
|
||||
if not modes:
|
||||
|
||||
@@ -5,6 +5,9 @@ when you run "manage.py test".
|
||||
Replace this with more appropriate tests for your application.
|
||||
"""
|
||||
|
||||
from datetime import datetime, timedelta
|
||||
import pytz
|
||||
|
||||
from django.test import TestCase
|
||||
from course_modes.models import CourseMode, Mode
|
||||
|
||||
@@ -22,7 +25,7 @@ class CourseModeModelTest(TestCase):
|
||||
"""
|
||||
Create a new course mode
|
||||
"""
|
||||
CourseMode.objects.get_or_create(
|
||||
return CourseMode.objects.get_or_create(
|
||||
course_id=self.course_id,
|
||||
mode_display_name=mode_name,
|
||||
mode_slug=mode_slug,
|
||||
@@ -46,7 +49,13 @@ class CourseModeModelTest(TestCase):
|
||||
|
||||
self.create_mode('verified', 'Verified Certificate')
|
||||
modes = CourseMode.modes_for_course(self.course_id)
|
||||
self.assertEqual([Mode(u'verified', u'Verified Certificate', 0, '', 'usd')], modes)
|
||||
mode = Mode(u'verified', u'Verified Certificate', 0, '', 'usd')
|
||||
self.assertEqual([mode], modes)
|
||||
|
||||
modes_dict = CourseMode.modes_for_course_dict(self.course_id)
|
||||
self.assertEqual(modes_dict['verified'], mode)
|
||||
self.assertEqual(CourseMode.mode_for_course(self.course_id, 'verified'),
|
||||
mode)
|
||||
|
||||
def test_modes_for_course_multiple(self):
|
||||
"""
|
||||
@@ -63,3 +72,15 @@ class CourseModeModelTest(TestCase):
|
||||
self.assertEqual(mode1, CourseMode.mode_for_course(self.course_id, u'honor'))
|
||||
self.assertEqual(mode2, CourseMode.mode_for_course(self.course_id, u'verified'))
|
||||
self.assertIsNone(CourseMode.mode_for_course(self.course_id, 'DNE'))
|
||||
|
||||
def test_modes_for_course_expired(self):
|
||||
expired_mode, _status = self.create_mode('verified', 'Verified Certificate')
|
||||
expired_mode.expiration_date = datetime.now(pytz.UTC) + timedelta(days=-1)
|
||||
expired_mode.save()
|
||||
modes = CourseMode.modes_for_course(self.course_id)
|
||||
self.assertEqual([CourseMode.DEFAULT_MODE], modes)
|
||||
|
||||
mode1 = Mode(u'honor', u'Honor Code Certificate', 0, '', 'usd')
|
||||
self.create_mode(mode1.slug, mode1.name, mode1.min_price, mode1.suggested_prices)
|
||||
modes = CourseMode.modes_for_course(self.course_id)
|
||||
self.assertEqual([mode1], modes)
|
||||
|
||||
@@ -391,6 +391,8 @@ def change_enrollment(request):
|
||||
reverse("course_modes_choose", kwargs={'course_id': course_id})
|
||||
)
|
||||
|
||||
current_mode = available_modes[0]
|
||||
|
||||
org, course_num, run = course_id.split("/")
|
||||
dog_stats_api.increment(
|
||||
"common.student.enrollment",
|
||||
@@ -399,7 +401,7 @@ def change_enrollment(request):
|
||||
"run:{0}".format(run)]
|
||||
)
|
||||
|
||||
CourseEnrollment.enroll(user, course.id)
|
||||
CourseEnrollment.enroll(user, course.id, mode=current_mode.slug)
|
||||
|
||||
return HttpResponse()
|
||||
|
||||
|
||||
Reference in New Issue
Block a user