How to Get and Hook WooCommerce Payment Gateways

In this post I want to share with you a couple of useful functions to work with payment gateways in your WooCommerce store.

#WooCommerce, #checkout  /    /   21

All the installed WooCommerce payment gateways under the Checkout tab in the shop settings.
You can find all the installed payment gateways in WooCommerce > Settings, under the Checkout tab. Here on the screenshot you can see Stripe, PayPal, PayPal Website Payments Pro etc.

All the below functions and hooks you can find in woocommerce/includes/class-wc-payment-gateways.php.

Get Payment Gateways #

Here I will show you how to work with two class methods WC()->payment_gateways->payment_gateways() and WC()->payment_gateways->payment_gateways().

All the installed payment methods

By default WooCommerce has 4 installed payment gateways: BACS, Check Payments, Cash on Delivery and PayPal. The additional payment methods can be installed with plugins. Usually if plugin is activated = the gateway is installed and you can find it in the shop settings.

$installed_payment_methods = WC()->payment_gateways->payment_gateways();

This class function returns objects of all payment gateways installed on your WooCommerce store. What is inside objects? Just print_r() the result and you’ll know.

$installed_payment_methods = WC()->payment_gateways->payment_gateways();
print_r( $installed_payment_methods );

In the below example let’s try to print the names of payments gateways:

$installed_payment_methods = WC()->payment_gateways->payment_gateways();
 
foreach( $installed_payment_methods as $method ) {
	echo $method->title . '<br />';
}

This function also has a filter woocommerce_payment_gateways. This filter runs on the early stage and allows you to completely remove any of WooCommerce default payment gateways. Read below how.

Only available gateways

WooCommerce uses this function when it gets the payment methods directly on the checkout page and while processing payment.

So, for example, if a specific payment method is not enabled in the shop settings, it won’t be shown.

$available_payment_methods = WC()->payment_gateways->get_available_payment_gateways();

The return result is similar to WC()->payment_gateways->payment_gateways(). It also has a filter woocommerce_available_payment_gateways, described below.

How to remove WooCommerce default payment gateways from everywhere: BACS, Check Payments, Cash on Delivery and PayPal #

function misha_remove_default_gateway( $load_gateways ){
 
	unset( $load_gateways[0] ); // WC_Gateway_BACS
	unset( $load_gateways[1] ); // WC_Gateway_Cheque
	unset( $load_gateways[2] ); // WC_Gateway_COD (Cash on Delivery)
	//unset( $load_gateways[3] ); // WC_Gateway_Paypal
 
	return $load_gateways;
}
 
add_filter( 'woocommerce_payment_gateways', 'misha_remove_default_gateway', 10, 1 );

Insert the code into your current theme functions.php and go to the shop checkout settings.

Remove WooCommerce default payment gateways: BACS, Check Payments, Cash on Delivery.
As the result you can see that only PayPal method is remained.

How to force allow a specific payment gateway when no gateways are available #

When you could need this?

Let me describe the situation from life. My client has the subscription-based website with WooCommerce Memberships and WooCommerce Subscriptions plugins installed. As a payment gateway we used Stripe. But it happened that Stripe stopped working with his business. After that we deactivate Stripe plugin, and even if we have another payment gateways installed, WooCommerce doesn’t allow the existing subscribers to renew their subscriptions with another payment gateway. And this was unacceptable.

The following small piece of code saved our lives.

/*
 * if no methods are allowed, allow PayPal Payflow
 */
function misha_change_wc_gateway_if_empty( $allowed_gateways ){
 
	if( empty( $allowed_gateways ) ) {
		$allowed_gateways = array();
		$all_gateways = WC()->payment_gateways->payment_gateways();
		$allowed_gateways['paypal_pro_payflow'] = $all_gateways['paypal_pro_payflow'];
	}
 
	return $allowed_gateways;
 
}
add_filter('woocommerce_available_payment_gateways','misha_change_wc_gateway_if_empty', 9999, 1 );
Misha Rudrastyh
About the author Misha Rudrastyh

Passionate about WordPress and snowboarding, creating websites for over 10 years! Let's work together — just contact me.

If you are a developer too, subscribe to my facebook page.

