def test_delete_payment(session, auth_mock, public_user_mock): """Assert that the payment records are soft deleted.""" payment_account = factory_payment_account() # payment = factory_payment() payment_account.save() # payment.save() invoice = factory_invoice(payment_account, total=10) invoice.save() invoice_reference = factory_invoice_reference(invoice.id).save() # Create a payment for this reference payment = factory_payment(invoice_number=invoice_reference.invoice_number, invoice_amount=10).save() fee_schedule = FeeSchedule.find_by_filing_type_and_corp_type('CP', 'OTANN') line = factory_payment_line_item( invoice.id, fee_schedule_id=fee_schedule.fee_schedule_id) line.save() transaction = factory_payment_transaction(payment.id) transaction.save() PaymentService.delete_invoice(invoice.id) invoice = Invoice.find_by_id(invoice.id) payment = Payment.find_by_id(payment.id) assert invoice.invoice_status_code == InvoiceStatus.DELETED.value assert payment.payment_status_code == PaymentStatus.DELETED.value
def test_create_duplicate_refund_for_paid_invoice(session, monkeypatch): """Assert that the create duplicate refund fails for paid invoices.""" payment_account = factory_payment_account() payment_account.save() i = factory_invoice(payment_account=payment_account) i.save() inv_ref = factory_invoice_reference(i.id) inv_ref.status_code = InvoiceReferenceStatus.COMPLETED.value inv_ref.save() payment = factory_payment(invoice_number=inv_ref.invoice_number).save() factory_payment_transaction(payment_id=payment.id, status_code=TransactionStatus.COMPLETED.value).save() i.invoice_status_code = InvoiceStatus.PAID.value i.save() factory_receipt(invoice_id=i.id).save() monkeypatch.setattr('pay_api.services.payment_transaction.publish_response', lambda *args, **kwargs: None) RefundService.create_refund(invoice_id=i.id, request={'reason': 'Test'}) i = InvoiceModel.find_by_id(i.id) payment: PaymentModel = PaymentModel.find_by_id(payment.id) assert i.invoice_status_code == InvoiceStatus.REFUND_REQUESTED.value assert payment.payment_status_code == PaymentStatus.REFUNDED.value with pytest.raises(Exception) as excinfo: RefundService.create_refund(invoice_id=i.id, request={'reason': 'Test'}) assert excinfo.type == BusinessException
def find_by_id(identifier: int): """Find payment by id.""" payment_dao = PaymentModel.find_by_id(identifier) payment = Payment() payment._dao = payment_dao # pylint: disable=protected-access current_app.logger.debug('>find_by_id') return payment
def test_patch_transaction_for_nsf_payment(session, monkeypatch): """Assert that the payment is saved to the table.""" # Create a FAILED payment (NSF), then clone the payment to create another one for CC payment # Create a transaction and assert it's success. # Patch transaction and check the status of records inv_number_1 = 'REG00001' payment_account = factory_payment_account( cfs_account_status=CfsAccountStatus.FREEZE.value, payment_method_code='PAD').save() invoice_1 = factory_invoice(payment_account, total=100) invoice_1.save() factory_payment_line_item(invoice_id=invoice_1.id, fee_schedule_id=1).save() factory_invoice_reference(invoice_1.id, invoice_number=inv_number_1).save() payment_1 = factory_payment(payment_status_code='FAILED', payment_account_id=payment_account.id, invoice_number=inv_number_1, invoice_amount=100, payment_method_code=PaymentMethod.PAD.value) payment_1.save() # Create payment for NSF payment. payment_2 = factory_payment(payment_status_code='CREATED', payment_account_id=payment_account.id, invoice_number=inv_number_1, invoice_amount=100, payment_method_code=PaymentMethod.CC.value) payment_2.save() def get_receipt(cls, payment_account, pay_response_url: str, invoice_reference): # pylint: disable=unused-argument; mocks of library methods return '1234567890', datetime.now(), 100.00 monkeypatch.setattr( 'pay_api.services.paybc_service.PaybcService.get_receipt', get_receipt) txn = PaymentTransactionService.create_transaction_for_payment( payment_2.id, get_paybc_transaction_request()) txn = PaymentTransactionService.update_transaction( txn.id, pay_response_url='receipt_number=123451') assert txn.status_code == 'COMPLETED' payment_2 = Payment.find_by_id(payment_2.id) assert payment_2.payment_status_code == 'COMPLETED' invoice_1: Invoice = Invoice.find_by_id(invoice_1.id) assert invoice_1.invoice_status_code == 'PAID' cfs_account = CfsAccount.find_effective_by_account_id(payment_account.id) assert cfs_account.status == 'ACTIVE'
def find_by_id(identifier: int, jwt: JwtManager = None, skip_auth_check: bool = False, one_of_roles: Tuple = ALL_ALLOWED_ROLES): """Find payment by id.""" payment_dao = PaymentModel.find_by_id(identifier) # Check if user is authorized to view the payment if not skip_auth_check and payment_dao: for invoice in payment_dao.invoices: check_auth(invoice.account.corp_number, jwt, one_of_roles=one_of_roles) payment = Payment() payment._dao = payment_dao # pylint: disable=protected-access current_app.logger.debug('>find_by_id') return payment
async def test_pad_reversal_reconciliations(session, app, stan_server, event_loop, client_id, events_stan, future, mock_publish): """Test Reconciliations worker for NSF.""" # Call back for the subscription from reconciliations.worker import cb_subscription_handler # register the handler to test it await subscribe_to_queue( events_stan, current_app.config.get('SUBSCRIPTION_OPTIONS').get('subject'), current_app.config.get('SUBSCRIPTION_OPTIONS').get('queue'), current_app.config.get('SUBSCRIPTION_OPTIONS').get('durable_name'), cb_subscription_handler) # 1. Create payment account # 2. Create invoices and related records for a completed payment # 3. Create CFS Invoice records # 4. Create a CFS settlement file, and verify the records cfs_account_number = '1234' pay_account: PaymentAccountModel = factory_create_pad_account( status=CfsAccountStatus.ACTIVE.value, account_number=cfs_account_number) invoice1: InvoiceModel = factory_invoice( payment_account=pay_account, total=100, service_fees=10.0, payment_method_code=PaymentMethod.PAD.value, status_code=InvoiceStatus.PAID.value) factory_payment_line_item(invoice_id=invoice1.id, filing_fees=90.0, service_fees=10.0, total=90.0) invoice2: InvoiceModel = factory_invoice( payment_account=pay_account, total=200, service_fees=10.0, payment_method_code=PaymentMethod.PAD.value, status_code=InvoiceStatus.PAID.value) factory_payment_line_item(invoice_id=invoice2.id, filing_fees=190.0, service_fees=10.0, total=190.0) invoice_number = '1234567890' receipt_number = '9999999999' factory_invoice_reference( invoice_id=invoice1.id, invoice_number=invoice_number, status_code=InvoiceReferenceStatus.COMPLETED.value) factory_invoice_reference( invoice_id=invoice2.id, invoice_number=invoice_number, status_code=InvoiceReferenceStatus.COMPLETED.value) receipt_id1 = factory_receipt(invoice_id=invoice1.id, receipt_number=receipt_number).save().id receipt_id2 = factory_receipt(invoice_id=invoice2.id, receipt_number=receipt_number).save().id invoice1_id = invoice1.id invoice2_id = invoice2.id pay_account_id = pay_account.id total = invoice1.total + invoice2.total payment = factory_payment(pay_account=pay_account, paid_amount=total, invoice_amount=total, invoice_number=invoice_number, receipt_number=receipt_number, status=PaymentStatus.COMPLETED.value) pay_id = payment.id # Now publish message saying payment has been reversed. # Create a settlement file and publish. file_name: str = 'cas_settlement_file.csv' # Settlement row date = datetime.now().strftime('%d-%b-%y') row = [ RecordType.PADR.value, SourceTransaction.PAD.value, receipt_number, 100001, date, 0, cfs_account_number, 'INV', invoice_number, total, total, Status.NOT_PAID.value ] create_and_upload_settlement_file(file_name, [row]) await helper_add_event_to_queue(events_stan, file_name=file_name) # The invoice should be in SETTLEMENT_SCHEDULED status and Payment should be FAILED updated_invoice1 = InvoiceModel.find_by_id(invoice1_id) assert updated_invoice1.invoice_status_code == InvoiceStatus.SETTLEMENT_SCHEDULED.value updated_invoice2 = InvoiceModel.find_by_id(invoice2_id) assert updated_invoice2.invoice_status_code == InvoiceStatus.SETTLEMENT_SCHEDULED.value payment: PaymentModel = PaymentModel.find_by_id(pay_id) assert payment.payment_status_code == PaymentStatus.FAILED.value assert payment.paid_amount == 0 assert payment.receipt_number == receipt_number assert payment.payment_method_code == PaymentMethod.PAD.value assert payment.invoice_number == invoice_number cfs_account: CfsAccountModel = CfsAccountModel.find_effective_by_account_id( pay_account_id) assert cfs_account.status == CfsAccountStatus.FREEZE.value # Receipt should be deleted assert ReceiptModel.find_by_id(receipt_id1) is None assert ReceiptModel.find_by_id(receipt_id2) is None
def find_by_id(identifier: int) -> Payment: """Find payment by id.""" payment_dao = PaymentModel.find_by_id(identifier) current_app.logger.debug('>find_by_id') return Payment._populate(payment_dao)