loading...

Paypal in React Native WebView

franko4don profile image Nwanze franklin Updated on ・3 min read

React native is one of the most popular and widely used Javascript cross platform mobile development framework. It is based on ReactJS thus making it easy for developers who are already good with ReactJS to delve into it. For more on React Native check here.

The Process
I was working on a project that needed Paypal integration recently and couldn’t find a stable open source React Native module for it so I came up with an implementation based on WebView.

Steps to complete before implementation

  • Create a Paypal account if you don’t have one already
  • Login to developer and create a sandbox account
  • Create an app with an already existing sandbox account and get a Client ID

Creating a new app with an existing sandbox account

Set up the React Native part

At this point it is assumed that most part of you app is working and perhaps you need the payment part to complete the flow process.
Since we are using WebView there will be a HTML file which we will design to suit our app user interface and a component to communicate with the WebView back and forth.

PayPal.js

Brief explanation of some functions and variables

const patchPostMessageFunction fixes the issue described here.

handleMessage function receives the data emitted from Javascript within paypal.html.

passValues function sends data from react native to paypal.html.

sent key in the state is used to mark when data has been passed from react native to WebView.

paypal.html

<!DOCTYPE html>
<html lang="">
  <head>
    <meta charset="utf-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <title>Paypal</title>
    <script src="https://www.paypal.com/sdk/js?client-id={clientID}"></script>

    <style>
        html, body{
            width: 100%;
            height: 100%;
            margin: 0;
            padding: 0;
            font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
            background: linear-gradient(180deg, #3D40AD 0%, #6B6ED7 100%);
        }
        .container{
            height: 100%;
            display: flex;
            margin-left: 20px;
            margin-right: 20px;
            overflow-y: scroll;
            justify-content: center;
            align-items: center;
        }
        p{
            color: white;
            font-size: 16px;
            text-align: justify;
            margin-bottom: 50px;
        }
        #preloaderSpinner{
          display: none;
        }
    </style>
  </head>
  <body>
      <div class="container">
            <div style="justify-content: center; text-align: center">
                <img width="80px" height="80px" src="logo.png"/>
                <p>
                </p>
                <div id="paypal-button-container"></div>
            </div>
      </div>


    <script>
      function payWithPayPal(amount, orderID) {
        paypal
          .Buttons({

            createOrder: function(data, actions) {
                return new Promise(function(resolve, reject){
                  resolve(orderID);
              });
            },
            onApprove: function(data, actions) {
              window.postMessage(JSON.stringify({
                    reference: data.orderID, 
                    message: 'Transaction Successful',
                    status: 'success'
                }));
            }
          })
          .render("#paypal-button-container");
      }
      document.addEventListener("message", function(data) {
        var details = JSON.parse(data.data);
        document.querySelector('p').innerText = "You are about to fund your wallet with USD "+details.amount+" on XYZ. Click on any of the payment options to proceed. Your account will be credited instantly after payment."
        payWithPayPal(details.amount, details.orderID);
      })

    </script>
  </body>
</html>

document.addEventListener("message", function(data)) part listens for message emitted from react native and receives the data sent. This data is then parsed back to JSON, used to prepare a display message and setup PayPal SDK as well.

Transactions are initiated from the server end via an API call and a payload containing the orderID from PayPal is returned.

To initiate a transaction from the backend, PayPal SDKs are very helpful and they can be found here for different languages.

Conclusion

React Native WebView Comes in handy for situations like this as well as plotting some complex animated graphs. I would like to hear from you and learn more too.

Posted on by:

franko4don profile

Nwanze franklin

@franko4don

I am a software developer passionate about technology and building community of developers

Discussion

markdown guide
 

Nwanze,

1) Great write-up! Might want to add “with WebView” to the title. I came here because I use PayPal SDK bridged to RN, and wanted to see if someone out there (you) had a different/better way of doing it.
2) WebView is no longer part of the react-native library. Instead, it’s being maintained by the react-native-community:

github.com/react-native-community/...

 

Thanks, I should have mentioned the React Native version I used for the Demo. I will update the title accordingly and would also like to see your implementation.

 
 

hey i follow your code i got this error any one up here help me please
could not find "store" in the context of "connect(paypal)". either wrap the root component in a , or pass a custom react contextprovider to and the corresponding react context consumer to connect(paypal) in connect options.

 

Did you run into issues with 2FA on ios? I keep getting 403 when I try to get the code

 

if we select Debit or Credit Card option it stuck with message "Something Went Wrong. We'll take you back to the checkout so you can try again."
And try again button not working in webview