Comments 21

  • Hi
    Very interesting post !

    Question : How can i use these functions to for BACS payment on a certain amount (eg Bacs payment when the amount of the checkout is legal or superior to 250€ ?

    Many thank !
    Regards
    Phil

  • …i would say : force BACS payment when the amount of checkout is ≥ to 250€ (sorry for my poor english)

  • Bülent Sakarya

    Hi..

    I’m taking an error.

    Call to a member function get_base_country() on null

    My code;

    class WC_Custom_Payment_Fields extends WC_Payment_Gateway {
    	/**
    	* Constructor for the gateway.
    	*/
    	public function __construct() {
     
    		$available_gateways = WC()->payment_gateways->payment_gateways();
    		var_dump($available_gateways);
    ...

    How can I fix it? Thanks..

  • hi is there a way to put the payment gateways to other page? other than checkout page?

    • Hi Nick,

      I tried to do something like this but it leads to many bugs and problems. I even have a plugin for it, but I won’t sell it anymore until I find a 100% working solution.

  • Divyesh kakrecha

    Hi,

    How i can change payment position. In my case i want to add payment option after checkout fields. If anyone know how to do this please let me know here.

    Thanks

  • Hi Misha!
    thx for the guide.
    I would like to enable payment methods also if no payment is needed (free cuopon for example).
    in this case, misha_change_wc_gateway_if_empty ins’t called, so I can’t enable this payment gateways.
    Any suggestion?
    Thanks!

  • jorge santos

    Very interesting.

    Q: How can hide some checkout billing field when certain gateway is checked?

    Thank you, and god work!

    • MishaAuthor

      Hi Jorge,

      Sure, we gonna use the code from the chechout fields tutorial too.

      The example of code that hide the billing company checkout field:

      add_filter( 'woocommerce_checkout_fields', 'misha_remove_field_depending_on_gateway', 100 );
       
      function misha_remove_field_depending_on_gateway( $fields ) {
       
      	/* if this gateway is activated in admin, remove a field */
      	$specific_gateway = 'bacs';
       
      	/* we do not need gateway objects, only keys */
      	$activated_ones = array_keys( WC()->payment_gateways->get_available_payment_gateways() );
       
      	if( in_array( $specific_gateway, $activated_ones ) ) {
      		unset( $fields['billing']['billing_company'] );
      	}
       
      	return $fields;
      }
      • jorge santos

        Excelent!

        But HTTP ERROR 500.

        thanks

      • jorge santos

        Only need hide one billing_field on checkout page

        Ex:

        If i click on Payment_method ‘PayPal’

        Need hide a field ‘billing_VAT’

        Is possible?

        • MishaAuthor

          Ok, I understand what you mean. Just one question, is billing_VAT a required field for another payment gateway?

          • Hi Misha

            Yes, is a required field from another payment method.

            Only need hide/unset for all other methods

            Thank you

        • Ok, some jQuery code should help you in this case, but please note that you do not have to include jQuery because it is already included in your checkout page:

          add_action('woocommerce_after_checkout_form', 'misha_remove_field_on_change' );
           
          function misha_remove_field_on_change(){
          	echo "<script>
          	jQuery(function($){
           
          		// in case the PayPal method IS selected by default, uncomment this line too:
          		// $('#billing_vat_field').hide(function(){ $(this).removeClass('validate-required').find('input').val('no'); });
           
          		$('body').on('change', 'input[name=\"payment_method\"]', function(){
          			if( $(this).val() == 'paypal' ) { // just an example
          				$('#billing_vat_field').hide(function(){
          					$(this).removeClass('validate-required').find('input').val('no');
          				});
          			} else {
          				$('#billing_vat_field').show(function(){
          					$(this).removeClass('woocommerce-validated').addClass('validate-required').find('input').val('');
          				});
          			}
          		});
          	});</script>";
          }

          But before using it make sure that your billing field ID is #billing_vat_field and the payment method ID is paypal. You can do it just in your browser – Right click, then Inspect.

          To insert the JS code you can also use wp_footer hook.

          • jorge santos

            Hi Misha,

            now i’m confused. Lol
            jquery is already included, because i try your code in footer.

            This new code can insert in function.php ?

          • Yes 🙃

            jQuery is not necessary because it is included by WooCommerce, just insert this code to the functions.php

Comments are closed.
If you need my personal help, please contact me. Contact me