예제 #1
0
def cancel_reservation(request, course_slug, reservation_id):

    if request.method in ['POST', 'DELETE']:

        course = get_course_if_user_can_view_or_404(course_slug, request)

        is_enrolled = course.students.filter(id=request.user.id).exists()

        if not is_enrolled:
            messages.error(request, _('You are not enrolled in this course'))
            return HttpResponseRedirect(reverse('course_overview',
                                        args=[course_slug]))

        reserv_remove = Reservation.objects.get(Q(id=reservation_id) & Q(user__id=request.user.id))
        if reserv_remove is None:
            messages.error(request, _('You are not the owner of this reservation'))
            return HttpResponseRedirect(reverse('course_reservations', args=[course.slug]))

        cancel_limit = datetime.utcnow().replace(tzinfo=pytz.utc)
        cancel_limit += timedelta(0, reserv_remove.asset.cancelation_in_advance * 60)

        if reserv_remove.reservation_begins < cancel_limit:
            messages.error(request, _('Not enough time in advance to cancel this reservation.'))
            return HttpResponseRedirect(reverse('course_reservations', args=[course.slug]))

        reserv_remove.delete()

        return HttpResponseRedirect(reverse('course_reservations', args=[course.slug]))

    else:
        return HttpResponseNotAllowed(['POST', 'DELETE'])
예제 #2
0
파일: views.py 프로젝트: MCHacker/moocng
def course_reviews(request, course_slug):
    course = get_course_if_user_can_view_or_404(course_slug, request)

    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(reverse('course_overview', args=[course_slug]))

    is_ready, ask_admin = is_course_ready(course)

    if not is_ready:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        }, context_instance=RequestContext(request))

    assignments = course_get_visible_peer_review_assignments(request.user,
                                                             course)

    collection = get_db().get_collection('peer_review_submissions')
    submissions = collection.find({
        'author': request.user.id,
        'course': course.id,
    }, {'kq': True, '_id': False})
    submissions = [s['kq'] for s in submissions]

    user_submissions = [a.id for a in assignments if a.kq.id in submissions]

    return render_to_response('peerreview/reviews.html', {
        'course': course,
        'assignments': assignments,
        'user_submissions': user_submissions,
        'is_enrolled': is_enrolled,
    }, context_instance=RequestContext(request))
예제 #3
0
def course_review_upload(request, course_slug):
    if request.method == "POST":
        course = get_course_if_user_can_view_or_404(course_slug, request)
        file_to_upload = request.FILES.get('pr_file', None)
        submission_text = request.POST.get('pr-submission', '')

        kq = get_object_or_404(KnowledgeQuantum, id=request.POST.get('kq_id', 0))
        unit = kq.unit

        if (file_to_upload.size / (1024 * 1024) >= settings.PEER_REVIEW_FILE_MAX_SIZE):
            messages.error(request, _('Your file is greater than the max allowed size (%d MB).') % settings.PEER_REVIEW_FILE_MAX_SIZE)
            return HttpResponseRedirect(reverse('course_classroom', args=[course_slug]) + "#unit%d/kq%d/p" % (unit.id, kq.id))

        if (len(submission_text) >= settings.PEER_REVIEW_TEXT_MAX_SIZE):
            messages.error(request, _('Your text is greater than the max allowed size (%d characters).') % settings.PEER_REVIEW_TEXT_MAX_SIZE)
            return HttpResponseRedirect(reverse('course_classroom', args=[course_slug]) + "#unit%d/kq%d/p" % (unit.id, kq.id))

        s3_upload(request.user.id, kq.id, file_to_upload.name, file_to_upload)
        file_url = s3_url(request.user.id, file_to_upload.name, kq.id)
        submission = {
            "author": request.user.id,
            "author_reviews": 0,
            "text": request.POST.get('pr-submission', ''),
            "file": file_url,
            "created": datetime.utcnow(),
            "reviews": 0,
            "course": course.id,
            "unit": unit.id,
            "kq": kq.id,
        }
        insert_p2p_if_does_not_exists_or_raise(submission)
        return HttpResponseRedirect(reverse('course_classroom', args=[course_slug]) + "#unit%d/kq%d/p" % (unit.id, kq.id))
예제 #4
0
def course_review_assign(request, course_slug, assignment_id):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    assignment = get_object_or_404(PeerReviewAssignment, id=assignment_id)
    user_id = request.user.id

    is_enrolled = course.students.filter(id=user_id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(reverse('course_overview', args=[course_slug]))

    if assignment.kq.unit.course != course:
        messages.error(request, _('The selected peer review assignment is not part of this course.'))
        return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))

    collection = get_db().get_collection('peer_review_submissions')

    submission = collection.find({
        'kq': assignment.kq.id,
        'assigned_to': user_id
    })
    if submission.count() > 0:
        messages.error(request, _('You already have a submission assigned.'))
        return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))

    max_hours_assigned = timedelta(hours=getattr(settings,
                                   "PEER_REVIEW_ASSIGNATION_EXPIRE", 24))

    assignation_expire = datetime.utcnow() - max_hours_assigned

    #Check number of course langs to assign a PeerReview
    is_user_lang_valid = False
    if course.languages.count() > 1:
        for lang in course.languages.all():
            if request.user.get_profile().language == lang.abbr:
                is_user_lang_valid = True
        if is_user_lang_valid:
            submission = _get_peer_review_submission(user_id, assignment.kq.id, assignation_expire, request.user.get_profile().language)
        else:
            submission = _get_peer_review_submission(user_id, assignment.kq.id, assignation_expire)
    else:
        submission = _get_peer_review_submission(user_id, assignment.kq.id, assignation_expire)

    if submission.count() == 0:
        # Deactivate while it is finished
        #if course.languages.count() > 1 and is_user_lang_valid:
        #    return HttpResponseRedirect(reverse('course_reviews_ignorelang', args=[course_slug, assignment.kq.id]))
        messages.error(request, _('There is no submission avaliable for you at this moment. Please, try again later.'))
        return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))
    else:
        collection.update({
            '_id': submission[0]['_id']
        }, {
            '$set': {
                'assigned_to': user_id,
                'assigned_when': datetime.utcnow()
            }
        })
        return HttpResponseRedirect(reverse('course_review_review', args=[course_slug, assignment_id]))
