404 Bad request: Unable to process transaction using sandbox testing payment integration in payfast

Hi team

I am passing some variables to payment integration testing using sandbox, but the problem i am getting 404 Bad request saying " amount: The amount field is required.

item_name: The item name field is required.

// payment_integration.php

<?php
// PayFast Integration Logic

// Get the order details from the checkout process
//$orderID = $_POST['order_id'];
//$products = $_POST['products'];
//$grandTotal = $_POST['grand_total'];
$amount = $_POST['amount'];
//$name = $_POST['name'];
//$email = $_POST['email'];
//$phone = $_POST['phone'];
//$address = $_POST['address'];

// Set your PayFast merchant details
$merchantID = '10010868'; // Replace with your actual merchant ID
$merchantKey = 'exnib****'; // Replace with your actual merchant key

// Set the PayFast URL based on your environment (testing or production)
$isTestingMode = true; // Set to true for testing environment or false for production environment
$payfastURL = $isTestingMode ? 'https://sandbox.payfast.co.za/eng/process' : 'https://www.payfast.co.za/eng/process';

// Generate the payment data
$data = array(
    'merchant_id' => $merchantID,
    'merchant_key' => $merchantKey,
    'return_url' => 'http://example.com/payment_success.php', // Replace with your actual success URL
    'cancel_url' => 'http://example.com/payment_cancel.php', // Replace with your actual cancel URL
    'notify_url' => 'http://example.com/payment_notify.php', // Replace with your actual notify URL
    'amount' => $amount,
    'item_name' => $description,
    'item_description' => $description,
    'email_address' => 'gcira2023@outlook.com', // Replace with the customer's email address
    'name_first' => 'John', // Replace with the customer's first name
    'name_last' => 'Doe', // Replace with the customer's last name
);

// Generate the signature for the payment data
$signature = md5(implode('', $data));

// Make sure the signature is exactly 32 characters long
if (strlen($signature) != 32) {
    die('Invalid signature length');
}

// Add the signature to the payment data
$data['signature'] = $signature;

// Create a hidden form with the payment data
echo "<form method='post' action='$payfastURL' id='payfastForm'>";
foreach ($data as $name => $value) {
    echo "<input type='hidden' name='$name' value='$value'>";
}
echo "<button type='submit'>Proceed to PayFast</button>";
echo "</form>";

// Automatically submit the form using JavaScript
echo "<script>document.getElementById('payfastForm').submit();</script>";
?>

// checkout.php(form fields)

<div class="container">
    <div class="row justify-content-center">
      <div class="col-lg-6 px-4 pb-4" id="order">
        <h4 class="text-center text-info p-2">Complete your order!</h4>
        <div class="jumbotron p-3 mb-2 text-center">
          <h6 class="lead"><b>Product(s) : </b><?= $allItems; ?></h6>
          <h6 class="lead"><b>Delivery Charge : </b>Free</h6>
		  <h6 class="lead"><b>Reference Number:</b><?=$referenceNumber?></h6>
          <h5><b>Total Amount Payable : </b><?= number_format($grand_total,2) ?>/-</h5>
        </div>
        <form method="post" action="payment_integration.php" id="placeOrder">
          <input type="hidden" name="products" value="<?= $allItems; ?>">
          <input type="hidden" name="grand_total" value="<?= $grand_total; ?>">
		  
          <div class="form-group">
            <input type="text" name="name" class="form-control" placeholder="Enter Name" required>
          </div>
          <div class="form-group">
            <input type="email" name="email" class="form-control" placeholder="Enter E-Mail" required>
          </div>
          <div class="form-group">
            <input type="tel" name="phone" class="form-control" placeholder="Enter Phone" required>
          </div>
          <div class="form-group">
            <textarea name="address" class="form-control" rows="3" cols="10" placeholder="Enter Delivery Address Here..."></textarea>
          </div>
          
                   
                    <div class="form-group" id="pay-now">
                        <button type="submit" class="btn btn-primary" >Proceed</button>
                    </div>
                
            </div>
        </div>
    </div>
</div>
        </form>
      </div>
    </div>
  </div>

so… where in your php file do you define $description?

payment_integration.php file

Show me a line where you define $description.

Also, your HTML form does not define a field for ‘amount’.

// define $description

// Generate the payment data

$data = array(
    'merchant_id' => $merchantID,
    'merchant_key' => $merchantKey,
    'return_url' => 'http://example.com/payment_success.php', // Replace with your actual success URL
    'cancel_url' => 'http://example.com/payment_cancel.php', // Replace with your actual cancel URL
    'notify_url' => 'http://example.com/payment_notify.php', // Replace with your actual notify URL
    'amount' => $amount,
    'item_name' => $description,
    'item_description' => $description,
    'email_address' => 'gcira2023@outlook.com', // Replace with the customer's email address
    'name_first' => 'John', // Replace with the customer's first name
    'name_last' => 'Doe', // Replace with the customer's last name
);

html form
// i did not defined the amount, tried to use hidden as a value as pass it <?$amount?>

that’s not DEFINING description, that’s USING description.

$description = "a thing";

is a definition.

Consider this:

$y = $x + 3;

What is the value of $y?

@m_hutley thanks i got it figured, how do i fix this one " signature: Generated signature does not match submitted signature".

Well, looking at the Documentation, the signature should be an MD5 of the array condensed into key=value with ampersand separators.

What you’re doing will generate a string with no separators and will only output the values.

You might want to look at http_build_query instead (or use the method they show in the documentation…).

This topic was automatically closed 91 days after the last reply. New replies are no longer allowed.