Recurring Transactions

Recurring Transactions are processed on the Base Commerce Platform using the RecurringTransaction object to encapsulate all of the data that is needed. It is processed using the BaseCommercePayClient processRecurringTransaction() method. This section details how to process a Recurring Transaction and how to cancel a Recurring Transaction.


Once a recurring transaction is created, every day at 8:30 AM EST, the system will check all enabled recurring transactions to see if there is, any that have a next run date as that day. If there is then an individual transaction will be processed under that merchant.

Once the individual transaction is processed from the recurring transaction, a push notification will be sent to the merchant's Push Notification URL if they have one set.

When a recurring transaction is processed, if it fails validation an email will be sent to the merchant with the failure reasons. The merchant will then want to review the errors to then process a single payment to cover the failed one, or cancel the recurring transaction and create a new one with the updates needed to fix the failure reasons.

If the payment is declined by the the card holder's issuer an email will be sent to the merchant. Also a push notification will be sent to the push notification URL set on the merchant, if one is set. On that push notification it will include the transaction on it which should be checked to confirm it was successful (based off the documentation on BankCardTransactions and BankAccountTransactions and which status you are expecting). If the status is declined, then the merchant will want to handle that recurring transaction the same way as if it failed, which is up to their judgement. A new single transaction can be made to cover the failed one, or a new recurring transaction it is up to the merchant either way they will need to have the reason it failed addressed before hand.

Whether the transaction fails validation or declines, the next frequency of the recurring transaction it will still be tried to process again but Base Commerce does not retry failed/declined single transactions that are processed from a recurring transaction.


If a recurring transaction needs to be updated/changed/modified, then the current one would need to be canceled (directions on how to below) and a new recurring transaction created. This is per card brand regulations, there should be an agreement/contract with the customer and that is what amount is agreed upon. If anything needs to be updated then a new agreement/contract should be obtained from the customer, which therefor means a brand new recurring transaction should be created.

Process a Recurring Transaction

FieldMethod on RecurringTransaction

Description

BankCardsetBankCard( BankCard vo_bank_card )Only one BankCard or BankAccount should be set on the RecurringTransaction, not both. If it is desired to use a BankCard that is stored in the vault, the setToken() method would be used on the BankCard class, then set the BankCard object on the Recurring Transaction object.
BankAccountsetBankAccount( BankAccount vo_bank_account )Only one BankCard or BankAccount should be set on the RecurringTransaction, not both. If it is desired to use a BankAccount that is stored in the vault, the setToken() method would be used on the BankAccount class, then set the BankAccount object on the Recurring Transaction object.

Frequency

setFrequency( String vs_frequency )Sets the frequency that the Recurring Transactions will be run. Use one of the listed frequencies below.
Start DatesetStartDate( Date vo_start_date )Sets the RecurringTransactions start date. The Recurring Transactions will be run at whatever frequency interval based off of this date.
End DatesetEndDate( Date vo_end_date )Sets the RecurringTransactions end date, the date that Recurring Transactions will stop running. This is optional, and if no end date is set, the number of transactions will be set to 2999, and depending on the frequency, it will auto set the end date 2999 intervals from the start date.
AmountsetAmount( double vd_amount )The amount the RecurringTransaction is for.
MessagesgetMessages()Used on the response of processing a RecurringTransaction. If there were errors creating the RecurringTransaction, this method will show the errors. If there were no errors, this will be empty.
StatusgetStatus()Returns the Status of the Recurring Transaction, which can be any of the Statuses that are listed below.
MethodsetMethod( String vs_method )

Sets the Method of the RecurringTransaction. This is only used for ACH RecurringTransactions. It can be any of the Methods that are listed in the table below and would be pulled as a static variable off the BankAccountTransaction object.

Example: BankAccountTransaction.XS_BAT_METHOD_CCD

TypesetType( String vs_type )

Sets the Type of the RecurringTransaction. It can be either XS_BAT_TYPE_CREDIT or XS_BAT_TYPE_DEBIT for ACH, and should be pulled from the BankAccountTransaction object's static variable. If it is a BankCardTransaction then it should be a type of SALE.

Example: BankAccountTransaction.XS_BAT_TYPE_CREDIT

Credit Card Example: BankCardTransaction.XS_BCT_TYPE_SALE

RecurringTransactionIDgetRecurringTransactionID()Returns the ID of the RecurringTransaction. This is the value that's used for canceling RecurringTransactions.

Frequencies

These static Strings are on the RecurringTransaction object and should be used for when setting the frequency of a RecurringTransaction.