예제 #5
0
파일: views.py 프로젝트: fid-jose/moocng
def course_extra_info(request, course_slug):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    is_enrolled = course.students.filter(id=request.user.id).exists()

    return render_to_response('courses/static_page.html', {
        'course': course,
        'is_enrolled': is_enrolled,  # required due course nav templatetag
        'is_teacher': is_teacher_test(request.user, course),
        'static_page': course.static_page,
    }, context_instance=RequestContext(request))
예제 #6
0
파일: views.py 프로젝트: MCHacker/moocng
def free_unenrollment(request, course_slug):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    if request.method == 'POST':
        user = request.user
        course.students.through.objects.get(student=user,
                                            course=course).delete()
        success(request,
                _(u'You have successfully unenroll in the course %(course)s')
                % {'course': unicode(course)})

    return HttpResponseRedirect(reverse('course_overview',
                                        args=(course.slug, )))
예제 #7
0
def course_classroom(request, course_slug):
    """
    Main view of the course content (class). If the user is not enrolled we
    show him a message. If the course is not ready and the user is not admin
    we redirect the user to a denied access page.

    :permissions: login
    :context: course, is_enrolled, ask_admin, unit_list, is_teacher, peer_view

    .. versionadded:: 0.1
    """
    course = get_course_if_user_can_view_or_404(course_slug, request)
    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(
            reverse('course_overview', args=[course_slug]))

    is_ready, ask_admin = is_course_ready(course)

    if not is_ready and not request.user.is_superuser:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        },
                                  context_instance=RequestContext(request))

    units = []
    for u in get_units_available_for_user(course, request.user):
        unit = {
            'id': u.id,
            'title': u.title,
            'unittype': u.unittype,
            'badge_class': get_unit_badge_class(u),
            'badge_tooltip': u.get_unit_type_name(),
        }
        units.append(unit)

    peer_review = {
        'text_max_size': settings.PEER_REVIEW_TEXT_MAX_SIZE,
        'file_max_size': settings.PEER_REVIEW_FILE_MAX_SIZE,
    }

    return render_to_response(
        'courses/classroom.html', {
            'course': course,
            'unit_list': units,
            'is_enrolled': is_enrolled,
            'is_teacher': is_teacher_test(request.user, course),
            'peer_review': peer_review
        },
        context_instance=RequestContext(request))
예제 #8
0
def course_extra_info(request, course_slug):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    is_enrolled = course.students.filter(id=request.user.id).exists()

    return render_to_response(
        'courses/static_page.html',
        {
            'course': course,
            'is_enrolled': is_enrolled,  # required due course nav templatetag
            'is_teacher': is_teacher_test(request.user, course),
            'static_page': course.static_page,
        },
        context_instance=RequestContext(request))
예제 #9
0
def course_reservations(request, course_slug):
    course = get_course_if_user_can_view_or_404(course_slug, request)

    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(
            reverse('course_overview', args=[course_slug]))

    is_ready, ask_admin = is_course_ready(course)

    if not is_ready:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        },
                                  context_instance=RequestContext(request))

    active_reservations = []
    for i in user_course_get_active_reservations(request.user, course):
        base = model_to_dict(i)
        base['concurrent'] = get_concurrent_reservations(i)
        base['asset'] = i.asset
        base['reserved_from'] = i.reserved_from
        active_reservations.append(base)

    past_reservations = []
    for i in user_course_get_past_reservations(request.user, course):
        base = model_to_dict(i)
        base['concurrent'] = get_concurrent_reservations(i)
        base['asset'] = i.asset
        base['reserved_from'] = i.reserved_from
        past_reservations.append(base)

    pending_reservations = []
    for i in user_course_get_pending_reservations(request.user, course):
        base = model_to_dict(i)
        base['concurrent'] = get_concurrent_reservations(i)
        base['asset'] = i.asset
        base['reserved_from'] = i.reserved_from
        pending_reservations.append(base)

    return render_to_response('assets/reservations.html', {
        'course': course,
        'is_enrolled': is_enrolled,
        'active_reservations': active_reservations,
        'past_reservations': past_reservations,
        'pending_reservations': pending_reservations,
    },
                              context_instance=RequestContext(request))
