Code Sample

Vaulting Accounts and Making Payments

668

Sample Checkout Page

<html>
	<head>
	<meta charset="utf-8">
	<title>PaySimpleJS</title>
	</head>
	<body>
    
		<form id="sample-form">
			<div class="merchant-form">
				<p>Merchant Checkout Page</p>
				<div class="form-field">
					<label for="firstName">First Name</label>
					<input type="text" id="firstName" />
				</div>
				<div class="form-field">
      		<label for="lastName">Last Name</label>
					<input type="text" id="lastName" />
      		</div>
    		<div class="form-field">
					<label for="email">Email</label>
					<input type="email" id="email" />
				</div>
			</div>
		
      <div class="psjs">
			<p>PaySimpleJS Payment Form</p>
			<div id="psjs">
			<!-- a PaySimpleJS Payment Form will be inserted here -->
			</div>
		</div>

		<div class="merchant-form">
			<p>Merchant Checkout Page</p>
				<button type="submit" id="submit">Complete Checkout</button>
		</div>
	</form>

<script src="https://api.paysimple.com/paysimplejs/v1/scripts/client.js"></script>
	</body>
</html>
p {
     font-family: Arial, sans-serif;
     font-weight: bold;
     margin: 0 0 10px;
     padding: 0;
}
 .merchant-form {
     border: blue solid 1px;
     margin: 15px 0;
     padding: 10px;
}
 .psjs {
     background-color: #f9f9f9;
     border: red solid 1px;
     margin: 15px 0;
     padding: 10px;
}
 .form-field {
     margin: 10px 0;
}
 .form-field label {
     display: block;
}
 .form-field input {
     display: block;
}
function loadPaysimpleJs(auth) {
    // Initialize the PaySimpleJS SDK with the checkout token and styles
    // where auth = { token: <Checkout Token from your server> }
    var paysimplejs = window.paysimpleJs({
        // Element that will contain the iframe
        container: document.querySelector('#psjs'),
        auth: auth,
        // Allows entry of international postal codes if true
        bypassPostalCodeValidation: false,
        // Attempts to prevent browsers from using autocompletion to pre-populate 
        // or suggest input previously stored by the user. Turn on for point of 
        // sale or kiosk type applications where many different customers 
        // will be using the same browser to enter payment information.
        preventAutocomplete : false,
        styles: {
            body: {
                backgroundColor: '#f9f9f9'
            }
        }
    });

    // Configure a callback to complete the checkout after the
    // PaySimpleJS SDK retrieves the account
    paysimplejs.on('accountRetrieved', onAccountRetrieved);
    // Listen to the 'formValidityChanged' event to enable
    // your submit button
    // where body = { validity: <'true' | 'false'> }
    paysimplejs.on('formValidityChanged', function(body) {
        // Add handling to enable your submit button
    });
    // Listen to the 'httpError' event
    // where error = {
    // errorKey: <'timeout' | 'bad_request' | 'server_error'
    // | 'unauthorized' | 'unknown'>,
    // errors: <array of { field: <string>, message: <string> }>,
    // status: <number - http status code returned>
    // }

    paysimplejs.on('httpError', function(error) {
        // Add your error handling
    });
    // Load the credit card key enter form
    paysimplejs.send.setMode('cc-key-enter');
    // Add an event listener to your submit button
    document.querySelector('#sample-form')
        .addEventListener('submit', onSubmit);

    // Called when the PaySimpleJS SDK retrieves the account info
    function onAccountRetrieved(accountInfo) {
            /* Example accountInfo:
             * {
             * "account": {
             * "id": 7313702
             * },
             * "customer": {
             * "id": 8041997,
             * "firstName": "John",
             * "lastName": "Snow",
             * "email": "[email protected]"
             * },
             * "paymentToken": "e1f1bb19-9fe4-4c96-a35e-cd921298d8e6"
             * }
             */

            // Send the accountInfo to your server to collect a payment
            // for an existing customer
            var xhr = new XMLHttpRequest();
            xhr.open('POST', '/payment');
            xhr.setRequestHeader('Content-Type', 'application/json');
            xhr.onload = function(e) {
                if (xhr.status < 300) {
                    var data = JSON.parse(this.response);
                    alert('Successfully created Payment:\nTrace #: ' + data.TraceNumber);
                } else {
                    alert('Failed to create Payment: (' + xhr.status + ') ' + xhr.responseText);
                }
            }
            xhr.send(JSON.stringify(accountInfo));
        }
        // Submit button event listener -- triggered when the user clicks
        // the submit button.
        // Sumbits the merchant form data to the PaySimpleJS SDK

    function onSubmit(event) {
        // Prevent the default submit behavior of the form
        event.preventDefault();
        // Extract the customer info (first name, last name, email)
        // from the form. These fields are required, and should be
        // validated prior to calling 'retrieveAccount'
        var customer = {
            firstName: document.querySelector('#firstName').value,
            lastName: document.querySelector('#lastName').value,
            email: document.querySelector('#email').value
        };
        // Request the PaySimpleJS SDK to exchange the card data for a
        // payment token; pass in the customer info captured on the
        // merchant form
        paysimplejs.send.retrieveAccount(customer);
    }
}

