Skip to content
Create account
or
Sign in
The Stripe Docs logo
/
Ask AI
Create account
Sign in
Get started
Payments
Revenue
Platforms and marketplaces
Money management
Developer tools
Overview
About Stripe payments
Upgrade your integration
Payments analytics
Online payments
OverviewFind your use caseManaged Payments
Use Payment Links
Build a checkout page
Build an advanced integration
Build an in-app integration
Payment Methods
Add payment methods
    Overview
    Payment method integration options
    Manage default payment methods in the Dashboard
    Payment method types
    Cards
    Pay with Stripe balance
    Crypto
    Bank debits
      ACH Direct Debit
      Bacs Direct Debit
      Pre-authorised debit in Canada
      Australia BECS Direct Debit
        Accept a payment
        Save bank details
      New Zeland BECS Direct Debit
      SEPA Direct Debit
    Bank redirects
    Bank transfers
    Credit transfers (Sources)
    Buy now, pay later
    Real-time payments
    Vouchers
    Wallets
    Enable local payment methods by country
    Custom payment methods
Manage payment methods
Faster checkout with Link
Payment interfaces
Payment Links
Checkout
Web Elements
In-app Elements
Payment scenarios
Custom payment flows
Flexible acquiring
Orchestration
In-person payments
Terminal
Other Stripe products
Financial Connections
Crypto
Climate
HomePaymentsAdd payment methodsBank debitsAustralia BECS Direct Debit

Accept an Australia BECS Direct Debit payment

Learn to accept Australia BECS Direct Debit payments.

Copy page

How it works

See the BECS Direct Debit overview to learn more about this payment method.

Stripe users in Australia can use the Payment Element and a Payment Intent to initiate BECS Direct Debit payments from customers with an AU bank account.

Caution

We recommend that you follow the Accept a payment guide unless you need to use manual server-side confirmation, or your integration requires presenting payment methods separately. If you’ve already integrated with Elements, see the Payment Element migration guide.

Use AuBECSDebitForm, Stripe’s prebuilt BECS payment details collection UI, to create a payment form that securely collects bank details without handling sensitive customer data. Accepting BECS Direct Debit payments in your app consists of:

  • Creating an object to track a payment
  • ​​Collecting payment method information and mandate acknowledgement
  • Submitting the payment to Stripe for processing

Stripe users in Australia can use the AuBECSDebitForm and a PaymentIntent to accept BECS Direct Debit payments from customers with an Australian bank account.

Set up Stripe
Server-side
Client-side

Server-side

This integration requires endpoints on your server that talk to the Stripe API. Use our official libraries for access to the Stripe API from your server:

Command Line
Ruby
# Available as a gem sudo gem install stripe
Gemfile
Ruby
# If you use bundler, you can add this line to your Gemfile gem 'stripe'

Client-side

The React Native SDK is open source and fully documented. Internally, it uses the native iOS and Android SDKs. To install Stripe’s React Native SDK, run one of the following commands in your project’s directory (depending on which package manager you use):

Command Line
yarn add @stripe/stripe-react-native

Next, install some other necessary dependencies:

  • For iOS, navigate to the ios directory and run pod install to ensure that you also install the required native dependencies.
  • For Android, there are no more dependencies to install.

Stripe initialisation

To initialise Stripe in your React Native app, either wrap your payment screen with the StripeProvider component, or use the initStripe initialisation method. Only the API publishable key in publishableKey is required. The following example shows how to initialise Stripe using the StripeProvider component.