예제 #10
0
파일: views.py 프로젝트: fid-jose/moocng
def course_classroom(request, course_slug):

    """
    Main view of the course content (class). If the user is not enrolled we
    show him a message. If the course is not ready and the user is not admin
    we redirect the user to a denied access page.

    :permissions: login
    :context: course, is_enrolled, ask_admin, unit_list, is_teacher, peer_view

    .. versionadded:: 0.1
    """
    course = get_course_if_user_can_view_or_404(course_slug, request)
    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(reverse('course_overview', args=[course_slug]))

    is_ready, ask_admin = is_course_ready(course)

    if not is_ready and not request.user.is_superuser:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        }, context_instance=RequestContext(request))

    units = []
    for u in get_units_available_for_user(course, request.user):
        unit = {
            'id': u.id,
            'title': u.title,
            'unittype': u.unittype,
            'badge_class': get_unit_badge_class(u),
            'badge_tooltip': u.get_unit_type_name(),
        }
        units.append(unit)

    peer_review = {
        'text_max_size': settings.PEER_REVIEW_TEXT_MAX_SIZE,
        'file_max_size': settings.PEER_REVIEW_FILE_MAX_SIZE,
    }

    return render_to_response('courses/classroom.html', {
        'course': course,
        'unit_list': units,
        'is_enrolled': is_enrolled,
        'is_teacher': is_teacher_test(request.user, course),
        'peer_review': peer_review
    }, context_instance=RequestContext(request))
예제 #11
0
def course_reservations(request, course_slug):
    course = get_course_if_user_can_view_or_404(course_slug, request)

    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(reverse('course_overview',
                                            args=[course_slug]))

    is_ready, ask_admin, is_outdated = is_course_ready(course)

    if not is_ready:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        }, context_instance=RequestContext(request))

    active_reservations = []
    for i in user_course_get_active_reservations(request.user, course):
        base = model_to_dict(i)
        base['concurrent'] = get_concurrent_reservations(i)
        base['asset'] = i.asset
        base['reserved_from'] = i.reserved_from
        active_reservations.append(base)

    past_reservations = []
    for i in user_course_get_past_reservations(request.user, course):
        base = model_to_dict(i)
        base['concurrent'] = get_concurrent_reservations(i)
        base['asset'] = i.asset
        base['reserved_from'] = i.reserved_from
        past_reservations.append(base)

    pending_reservations = []
    for i in user_course_get_pending_reservations(request.user, course):
        base = model_to_dict(i)
        base['concurrent'] = get_concurrent_reservations(i)
        base['asset'] = i.asset
        base['reserved_from'] = i.reserved_from
        pending_reservations.append(base)

    return render_to_response('assets/reservations.html', {
        'course': course,
        'is_enrolled': is_enrolled,
        'active_reservations': active_reservations,
        'past_reservations': past_reservations,
        'pending_reservations': pending_reservations,
    }, context_instance=RequestContext(request))
예제 #12
0
def reservation_create(request, course_slug, kq_id, asset_id):

    if request.method in ['POST', 'PUT']:
        course = get_course_if_user_can_view_or_404(course_slug, request)
        is_enrolled = course.students.filter(id=request.user.id).exists()

        if not is_enrolled:
            messages.error(request, _('You are not enrolled in this course'))
            return HttpResponseRedirect(
                reverse('course_overview', args=[course_slug]))

        kq = get_object_or_404(KnowledgeQuantum, id=kq_id)
        asset = get_object_or_404(Asset, id=asset_id)

        try:
            availability = kq.asset_availability
        except AssetAvailability.DoesNotExist:
            messages.error(request, _('This nugget has no available asset'))
            return HttpResponseRedirect(
                reverse('course_reservations', args=[course_slug]))

        if not ('reservation_date' in request.POST
                and 'reservation_time' in request.POST):
            messages.error(request, _('No initial time specified'))
            return HttpResponseRedirect(
                reverse('course_reservations', args=[course_slug]))

        try:
            reservation_starts = datetime.strptime(
                request.POST['reservation_date'] + ' ' +
                request.POST['reservation_time'], '%Y-%m-%d %H:%M')
        except ValueError:
            messages.error(request, _('Incorrect booking time specified'))
            return HttpResponseRedirect(
                reverse('course_overview', args=[course_slug]))

        did_book = book_asset(
            request.user, asset, availability, reservation_starts,
            reservation_starts + timedelta(0, asset.slot_duration * 60))
        if did_book[0]:
            messages.success(request, did_book[1])
        else:
            messages.error(request, did_book[1])

        return HttpResponseRedirect(
            reverse('course_reservations', args=[course_slug]))
    else:
        return HttpResponseNotAllowed(['POST', 'PUT'])
예제 #13
0
def course_progress(request, course_slug):
    """
    Main view for the user progress in the course. This will return the units for
    the user in the current course.

    :permissions: login
    :context: course, is_enrolled, ask_admin, course, unit_list, is_teacher

    .. versionadded:: 0.1
    """
    course = get_course_if_user_can_view_or_404(course_slug, request)

    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(
            reverse('course_overview', args=[course_slug]))

    is_ready, ask_admin = is_course_ready(course)

    if not is_ready:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        },
                                  context_instance=RequestContext(request))

    units = []
    for u in get_units_available_for_user(course, request.user):
        unit = {
            'id': u.id,
            'title': u.title,
            'unittype': u.unittype,
            'badge_class': get_unit_badge_class(u),
            'badge_tooltip': u.get_unit_type_name(),
        }
        units.append(unit)

    return render_to_response(
        'courses/progress.html',
        {
            'course': course,
            'unit_list': units,
            'is_enrolled': is_enrolled,  # required due course nav templatetag
            'is_teacher': is_teacher_test(request.user, course),
        },
        context_instance=RequestContext(request))
