Standard Checkout (Deprecated)

Checkout Form is the simplest way to integrate Cashfree Payment Gateway in your website to accept payments quickly.

In the Standard Checkout integration method, you prepare the checkout form with the correct order and customer details and redirect users from your checkout page to Cashfree’s payment screen. Cashfree payment gateway supports all major payment methods such as credit and debit cards, wallets, UPI, and net banking.

The Checkout form provides customers with a streamlined flow for initiating payments. Your customers enter payment details on the payment screen hosted by Cashfree and complete the payment. Cashfree handles the PCI compliance guidelines on your behalf in this integration method.

Watch the video to know how to integrate Cashfree Payment Gateway using PHP.

Steps to Create Checkout Form

  1. Create Checkout Form
  2. Generate Signature
  3. Submit Checkout Form

Create Checkout Form

Customers orders are associated with a unique identifier orderId for each order. The order amount is associated with an identifier orderAmount. To process the payments for these orders, you must send us the orderId and the corresponding orderAmount. We send you the payment status against each order.

You need to send us a few more details to process the payment. Click here to see all the Request Parameters.

Every request to Cashfree must contain authentication information to establish the identity of the user making the request, we use the signature field for this authentication.

See the code below on how to generate a valid signature for Checkout integration.

Create a sample HTML form as shown below. Ensure to fill in the correct credentials for appId and secret key. You can find your AppId and Secret key in the merchant dashboard.

For Production/Live Environment set the action attribute of the form to:
https://www.cashfree.com/checkout/post/submit

For Test Environment set the action attribute to:
https://test.cashfree.com/billpay/checkout/post/submit

<form id="redirectForm" method="post" action="https://test.cashfree.com/billpay/checkout/post/submit">
<input type="hidden" name="appId" value="<YOUR_APPID_HERE>"/>
<input type="hidden" name="orderId" value="order00001"/>
<input type="hidden" name="orderAmount" value="100"/>
<input type="hidden" name="orderCurrency" value="INR"/>
<input type="hidden" name="orderNote" value="test"/>
<input type="hidden" name="customerName" value="John Doe"/>
<input type="hidden" name="customerEmail" value="[email protected]"/>
<input type="hidden" name="customerPhone" value="9999999999"/>
<input type="hidden" name="merchantData" value="<GENERATED_BASE64_MERCHANTDATA>"/>
<input type="hidden" name="returnUrl" value="<RETURN_URL>"/>
<input type="hidden" name="notifyUrl" value="<NOTIFY_URL>"/>
<input type="hidden" name="signature" value="<GENERATED_SIGNATURE>"/>

Request Parameters

The checkout form accepts all the request parameters mentioned below. Ensure you send us all the required fields. Requests with an invalid signature will be rejected.

ParameterRequiredDescription
appIdYesYour app ID.
orderIdYesOrder/Invoice ID.
orderAmountYesBill amount of the order.
orderCurrencyNoCurrency for the order. The default currency is INR. See Currencies Supported for the list of available currencies. Contact [email protected] to enable new currencies.
orderNoteNoText that will help customers know more about their order.
customerNameYesName of the customer.
customerPhoneYesPhone number of the customer.
customerEmailYesEmail ID of the customer.
merchantDataNoA base 64 encoded json array (as a key value pair). Maximum 10 pairs allowed, at max 64 chars for each key and 256 chars for each value.
returnUrlYesThe URL to which the user must be redirected to after completing the payment. We recommend you to use an HTTPS URL for the returnURL.
notifyUrlNoNotification URL is for server-server communication. This URL receives a notification for every successful order. notifyUrl must be an HTTPS URL.
paymentModesNoPayment modes allowed to complete the payment for the order. Available values: cc, dc, nb, upi, paypal, wallet. Example values: "cc", "cc,dc", "paypal, nb", etc.
If this parameter is empty, all available payment modes are displayed.
signatureYesRequest signature.

Generate Signature

Every request to Cashfree must contain authentication information to establish the identity of the user making the request. We use a digital signature to validate each transaction. This will ensure integrity of the signed data against tampering.

In the sample form above, generate a signature for every checkout. The signature is generated as the HMAC value of the data being passed which is using SHA256 hash function in combination with your secret key.

We will generate a signature at our end and want you to do the same with the posted data and match it with the passed argument.

📘

Signature generation varies across integration methods, ensure you are using the right signature generation method.

You can find your appId and secret key in the merchant dashboard here.

