Files
edx-platform/lms/djangoapps/instructor/paidcourse_enrollment_report.py
2017-06-11 21:48:06 -04:00

195 lines
8.9 KiB
Python

"""
Defines concrete class for cybersource Enrollment Report.
"""
import collections
from django.conf import settings
from django.utils.translation import ugettext as _
from courseware.access import has_access
from courseware.courses import get_course_by_id
from lms.djangoapps.instructor.enrollment_report import BaseAbstractEnrollmentReportProvider
from openedx.core.djangoapps.site_configuration import helpers as configuration_helpers
from shoppingcart.models import (
CouponRedemption,
InvoiceTransaction,
OrderItem,
PaidCourseRegistration,
RegistrationCodeRedemption
)
from student.models import CourseEnrollment, ManualEnrollmentAudit
class PaidCourseEnrollmentReportProvider(BaseAbstractEnrollmentReportProvider):
"""
The concrete class for all CyberSource Enrollment Reports.
"""
def get_enrollment_info(self, user, course_id):
"""
Returns the User Enrollment information.
"""
course = get_course_by_id(course_id, depth=0)
is_course_staff = bool(has_access(user, 'staff', course))
manual_enrollment_reason = 'N/A'
# check the user enrollment role
if user.is_staff:
platform_name = configuration_helpers.get_value('platform_name', settings.PLATFORM_NAME)
enrollment_role = _('{platform_name} Staff').format(platform_name=platform_name)
elif is_course_staff:
enrollment_role = _('Course Staff')
else:
enrollment_role = _('Student')
course_enrollment = CourseEnrollment.get_enrollment(user=user, course_key=course_id)
if is_course_staff:
enrollment_source = _('Staff')
else:
# get the registration_code_redemption object if exists
registration_code_redemption = RegistrationCodeRedemption.registration_code_used_for_enrollment(
course_enrollment)
# get the paid_course registration item if exists
paid_course_reg_item = PaidCourseRegistration.get_course_item_for_user_enrollment(
user=user,
course_id=course_id,
course_enrollment=course_enrollment
)
# from where the user get here
if registration_code_redemption is not None:
enrollment_source = _('Used Registration Code')
elif paid_course_reg_item is not None:
enrollment_source = _('Credit Card - Individual')
else:
manual_enrollment = ManualEnrollmentAudit.get_manual_enrollment(course_enrollment)
if manual_enrollment is not None:
enrollment_source = _(
'manually enrolled by username: {username}'
).format(username=manual_enrollment.enrolled_by.username)
manual_enrollment_reason = manual_enrollment.reason
else:
enrollment_source = _('Manually Enrolled')
enrollment_date = course_enrollment.created.strftime("%B %d, %Y")
currently_enrolled = course_enrollment.is_active
course_enrollment_data = collections.OrderedDict()
course_enrollment_data['Enrollment Date'] = enrollment_date
course_enrollment_data['Currently Enrolled'] = currently_enrolled
course_enrollment_data['Enrollment Source'] = enrollment_source
course_enrollment_data['Manual (Un)Enrollment Reason'] = manual_enrollment_reason
course_enrollment_data['Enrollment Role'] = enrollment_role
return course_enrollment_data
def get_payment_info(self, user, course_id):
"""
Returns the User Payment information.
"""
course_enrollment = CourseEnrollment.get_enrollment(user=user, course_key=course_id)
paid_course_reg_item = PaidCourseRegistration.get_course_item_for_user_enrollment(
user=user,
course_id=course_id,
course_enrollment=course_enrollment
)
payment_data = collections.OrderedDict()
# check if the user made a single self purchase scenario
# for enrollment in the course.
if paid_course_reg_item is not None:
coupon_redemption = CouponRedemption.objects.select_related('coupon').filter(
order_id=paid_course_reg_item.order_id)
coupon_codes = [redemption.coupon.code for redemption in coupon_redemption]
coupon_codes = ", ".join(coupon_codes)
registration_code_used = 'N/A'
list_price = paid_course_reg_item.get_list_price()
payment_amount = paid_course_reg_item.unit_cost
coupon_codes_used = coupon_codes
payment_status = paid_course_reg_item.status
transaction_reference_number = paid_course_reg_item.order_id
else:
# check if the user used a registration code for the enrollment.
registration_code_redemption = RegistrationCodeRedemption.registration_code_used_for_enrollment(
course_enrollment)
if registration_code_redemption is not None:
registration_code = registration_code_redemption.registration_code
registration_code_used = registration_code.code
if registration_code.invoice_item_id:
list_price, payment_amount, payment_status, transaction_reference_number =\
self._get_invoice_data(registration_code_redemption)
coupon_codes_used = 'N/A'
elif registration_code_redemption.registration_code.order_id:
list_price, payment_amount, coupon_codes_used, payment_status, transaction_reference_number = \
self._get_order_data(registration_code_redemption, course_id)
else:
# this happens when the registration code is not created via invoice or bulk purchase
# scenario.
list_price = 'N/A'
payment_amount = 'N/A'
coupon_codes_used = 'N/A'
registration_code_used = 'N/A'
payment_status = _('Data Integrity Error')
transaction_reference_number = 'N/A'
else:
list_price = 'N/A'
payment_amount = 'N/A'
coupon_codes_used = 'N/A'
registration_code_used = 'N/A'
payment_status = _('TBD')
transaction_reference_number = 'N/A'
payment_data['List Price'] = list_price
payment_data['Payment Amount'] = payment_amount
payment_data['Coupon Codes Used'] = coupon_codes_used
payment_data['Registration Code Used'] = registration_code_used
payment_data['Payment Status'] = payment_status
payment_data['Transaction Reference Number'] = transaction_reference_number
return payment_data
def _get_order_data(self, registration_code_redemption, course_id):
"""
Returns the order data
"""
order_item = OrderItem.objects.get(order=registration_code_redemption.registration_code.order,
courseregcodeitem__course_id=course_id)
coupon_redemption = CouponRedemption.objects.select_related('coupon').filter(
order_id=registration_code_redemption.registration_code.order)
coupon_codes = [redemption.coupon.code for redemption in coupon_redemption]
coupon_codes = ", ".join(coupon_codes)
list_price = order_item.get_list_price()
payment_amount = order_item.unit_cost
coupon_codes_used = coupon_codes
payment_status = order_item.status
transaction_reference_number = order_item.order_id
return list_price, payment_amount, coupon_codes_used, payment_status, transaction_reference_number
def _get_invoice_data(self, registration_code_redemption):
"""
Returns the Invoice data
"""
registration_code = registration_code_redemption.registration_code
list_price = registration_code.invoice_item.unit_price
total_amount = registration_code_redemption.registration_code.invoice.total_amount
qty = registration_code_redemption.registration_code.invoice_item.qty
payment_amount = total_amount / qty
invoice_transaction = InvoiceTransaction.get_invoice_transaction(
invoice_id=registration_code_redemption.registration_code.invoice.id)
if invoice_transaction is not None:
# amount greater than 0 is invoice has bee paid
if invoice_transaction.amount > 0:
payment_status = 'Invoice Paid'
else:
# amount less than 0 is invoice has been refunded
payment_status = 'Refunded'
else:
payment_status = 'Invoice Outstanding'
transaction_reference_number = registration_code_redemption.registration_code.invoice_id
return list_price, payment_amount, payment_status, transaction_reference_number