예제 #14
0
def course_reviews(request, course_slug, kq_id=None, ignore_langs=False):
    course = get_course_if_user_can_view_or_404(course_slug, request)

    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(reverse('course_overview', args=[course_slug]))

    is_ready, ask_admin, is_outdated = is_course_ready(course)
    is_teacher = is_teacher_test(request.user, course)

    if not is_ready and not is_teacher and not request.user.is_staff and not request.user.is_superuser:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        }, context_instance=RequestContext(request))

    assignments = course_get_visible_peer_review_assignments(request.user,
                                                             course)

    collection = get_db().get_collection('peer_review_submissions')
    submissions = collection.find({
        'author': request.user.id,
        'course': course.id,
    }, {'kq': True, '_id': False})
    submissions = [s['kq'] for s in submissions]

    user_submissions = [a.id for a in assignments if a.kq.id in submissions]
    tasks = get_tasks_available_for_user(course, request.user)
    group = get_group_by_user_and_course(request.user.id, course.id)

    return render_to_response('peerreview/reviews.html', {
        'course': course,
        'assignments': assignments,
        'user_submissions': user_submissions,
        'kq_id': kq_id,
        'ignore_langs': ignore_langs,
        'is_enrolled': is_enrolled,
        'is_ready': is_ready,
        'is_outdated': is_outdated,
        'can_review': date.today() < course.end_date+timedelta(days=14),
        'task_list': tasks[0],
        'tasks_done': tasks[1],
        'progress': get_course_progress_for_user(course, request.user),
        'passed': has_user_passed_course(request.user, course),
        'group': group,
    }, context_instance=RequestContext(request))
예제 #15
0
파일: views.py 프로젝트: fid-jose/moocng
def clone_activity(request, course_slug):
    if request.method != 'POST':
        raise HttpResponseBadRequest
    user = request.user
    course = get_course_if_user_can_view_or_404(course_slug, request)
    course_student_relation = get_object_or_404(user.coursestudent_set, course=course)
    if not course_student_relation.can_clone_activity():
        return HttpResponseBadRequest()
    course_student_relation.old_course_status = 'c'
    course_student_relation.save()
    clone_activity_user_course_task.apply_async(args=[user, course, get_language()],
                                                queue='courses')
    message = _(u'We are cloning the activity from %(course)s. You will receive an email soon')
    messages.success(request,
                     message % {'course': unicode(course)})
    return HttpResponseRedirect(course.get_absolute_url())
예제 #16
0
파일: views.py 프로젝트: fid-jose/moocng
def announcement_detail(request, course_slug, announcement_id, announcement_slug):

    """
    Show a detail view of an announcement.

    :context: course, announcement

    .. versionadded:: 0.1
    """
    course = get_course_if_user_can_view_or_404(course_slug, request)
    announcement = get_object_or_404(Announcement, id=announcement_id)

    return render_to_response('courses/announcement.html', {
        'course': course,
        'announcement': announcement,
        'template_base': 'courses/base_course.html'
    }, context_instance=RequestContext(request))
예제 #17
0
파일: views.py 프로젝트: ntwuxc/moocng
def course_review_upload(request, course_slug):
    if request.method == "POST":
        course = get_course_if_user_can_view_or_404(course_slug, request)
        file_to_upload = request.FILES.get('pr_file', None)
        submission_text = request.POST.get('pr-submission', '')

        kq = get_object_or_404(KnowledgeQuantum,
                               id=request.POST.get('kq_id', 0))
        unit = kq.unit

        if (file_to_upload.size /
            (1024 * 1024) >= settings.PEER_REVIEW_FILE_MAX_SIZE):
            messages.error(
                request,
                _('Your file is greater than the max allowed size (%d MB).') %
                settings.PEER_REVIEW_FILE_MAX_SIZE)
            return HttpResponseRedirect(
                reverse('course_classroom', args=[course_slug]) +
                "#unit%d/kq%d/p" % (unit.id, kq.id))

        if (len(submission_text) >= settings.PEER_REVIEW_TEXT_MAX_SIZE):
            messages.error(
                request,
                _('Your text is greater than the max allowed size (%d characters).'
                  ) % settings.PEER_REVIEW_TEXT_MAX_SIZE)
            return HttpResponseRedirect(
                reverse('course_classroom', args=[course_slug]) +
                "#unit%d/kq%d/p" % (unit.id, kq.id))

        s3_upload(request.user.id, kq.id, file_to_upload.name, file_to_upload)
        file_url = s3_url(request.user.id, file_to_upload.name, kq.id)
        submission = {
            "author": request.user.id,
            "author_reviews": 0,
            "text": request.POST.get('pr-submission', ''),
            "file": file_url,
            "created": datetime.utcnow(),
            "reviews": 0,
            "course": course.id,
            "unit": unit.id,
            "kq": kq.id,
        }
        insert_p2p_if_does_not_exists_or_raise(submission)
        return HttpResponseRedirect(
            reverse('course_classroom', args=[course_slug]) +
            "#unit%d/kq%d/p" % (unit.id, kq.id))