$secretKey = "secret_key";
$merchantData = array(
     "key1" => "value1",
     "key2" => "value2",
     "key3" => "value3"
);
$merchantData = base64_encode(json_encode($merchantData));

$postData = array(
  "appId" => $appId,
  "orderId" => $orderId,
  "orderAmount" => $orderAmount,
  "orderCurrency" => $orderCurrency,
  "orderNote" => $orderNote,
  "customerName" => $customerName,
  "customerPhone" => $customerPhone,
  "customerEmail" => $customerEmail,
  "merchantData" => $merchantData,  
  "returnUrl" => $returnUrl,
  "notifyUrl" => $notifyUrl,
);
 // get secret key from your config
 ksort($postData);
 $signatureData = "";
 foreach ($postData as $key => $value){
      $signatureData .= $key.$value;
 }
 $signature = hash_hmac('sha256', $signatureData, $secretKey,true);
 $signature = base64_encode($signature);
import hashlib
import hmac
import base64

postData = {
  "appId" : appId,
  "orderId" : orderId,
  "orderAmount" : orderAmount,
  "orderCurrency" : orderCurrency,
  "orderNote" : orderNote,
  "customerName" : customerName,
  "customerPhone" : customerPhone,
  "customerEmail" : customerEmail,
  "returnUrl" : returnUrl,
  "notifyUrl" : notifyUrl
}

sortedKeys = sorted(postData)
signatureData = ""
for key in sortedKeys:
  signatureData += key+postData[key];

message = bytes(signatureData).encode('utf-8')
#get secret key from your config
secret = bytes(secretKey).encode('utf-8')
signature = base64.b64encode(hmac.new(secret, message,digestmod=hashlib.sha256).digest())
Map<String, String> postData = new HashMap<String, String>();
  postData.put("appId", appId);
  postData.put("orderId", ORDERID);
  postData.put("orderAmount", ORDERAMOUNT);
  postData.put("orderCurrency", ORDER_CURRENCY);
  postData.put("orderNote", ORDERNOTE);
  postData.put("customerName", CUSTOMER_NAME);
  postData.put("customerEmail", CUSTOMER_EMAIL);
  postData.put("customerPhone", CUSTOMER_PHONE);
  postData.put("returnUrl",RETURN_URL);
  postData.put("notifyUrl", NOTIFY_URL);
  String data = "";
  SortedSet<String> keys = new TreeSet<String>(postData.keySet());
  for (String key : keys) {
      data = data + key + postData.get(key);
  }
  Mac sha256_HMAC = Mac.getInstance("HmacSHA256");
  SecretKeySpec secret_key_spec = new
  SecretKeySpec(secretKey.getBytes(),"HmacSHA256");
  sha256_HMAC.init(secret_key_spec);
  String signature = Base64.getEncoder().encodeToString(sha256_HMAC.doFinal(data.getBytes()));
using System;
using System.Security.Cryptography;
using System.Collections.Generic;
namespace Rextester {
public class Program {
  private string CreateToken(string message, string secret){
    secret = secret ?? "";
    var encoding = new System.Text.ASCIIEncoding();
    byte[] keyByte = encoding.GetBytes(secret);
    byte[] messageBytes = encoding.GetBytes(message);

    using (var hmacsha256 = new HMACSHA256(keyByte))
    {
      byte[] hashmessage = hmacsha256.ComputeHash(messageBytes);
      return Convert.ToBase64String(hashmessage);
    }
  }
  public static void Main(string[] args) {

    string secret = "<your_secret_key>";
    string data = "";  

    SortedDictionary<string, string> formParams = new SortedDictionary<string, string>();
    formParams.Add("appId", "<your_app_id>");
    formParams.Add("orderId", "FEX101");
    formParams.Add("orderAmount", "10.00");
    formParams.Add("orderCurrency", "INR");
    formParams.Add("orderNote", "Test payment");
    formParams.Add("customerName", "Customer Name");
    formParams.Add("customerPhone", "9900000085");
    formParams.Add("customerEmail", "[email protected]");
    formParams.Add("returnUrl", "http://example.com");
    formParams.Add("notifyUrl", "http://example.com");
    foreach (var kvp in formParams) {
      data = data + kvp.Key + kvp.Value;
    }
    Program n = new Program();
    string signature = n.CreateToken(data, secret);
    Console.WriteLine(signature);
    }
  }
}
Map<String, String> postData = new HashMap<String, String>();
  postData.put("appId", appId);
  postData.put("orderId", ORDERID);
  postData.put("orderAmount", ORDERAMOUNT);
  postData.put("orderCurrency", ORDER_CURRENCY);
  postData.put("orderNote", ORDERNOTE);
  postData.put("customerName", CUSTOMER_NAME);
  postData.put("customerEmail", CUSTOMER_EMAIL);
  postData.put("customerPhone", CUSTOMER_PHONE);
  postData.put("returnUrl",RETURN_URL);
  postData.put("notifyUrl", NOTIFY_URL);
  String data = "";
  SortedSet<String> keys = new TreeSet<String>(postData.keySet());
  for (String key : keys) {
      data = data + key + postData.get(key);
  }
  Mac sha256_HMAC = Mac.getInstance("HmacSHA256");
  SecretKeySpec secret_key_spec = new
  SecretKeySpec(secretKey.getBytes(),"HmacSHA256");
  sha256_HMAC.init(secret_key_spec);
  String signature = Base64.getEncoder().encodeToString(sha256_HMAC.doFinal(data.getBytes()));