Frequency TypeDescription
XS_FREQUENCY_ANNUALLYAnnually, once a year, the transaction will be run.
XS_FREQUENCY_QUARTERLYQuarterly, January 1st, April 1st, July 1st, and October 1st, the transactions will be run.
XS_FREQUENCY_MONTHLYMonthly, every month, the transaction will be run.
XS_FREQUENCY_BIWEEKLYBi-Weekly, every 14 days, the transaction will be run.
XS_FREQUENCY_WEEKLYWeekly, every 7 days, the transaction will be run.
XS_FREQUENCY_DAILYDaily, every day, the transaction will be run.

Statuses

These are the Statuses that a RecurringTransaction can be in.

Status TypeDescription
XS_RECURRING_STATUS_ENABLEDThe RecurringTransaction is enabled.
XS_RECURRING_STATUS_FAILEDThe RecurringTransaction failed, check getMessages() function to see why it failed.
XS_RECURRING_STATUS_DISABLEDThe RecurringTransaction is disabled.

BankAccountTransaction Methods

XS_BAT_METHOD_CCDCorporate credit or debit. Primarily used for business-to-business transactions.
XS_BAT_METHOD_PPDPrearranged payment and deposits. Used to credit or debit a consumer account. Popularly used for payroll direct deposits and preauthorized bill payments.
XS_BAT_METHOD_TELTelephone-initiated entry. Oral authorization by telephone to issue an ACH entry such as checks by phone. (TEL code allowed for inbound telephone orders only. NACHA does not allow the use of this code for outbound telephone solicitations unless a prior business arrangement with the customer has been established.)
XS_BAT_METHOD_WEBWeb-initiated entry. Electronic authorization through the Internet to create an ACH entry.


Example JAVA Process RecurringTransaction ( BankAccount)

		RecurringTransaction o_recurring_transaction = new RecurringTransaction();
        o_recurring_transaction.setAmount(19.99);
        o_recurring_transaction.setFrequency( RecurringTransaction.XS_FREQUENCY_MONTHLY );
        o_recurring_transaction.setType( BankAccountTransaction.XS_BAT_TYPE_CREDIT );
        o_recurring_transaction.setMethod( BankAccountTransaction.XS_BAT_METHOD_CCD );
        
        SimpleDateFormat o_sdf = new SimpleDateFormat("MM/dd/yyyy");
        try {
            o_recurring_transaction.setStartDate( o_sdf.parse("10/10/2015") );
            o_recurring_transaction.setEndDate( o_sdf.parse("11/12/2019") );
        } catch(ParseException e) {
            System.out.println("Error occured :" + e.getMessage());
        }
        
        BankAccount o_bank_account = new BankAccount();
        Address o_address = new Address(Address.XS_ADDRESS_NAME_BILLING);
        o_address.setLine1("1239 test lane");
        o_address.setZipcode("12345");
        o_address.setCity("looney town");
        o_address.setState("az");
        o_address.setCountry("us");
        //Create a new BankAccount object
        o_bank_account.setBillingAddress( o_address );
        o_bank_account.setName( "Test Name" );
        o_bank_account.setAccountNumber( "123123123" );
        o_bank_account.setType( BankAccount.XS_BA_TYPE_CHECKING );
        o_bank_account.setRoutingNumber( "111000025" ); 
        
        o_bank_account.setBillingAddress(o_address);
        o_recurring_transaction.setBankAccount( o_bank_account );

        BaseCommerceClient o_client = new BaseCommerceClient(XS_USERNAME, XS_PASSWORD, XS_KEY);
        o_client.setSandbox(true);

        o_recurring_transaction = o_client.processRecurringTransaction(o_recurring_transaction);

        if ( RecurringTransaction.XS_RECURRING_STATUS_FAILED.equals( o_recurring_transaction.getStatus() ) ) {
            // RecurringTransaction failed, look at messages for reason why
            System.out.println("failed: " + o_recurring_transaction.getMessages() );
        } else if (RecurringTransaction.XS_RECURRING_STATUS_ENABLED.equals( o_recurring_transaction.getStatus() ) ) {
            // RecurringTransaction Successful
            System.out.println("Process successful; Recurring transaction enabled with transaction ID:" + o_recurring_transaction.getRecurringTransactionID() );
        } else if ( RecurringTransaction.XS_RECURRING_STATUS_DISABLED.equals(o_recurring_transaction.getStatus())) {
            // RecurringTransaction disabled
            System.out.println("disabled");
        }

Example PHP Process RecurringTransaction ( BankAccount)