예제 #18
0
def reservation_create(request, course_slug, kq_id, asset_id):

    if request.method in ['POST', 'PUT']:
        course = get_course_if_user_can_view_or_404(course_slug, request)
        is_enrolled = course.students.filter(id=request.user.id).exists()

        if not is_enrolled:
            messages.error(request, _('You are not enrolled in this course'))
            return HttpResponseRedirect(reverse('course_overview',
                                                args=[course_slug]))

        kq = get_object_or_404(KnowledgeQuantum, id=kq_id)
        asset = get_object_or_404(Asset, id=asset_id)

        try:
            availability = kq.asset_availability
        except AssetAvailability.DoesNotExist:
            messages.error(request, _('This nugget has no available asset'))
            return HttpResponseRedirect(reverse('course_reservations',
                                        args=[course_slug]))

        if not ('reservation_date' in request.POST and 'reservation_time' in request.POST):
            messages.error(request, _('No initial time specified'))
            return HttpResponseRedirect(reverse('course_reservations',
                                        args=[course_slug]))

        try:
            reservation_starts = datetime.strptime(request.POST['reservation_date'] + ' ' + request.POST['reservation_time'],
                                                   '%Y-%m-%d %H:%M')
        except ValueError:
            messages.error(request, _('Incorrect booking time specified'))
            return HttpResponseRedirect(reverse('course_overview',
                                        args=[course_slug]))

        did_book = book_asset(request.user, asset, availability, reservation_starts,
                              reservation_starts + timedelta(0, asset.slot_duration * 60))
        if did_book[0]:
            messages.success(request, did_book[1])
        else:
            messages.error(request, did_book[1])

        return HttpResponseRedirect(reverse('course_reservations',
                                    args=[course_slug]))
    else:
        return HttpResponseNotAllowed(['POST', 'PUT'])
예제 #19
0
def announcement_detail(request, course_slug, announcement_id,
                        announcement_slug):
    """
    Show a detail view of an announcement.

    :context: course, announcement

    .. versionadded:: 0.1
    """
    course = get_course_if_user_can_view_or_404(course_slug, request)
    announcement = get_object_or_404(Announcement, id=announcement_id)

    return render_to_response('courses/announcement.html', {
        'course': course,
        'announcement': announcement,
        'template_base': 'courses/base_course.html'
    },
                              context_instance=RequestContext(request))
예제 #20
0
def clone_activity(request, course_slug):
    if request.method != 'POST':
        raise HttpResponseBadRequest
    user = request.user
    course = get_course_if_user_can_view_or_404(course_slug, request)
    course_student_relation = get_object_or_404(user.coursestudent_set,
                                                course=course)
    if not course_student_relation.can_clone_activity():
        return HttpResponseBadRequest()
    course_student_relation.old_course_status = 'c'
    course_student_relation.save()
    clone_activity_user_course_task.apply_async(
        args=[user, course, get_language()], queue='courses')
    message = _(
        u'We are cloning the activity from %(course)s. You will receive an email soon'
    )
    messages.success(request, message % {'course': unicode(course)})
    return HttpResponseRedirect(course.get_absolute_url())
예제 #21
0
파일: views.py 프로젝트: fid-jose/moocng
def course_progress(request, course_slug):

    """
    Main view for the user progress in the course. This will return the units for
    the user in the current course.

    :permissions: login
    :context: course, is_enrolled, ask_admin, course, unit_list, is_teacher

    .. versionadded:: 0.1
    """
    course = get_course_if_user_can_view_or_404(course_slug, request)

    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(reverse('course_overview', args=[course_slug]))

    is_ready, ask_admin = is_course_ready(course)

    if not is_ready:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        }, context_instance=RequestContext(request))

    units = []
    for u in get_units_available_for_user(course, request.user):
        unit = {
            'id': u.id,
            'title': u.title,
            'unittype': u.unittype,
            'badge_class': get_unit_badge_class(u),
            'badge_tooltip': u.get_unit_type_name(),
        }
        units.append(unit)

    return render_to_response('courses/progress.html', {
        'course': course,
        'unit_list': units,
        'is_enrolled': is_enrolled,  # required due course nav templatetag
        'is_teacher': is_teacher_test(request.user, course),
    }, context_instance=RequestContext(request))
예제 #22
0
파일: views.py 프로젝트: MCHacker/moocng
def free_enrollment(request, course_slug):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    if request.method == 'POST':
        user = request.user
        old_course_status = 'f'
        if course.created_from:
            if course.created_from.students.filter(pk=user.pk):
                old_course_status = 'n'
        course.students.through.objects.create(student=user,
                                               course=course,
                                               old_course_status=old_course_status)
        if getattr(settings, 'FREE_ENROLLMENT_CONSISTENT', False):
            enroll_course_at_idp(request.user, course)
        success(request,
                _(u'Congratulations, you have successfully enroll in the course %(course)s')
                % {'course': unicode(course)})

    return HttpResponseRedirect(reverse('course_overview',
                                        args=(course.slug, )))