// Obtain a Checkout Token from your server
function getAuth(callback) {
    var xhr = new XMLHttpRequest();
    xhr.open('GET', '/token');
    xhr.onload = function(e) {
        if (xhr.status < 300) {
            var data = JSON.parse(this.response);
            callback.call(null, {
                token: data.JwtToken
            });
            return;
        }
        alert('Failed to get Checkout Token: (' + xhr.status + ') ' + xhr.responseText);
    }
    xhr.send();
}
getAuth(loadPaysimpleJs);

Sample Server Code

'use strict';
const express = require('express');
const bodyParser = require('body-parser');
const request = require('request');
const crypto = require('crypto');
	// Replace username and apikey with your PaySimple 4.0 API credentials
const settings = {
		port: 8080,
    apiv4url: https: //api.paysimple.com/v4, 
  	// set to https://sandbox-api.paysimple.com/v4 for testing in the sandbox environment
		username: 'APIUser9999999',
    apikey: 'NTqVg...V8W0'
};
let app = express();
app.use(express.static('public'));
app.use(bodyParser.json());
// The authorization header for PaySimple 4.0
function getAuthHeader() {
    let time = (new Date()).toISOString();
    let hash = crypto.createHmac('SHA256', settings.apikey)
    .update(time)
    .digest('base64');
    return 'PSSERVER ' + "accessid=" + settings.username +
        "; timestamp=" + time + "; signature=" + hash;
}

// Simple endpoint to communicate with PaySimple 4.0 API to retrieve a JWT
// that can be passed to the PaySimpleJS
// Example response body:
// {
// "JwtToken": "eyJ0eXAiOiJKV1...lNbw",
// "Expiration":"2017-02-28T22:03:36Z"
// }

app.get('/token', function(req, res) {
    let options = {
        method: "POST",
        uri: settings.apiv4url + '/checkouttoken',
        headers: {
            Authorization: getAuthHeader()
        },
        body: {},
        json: true,
    };

    request(options, function(error, response, body) {
        if (!error && response && response.statusCode < 300) {
            res.json(body.Response);
            return;
        }
        res.status((response && response.statusCode) || 500).send(error);
    });
});

// Mocked up endpoint to initiate a payment via the PaySimple 4.0 API with
// the payment token returned by the PaySimpleJS

app.post('/payment', function(req, res) {
		var accountInfo = req.body;
    let options = {
        method: "POST",
        uri: settings.apiv4url + '/payment',
        headers: {
            Authorization: getAuthHeader()
        },
        body: {
            AccountId: accountInfo.account.id,
            PaymentToken: accountInfo.paymentToken,
            // Payment Specific information...
            Amount: 3.50,
            PurchaseOrderNumber: '123456',
            OrderId: 'O-4242',
            Description: 'Really good description of order',
            PaymentSubType: 'MOTO'
        },
        json: true,
    };

    request(options, function(error, response, body) {
        // The return code for /payment will be a 201 (CREATED)
        if (!error && response && response.statusCode < 300) {
            res.json(body.Response);
            return;
        }
        res.status((response && response.statusCode) || 500).send(error);
    });
});
// Endpoint to get a JWT token for a customer that has been authenticated
// by the merchant. The PaySimple customer id should NOT be passed into this service
// to prevent unauthorized access.

app.get('/customertoken, function(req, res) {
let customerid = 1234; // do a lookup in your system to fetch the PaySimple customer id for the authenticated customer
let options = {
    method: "GET",
    uri: settings.apiv4url + '/customer/' + customerId + "/token",
    headers: {
        Authorization: getAuthHeader()
    },
    json: true,
};

request(options, function(error, response, body) {
    if (!error && response && response.statusCode < 300) {
        res.json(body.Response);
        return;
    }
    res.status((response && response.statusCode) || 500).send(error);
});
});

app.listen(settings.port, function() {
    console.log('PaySimpleJS backend listening on port ' + settings.port);
});
using System.Configuration;
using System.Threading.Tasks;
using System.Web.Mvc;
using PaySimpleSdk.Accounts;
using PaySimpleSdk.Customers;
using PaySimpleSdk.Models;
using PaySimpleSdk.Payments;

namespace PaySimple.NetSDKSample.Web.Controllers
{
    public class PaySimpleController : Controller
    {
        private static readonly IPaySimpleSettings PSSettings = new PaySimpleSettings(ConfigurationManager.AppSettings["PS.ApiKey"], ConfigurationManager.AppSettings["PS.UserId"],
                ConfigurationManager.AppSettings["PS.BaseUrl"]);

        [HttpPost]
        public async Task<ActionResult> CheckoutToken()
        {
            var paymentService = new PaymentService(PSSettings);
            var token = await paymentService.GetCheckoutTokenAsync();
            return Json(token);
        }

        [HttpPost]
        public async Task<ActionResult> PaymentToken(PaymentTokenRequest paymentTokenRequest)
        {
            var paymentService = new PaymentService(PSSettings);
            var token = await paymentService.GetPaymentTokenAsync(paymentTokenRequest);
            return Json(token);
        }

        [HttpPost]
        public async Task<ActionResult> Payment(decimal amount, Account account, Customer customer, string paymentToken)
        {
            var payment = new Payment
            {
                Amount = amount,
                AccountId = account.Id,
                PaymentToken = paymentToken
            };

            var paymentService = new PaymentService(PSSettings);
            payment = await paymentService.CreatePaymentAsync(payment);
            return Json(payment);
        }
    }
}