using System;
using System.Security.Cryptography;
using System.Collections.Generic;
namespace Rextester {
public class Program {
  private string CreateToken(string message, string secret){
    secret = secret ?? "";
    var encoding = new System.Text.ASCIIEncoding();
    byte[] keyByte = encoding.GetBytes(secret);
    byte[] messageBytes = encoding.GetBytes(message);

    using (var hmacsha256 = new HMACSHA256(keyByte))
    {
      byte[] hashmessage = hmacsha256.ComputeHash(messageBytes);
      return Convert.ToBase64String(hashmessage);
    }
  }
  public static void Main(string[] args) {

    string secret = "<your_secret_key>";
    string data = "";  

    SortedDictionary<string, string> formParams = new SortedDictionary<string, string>();
    formParams.Add("appId", "<your_app_id>");
    formParams.Add("orderId", "FEX101");
    formParams.Add("orderAmount", "10.00");
    formParams.Add("orderCurrency", "INR");
    formParams.Add("orderNote", "Test payment");
    formParams.Add("customerName", "Customer Name");
    formParams.Add("customerPhone", "9900000085");
    formParams.Add("customerEmail", "[email protected]");
    formParams.Add("returnUrl", "http://example.com");
    formParams.Add("notifyUrl", "http://example.com");
    foreach (var kvp in formParams) {
      data = data + kvp.Key + kvp.Value;
    }
    Program n = new Program();
    string signature = n.CreateToken(data, secret);
    Console.WriteLine(signature);
    }
  }

Submit Checkout Form

Once you have the checkout form prepared, paste below HTML just before the closing tag. By default all the fields in the above HTML form are hidden, you can make them visible by removing the type="hidden" text from every input field.

<input type="submit" value="Pay">

Do not add a name parameter to the HTML submit button.

Alternatively, you can submit the above form automatically on page load without waiting for the user's click. To do this, paste the below javascript code just before the closing body tag.

 <script>document.getElementById("redirectForm").submit();</script>

Webhook Notification

Webhooks are events that notify you about the payment. A notification is sent to your backend from Cashfree when payments are successful. These notifications are useful in cases when the internet connection is unstable or slow while the payment is being processed. This will allow you to reconcile all the successful orders at your end. Notifications will be sent to notifyUrl which is a part of the request parameter specified while creating an order request.

📘

  • Notifications are sent only for successful payments.
  • Sometimes you may receive the same notification more than once. It is recommended to ensure that your implementation of the webhook is idempotent.

Response Parameters

CashFree sends details about every transaction to both returnUrl and the notifyUrl. These parameters will be posted to the services you host on these URLs.

The returnUrl is the webpage where your customer will be redirected to after completing the payment on the Cashfree payment page, we will post the response parameters to this page. Cashfree will also post form variables to notifyUrl you specify, which runs a program to process these variables.

ParameterDescription
orderIdOrder ID for which transaction has been processed.
Example, GZ-212
orderAmountBill amount of the order. Example, 256.00
referenceIdCashfree generated unique transaction ID. Example, 140388038803
txStatusPayment status for that order. Values can be: SUCCESS, FLAGGED, PENDING, FAILED, CANCELLED, USER_DROPPED.
paymentModePayment mode used by customers to make the payment. Example, DEBIT_CARD, PREPAID_CARD, MobiKwik.
txMsgMessage related to the transaction. Payment failure reason is included here.
txTimeTime of the transaction
signatureResponse signature.

Response Verification

Similar to every request signature, we send a digital signature in our response message. We recommend you verify this response signature to check the authenticity of the transaction response. This will ensure that the response has not tampered.

<?php  
 $orderId = $_POST["orderId"];
 $orderAmount = $_POST["orderAmount"];
 $referenceId = $_POST["referenceId"];
 $txStatus = $_POST["txStatus"];
 $paymentMode = $_POST["paymentMode"];
 $txMsg = $_POST["txMsg"];
 $txTime = $_POST["txTime"];
 $signature = $_POST["signature"];
 $data = $orderId.$orderAmount.$referenceId.$txStatus.$paymentMode.$txMsg.$txTime;
 $hash_hmac = hash_hmac('sha256', $data, $secretkey, true) ;
 $computedSignature = base64_encode($hash_hmac);
 if ($signature == $computedSignature) {
    // Proceed
  } else {
   // Reject this call
 }
 ?>
import hashlib
import hmac
import base64

@app.route('/notify_url/', methods=["POST"])
def notify_url_process():