예제 #23
0
파일: views.py 프로젝트: ntwuxc/moocng
def course_reviews(request, course_slug):
    course = get_course_if_user_can_view_or_404(course_slug, request)

    is_enrolled = course.students.filter(id=request.user.id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(
            reverse('course_overview', args=[course_slug]))

    is_ready, ask_admin = is_course_ready(course)

    if not is_ready:
        return render_to_response('courses/no_content.html', {
            'course': course,
            'is_enrolled': is_enrolled,
            'ask_admin': ask_admin,
        },
                                  context_instance=RequestContext(request))

    assignments = course_get_visible_peer_review_assignments(
        request.user, course)

    collection = get_db().get_collection('peer_review_submissions')
    submissions = collection.find(
        {
            'author': request.user.id,
            'course': course.id,
        }, {
            'kq': True,
            '_id': False
        })
    submissions = [s['kq'] for s in submissions]

    user_submissions = [a.id for a in assignments if a.kq.id in submissions]

    return render_to_response('peerreview/reviews.html', {
        'course': course,
        'assignments': assignments,
        'user_submissions': user_submissions,
        'is_enrolled': is_enrolled,
    },
                              context_instance=RequestContext(request))
예제 #24
0
def course_overview(request, course_slug):
    """
    Show the course main page. This will show the main information about the
    course and the 'register to this course' button.

    .. note:: **use_old_calculus** is a compatibility method with old evaluation
              methods, which allowed the normal units to be evaluated. The new
              system does not evaluate normal units, only tasks and exams.

    :context: course, units, is_enrolled, is_teacher, request, course_teachers,
              announcements, use_old_calculus

    .. versionadded:: 0.1
    """
    course = get_course_if_user_can_view_or_404(course_slug, request)

    if request.user.is_authenticated():
        is_enrolled = course.students.filter(id=request.user.id).exists()
        is_teacher = is_teacher_test(request.user, course)
    else:
        is_enrolled = False
        is_teacher = False

    course_teachers = CourseTeacher.objects.filter(course=course)
    announcements = Announcement.objects.filter(
        course=course).order_by('datetime').reverse()[:5]
    units = get_units_available_for_user(course, request.user, True)

    return render_to_response(
        'courses/overview.html', {
            'course': course,
            'units': units,
            'is_enrolled': is_enrolled,
            'is_teacher': is_teacher,
            'request': request,
            'course_teachers': course_teachers,
            'announcements': announcements,
            'use_old_calculus': settings.COURSES_USING_OLD_TRANSCRIPT,
        },
        context_instance=RequestContext(request))
예제 #25
0
def cancel_reservation(request, course_slug, reservation_id):

    if request.method in ['POST', 'DELETE']:

        course = get_course_if_user_can_view_or_404(course_slug, request)

        is_enrolled = course.students.filter(id=request.user.id).exists()

        if not is_enrolled:
            messages.error(request, _('You are not enrolled in this course'))
            return HttpResponseRedirect(
                reverse('course_overview', args=[course_slug]))

        reserv_remove = Reservation.objects.get(
            Q(id=reservation_id) & Q(user__id=request.user.id))
        if reserv_remove is None:
            messages.error(request,
                           _('You are not the owner of this reservation'))
            return HttpResponseRedirect(
                reverse('course_reservations', args=[course.slug]))

        cancel_limit = datetime.utcnow().replace(tzinfo=pytz.utc)
        cancel_limit += timedelta(
            0, reserv_remove.asset.cancelation_in_advance * 60)

        if reserv_remove.reservation_begins < cancel_limit:
            messages.error(
                request,
                _('Not enough time in advance to cancel this reservation.'))
            return HttpResponseRedirect(
                reverse('course_reservations', args=[course.slug]))

        reserv_remove.delete()

        return HttpResponseRedirect(
            reverse('course_reservations', args=[course.slug]))

    else:
        return HttpResponseNotAllowed(['POST', 'DELETE'])
예제 #26
0
파일: views.py 프로젝트: fid-jose/moocng
def course_overview(request, course_slug):

    """
    Show the course main page. This will show the main information about the
    course and the 'register to this course' button.

    .. note:: **use_old_calculus** is a compatibility method with old evaluation
              methods, which allowed the normal units to be evaluated. The new
              system does not evaluate normal units, only tasks and exams.

    :context: course, units, is_enrolled, is_teacher, request, course_teachers,
              announcements, use_old_calculus

    .. versionadded:: 0.1
    """
    course = get_course_if_user_can_view_or_404(course_slug, request)

    if request.user.is_authenticated():
        is_enrolled = course.students.filter(id=request.user.id).exists()
        is_teacher = is_teacher_test(request.user, course)
    else:
        is_enrolled = False
        is_teacher = False

    course_teachers = CourseTeacher.objects.filter(course=course)
    announcements = Announcement.objects.filter(course=course).order_by('datetime').reverse()[:5]
    units = get_units_available_for_user(course, request.user, True)

    return render_to_response('courses/overview.html', {
        'course': course,
        'units': units,
        'is_enrolled': is_enrolled,
        'is_teacher': is_teacher,
        'request': request,
        'course_teachers': course_teachers,
        'announcements': announcements,
        'use_old_calculus': settings.COURSES_USING_OLD_TRANSCRIPT,
    }, context_instance=RequestContext(request))
예제 #27
0
파일: views.py 프로젝트: MCHacker/moocng
def course_review_assign(request, course_slug, assignment_id):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    assignment = get_object_or_404(PeerReviewAssignment, id=assignment_id)
    user_id = request.user.id

    is_enrolled = course.students.filter(id=user_id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(reverse('course_overview', args=[course_slug]))

    if assignment.kq.unit.course != course:
        messages.error(request, _('The selected peer review assignment is not part of this course.'))
        return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))

    collection = get_db().get_collection('peer_review_submissions')

    submission = collection.find({
        'kq': assignment.kq.id,
        'assigned_to': user_id
    })
    if submission.count() > 0:
        messages.error(request, _('You already have a submission assigned.'))
        return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))

    max_hours_assigned = timedelta(hours=getattr(settings,
                                   "PEER_REVIEW_ASSIGNATION_EXPIRE", 24))

    assignation_expire = datetime.utcnow() - max_hours_assigned

    submission = collection.find({
        'kq': assignment.kq.id,
        '$or': [
            {
                'assigned_to': {
                    '$exists': False
                },
            },
            {
                'assigned_when': {
                    '$lt': assignation_expire
                },
            }
        ],
        'author': {
            '$ne': user_id
        },
        'reviewers': {
            '$ne': user_id
        }
    }).sort([
        ('reviews', pymongo.ASCENDING),
        ('author_reviews', pymongo.DESCENDING),
    ]).limit(1)

    if submission.count() == 0:
        messages.error(request, _('There is no submission avaliable for you at this moment. Please, try again later.'))
        return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))
    else:
        collection.update({
            '_id': submission[0]['_id']
        }, {
            '$set': {
                'assigned_to': user_id,
                'assigned_when': datetime.utcnow()
            }
        })
        return HttpResponseRedirect(reverse('course_review_review', args=[course_slug, assignment_id]))