function processRecurringTransactionMonthlyWithNewBankAccount() {
        // Create BaseCommerceClient with your given username, password, and key and set sandbox to true
        $o_bcpc = new BaseCommerceClient($this->s_username, $this->s_password, $this->s_key);
        $o_bcpc->setSandbox(true);
        // Create a new RecurringTransaction and set all the appropriate fields
        $o_recurring_transaction = new RecurringTransaction();
        $o_recurring_transaction->setFrequency(RecurringTransaction::$XS_FREQUENCY_MONTHLY);
        $o_recurring_transaction->setStartDate((new DateTime('9/15/2019'))->format('m/d/Y'));
        $o_recurring_transaction->setEndDate( ( new DateTime('9/15/2020'))->format('m/d/Y') );
        $o_recurring_transaction->setAmount(100.00);
        $o_recurring_transaction->setType(BankAccountTransaction::$XS_BAT_TYPE_DEBIT);
        $o_recurring_transaction->setMethod(BankAccountTransaction::$XS_BAT_METHOD_CCD);
        // Create a BankCard and add it to the recurring transaction
        //create the billing Address object
        $o_address = new Address();
        $o_address->setName(Address::$XS_ADDRESS_NAME_BILLING);
        $o_address->setLine1("123 Some Address");
        $o_address->setCity("Tempe");
        $o_address->setState("AZ");
        $o_address->setZipcode("12345");
        //Create a new BankCard object
        $o_ba = new BankAccount();
        $o_ba->setBillingAddress($o_address);
        $o_ba->setName("Test Name");
        $o_ba->setAccountNumber("123123123");
        $o_ba->setAccountType(BankAccount::$XS_BA_TYPE_CHECKING);
        $o_ba->setRoutingNumber("011000015");
        $o_recurring_transaction->setBankAccount($o_ba);
        $o_returned_rt = $o_bcpc->processRecurringTransaction($o_recurring_transaction);
        var_dump($o_returned_rt->getRecurringTransactionID());
        var_dump($o_returned_rt->getStatus());
        var_dump($o_returned_rt->getMessages());
        var_dump($o_returned_rt->getJSON());
        
    }



Example PHP Process RecurringTransaction ( BankCard)

public function processRecurringTransactionMonthlyWithNewBankCard() {
        //create BaseCommerceClient with your given username, password, and key and set sandbox to true
        $o_bcpc = new BaseCommerceClient($this->s_username, $this->s_password, $this->s_key);
        $o_bcpc->setSandbox(true);
        // Create a new RecurringTransaction and set all the appropriate fields
        $o_recurring_transaction = new RecurringTransaction();
        $o_recurring_transaction->setFrequency(RecurringTransaction::$XS_FREQUENCY_MONTHLY);
        $o_recurring_transaction->setStartDate(( new DateTime('9/15/2019'))->format('m/d/Y'));
        $o_recurring_transaction->setEndDate( ( new DateTime('9/15/2020'))->format('m/d/Y') );
        $o_recurring_transaction->setAmount(100.00);
        $o_recurring_transaction->setType(BankCardTransaction::$XS_BCT_TYPE_SALE);
        // Create a BankCard and add it to the recurring transaction
        //create the billing Address object
        $o_address = new Address();
        $o_address->setName(Address::$XS_ADDRESS_NAME_BILLING);
        $o_address->setLine1("123 Some Address");
        $o_address->setCity("Tempe");
        $o_address->setState("AZ");
        $o_address->setZipcode("12345");
        //Create a new BankCard object
        $o_bc = new BankCard();
        $o_bc->setBillingAddress($o_address);
        $o_bc->setExpirationMonth("02");
        $o_bc->setExpirationYear("2020");
        $o_bc->setName("Test Name");
        $o_bc->setNumber("4111111111111111");
        $o_recurring_transaction->setBankCard($o_bc);
        $o_returned_rt = $o_bcpc->processRecurringTransaction($o_recurring_transaction);
        var_dump($o_returned_rt->getRecurringTransactionID());
        var_dump($o_returned_rt->getStatus());
        var_dump($o_returned_rt->getBankCard()->getToken());
        var_dump($o_returned_rt->getMessages());
    }

Cancel RecurringTransaction

To cancel a RecurringTransaction, all that is needed is the RecurringTransaction's ID, which can be obtained by the getRecurringTransactionID() method. That ID is passed into the cancelRecurringTransaction( int n_id ) method and that is all that is needed.

The user is able to Cancel/Disable only those Recurring Transaction which are in Active/Completed status. No failed transaction could be cancelled.

Example Cancel RecurringTransaction

		RecurringTransaction o_recurring_transaction = new RecurringTransaction();
        int n_recurring_transaction_id = 22;
        BaseCommerceClient o_client = new BaseCommerceClient(XS_USERNAME, XS_PASSWORD, XS_KEY);
        o_client.setSandbox(true);
        
        o_recurring_transaction = o_client.cancelRecurringTransaction( n_recurring_transaction_id );

        if ( RecurringTransaction.XS_RECURRING_STATUS_DISABLED.equals( o_recurring_transaction.getStatus() ) ) {
            // RecurringTransaction Successful
            System.out.println("Cancellation Successful for transaction ID :" + o_recurring_transaction.getRecurringTransactionID() );
        } else {
            System.out.println("Cancellation failed: " + o_recurring_transaction.getMessages() );
        }