class UpdateEffectiveContractDiscountTests(TestCase): """ Tests the enrollment code creation command. """ def setUp(self): """ Create test data. """ super(UpdateEffectiveContractDiscountTests, self).setUp() # Set up orders with a enterprise_customer self.enterprise_customer_uuid = '123e4567-e89b-12d3-a456-426655440000' self.unit_price = 100 self.condition = ManualEnrollmentOrderDiscountConditionFactory( enterprise_customer_uuid=self.enterprise_customer_uuid ) self.offer = ConditionalOfferFactory(condition=self.condition, id=9999) self.order = OrderFactory() self.order_discount = OrderDiscountFactory(offer_id=self.offer.id, order=self.order) self.line = OrderLineFactory(order=self.order, unit_price_excl_tax=self.unit_price) self.line.save() self.order_discount = OrderDiscountFactory(offer_id=self.offer.id, order=self.order) self.order.save() self.offer.save() self.condition.save() def test_discount_update(self): discount_percentage = 20 call_command( 'update_effective_contract_discount', '--enterprise-customer={}'.format(self.enterprise_customer_uuid), '--discount-percentage={}'.format(discount_percentage) ) assert self.line.order == self.order
def test_convert_course(self, initial_cert_type, direction, new_cert_type): """Verify that an honor course can be converted to audit correctly.""" course = CourseFactory(partner=self.partner) seat_to_convert = course.create_or_update_seat(initial_cert_type, False, 0) stock_record = StockRecord.objects.get(product=seat_to_convert) order_line = OrderLineFactory(stockrecord=stock_record, product=seat_to_convert, partner_sku='test_sku') old_stock_record_sku = stock_record.partner_sku old_order_line_sku = order_line.partner_sku # Mock the LMS call with mock.patch.object(LMSPublisher, 'publish') as mock_publish: mock_publish.return_value = True call_command('convert_course', course.id, commit=True, direction=direction, partner=self.partner.code) # Calling refresh_from_db doesn't seem to update the product's attributes seat_to_convert = Product.objects.get(pk=seat_to_convert.pk) stock_record.refresh_from_db() order_line.refresh_from_db() self.assertEqual(getattr(seat_to_convert.attr, 'certificate_type', ''), new_cert_type) if new_cert_type == '': self.assertNotIn('with honor certificate', seat_to_convert.title) else: self.assertIn(' with honor certificate', seat_to_convert.title) # Verify that partner SKUs are correctly updated self.assertNotEqual(old_stock_record_sku, stock_record.partner_sku) self.assertNotEqual(old_order_line_sku, order_line.partner_sku) self.assertEqual(order_line.partner_sku, stock_record.partner_sku) self.assertTrue(mock_publish.called)
def use_voucher(self, order_num, voucher, user, add_entitlement=False, product=None): """ Mark voucher as used by provided users Args: order_num (string): Order number voucher (Voucher): voucher to be marked as used users (list): list of users """ order = OrderFactory(number=order_num) if add_entitlement: order_line = OrderLineFactory(product=self.entitlement, partner_sku=self.partner_sku) order.lines.add(order_line) product = product if product else self.verified_seat order_line = OrderLineFactory(product=product, partner_sku=self.partner_sku) order.lines.add(order_line) voucher.record_usage(order, user) voucher.offers.first().record_usage(discount={ 'freq': 1, 'discount': 1 })
def test_generate_coupon_report_for_query_coupon_with_multi_line_order( self): """ Test that coupon report for a query coupon that was used on multi-line order contains ids from all courses in that order. """ course1 = CourseFactory() course2 = CourseFactory() order = OrderFactory(number='TESTORDER') order.lines.add( OrderLineFactory(product=course1.create_or_update_seat( 'verified', False, 101), partner_sku=self.partner_sku)) order.lines.add( OrderLineFactory(product=course2.create_or_update_seat( 'verified', False, 110), partner_sku=self.partner_sku)) query_coupon = self.create_catalog_coupon(catalog_query='*:*') voucher = query_coupon.attr.coupon_vouchers.vouchers.first() voucher.record_usage(order, self.user) field_names, rows = generate_coupon_report( [query_coupon.attr.coupon_vouchers]) expected_redemed_course_ids = '{}, {}'.format(course1.id, course2.id) self.assertEqual(rows[-1]['Redeemed For Course IDs'], expected_redemed_course_ids) self.assertEqual(rows[-1].get('Redeemed For Course ID'), None) self.assertIn('Redeemed For Course ID', field_names) self.assertIn('Redeemed For Course IDs', field_names)
def test_shipping_status(self): order = OrderFactory() line_1 = OrderLineFactory(order=order, partner_sku='SKU1234', quantity=2) line_2 = OrderLineFactory(order=order, partner_sku='SKU5678', quantity=1) self.assertEqual(order.shipping_status, '') event_1 = ShippingEventFactory(order=order, event_type__name='Shipped') event_2 = ShippingEventFactory(order=order, event_type__name='Returned') # Default status self.assertEqual(order.shipping_status, _('In progress')) # Set first line to shipped event_1.line_quantities.create(line=line_1, quantity=2) self.assertEqual(order.shipping_status, _('In progress')) # Set first line to returned event_2.line_quantities.create(line=line_1, quantity=2) self.assertEqual(order.shipping_status, _('In progress')) # Set second line to shipped event_1.line_quantities.create(line=line_2, quantity=1) self.assertEqual(order.shipping_status, _('Shipped')) # Set second line to returned event_2.line_quantities.create(line=line_2, quantity=1) self.assertEqual(order.shipping_status, _('Returned'))
def setUp(self): # Timestamp in the middle of the time window time_delta = (DEFAULT_START_DELTA_TIME + DEFAULT_END_DELTA_TIME) / 2 self.timestamp = datetime.datetime.now(pytz.utc) - datetime.timedelta(minutes=time_delta) self.payevent, __ = PaymentEventType.objects.get_or_create(name=PaymentEventTypeName.PAID) self.refundevent, __ = PaymentEventType.objects.get_or_create(name=PaymentEventTypeName.REFUNDED) self.seat_product_class, __ = ProductClass.objects.get_or_create(name=SEAT_PRODUCT_CLASS_NAME) self.order = OrderFactory(total_incl_tax=90, date_placed=self.timestamp) self.product = ProductFactory(product_class=self.seat_product_class, categories=None) self.line = OrderLineFactory(order=self.order, product=self.product, partner_sku='test_sku') self.line.save() self.product.save() self.order.save()
def test_threshold(self): """Test verify_transactions only fails if there are too many anomolies""" for i in range(3): # Create some "good" orders w/ payments order = OrderFactory(total_incl_tax=50 + i, date_placed=self.timestamp) line = OrderLineFactory(order=order, product=self.product, partner_sku='test_sku') payment = PaymentEventFactory(order=order, amount=50 + i, event_type_id=self.payevent.id, date_created=self.timestamp) payment.save() line.save() order.save() # self.order fixture should still have no payment with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders are without payments", exception) self.assertIn(str(self.order.id), exception) try: call_command('verify_transactions', '--threshold=1') # allow 1 anomoly except CommandError as e: self.fail( "Failed to verify transactions when no failure was expected. {}" .format(e)) try: call_command( 'verify_transactions', '--threshold=0.25') # 1-in-4 should be just on the line except CommandError as e: self.fail( "Failed to verify transactions when no failure was expected. {}" .format(e)) with self.assertRaises(CommandError) as cm: call_command('verify_transactions', '--threshold=0.2') exception = six.text_type(cm.exception) self.assertIn("The following orders are without payments", exception) self.assertIn(str(self.order.id), exception)
def test_successful_response(self): """ Verify a successful response is returned. """ voucher = VoucherFactory(code='ENROLLMENT') order = OrderFactory(user=self.user) line = OrderLineFactory(order=order) order_line_vouchers = OrderLineVouchers.objects.create(line=line) order_line_vouchers.vouchers.add(voucher) response = self.client.get(reverse(self.path, args=[order.number])) self.assertEqual(response.status_code, 200) self.assertEqual(response['content-type'], 'text/csv')
def test_omitting_already_bought_credit_seat(self): """ Verify a seat that the user bought is omitted from offer page results. """ products, request, voucher = self.prepare_get_offers_response(quantity=2, seat_type='credit') self.mock_eligibility_api(request, self.user, 'a/b/c', eligible=True) offers = VoucherViewSet().get_offers(request=request, voucher=voucher)['results'] self.assertEqual(len(offers), 2) order = OrderFactory(user=self.user) order.lines.add(OrderLineFactory(product=products[0])) offers = VoucherViewSet().get_offers(request=request, voucher=voucher)['results'] self.assertEqual(len(offers), 1)
def setUp(self): """ Create test data. """ super(UpdateEffectiveContractDiscountTests, self).setUp() # Set up orders with a enterprise_customer self.enterprise_customer_uuid = '123e4567-e89b-12d3-a456-426655440000' self.unit_price = 100 self.condition = ManualEnrollmentOrderDiscountConditionFactory( enterprise_customer_uuid=self.enterprise_customer_uuid ) self.offer = ConditionalOfferFactory(condition=self.condition, id=9999) self.order = OrderFactory() self.order_discount = OrderDiscountFactory(offer_id=self.offer.id, order=self.order) self.line = OrderLineFactory(order=self.order, unit_price_excl_tax=self.unit_price) self.line.save() self.order_discount = OrderDiscountFactory(offer_id=self.offer.id, order=self.order) self.order.save() self.offer.save() self.condition.save()
def test_successful_response(self, product_title): """ Verify a successful response is returned. """ voucher = VoucherFactory() order = OrderFactory(user=self.user) product = ProductFactory(title=product_title, categories=[]) line = OrderLineFactory(order=order, product=product) order_line_vouchers = OrderLineVouchers.objects.create(line=line) order_line_vouchers.vouchers.add(voucher) response = self.client.get(reverse(self.path, args=[order.number])) self.assertEqual(response.status_code, 200) self.assertEqual(response['content-type'], 'text/csv')
def use_voucher(self, voucher, user): """ Mark voucher as used by provided user """ partner = PartnerFactory(short_code='testX') course = CourseFactory(id='course-v1:test-org+course+run', partner=partner) verified_seat = course.create_or_update_seat('verified', False, 100) order = OrderFactory() order_line = OrderLineFactory(product=verified_seat, partner_sku='test_sku') order.lines.add(order_line) voucher.record_usage(order, user) voucher.offers.first().record_usage(discount={'freq': 1, 'discount': 1})
def test_convert_course(self, initial_cert_type, direction, new_cert_type): """Verify that an honor course can be converted to audit correctly.""" course = CourseFactory() seat_to_convert = course.create_or_update_seat(initial_cert_type, False, 0, self.partner) stock_record = StockRecord.objects.get(product=seat_to_convert) order_line = OrderLineFactory(stockrecord=stock_record, product=seat_to_convert) old_stock_record_sku = stock_record.partner_sku old_order_line_sku = order_line.partner_sku # Mock the LMS call with mock.patch.object(LMSPublisher, 'publish') as mock_publish: mock_publish.return_value = True call_command( 'convert_course', course.id, access_token=ACCESS_TOKEN, commit=True, direction=direction, partner=self.partner.code ) # Calling refresh_from_db doesn't seem to update the product's attributes seat_to_convert = Product.objects.get(pk=seat_to_convert.pk) stock_record.refresh_from_db() order_line.refresh_from_db() self.assertEqual(getattr(seat_to_convert.attr, 'certificate_type', ''), new_cert_type) if new_cert_type == '': self.assertNotIn('with honor certificate', seat_to_convert.title) else: self.assertIn(' with honor certificate', seat_to_convert.title) # Verify that partner SKUs are correctly updated self.assertNotEqual(old_stock_record_sku, stock_record.partner_sku) self.assertNotEqual(old_order_line_sku, order_line.partner_sku) self.assertEqual(order_line.partner_sku, stock_record.partner_sku) self.assertTrue(mock_publish.called)
class VerifyTransactionsTest(TestCase): def setUp(self): # Timestamp in the middle of the time window time_delta = (DEFAULT_START_DELTA_TIME + DEFAULT_END_DELTA_TIME) / 2 self.timestamp = datetime.datetime.now( pytz.utc) - datetime.timedelta(minutes=time_delta) self.payevent, __ = PaymentEventType.objects.get_or_create( name=PaymentEventTypeName.PAID) self.refundevent, __ = PaymentEventType.objects.get_or_create( name=PaymentEventTypeName.REFUNDED) self.seat_product_class, __ = ProductClass.objects.get_or_create( name=SEAT_PRODUCT_CLASS_NAME) self.order = OrderFactory(total_incl_tax=90, date_placed=self.timestamp) self.product = ProductFactory(product_class=self.seat_product_class, categories=None) self.line = OrderLineFactory(order=self.order, product=self.product, partner_sku='test_sku') self.line.save() self.product.save() self.order.save() def test_time_window(self): """Test verify_transactions only examines the correct time window""" with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders are without payments", exception) self.assertIn(str(self.order.id), exception) time_outside_window = DEFAULT_START_DELTA_TIME + DEFAULT_END_DELTA_TIME + 1 time_outside_window_datetime = datetime.datetime.now( pytz.utc) - datetime.timedelta(minutes=time_outside_window) self.order.date_placed = time_outside_window_datetime self.order.save() try: call_command('verify_transactions') except CommandError as e: self.fail( "Failed to verify transactions when no errors were expected. {}" .format(e)) def test_no_errors(self): """Test verify_transactions with order and payment of same amount.""" payment = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment.save() refund = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.refundevent.id, date_created=self.timestamp) refund.save() try: call_command('verify_transactions') except CommandError as e: self.fail( "Failed to verify transactions when no errors were expected. {}" .format(e)) def test_zero_dollar_order(self): """Verify zero dollar orders are not flagged as errors.""" total_incl_tax_before = self.order.total_incl_tax self.order.total_incl_tax = 0 self.order.save() try: call_command('verify_transactions') except CommandError as e: self.fail( "Failed to verify transactions when no errors were expected. {}" .format(e)) finally: self.order.total_incl_tax = total_incl_tax_before self.order.save() def test_no_payment_for_valid_product_order(self): """Verify errors are thrown when there are valid product orders without payments.""" with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders are without payments", exception) self.assertIn(str(self.order.id), exception) def test_no_payment_for_filtered_product_order(self): """Verify errors are not thrown when there are filtered product orders without payments.""" new_product_class, __ = ProductClass.objects.get_or_create( name="Test Product Class") self.product.product_class = new_product_class self.product.save() try: call_command('verify_transactions') except CommandError as e: self.fail( "Failed to verify transactions when no errors were expected. {}" .format(e)) finally: self.product.product_class = self.seat_product_class self.product.save() def test_two_same_payments_for_order(self): """ Verify that errors are thrown when their are multiple payments on an order.""" payment1 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment2 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment1.save() payment2.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders had multiple payments ", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(payment1.id), exception) self.assertIn(str(payment2.id), exception) def test_multiple_payments_for_order(self): """ Verify that errors are thrown when their are multiple payments on an order.""" payment1 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment2 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment3 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment1.save() payment2.save() payment3.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders had multiple payments ", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(payment1.id), exception) self.assertIn(str(payment2.id), exception) self.assertIn(str(payment3.id), exception) def test_totals_mismatch(self): """ Verify errors thrown when payment and order totals don't match.""" payment = PaymentEventFactory(order=self.order, amount=100, event_type_id=self.payevent.id, date_created=self.timestamp) payment.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("Order totals mismatch with payments received", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(payment.id), exception) self.assertIn("Amount: 90.00", exception) self.assertIn("Amount: 100.00", exception) self.assertIn("Amount: 100.00", exception) def test_refund_exceeded(self): """Test verify_transactions with refund which exceed amount paid.""" payment = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment.save() refund = PaymentEventFactory(order=self.order, amount=100, event_type_id=self.refundevent.id, date_created=self.timestamp) refund.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders had excessive refunds", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(refund.id), exception) self.assertIn("Amount: 90.00", exception) self.assertIn("Amount: 100.00", exception)
class VerifyTransactionsTest(TestCase): def setUp(self): # Timestamp in the middle of the time window time_delta = (DEFAULT_START_DELTA_TIME + DEFAULT_END_DELTA_TIME) / 2 self.timestamp = datetime.datetime.now(pytz.utc) - datetime.timedelta(minutes=time_delta) self.payevent, __ = PaymentEventType.objects.get_or_create(name=PaymentEventTypeName.PAID) self.refundevent, __ = PaymentEventType.objects.get_or_create(name=PaymentEventTypeName.REFUNDED) self.seat_product_class, __ = ProductClass.objects.get_or_create(name=SEAT_PRODUCT_CLASS_NAME) self.order = OrderFactory(total_incl_tax=90, date_placed=self.timestamp) self.product = ProductFactory(product_class=self.seat_product_class, categories=None) self.line = OrderLineFactory(order=self.order, product=self.product, partner_sku='test_sku') self.line.save() self.product.save() self.order.save() def test_time_window(self): """ Test verify_transactions only examines the correct time window """ with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders are without payments", exception) self.assertIn(str(self.order.id), exception) time_outside_window = DEFAULT_START_DELTA_TIME + DEFAULT_END_DELTA_TIME + 1 time_outside_window_datetime = datetime.datetime.now(pytz.utc) - datetime.timedelta(minutes=time_outside_window) self.order.date_placed = time_outside_window_datetime self.order.save() try: call_command('verify_transactions') except CommandError as e: self.fail("Failed to verify transactions when no errors were expected. {}".format(e)) def test_threshold(self): """ Test verify_transactions only fails if there are too many anomolies """ for i in range(3): # Create some "good" orders w/ payments order = OrderFactory(total_incl_tax=50 + i, date_placed=self.timestamp) line = OrderLineFactory(order=order, product=self.product, partner_sku='test_sku') payment = PaymentEventFactory( order=order, amount=50 + i, event_type_id=self.payevent.id, date_created=self.timestamp ) payment.save() line.save() order.save() # self.order fixture should still have no payment with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders are without payments", exception) self.assertIn(str(self.order.id), exception) try: call_command('verify_transactions', '--threshold=1') # allow 1 anomoly except CommandError as e: self.fail("Failed to verify transactions when no failure was expected. {}".format(e)) try: call_command('verify_transactions', '--threshold=0.25') # 1-in-4 should be just on the line except CommandError as e: self.fail("Failed to verify transactions when no failure was expected. {}".format(e)) with self.assertRaises(CommandError) as cm: call_command('verify_transactions', '--threshold=0.2') exception = six.text_type(cm.exception) self.assertIn("The following orders are without payments", exception) self.assertIn(str(self.order.id), exception) def test_no_errors(self): """ Test verify_transactions with order and payment of same amount """ payment = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment.save() refund = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.refundevent.id, date_created=self.timestamp) refund.save() try: call_command('verify_transactions') except CommandError as e: self.fail("Failed to verify transactions when no errors were expected. {}".format(e)) def test_zero_dollar_order(self): """ Verify zero dollar orders are not flagged as errors """ total_incl_tax_before = self.order.total_incl_tax self.order.total_incl_tax = 0 self.order.save() try: call_command('verify_transactions') except CommandError as e: self.fail("Failed to verify transactions when no errors were expected. {}".format(e)) finally: self.order.total_incl_tax = total_incl_tax_before self.order.save() def test_no_payment_for_valid_product_order(self): """ Verify errors are thrown when there are valid product orders without payments """ with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders are without payments", exception) self.assertIn(str(self.order.id), exception) def test_no_payment_for_filtered_product_order(self): """ Verify errors are not thrown when there are filtered product orders without payments """ new_product_class, __ = ProductClass.objects.get_or_create(name="Test Product Class") self.product.product_class = new_product_class self.product.save() try: call_command('verify_transactions') except CommandError as e: self.fail("Failed to verify transactions when no errors were expected. {}".format(e)) finally: self.product.product_class = self.seat_product_class self.product.save() def test_two_same_payments_for_order(self): """ Verify that errors are thrown when their are multiple payments on an order """ payment1 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment2 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment1.save() payment2.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders had multiple payments", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(payment1.id), exception) self.assertIn(str(payment2.id), exception) def test_multiple_payments_for_order(self): """ Verify that errors are thrown when their are multiple payments on an order """ payment1 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment2 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment3 = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment1.save() payment2.save() payment3.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders had multiple payments", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(payment1.id), exception) self.assertIn(str(payment2.id), exception) self.assertIn(str(payment3.id), exception) @ddt.data(80, 100) def test_totals_mismatch(self, amount): """ Verify errors thrown when payment and order totals don't match """ payment = PaymentEventFactory(order=self.order, amount=amount, event_type_id=self.payevent.id, date_created=self.timestamp) payment.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following order totals mismatch payments received", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(payment.id), exception) self.assertIn('"amount": 90.0', exception) self.assertIn('"amount": {}'.format(amount), exception) def test_totals_mismatch_support(self): """ Verify errors thrown when payment amount is greater than order amount and a refund is required from Support """ payment = PaymentEventFactory(order=self.order, amount=100, event_type_id=self.payevent.id, date_created=self.timestamp) payment.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions', '--support') exception = six.text_type(cm.exception) self.assertTrue(payment.amount != self.order.total_incl_tax) self.assertIn("There was a mismatch in the totals in the following order that require a refund", exception) self.assertIn("orders_mismatched_totals_support", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(payment.id), exception) self.assertIn('"order_amount": 90.0', exception) self.assertIn('"payment_amount": 100.0', exception) self.assertIn('"refund_amount": 10.0', exception) def test_refund_exceeded(self): """ Test verify_transactions with refund which exceed amount paid """ payment = PaymentEventFactory(order=self.order, amount=90, event_type_id=self.payevent.id, date_created=self.timestamp) payment.save() refund = PaymentEventFactory(order=self.order, amount=100, event_type_id=self.refundevent.id, date_created=self.timestamp) refund.save() with self.assertRaises(CommandError) as cm: call_command('verify_transactions') exception = six.text_type(cm.exception) self.assertIn("The following orders had excessive refunds", exception) self.assertIn(str(self.order.id), exception) self.assertIn(str(refund.id), exception) self.assertIn('"amount": 90.0', exception) self.assertIn('"amount": 100.0', exception)