예제 #28
0
파일: views.py 프로젝트: ntwuxc/moocng
def course_review_review(request, course_slug, assignment_id):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    assignment = get_object_or_404(PeerReviewAssignment, id=assignment_id)
    user_id = request.user.id

    is_enrolled = course.students.filter(id=user_id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(
            reverse('course_overview', args=[course_slug]))

    if assignment.kq.unit.course != course:
        messages.error(
            request,
            _('The selected peer review assignment is not part of this course.'
              ))
        return HttpResponseRedirect(
            reverse('course_reviews', args=[course_slug]))

    collection = get_db().get_collection('peer_review_submissions')

    submission = collection.find({
        'kq': assignment.kq.id,
        'assigned_to': user_id
    })

    if submission.count() == 0:
        messages.error(request, _('You don\'t have this submission assigned.'))
        return HttpResponseRedirect(
            reverse('course_reviews', args=[course_slug]))

    submission_obj = submission[0]

    submitter = User.objects.get(id=int(submission_obj['author']))

    criteria_initial = [{
        'evaluation_criterion_id': criterion.id
    } for criterion in assignment.criteria.all()]
    EvalutionCriteriaResponseFormSet = formset_factory(
        EvalutionCriteriaResponseForm, extra=0, max_num=len(criteria_initial))

    if request.method == "POST":
        submission_form = ReviewSubmissionForm(request.POST)
        criteria_formset = EvalutionCriteriaResponseFormSet(
            request.POST, initial=criteria_initial)
        if criteria_formset.is_valid() and submission_form.is_valid():
            criteria_values = [
                (int(form.cleaned_data['evaluation_criterion_id']),
                 int(form.cleaned_data['value'])) for form in criteria_formset
            ]
            try:
                review = save_review(assignment.kq, request.user, submitter,
                                     criteria_values,
                                     submission_form.cleaned_data['comments'])

                reviews = get_db().get_collection('peer_review_reviews')
                reviewed_count = reviews.find({
                    'reviewer': user_id,
                    'kq': assignment.kq.id
                }).count()
                on_peerreviewreview_created_task.apply_async(
                    args=[review, reviewed_count],
                    queue='stats',
                )

                current_site_name = get_current_site(request).name
                send_mail_to_submission_owner(current_site_name, assignment,
                                              review, submitter)
            except IntegrityError:
                messages.error(
                    request,
                    _('Your can\'t submit two times the same review.'))
                return HttpResponseRedirect(
                    reverse('course_reviews', args=[course_slug]))

            pending = assignment.minimum_reviewers - reviewed_count
            if pending > 0:
                messages.success(
                    request,
                    _('Your review has been submitted. You have to review at least %d exercises more.'
                      ) % pending)
            else:
                messages.success(request, _('Your review has been submitted.'))
            return HttpResponseRedirect(
                reverse('course_reviews', args=[course_slug]))
    else:
        submission_form = ReviewSubmissionForm()
        criteria_formset = EvalutionCriteriaResponseFormSet(
            initial=criteria_initial)

    max_hours_assigned = timedelta(
        hours=getattr(settings, "PEER_REVIEW_ASSIGNATION_EXPIRE", 24))

    assigned_when = submission[0]["assigned_when"]
    assignation_expire = assigned_when + max_hours_assigned

    now = datetime.now(assigned_when.tzinfo)
    is_assignation_expired = now > assignation_expire

    return render_to_response('peerreview/review_review.html', {
        'submission': submission[0],
        'is_assignation_expired': is_assignation_expired,
        'assignation_expire': assignation_expire,
        'submission_form': submission_form,
        'criteria_formset': criteria_formset,
        'course': course,
        'assignment': assignment,
        'is_enrolled': is_enrolled,
    },
                              context_instance=RequestContext(request))
예제 #29
0
def course_review_review(request, course_slug, assignment_id):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    assignment = get_object_or_404(PeerReviewAssignment, id=assignment_id)
    user_id = request.user.id

    is_enrolled = course.students.filter(id=user_id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(reverse('course_overview', args=[course_slug]))

    if assignment.kq.unit.course != course:
        messages.error(request, _('The selected peer review assignment is not part of this course.'))
        return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))

    collection = get_db().get_collection('peer_review_submissions')

    submission = collection.find({
        'kq': assignment.kq.id,
        'assigned_to': user_id
    })

    if submission.count() == 0:
        messages.error(request, _('You don\'t have this submission assigned.'))
        return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))

    submission_obj = submission[0]

    submitter = User.objects.get(id=int(submission_obj['author']))

    criteria_initial = [{'evaluation_criterion_id': criterion.id} for criterion in assignment.criteria.all()]
    EvalutionCriteriaResponseFormSet = formset_factory(EvalutionCriteriaResponseForm, extra=0, max_num=len(criteria_initial))

    if request.method == "POST":
        submission_form = ReviewSubmissionForm(request.POST)
        criteria_formset = EvalutionCriteriaResponseFormSet(request.POST, initial=criteria_initial)
        if criteria_formset.is_valid() and submission_form.is_valid():
            criteria_values = [(int(form.cleaned_data['evaluation_criterion_id']), int(form.cleaned_data['value'])) for form in criteria_formset]
            try:
                review = save_review(assignment.kq, request.user, submitter, criteria_values, submission_form.cleaned_data['comments'])

                reviews = get_db().get_collection('peer_review_reviews')
                reviewed_count = reviews.find({
                    'reviewer': user_id,
                    'kq': assignment.kq.id
                }).count()

                review_scores = [int(form.cleaned_data['value']) for form in criteria_formset]
                if len(review_scores) > 0:
                    score = float(sum(review_scores) / len(review_scores)) * 2 / 10
                else:
                    score = 1
                extra = {
                    'geolocation': {
                        'lat': float(request.POST.get("context_geo_lat", "0.0")),
                        'lon': float(request.POST.get("context_geo_lon", "0.0")),
                    },
                    'url': request.build_absolute_uri(),
                    'result': {
                        'score': score,
                        'comment': submission_form.cleaned_data['comments']
                    }
                }
                on_peerreviewreview_created_task.apply_async(
                    args=[review, reviewed_count, extra],
                    queue='stats',
                )

                current_site_name = get_current_site(request).name
                send_mail_to_submission_owner(current_site_name, assignment, review, submitter)
            except IntegrityError:
                messages.error(request, _('Your can\'t submit two times the same review.'))
                return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))

            pending = assignment.minimum_reviewers - reviewed_count
            if pending > 0:
                messages.success(request, _('Your review has been submitted. You have to review at least %d exercises more.') % pending)
            else:
                messages.success(request, _('Your review has been submitted.'))
            return HttpResponseRedirect(reverse('course_reviews', args=[course_slug]))
    else:
        submission_form = ReviewSubmissionForm()
        criteria_formset = EvalutionCriteriaResponseFormSet(initial=criteria_initial)

    max_hours_assigned = timedelta(hours=getattr(settings,
                                   "PEER_REVIEW_ASSIGNATION_EXPIRE", 24))

    assigned_when = submission[0]["assigned_when"]
    assignation_expire = assigned_when + max_hours_assigned

    now = datetime.now(assigned_when.tzinfo)
    is_assignation_expired = now > assignation_expire

    return render_to_response('peerreview/review_review.html', {
        'submission': submission[0],
        'is_assignation_expired': is_assignation_expired,
        'assignation_expire': assignation_expire,
        'submission_form': submission_form,
        'criteria_formset': criteria_formset,
        'course': course,
        'assignment': assignment,
        'is_enrolled': is_enrolled,
    }, context_instance=RequestContext(request))