import React, { useState, useEffect } from 'react'; import { StripeProvider } from '@stripe/stripe-react-native'; function App() { const [publishableKey, setPublishableKey] = useState(''); const fetchPublishableKey = async () => { const key = await fetchKey(); // fetch key from your server here setPublishableKey(key); }; useEffect(() => { fetchPublishableKey(); }, []); return ( <StripeProvider publishableKey={publishableKey} merchantIdentifier="merchant.identifier" // required for Apple Pay urlScheme="your-url-scheme" // required for 3D Secure and bank redirects > // Your app code here </StripeProvider> ); }

Note

Use your API test keys while you test and develop, and your live mode keys when you publish your app.

Collect payment method details and mandate acknowledgment
Client-side

You can securely collect Australia BECS Direct Debit payment information with AuBECSDebitForm component, a drop-in UI component provided by the SDK. AuBECSDebitForm provides a UI for customers to enter their name, email, BSB number, and account number in addition to displaying the Australia BECS Direct Debit Terms.

Add an AuBECSDebitForm component to the screen with your company name as a prop. You can also customize AuBECSDebitForm to match the look and feel of your app by providing the formStyle prop. Collect form details with the onComplete prop when confirming the payment.

function PaymentScreen() { const [formDetails, setFormDetails] = useState< AuBECSDebitFormComponent.FormDetails >(); return ( <View> <AuBECSDebitForm onComplete={(value) => setFormDetails(value)} companyName="Example Company Inc." formStyle={{ textColor: '#000000', fontSize: 22, placeholderColor: '#999999', }} /> <Button title="Pay" variant="primary" onPress={handlePayPress} /> </View> ); }

Create a PaymentIntent
Server-side

Server-side

A PaymentIntent is an object that represents your intent to collect a payment. The PaymentIntent tracks the lifecycle of the payment process through each stage. First, create a PaymentIntent on your server and specify the amount to collect and the aud currency (BECS Direct Debit doesn’t support other currencies). If you already have an integration using the Payment Intents API, add au_becs_debit to the list of payment method types for your PaymentIntent.

To save the BECS Direct Debit account for reuse, set the setup_future_usage parameter to off_session. BECS Direct Debit only accepts an off_session value for this parameter.

Command Line
curl
curl https://api.stripe.com/v1/payment_intents \ -u
sk_test_BQokikJOvBiI2HlWgH4olfQ2
:
\ -d "amount"=1099 \ -d "setup_future_usage"="off_session" \ -d "currency"="aud" \ -d "customer"="{{CUSTOMER_ID}}" \ -d "payment_method_types[]"="au_becs_debit"

After creating a PaymentIntent, Stripe returns a PaymentIntent object containing a client_secret property. Pass the client secret to the client side.

Warning

Use the client secret to charge the customer the amount specified on the PaymentIntent. Don’t log it, embed it in URLs, or expose it to anyone other than your customer.

Client-side

On the client, request a PaymentIntent from your server and store its client secret.

const fetchPaymentIntentClientSecret = async () => { const response = await fetch(`${API_URL}/create-payment-intent`, { method: 'POST', headers: { 'Content-Type': 'application/json', }, body: JSON.stringify({ currency: 'aud', payment_method_types: ['au_becs_debit'], }), }); const { clientSecret, error } = await response.json(); return { clientSecret, error }; };

Submit the payment to Stripe
Client-side

Retrieve the client secret from the PaymentIntent you created and call confirmPayment. This presents a webview where the customer can complete the payment on their bank’s website or app. Afterwards, the promise resolves with the result of the payment.

function PaymentScreen() { const { confirmPayment, loading } = useConfirmPayment(); const [formDetails, setFormDetails] = useState< AuBECSDebitFormComponent.FormDetails >(); const handlePayPress = async () => { const { error, paymentIntent } = await confirmPayment(clientSecret, { paymentMethodType: 'AuBecsDebit', paymentMethodData: { formDetails, } }); if (error) { Alert.alert(`Error code: ${error.code}`, error.message); console.log('Payment confirmation error', error.message); } else if (paymentIntent) { if (paymentIntent.status === PaymentIntents.Status.Processing) { Alert.alert( 'Processing', `The debit has been successfully submitted and is now processing.` ); } else if (paymentIntent.status === PaymentIntents.Status.Succeeded) { Alert.alert( 'Success', `The payment was confirmed successfully! currency: ${paymentIntent.currency}` ); } else { Alert.alert('Payment status:', paymentIntent.status); } } }; return ( <View> <AuBECSDebitForm onComplete={(value) => setFormDetails(value)} companyName="Example Company Inc." formStyle={{ textColor: '#000000', fontSize: 22, placeholderColor: '#999999', }} /> <Button title="Pay" variant="primary" onPress={handlePayPress} /> </View> ); }

Confirm the PaymentIntent succeeded
Server-side

BECS Direct Debit is a delayed notification payment method, which means that funds aren’t immediately available. A BECS Direct Debit PaymentIntent typically remains in a processing state for 2 business days after submission to the BECS network. This submission happens once per day. Once the payment succeeds, the associated PaymentIntent status updates from processing to succeeded.

The following events are sent when the PaymentIntent status is updated:

EventDescriptionNext steps
payment_intent.processingThe customer’s payment was submitted to Stripe successfully.Wait for the initiated payment to succeed or fail.
payment_intent.succeededThe customer’s payment succeeded.Fulfill the goods or services that were purchased.
payment_intent.payment_failedThe customer’s payment was declined.Contact the customer via email or push notification and request another payment method.

Because setup_future_usage and customer were set, the PaymentMethod will be attached to the Customer object when the payment enters the processing state. This attachment happens regardless of whether payment eventually succeeds or fails.

When a Direct Debit attempt fails, Stripe sends a payment_intent.payment_failed event containing a PaymentIntent object. The last_payment_error attribute on the PaymentIntent contains a code and message describing details of the failure.

The failures can be transient or final for the mandate associated with the failed PaymentIntent. In the event of a final failure, Stripe revokes the mandate to prevent additional failure costs. When this happens, and you need your customer to pay, it’s your responsibility to contact your customer to establish a new mandate by re-collecting the bank account information.

For the following failure codes returned, Stripe updates the mandate status as follows:

Failure CodeDescriptionMandate Status
debit_not_authorizedThere’s a permanent failure due to a restriction or block to debit the account and you should contact your customer.inactive
account_closedThere’s a permanent failure because the account has been closed and you should contact your customer.inactive
no_accountThere’s a permanent failure because there’s no account for the provided bank information and you should contact your customer.inactive
refer_to_customerThere’s a transient failure (for example, insufficient funds) and you can re-attempt to debit without collecting a new mandate.active

We recommend using webhooks to confirm the charge succeeds or fails, and to notify the customer whether mandate establishment and payment are complete or if they require additional attention.

Test the integration

Test your form using the test BSB number 000-000 and one of the test account numbers below when you call confirmPayment.

BSB NumberAccount NumberDescription
000-000000123456The PaymentIntent status transitions from processing to succeeded. The mandate status remains active.
000-000900123456The PaymentIntent status transitions from processing to succeeded (with a three-minute delay). The mandate status remains active.
000-000111111113The PaymentIntent status transitions from processing to requires_payment_method with an account_closed failure code. The mandate status becomes inactive.
000-000111111116The PaymentIntent status transitions from processing to requires_payment_method with a no_account failure code. The mandate status becomes inactive.
000-000222222227The PaymentIntent status transitions from processing to requires_payment_method with a refer_to_customer failure code. The mandate status remains active.
000-000922222227The PaymentIntent status transitions from processing to requires_payment_method with a refer_to_customer failure code (with a three-minute delay). The mandate status remains active.
000-000333333335The PaymentIntent status transitions from processing to requires_payment_method with a debit_not_authorized failure code. The mandate status becomes inactive.
000-000666666660The PaymentIntent status transitions from processing to succeeded, but a dispute is immediately created.
000-000343434343The PaymentIntent fails with a charge_exceeds_source_limit error due to the payment amount causing the account to exceed its weekly payment volume limit.
000-000121212121The PaymentIntent fails with a charge_exceeds_transaction_limit error due to the payment amount exceeding the account’s transaction volume limit.

Webhook events are triggered when using test account numbers. In a sandbox, PaymentIntents succeed and fail immediately, and as a result, the respective payment_intent.succeeded and payment_intent.payment_failed events trigger immediately as well. In live mode, the webhooks get triggered with the same delays as those of their related PaymentIntent successes and failures.

See also

  • Save Australia BECS Direct Debit details for future payments
  • Connect payments
Was this page helpful?
YesNo
Need help? Contact Support.
Join our early access programme.
Check out our changelog.
Questions? Contact Sales.
LLM? Read llms.txt.
Powered by Markdoc