 postData = {
  "orderId" : request.form['orderId'], 
  "orderAmount" : request.form['orderAmount'], 
  "referenceId" : request.form['referenceId'], 
  "txStatus" : request.form['txStatus'], 
  "paymentMode" : request.form['paymentMode'], 
  "txMsg" : request.form['txMsg'], 
  "txTime" : request.form['txTime'], 
 }

 signatureData = postData["orderId"] + postData["orderAmount"] + postData["referenceId"] + postData["txStatus"] + postData["paymentMode"] + postData["txMsg"] + postData["txTime"]

 message = bytes(signatureData).encode('utf-8')
 #get secret key from your config
 secret = bytes(secretKey).encode('utf-8')
 signature = base64.b64encode(hmac.new(secret, 
   message,digestmod=hashlib.sha256).digest())
LinkedHashMap<String, String> postData = new LinkedHashMap<String, String>();

postData.put("orderId", ORDERID);
postData.put("orderAmount", ORDERAMOUNT);
postData.put("referenceId", REFERENCE_ID);
postData.put("txStatus", TXN_STATUS);
postData.put("paymentMode", PAYMENT_MODE);
postData.put("txMsg", TX_MSG);
postData.put("txTime", TX_TIME);

String data = "";
Set<String> keys = postData.keySet();

for (String key : keys) {
    data = data + postData.get(key);
}
String secretKey = "" // Get secret key from config;
Mac sha256_HMAC = Mac.getInstance("HmacSHA256");
SecretKeySpec secret_key_spec = new
SecretKeySpec(secretKey.getBytes(),"HmacSHA256");
sha256_HMAC.init(secret_key_spec);

String signature = Base64.getEncoder().encodeToString(sha256_HMAC.doFinal(data.getBytes()));
using System;
using System.Security.Cryptography;
using System.Collections.Generic;
namespace Rextester {
  public class Program {
    private string CreateToken(string message, string secret){
      secret = secret ?? "";
      var encoding = new System.Text.ASCIIEncoding();
      byte[] keyByte = encoding.GetBytes(secret);
      byte[] messageBytes = encoding.GetBytes(message);
      
      using (var hmacsha256 = new HMACSHA256(keyByte))
      {
        byte[] hashmessage = hmacsha256.ComputeHash(messageBytes);
        return Convert.ToBase64String(hashmessage);
      }
    }

    public static void Main(string[] args) {
        
      string secret = "<your_secret_key>";
      string data = "";  
        
      data = data + "FEX101";
      data = data + "10.00";
      data = data + "19992";
      data = data + "SUCCESS";
      data = data + "pg";
      data = data + "payment done";
      data = data + "2018-02-02 17:29:12";

      Program n = new Program();
      string signature = n.CreateToken(data, secret);
      Console.WriteLine(signature);
    }
  }
}

Integration Kits

The integration kits for all major platforms are available below:

Test the Integration

After the integration is complete, you can test the flow of the transaction before you start accepting payments online. Click here to know how to view/generate API keys.

You can make a test transaction using the test card and net banking details available below. You can verify the payment status using the PG Dashboard, APIs, or webhooks. After completing the test, you can start accepting payments from your customers in real-time.

Card Details

Card NumberExpiryCVVName
4444 3333 2222 111107/23123Test
4111 1111 1111 111107/23123Test

*Netbanking Details

BankPayment Code
Test Bank3333

Test Signature

Generate a signature and verify it using the checksum tool available here.

If you see the message, Failed to verify merchant credentials, check and correct the details you provided in the checksum tool.

Important

We have decided to close down our old integration methods (standard checkout, seamless basic and seamless pro). We suggest you head over to the new APIs to complete your integration.

Read more here.