예제 #30
0
파일: views.py 프로젝트: ntwuxc/moocng
def course_review_assign(request, course_slug, assignment_id):
    course = get_course_if_user_can_view_or_404(course_slug, request)
    assignment = get_object_or_404(PeerReviewAssignment, id=assignment_id)
    user_id = request.user.id

    is_enrolled = course.students.filter(id=user_id).exists()
    if not is_enrolled:
        messages.error(request, _('You are not enrolled in this course'))
        return HttpResponseRedirect(
            reverse('course_overview', args=[course_slug]))

    if assignment.kq.unit.course != course:
        messages.error(
            request,
            _('The selected peer review assignment is not part of this course.'
              ))
        return HttpResponseRedirect(
            reverse('course_reviews', args=[course_slug]))

    collection = get_db().get_collection('peer_review_submissions')

    submission = collection.find({
        'kq': assignment.kq.id,
        'assigned_to': user_id
    })
    if submission.count() > 0:
        messages.error(request, _('You already have a submission assigned.'))
        return HttpResponseRedirect(
            reverse('course_reviews', args=[course_slug]))

    max_hours_assigned = timedelta(
        hours=getattr(settings, "PEER_REVIEW_ASSIGNATION_EXPIRE", 24))

    assignation_expire = datetime.utcnow() - max_hours_assigned

    submission = collection.find({
        'kq':
        assignment.kq.id,
        '$or': [{
            'assigned_to': {
                '$exists': False
            },
        }, {
            'assigned_when': {
                '$lt': assignation_expire
            },
        }],
        'author': {
            '$ne': user_id
        },
        'reviewers': {
            '$ne': user_id
        }
    }).sort([
        ('reviews', pymongo.ASCENDING),
        ('author_reviews', pymongo.DESCENDING),
    ]).limit(1)

    if submission.count() == 0:
        messages.error(
            request,
            _('There is no submission avaliable for you at this moment. Please, try again later.'
              ))
        return HttpResponseRedirect(
            reverse('course_reviews', args=[course_slug]))
    else:
        collection.update({'_id': submission[0]['_id']}, {
            '$set': {
                'assigned_to': user_id,
                'assigned_when': datetime.utcnow()
            }
        })
        return HttpResponseRedirect(
            reverse('course_review_review', args=[course_slug, assignment_id]))