I'm using Paypal Express Checkout on my website and i receive this error:
SetExpressCheckout API call failed. Detailed Error Message: The totals of the cart item amounts do not match order amounts.Short Error Message: Transaction refused because of an invalid argument. See additional error messages for details.Error Code: 10413Error Severity Code: Error
When i enter a quantity of 1 everything is working fine but when i enter 2 or more i get the error.
I'm using SMARTY Templating.
<form class="pull-right" action="../Checkout/paypal_ec_redirect.php" method="POST">
<input type="hidden" name="L_PAYMENTREQUEST_0_NAME0" value="{$product_naam}"></input>
<input type="hidden" name="L_PAYMENTREQUEST_0_AMT0" value="{$product_productprijs}"></input>
<input type="hidden" name="L_PAYMENTREQUEST_0_QTY0" value="{$product_aantal}"></input>
<input type="hidden" name="PAYMENTREQUEST_0_ITEMAMT" value="{$product_subtotaal}"></input>
<input type="hidden" name="PAYMENTREQUEST_0_TAXAMT" value="{$product_btw}"></input>
<input type="hidden" name="PAYMENTREQUEST_0_AMT" value="{$product_totaalprijs}"></input>
<input type="hidden" name="currencyCodeType" value="EUR"></input>
<input type="hidden" name="paymentType" value="Sale"></input>
<input type="image" src="https://www.paypalobjects.com/webstatic/en_US/i/buttons/checkout-logo-large.png" alt="Check out with PayPal"></input>
</form>
</div>
</div>
</div>
Here is the PHP:
foreach ($getproduct as $row) {
$productaantal = $aantalbesteld;
$productnaam = $row['naam'];
$productprijs = $row['prijs'];
$btwtarief = $row['btw_tarief'];
$btwbedrag = ($productprijs*$aantalbesteld)/100*$btwtarief;
$subtotaal = ($productprijs*$aantalbesteld)-$btwbedrag;
$totaalprijs = $productprijs*$aantalbesteld;
}
//Product
$smarty->assign('product_naam', $productnaam);
$smarty->assign('product_aantal', $productaantal);
$smarty->assign('product_prijs', money_format('%.2n', $productprijs));
$smarty->assign('product_subtotaal', money_format('%.2n', $subtotaal));
$smarty->assign('product_btw', money_format('%.2n', $btwbedrag));
$smarty->assign('product_totaalprijs', money_format('%.2n', $totaalprijs));
$smarty->assign('product_bestelknop', 'Bestellen');
EDIT: Even this isn't working:
<form class="pull-right" action="../Checkout/paypal_ec_redirect.php" method="POST">
<input type="hidden" name="L_PAYMENTREQUEST_0_NAME0" value="{$product_naam}"></input>
<input type="hidden" name="L_PAYMENTREQUEST_0_AMT0" value="5.00"></input>
<input type="hidden" name="L_PAYMENTREQUEST_0_QTY0" value="2"></input>
<input type="hidden" name="PAYMENTREQUEST_0_ITEMAMT" value="10.00"></input>
<input type="hidden" name="PAYMENTREQUEST_0_TAXAMT" value="2.10"></input>
<input type="hidden" name="PAYMENTREQUEST_0_AMT" value="12.10"></input>
<input type="hidden" name="currencyCodeType" value="EUR"></input>
<input type="hidden" name="paymentType" value="Sale"></input>
<input type="image" src="https://www.paypalobjects.com/webstatic/en_US/i/buttons/checkout-logo-large.png" alt="Check out with PayPal"></input>
</form>
It says when they multiply quantity and amount it doesn't add up to what you specify as totalamount
$btwbedrag = ($productprijs*$aantalbesteld)/100*$btwtarief;
$subtotaal = ($productprijs*$aantalbesteld)-$btwbedrag;
$totaalprijs = $productprijs*$aantalbesteld;
Your VAT is calculated by taking 1% of the total price amount multiply by VAT rate. This assumes your product amounts are exclusive VAT.
Then in the next line you remove VAT from $subtotaal, why? It wasn't included in the first place. Or if it was then you should divide by 121 instead of 100.
$totaalprijs seems to be calculated assuming VAT is included already.
Did you check the values of your hidden fields in the source of your page?
When I changed the qty to 2, this is the request that is sent to PayPal.
paymentrequest_0_currencycode "EUR"
paymentrequest_0_amt "89.90"
paymentrequest_0_itemamt "71.02"
paymentrequest_0_taxamt "18.88"
paymentrequest_0_paymentaction "Sale"
paymentrequest_0_name "Sweaters van Superdry"
paymentrequest_0_qty "2"
Ideally, the request should be like this:
paymentrequest_0_itemamt=71.02
paymentrequest_0_taxamt=18.88
paymentrequest_0_amt=89.90
L_PAYMENTREQUEST_0_NAME0 = Sweaters van Superdry
L_PAYMENTREQUEST_0_AMT0= 35.51
L_PAYMENTREQUEST_0_QTY0= 2
This is causing the problem.
There is no paymentrequest_0_qty parameter.
You can test it here :
https://api-3t.sandbox.paypal.com/nvp?&user=us-30_api1.cri.com&pwd=EYFNSNUSV85CT34Z&signature=AH57zE.nAaElaFFAysViNA9TIte1AxtSpBjx2HLqHJOiu2js3l1Kd48i&version=70.0&METHOD=SetExpressCheckout&RETURNURL=http://www.paypal.com/test.php&CANCELURL=http://www.paypal.com/test.php&PAYMENTACTION=Sale&paymentrequest_0_itemamt=71.02&paymentrequest_0_taxamt=18.88&paymentrequest_0_amt=89.90&L_PAYMENTREQUEST_0_NAME0=Sweateranuperdry&L_PAYMENTREQUEST_0_AMT0=35.51&L_PAYMENTREQUEST_0_QTY0=2
Just click/copy-pasate the link above and see the reponse
Related
I have created a non-hosted PayPal-Button with a text input to let users define an amount to pay. It's a subscription button.
Now the problem is that there must be a minimum amount to pay, say 101 (CHF - Swiss francs).
According to the docs of PayPal HTML-Variables I have the possibility to add the following vars in hidden inputs to my form to get it to work.
set_customer_limit with a value of max_limit_own
min_amount with a value of 101
The set_customer_limit is working but not the min_amount. Any amount is accepted.
I opened a ticket at the technical support, but no reply till now.
Here's my form:
<form action="https://www.paypal.com/cgi-bin/webscr" method="post" target="_top">
<input type="hidden" name="cmd" value="_xclick-subscriptions">
<!-- //... -->
<input type="hidden" name="cancel_return" value="mydomain.com/cancel">
<input type="hidden" name="return" value="mydomain.com/paid">
<input type="hidden" name="token" value="<?php echo $token; ?>">
<input type="hidden" name="src" value="1">
<input type="text" name="a3" value="101.00">
<input type="hidden" name="p3" value="1">
<input type="hidden" name="t3" value="Y">
<input type="hidden" name="currency_code" value="CHF">
<input type="hidden" name="bn" value="PP-SubscriptionsBF:btn_subscribeCC_LG.gif:NonHostedGuest">
<!-- the concerned inputs -->
<input type="hidden" name="set_customer_limit" value="max_limit_own">
<input type="hidden" name="min_amount" value="101">
<!-- ---- -->
<input type="image" src="https://www.paypalobjects.com/de_DE/CH/i/btn/btn_subscribeCC_LG.gif" border="0" name="submit" alt="Jetzt einfach, schnell und sicher online bezahlen – mit PayPal.">
<img alt="" border="0" src="https://www.paypalobjects.com/de_DE/i/scr/pixel.gif" width="1" height="1">
</form>
As for the moment, I just validate the minimum amount with JavaScript, which isn't really secure...
EDIT
As an idea, I could implement another form (submit it by AJAX, onchange, onkeyup, whatever), which sets the minimum amount given by the user before the PayPal-form and put it into the PayPal-input then (set to hidden again):
<input type="hidden" name="a3" value="<?php echo $_POST['pre_min_amount'] ?>">
That way I could validate the minimum amount with PhP, before submitting the PayPal-form. But that doesn't seem a clean way to me. Really Glad if anybody could give me a hint!
The answer of the PayPal technical support is: No it is not possible!
(Date of answering was 05/02/2015) Hopefully, this will be possible in the future. If so please post your answer!
I'd really suggest using the PayPal API for this kind of thing (including creating a developer account, byting thru the docs, etc).
So this "solution" is a quick & dirty workaround.
First, add a small form (I call it the min_amount -form for now) to the page (telling the user, he has to set the amount first):
<form id="min_amount" method="post" action="<?php echo $_SERVER['PHP_SELF'] ?>">
<input type="text" id="pre_min_amount" name="pre_min_amount" value="101">
<input type="submit" value="Set min. Amount">
</form>
Then, add the whole PayPal form to a PHP variable with NowDoc and add the posted value from the min_amount-form to the a3 input:
$min_amount = 0;
$payPalForm = <<<SOME
<form action="https://www.paypal.com/cgi-bin/webscr" method="post" target="_top">
<!-- //... -->
<input type="hidden" name="a3" value="$min_amount">
</form>
SOME;
After submitting, check if the minimum amount is true and then only show the PayPal-form:
if (isset($_POST['pre_min_amount']) && is_numeric($_POST['pre_min_amount']) && floatval($_POST['pre_min_amount']) >= 101) {
$min_amount = htmlspecialchars($_POST['pre_min_amount']);
echo $payPalForm;
}
As I said, it's quick and dirty (no more time for this project), but you ensure to validate the minimum amount on the server-side, not just with Javascript. You could also submit the min_amount-form with an AJAX call, but then the return of this call is on the client-side, which isn't really secure either. (Sure you may also)
BTW, I am not proud of this solution at all, but sometimes, a programmers life is hard and I'm sure all you coders out there had to do some q&d code somehow, somewhere ;-)...
Update: 08/05/2015
All depends on the country in which the concerning account is registered. Full services guaranted by PayPal only in the USA and Canada
I am implementing Sagepay payment gateway in PHP, it is working fine with 2.23 protocol. But when i change it to 3.00 it gives my an error code: 3195, which means that the line item amount details do not add up correctly.
I have tried all the solutions but nothing helped me.
Here is some of my code which I am using currently:
$sagePay = new SagePay();
$sagePay->setCurrency('GBP');
$sagePay->setAmount($_SESSION['amount']);
$sagePay->setDescription($_SESSION['tripcode']);
$sagePay->setBillingSurname('Mustermann');
$sagePay->setBillingFirstnames('Amrinder');
$sagePay->setBillingCity('London');
$sagePay->setBillingPostCode('GL51 3AA');
$sagePay->setBillingAddress1('Bahnhofstr. 1');
$sagePay->setBillingCountry('de');
$sagePay->setDeliverySameAsBilling();
<form method="POST" id="SagePayForm" action="https://live.sagepay.com/gateway/service/vspform-register.vsp" style="display:none;">
<input type="hidden" name="VPSProtocol" value= "2.23">
<input type="hidden" name="TxType" value= "PAYMENT">
<input type="hidden" name="Vendor" value= "alpinetravelint">
<input type="hidden" name="Crypt" value= "<?php echo $sagePay->getCrypt(); ?>">
<input type="submit" value="continue to SagePay">
</form>
How can I resolve this problem?
The error refers to the basket field. You have the first item value as 100, tax as 10 and the line total as 100.
The fields in the basket are Quantity:Item Value:Item Tax:Item Total:Line Total
The item value should be the net amount if you are going to use the tax field, so your values should be 1:90.00:10.00:100.00:100.00
I am using the following code to integrate PayPal Payment System to my website and after the payment I am getting the following Notices and "Payment Failed" even when everything went smooth.
Notice: Undefined index: item_name in /Applications/XAMPP/xamppfiles/htdocs/payment/success.php on line 2
Notice: Undefined index: tx in /Applications/XAMPP/xamppfiles/htdocs/payment/success.php on line 3
Notice: Undefined index: amount in /Applications/XAMPP/xamppfiles/htdocs/payment/success.php on line 4
Notice: Undefined index: currency_code in /Applications/XAMPP/xamppfiles/htdocs/payment/success.php on line 5
Payment Failed
I am using the following code to create the payment button
<div class="btn">
<form action="<?php echo $paypal_url ?>" method="post" name="frmPayPal1">
<input type="hidden" name="business" value="<?php echo $paypal_id ?>">
<input type="hidden" name="cmd" value="_xclick">
<input type="hidden" name="item_name" value="20Percents (12 Credits)">
<input type="hidden" name="item_number" value="1">
<input type="hidden" name="credits" value="12">
<input type="hidden" name="userid" value="1">
<input type="hidden" name="amount" value="10">
<input type="hidden" name="cpp_header_image" value="http://20percents.com/wp-content/uploads/2014/06/logo-1.png">
<input type="hidden" name="no_shipping" value="1">
<input type="hidden" name="currency_code" value="USD">
<input type="hidden" name="handling" value="0">
<input type="hidden" name="cancel_return" value="http://localhost/payment/cancel.php">
<input type="hidden" name="return" value="http://localhost/payment/success.php">
<input type="image" src="https://www.sandbox.paypal.com/en_US/i/btn/btn_buynowCC_LG.gif" border="0" name="submit" alt="PayPal - The safer, easier way to pay online!">
<img alt="" border="0" src="https://www.sandbox.paypal.com/en_US/i/scr/pixel.gif" width="1" height="1">
</form>
And, the following code to verify the payment:
<?php
$item_name = $_GET['item_name']; // I also tried $_REQUEST['item_name']; instead
$item_transaction = $_GET['tx']; // Paypal transaction ID
$item_price = $_GET['amount']; // Paypal received amount
$item_currency = $_GET['currency_code']; // Paypal received currency type
$price = '10.00';
$currency='USD';
//Rechecking the product price and currency details
if($item_price==$price && $item_currency==$currency)
{
$content = "<h1>Welcome, Guest</h1>";
$content .= "<h1>Payment Successful</h1>";
}
else
{
$content = "<h1>Payment Failed</h1>";
}
?>
I don't know why I am receiving these notices, any help is highly appreciated. Thanks
The method you gave in form is POST. But getting values using $_GET[].
Change form to
<form action="<?php echo $paypal_url ?>" method="get" name="frmPayPal1">
or change
$item_name = $_GET['item_name'];
to
$item_name = $_POST['item_name'];
Follow these steps to configure your account for PDT:
Log in to your PayPal account.
Click the Profile subtab.
Click Website Payment Preferences in the Seller Preferences column.
Under Auto Return for Website Payments, click the On radio button.
For the Return URL, enter the URL on your site that will receive the transaction ID posted by PayPal after a customer payment.
Under Payment Data Transfer, click the On radio button.
Click Save.
Click Website Payment Preferences in the Seller Preferences column.
Scroll down to the Payment Data Transfer section of the page to view your PDT identity token.
I know this is old, but these parameters worked for me with $_POST method. I added them to my ipn.php file
$item_transaction = $_POST['txn_id'];
$item_price = $_POST['mc_gross'];
$item_currency = $_POST['mc_currency'];
i am using Virtual Merchant online payment.
i have one demo account :
https://demo.myvirtualmerchant.com/VirtualMerchantDemo/login.do
Account ID: 002549
User ID : 002549
Password : Abcd.1234gd
the submitting form code:
<form action="https://demo.myvirtualmerchant.com/VirtualMerchantDemo/process.do" method="POST">
<input type="hidden" name="ssl_amount" value="75.00">
<input type="hidden" name="ssl_merchant_id" value="002549">
<input type="hidden" name="ssl_user_id" value="002549">
<input type="hidden" name="ssl_pin" value="2R56WU">
<input type="hidden" name="ssl_transaction_type" value="ccsale">
<input type="hidden" name="ssl_show_form" value="true">
<input type="hidden" name="ssl_cvv2cvc2_indicator" value="1">
<input type="hidden" name="ssl_invoice_number" value="20131226">
<input type="hidden" name="ssl_customer_code" value="test demo">
<input type="hidden" name="ssl_email" value="demo#gmail.com">
<input type="submit" value="Pay Now" class="button1">
i got one test credit card number: 4005550000000019 from http://www.infomerchant.net/creditcardprocessing/credit_card_test_numbers.html
after submitting, the result is:
after clicking the process button, the result is :
the text is :
Error Code : 4000
Error Name : VID Not Supplied
Error Message : The VirtualMerchant ID was not supplied in the authorization request.
could you know how to fix it ? or any suggestion.
ssl_merchant_id: 002549
ssl_user_id: 002549
ssl_pin: 2R56WU (it is from demo account under menu: user=>change pin)
I encountered a similar issue. The culprit turned up on my end, before my form POSTed data to VirtualMerchant. Make sure the data/string(s) are properly encoded, without any stray white space.
Hello I would like to create a paypal buy button which has a dynamic set amount.
I would like to pass the amount by a text input field within the form and the item_number by a hidden field.
The issue is that what ever I do I get a encrypted s-xclick button from the paypal website.
This button does not allow hidden variables being placed in the form.
I think what I need is a xclick button. My goal is to allow users to increase their internally credit of my website.
EDIT (moving the addition to the question from the answer to the question)(from here #tokam:
To add this to the discussion I would like to show my current solution for the problem:
Here we have some Javascript validation which helps the user with the input. Recognize that it opens a lightbox on success
function validatePaypalForm()
{
var val = $('#paypalPaymentAmount').val().replace(/\s*$/, "").replace(/,/ , ".").replace(/€$/, "");
var errormsg = '';
var ret, amountField;
if( val==='' || isNaN( parseFloat(val) ) || !isFinite(val) )
{
errormsg = 'Bitte geben Sie einen gültigen Betrag an';
}else if( parseFloat( val ) < <?php echo $this->minimum?> )
{
errormsg = 'Das Einzahlungsminimum beträgt <?php echo $this->minimum?>€';
}
ret = ( errormsg === '' );
amountField = $( '#paypalAmountField' );
if( ret )
{
amountField.removeClass( 'error' );
$('#paypalAmountErrorMessage').html( ' ' );
$('#paypalPaymentAmount').val( val );
fb.start(
'<p><strong>Sie werden in kürze zur Seite von Paypal weitergeleitet.</strong></p>',
'width:700 showPrint:false modal:true showClose:false showOuterClose:true showItemNumber:false closeOnNewWindow:false outsideClickCloses:true innerBorder:0 imageClickCloses:false scrolling: no'
);
}else{
amountField.addClass( 'error' );
$('#paypalAmountErrorMessage').html( errormsg );
}
return ret;
}
Here comes my button now. The issues I am having with are e.g. that it is easy for the user to set an other currency code. I could handle this in my IPN Listener by refunding the payment. Are there other issues which come with an unencrypted changeable button?
<form onsubmit="return validatePaypalForm();" class="stn-form" action="https://www.paypal.com/cgi-bin/webscr" method="post">
<fieldset id="fieldset-p"><legend><span>2.</span>myproject Guthaben aufladen per Paypal Zahlung</legend>
<div id='paypalAmountField' class="field">
<label for='paypalPaymentAmount' >Betrag €:</label>
<input id='paypalPaymentAmount' type="text" name='amount' value='' />
<span style='display:block;' id='paypalAmountErrorMessage' class='errorText'>' </span>
</div>
<input type="hidden" name="cmd" value="_xclick">
<input type="hidden" name="business" value="THE_ID_OF_MY_CLIENT">
<input type="hidden" name="lc" value="DE">
<input type="hidden" name="item_name" value="myproject Advertiser Vorkasse">
<input type="hidden" name='item_number' value="11500">
<input type="hidden" name="currency_code" value="EUR">
<input type="hidden" name="button_subtype" value="services">
<input type="hidden" name="no_note" value="1">
<input type="hidden" name="no_shipping" value="1">
<input type="hidden" name="bn" value="PP-BuyNowBF:btn_paynowCC_LG.gif:NonHosted">
<input type="hidden" name="rm" value="1">
<input type="hidden" name='cbt' value="Zu myproject.de zurückkehren">
<input type="hidden" name="currency_code" value="EUR">
<input type="hidden" name="return" value="http://myproject.somedomain.net/advertiser/guthaben-aufladen/ret/success" />
<input type="hidden" name="cancel_ return" value="http://myproject.somedomain.net/advertiser/guthaben-aufladen/ret/canceled" />
<div class="actionrow">
<input type="image" src="https://www.paypalobjects.com/de_DE/DE/i/btn/btn_paynowCC_LG.gif" border="0" name="submit" alt="Jetzt einfach, schnell und sicher online bezahlen – mit PayPal.">
<img alt="" border="0" src="https://www.paypalobjects.com/de_DE/i/scr/pixel.gif" width="1" height="1">
</div>
</fieldset>
</form>
The reason you can't override the amount dynamically, is because you have a so-called 'PayPal hosted button'.
With a hosted button, the amount is stored on PayPal's side and can't be overwritten with the 'amount' variable.
You'll either want to use a non-hosted button, or use the BMUpdateButton API call to dynamically update the button's amount.
To use a non-hosted button, simply find 'Step 2' in the button creation tool and untick 'Host button with PayPal'.
Option 2:
Still use the hosted button, and use the BMUpdateButton API to update the amount. An example request for BMUpdateButton would look as follows:
USER=Your API username
PWD=Your API password
SIGNATURE=Your API signature
VERSION=82.0
HOSTEDUBTTONID=The value of <input type="hidden" name="hosted_button_id" value="">
BUTTONTYPE=The type of button. E.g. BUYNOW
BUTTONCODE=The type of code you want to get back. E.g. HOSTED
L_BUTTONVAR0=amount=The new amount with a period as separator
L_BUTTONVAR1=item_name=Optional: a new item name if you wish
Similary, you could also use the BMCreateButton API to create a new button, or use the BMButtonSearch API to search through a list of all your stored hosted buttons (to find the hosted_button_id of your button automatically, for example)
The reason to use a hosted button is because it's more secure. A non-hosted, unencrypted button would basically leave the amounts open to manipulation. Fraudulent transactions waiting to happen.
you shouldn't use xclick which isn't encrypted . the way I solved this is using paypal button api - with some kind of caching in the client so you won't do the whole http request response every time.
note that paypal uses 2 types of api - the NVP which is sort of restful (also not really) and SOAP (I used the NVP method)
you could also generate the the encrypted button in your server using openssl - but I run into unsolvable problems with this method and couldn't get any help for that either here or in paypal horrible developer forums
edit: the problem with not encrypted buttons are that anyone using firebug (not talking about more advanced tools) could interecept a payment and change the cost etc'..
If you insist in that direction you could follow the simple html form from paypal to create this button. you do it in paypal site and create an unencrypted button and then just edit the html and change the needed field to <?php $variable?>. I would strongly advice against this path.
I think this might work for you if you update ... "you#yoursite.com" ... it's non encrypted and still seems to host on paypal's site for clearing
drop the: value="my_default_price"
if you want the user to enter it into a blank text box ... for my page, prices are tied to the price of gold, so I have to dynamically update the variable "amount" and i just leave off value=
<form action="https://www.paypal.com/cgi-bin/webscr" method="post">
<input type="hidden" name="cmd" value="_xclick">
<input type="hidden" name="business" value="you#yoursite.com">
<input type="hidden" name="item_name" value="example description">
<input type="hidden" name="item_number" value="">
<input type="text" name="amount" value="my_default_price">
<input type="hidden" name="no_shipping" value="1">
<input type="hidden" name="return" value="http://www.yoursite.com/returnpage.php">
<input type="hidden" name="currency_code" value="USD">
<input type="hidden" name="lc" value="US">
<input type="hidden" name="bn" value="PP-BuyNowBF">
<input type="image" src="https://www.paypal.com/en_US/i/btn/x-click-but02.gif" border="0" name="submit" alt="Make your payments with PayPal. It is free, secure, effective.">
<img alt="" border="0" src="https://www.paypal.com/it_IT/i/scr/pixel.gif" width="1" height="1">
</form>