Page 5 of 6

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Fri Nov 29, 2013 11:58 am
by Eric!
You're close to understanding it. From button -> data to Paypal->User Buys->Returns to site. PayPal->processes payment->sends data to your Listener->Your Listener Processes->verifies->run checks to confirm valid purchase->processes purchase with both buyer and seller.

What you do to verify your payments, mark items sold, verify the purchaser, and other checks mentioned by paypal (which you've posted here) and in your code comments are up to you.

Read the PayPal instruction link in my answer viewtopic.php?f=1&t=138708&start=15#p689210 and study their diagrams so you can get a complete picture. In the instructions note that you are not using the API. You are using button forms with IPN, the other stuff about the API you can skip.

Here is a sample database structure for logging ALL your IPN activity. This would be something you just insert each new record into. This logs subscriptions, reoccurring payments, all sorts of options. etc.

[text]-- Table structure for table `instant_payment_notifications`

CREATE TABLE IF NOT EXISTS `instant_payment_notifications` (
`id` varchar(36) COLLATE utf8_unicode_ci NOT NULL,
`pay_key` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL,
`sell_file_id` int(11) DEFAULT NULL,
`valid` tinyint(1) NOT NULL DEFAULT '0',
`notify_version` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'IPN Version Number',
`verify_sign` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Encrypted string used to verify the authenticity of the tansaction',
`test_ipn` tinyint(1) DEFAULT NULL,
`address_city` varchar(40) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'City of customers address',
`address_country` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Country of customers address',
`address_country_code` varchar(2) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Two character ISO 3166 country code',
`address_name` varchar(128) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Name used with address (included when customer provides a Gift address)',
`address_state` varchar(40) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'State of customer address',
`address_status` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'confirmed/unconfirmed',
`address_street` varchar(200) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Customer''s street address',
`address_zip` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Zip code of customer''s address',
`first_name` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Customer''s first name',
`last_name` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Customer''s last name',
`payer_business_name` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Customer''s company name, if customer represents a business',
`payer_email` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Customer''s primary email address. Use this email to provide any credits',
`payer_id` varchar(13) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Unique customer ID.',
`payer_status` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'verified/unverified',
`contact_phone` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Customer''s telephone number.',
`residence_country` varchar(2) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Two-Character ISO 3166 country code',
`business` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Email address or account ID of the payment recipient (that is, the merchant). Equivalent to the values of receiver_email (If payment is sent to primary account) and business set in the Website Payment HTML.',
`item_name` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Item name as passed by you, the merchant. Or, if not passed by you, as entered by your customer. If this is a shopping cart transaction, Paypal will append the number of the item (e.g., item_name_1,item_name_2, and so forth).',
`item_number` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Pass-through variable for you to track purchases. It will get passed back to you at the completion of the payment. If omitted, no variable will be passed back to you.',
`quantity` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Quantity as entered by your customer or as passed by you, the merchant. If this is a shopping cart transaction, PayPal appends the number of the item (e.g., quantity1,quantity2).',
`receiver_email` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Primary email address of the payment recipient (that is, the merchant). If the payment is sent to a non-primary email address on your PayPal account, the receiver_email is still your primary email.',
`receiver_id` varchar(13) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Unique account ID of the payment recipient (i.e., the merchant). This is the same as the recipients referral ID.',
`custom` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Custom value as passed by you, the merchant. These are pass-through variables that are never presented to your customer.',
`invoice` varchar(127) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Pass through variable you can use to identify your invoice number for this purchase. If omitted, no variable is passed back.',
`memo` varchar(1000) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Memo as entered by your customer in PayPal Website Payments note field.',
`option_name1` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Option name 1 as requested by you',
`option_name2` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Option 2 name as requested by you',
`option_selection1` varchar(200) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Option 1 choice as entered by your customer',
`option_selection2` varchar(200) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Option 2 choice as entered by your customer',
`tax` float(10,2) DEFAULT NULL COMMENT 'Amount of tax charged on payment',
`auth_id` varchar(19) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Authorization identification number',
`auth_exp` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Authorization expiration date and time, in the following format: HH:MM:SS DD Mmm YY, YYYY PST',
`auth_amount` int(11) DEFAULT NULL COMMENT 'Authorization amount',
`auth_status` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Status of authorization',
`num_cart_items` int(11) DEFAULT NULL COMMENT 'If this is a PayPal shopping cart transaction, number of items in the cart',
`parent_txn_id` varchar(19) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'In the case of a refund, reversal, or cancelled reversal, this variable contains the txn_id of the original transaction, while txn_id contains a new ID for the new transaction.',
`payment_date` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Time/date stamp generated by PayPal, in the following format: HH:MM:SS DD Mmm YY, YYYY PST',
`payment_status` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Payment status of the payment',
`payment_type` varchar(10) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'echeck/instant',
`pending_reason` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'This variable is only set if payment_status=pending',
`reason_code` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'This variable is only set if payment_status=reversed',
`remaining_settle` int(11) DEFAULT NULL COMMENT 'Remaining amount that can be captured with Authorization and Capture',
`shipping_method` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'The name of a shipping method from the shipping calculations section of the merchants account profile. The buyer selected the named shipping method for this transaction',
`shipping` float(10,2) DEFAULT NULL COMMENT 'Shipping charges associated with this transaction. Format unsigned, no currency symbol, two decimal places',
`transaction_entity` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Authorization and capture transaction entity',
`txn_id` varchar(19) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'A unique transaction ID generated by PayPal',
`txn_type` varchar(20) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'cart/express_checkout/send-money/virtual-terminal/web-accept',
`exchange_rate` float(10,2) DEFAULT NULL COMMENT 'Exchange rate used if a currency conversion occured',
`mc_currency` varchar(3) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Three character country code. For payment IPN notifications, this is the currency of the payment, for non-payment subscription IPN notifications, this is the currency of the subscription.',
`mc_fee` float(10,2) DEFAULT NULL COMMENT 'Transaction fee associated with the payment, mc_gross minus mc_fee equals the amount deposited into the receiver_email account. Equivalent to payment_fee for USD payments. If this amount is negative, it signifies a refund or reversal, and either ofthose p',
`mc_gross` float(10,2) DEFAULT NULL COMMENT 'Full amount of the customer''s payment',
`mc_handling` float(10,2) DEFAULT NULL COMMENT 'Total handling charge associated with the transaction',
`mc_shipping` float(10,2) DEFAULT NULL COMMENT 'Total shipping amount associated with the transaction',
`payment_fee` float(10,2) DEFAULT NULL COMMENT 'USD transaction fee associated with the payment',
`payment_gross` float(10,2) DEFAULT NULL COMMENT 'Full USD amount of the customers payment transaction, before payment_fee is subtracted',
`settle_amount` float(10,2) DEFAULT NULL COMMENT 'Amount that is deposited into the account''s primary balance after a currency conversion',
`settle_currency` varchar(3) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Currency of settle amount. Three digit currency code',
`auction_buyer_id` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'The customer''s auction ID.',
`auction_closing_date` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'The auction''s close date. In the format: HH:MM:SS DD Mmm YY, YYYY PSD',
`auction_multi_item` int(11) DEFAULT NULL COMMENT 'The number of items purchased in multi-item auction payments',
`for_auction` varchar(10) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'This is an auction payment - payments made using Pay for eBay Items or Smart Logos - as well as send money/money request payments with the type eBay items or Auction Goods(non-eBay)',
`subscr_date` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Start date or cancellation date depending on whether txn_type is subcr_signup or subscr_cancel',
`subscr_effective` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Date when a subscription modification becomes effective',
`period1` varchar(10) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT '(Optional) Trial subscription interval in days, weeks, months, years (example a 4 day interval is 4 D',
`period2` varchar(10) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT '(Optional) Trial period',
`period3` varchar(10) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Regular subscription interval in days, weeks, months, years',
`amount1` float(10,2) DEFAULT NULL COMMENT 'Amount of payment for Trial period 1 for USD',
`amount2` float(10,2) DEFAULT NULL COMMENT 'Amount of payment for Trial period 2 for USD',
`amount3` float(10,2) DEFAULT NULL COMMENT 'Amount of payment for regular subscription period 1 for USD',
`mc_amount1` float(10,2) DEFAULT NULL COMMENT 'Amount of payment for trial period 1 regardless of currency',
`mc_amount2` float(10,2) DEFAULT NULL COMMENT 'Amount of payment for trial period 2 regardless of currency',
`mc_amount3` float(10,2) DEFAULT NULL COMMENT 'Amount of payment for regular subscription period regardless of currency',
`recurring` varchar(1) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Indicates whether rate recurs (1 is yes, blank is no)',
`reattempt` varchar(1) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Indicates whether reattempts should occur on payment failure (1 is yes, blank is no)',
`retry_at` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Date PayPal will retry a failed subscription payment',
`recur_times` int(11) DEFAULT NULL COMMENT 'The number of payment installations that will occur at the regular rate',
`username` varchar(64) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT '(Optional) Username generated by PayPal and given to subscriber to access the subscription',
`password` varchar(24) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT '(Optional) Password generated by PayPal and given to subscriber to access the subscription (Encrypted)',
`subscr_id` varchar(19) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'ID generated by PayPal for the subscriber',
`case_id` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Case identification number',
`case_type` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'complaint/chargeback',
`case_creation_date` varchar(28) COLLATE utf8_unicode_ci DEFAULT NULL COMMENT 'Date/Time the case was registered',
`log_default_shipping_address_in_transaction` tinyint(1) DEFAULT NULL,
`action_type` varchar(25) COLLATE utf8_unicode_ci NOT NULL,
`ipn_notification_url` varchar(64) COLLATE utf8_unicode_ci NOT NULL,
`charset` varchar(25) COLLATE utf8_unicode_ci NOT NULL,
`transaction_type` varchar(25) COLLATE utf8_unicode_ci NOT NULL,
`cancel_url` varchar(64) COLLATE utf8_unicode_ci NOT NULL,
`sender_email` varchar(127) COLLATE utf8_unicode_ci NOT NULL,
`fees_payer` varchar(25) COLLATE utf8_unicode_ci NOT NULL,
`return_url` varchar(64) COLLATE utf8_unicode_ci NOT NULL,
`reverse_all_parallel_payments_on_error` tinyint(1) DEFAULT NULL,
`status` varchar(25) COLLATE utf8_unicode_ci NOT NULL,
`payment_request_date` datetime NOT NULL,
`ip` varchar(16) COLLATE utf8_unicode_ci DEFAULT NULL,
`raw` text COLLATE utf8_unicode_ci NOT NULL,
`created` datetime DEFAULT NULL,
`modified` datetime DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `pay_key` (`pay_key`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
[/text]

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Mon Dec 02, 2013 8:46 am
by simonmlewis
[if anyone else has anything to add, please feel free - it's not a private convo between me and Eric]

Just for now although I need to collate all data being passed, I just want to learn how to get the PRICE - to ensure that is right.
Once I have grasped that, I am certain the rest will fall into place, as will become more obvious to me.

The bits I still do not understand - and apologies if they have been instructed but still... are:

1) how does that Transaction ID get into my button code?? Is it a PayPal script I put in there, and with some reference to my Listener script, it talks to PayPal and gets the ID there "from PayPal"??
2) if the above is as I am guessing, I therefore assume the data in that button is POSTed to PayPal.
3) PayPal does an IPN Listener at some stage in the process to check VIA MY IPN LISTENER to ask "is this price of £50.00 the same price of product ID 123". <runs query> Yes it is - ok good.
4) payment goes through anyway, returns back to my site.
5) because the payment amount was correct, it's been marked as sold in my DB_Products table.

HOWEVER....

...3) returns to me from within PayPal to ask my IPN LISTENER "is the price of Product ID 123 £0.50p"..... NO. Value = £50.00. OK.
4) user is returned to me, (is payment still taken???), and product not marked as sold, and I get tell the buyer on screen "sorry something has gone wrong, please contact the seller".

This is my own lamens terms. If this is not right, or in the wrong order, can you just (if it's that simple) move the numbers are?

Next, and I have asked this, but I think you feel I am more "cottoned on" to this than I really am - WHERE in that IPN listener code to I update my database? Where precisely, as I just don't see it.

There is VERIFIED, and INVALID. Saying "it goes there in VERIFIED" (for example), isn't enough. As you know yourself, ask someone every step it takes to make some tea, and they will always miss something. That has to be bang on!!

Thanks again. I honestly feel I'll get there, but this is clearly one of the toughest upgrades I've been learning.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Mon Dec 02, 2013 9:04 am
by simonmlewis
From button -> data to Paypal->User Buys->Returns to site. PayPal->processes payment->sends data to your Listener->Your Listener Processes->verifies->run checks to confirm valid purchase->processes purchase with both buyer and seller.

What you do to verify your payments, mark items sold, verify the purchaser, and other checks mentioned by paypal (which you've posted here) and in your code comments are up to you.
I missed commenting on this part of your message.
Are you saying once the buyer is taken back to my site after making payment, is isn't straight away taken to a page on my site where I run those "mark as sold" type queries?

Does that happen entirely separately via the listener instead?

Or is "the norm" the take them back to my page via the screenshot method I sent earlier, and "fake it".
Thanks for your payment, the item will be despatched and you will receive a confirmation email soon.
But in reality, the item will be marked as sold, IF the payment is the right one, via the Listener script?

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Mon Dec 02, 2013 9:17 am
by simonmlewis
Is this snippet correct?
So the data comes back from PayPal VERIFIED, and then checks my database.

Code: Select all

if (strcmp ($res, "VERIFIED") == 0) {
        // check whether the payment_status is Completed
        // check that txn_id has not been previously processed
        // check that receiver_email is your PayPal email
        // check that payment_amount/payment_currency are correct
        // process payment and mark item as paid.
        // assign posted variables to local variables
        
        $item_name = $_POST['item_name'];
        $item_number = $_POST['item_number'];
        $payment_status = $_POST['payment_status'];
        $payment_amount = $_POST['mc_gross'];
        $payment_currency = $_POST['mc_currency'];
        $txn_id = $_POST['txn_id'];
        $receiver_email = $_POST['receiver_email'];
        $payer_email = $_POST['payer_email'];
        
        include "dbconn.php";
        $query = "SELECT id FROM db_products WHERE id = :item_number AND price = :payment_amount";
$result = $pdo->prepare($query);
$result->execute(array(':item_number' => $item_number, ':payment_amount' => $payment_amount));
while ($row = $result->fetch(PDO::FETCH_OBJ)) 
  {
  // if the two match up, mark item as sold
  // if the two do NOT match up, inform the seller by email
  }
        
        
        if(DEBUG == true) {
                error_log(date('[Y-m-d H:i e] '). "Verified IPN: $req ". PHP_EOL, 3, LOG_FILE);
        }
}
I think the secondary bit "if the two do NOT match up" would have to come after it tho, and I'd do it as a count. But you get the flow...........
I'm still unclear tho where the TransID comes from on the Standard Payment Button. but I think I saw in that button is the URL of my listener???

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Mon Dec 02, 2013 4:59 pm
by Eric!
I don't know why I have to keep repeating myself. Either I'm not being clear or you're not paying attention. I'm repeating all this again for at least the 2nd time.

The transaction ID can not be done in the front end. It comes from paypal AFTER the transaction is done and the ID is generated. It is there in your code...$txn_id = $_POST['txn_id']; YOU WILL NOT KNOW THE TX ID UNTIL AFTER THE BUYER BUYS. And as I pointed out there is a lot of data you are ignoring and you shouldn't do that.

Do more checks. What if they buy 2? What if they spoof it and set it to amount=0 and pay $0? (0* $0 = 0 * $1000!) You should use the 'custom' variable as I've mentioned a dozen times now to identify the buyer correctly...don't trust the email from paypal to match your system's email. You also need to follow the suggestions made by paypal (and in your code) that you reposted here.

Again...user buys product, returns to site (Get's message...thanks, we are processing your order now. Your purchased items should be available soon.) You can send an email if you want, or whatever when it's complete or they can keep refreshing your site until the sale posts or you can do some AJAX notification thing. As I said before they might have to wait 10 minutes or 5 days depending on how they purchased the item before your listener will receive the COMPLETED and VERIFIED messages from PayPal on their purchase. If they buy with an eCheck for example you'll get an IPN PENDING message, and days later an IPN COMPLETED message. Don't give them items under a PENDING status...make them wait.

If you want it to be instant and more integrated inside your site, you need to integrate the API for Express Checkouts or pay for Web Flow Pro service. And if you think the IPN is hard, then you'll probably need to hire someone to do the API integration or flow pro design.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Mon Dec 02, 2013 5:06 pm
by simonmlewis
[quote]<form action='https://www.sandbox.paypal.com/cgi-bin/webscr' method='post'>
<input type='hidden' name='business' value='seller_email@email.com ' />
<input type='hidden' name='notify_url' value='http://YOURDOMAIN/paypal_ipn/process.php' />
<input type='hidden' name='currency_code' value='USD' />
<input type='hidden' name='lc' value='US' />
<input type='hidden' name='item_name' value='Subscription' />
<input type='hidden' name='amount' value='$15.00' />
<input type='hidden' name='sandbox' value='1' />
<input type='hidden' name='type' value='paynow' />
<input type='hidden' name='class' value='signup' />
<input type='hidden' name='custom' value='64b1add1e6349e3a2900fd4a9cf90e1f9e9090c54a983fdd56a3978812e66115' />
<input type='hidden' name='return_url' value='/Purchases' />
<input type='hidden' name='item_number' value='24adf829-15e6-11e3-b5bd-e0cb4e1c48db' />
<input type='hidden' name='cmd' value='_xclick' />
<input type="submit" value="Buy Now"/>
</form>/quote]
Your quotation here - it shows the CUSTOM URL with the transaction ID in it.
This is BEFORE the Buy Now button is even pushed.
So how can this id be generated AFTER the transaction has gone thru, if this is there BEFORE they even consider "oh, I'll buy it now".

Or am I missing something?

And yet again, I ask where in that Listener code does my DB Query go? I did ask several times, and you kept saying "it's all there in the code".

It isn't. I gave an example of what I think it should be, and you've not told me if I am right.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Mon Dec 02, 2013 8:33 pm
by Eric!
That 'custom' value is a unique value that YOU generate based on the USER's data who is logged in and viewing that button. In my example this is a hash I created by some user specific data and a random salt. This is used to identify the buyer.

The paypal generated transation ID is a 17-character string (letters and numbers) that is used to identify a single PayPal transaction. It does not identify the buyer.

The code itself tells you where to put in your checks. And I didn't say you put it in the wrong place, I said you need to do more checks.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Mon Dec 02, 2013 11:25 pm
by Eric!
I see I missed an earlier post of yours.
[quote='simonmlewis"]The bits I still do not understand - and apologies if they have been instructed but still... are:

1) how does that Transaction ID get into my button code?? Is it a PayPal script I put in there, and with some reference to my Listener script, it talks to PayPal and gets the ID there "from PayPal"??
2) if the above is as I am guessing, I therefore assume the data in that button is POSTed to PayPal.
3) PayPal does an IPN Listener at some stage in the process to check VIA MY IPN LISTENER to ask "is this price of £50.00 the same price of product ID 123". <runs query> Yes it is - ok good.
4) payment goes through anyway, returns back to my site.
5) because the payment amount was correct, it's been marked as sold in my DB_Products table.
[/quote]
1. No. It is not in your button form at all.
2. Yes, the purchase data is posted to paypal with the button.
3. No. Paypal processes the payment, then tells you about it after it has been completed. It doesn't care if you consider it a valid payment or not. If the purchase went through then as far as Paypal cares they are done and just notifying you.
4. No. The user makes a payment and Paypal sends them back to whatever return_url you specified in the button. Paypal then does it's magic and when they get around to it, they tell you listener the results.
5. No. You have to process all the data from paypal and decide if EVERYTHING is correct: price, quantity, item, buyer, seller, yada yada yada.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Tue Dec 03, 2013 7:53 am
by simonmlewis
Ok Eric, gotchya. I thought that WAS the transaction ID, and was contrary to what you said.

So on my product page I have this:

Code: Select all

<form action='https://www.paypal.com/cgi-bin/webscr' method='post'>
<input type='hidden' name='business' value='$row->selleremail' />
<input type='hidden' name='notify_url' value='http://mydomain.co.uk/paypal_ipn/ipnLISTENER.php' />
<input type='hidden' name='currency_code' value='GBP' />
<input type='hidden' name='lc' value='GB' />
<input type='hidden' name='item_name' value='$row->title' />
<input type='hidden' name='amount' value='£25.00' />
<input type='hidden' name='sandbox' value='1' />
<input type='hidden' name='type' value='paynow' />
<input type='hidden' name='class' value='signup' />
<input type='hidden' name='custom' value='(random code I can generate myself)' />
<input type='hidden' name='return_url' value='/purchasecomplete' />
<input type='hidden' name='item_number' value='4499675' />
<input type='hidden' name='cmd' value='_xclick' />
<input  type="submit" value="Buy Now"/>
</form>
They click buy now. Go thru the process of paying the "selleremail", and it takes them back to /purchasecomplete, on completion at PayPal.

purchasecomplete.inc (or whatever file I route them to) does the "thanks, ta" stuff.
While at some stage, /paypal_ipn/ipnLISTENER.php is triggered by PayPal and will run my script. And my script will do whatever else I tell it to my DB.

In that script, I can check, based on (at the very least) the $price that is _POSTed to me, to ensure it is the right figure, as well as other things you have pointed out to me.

Ok so if I am on the right track now "finally", how do test my listener works and runs queries on my database? CAn I modify the listener simulator to query certain things on my database, immediately?

Do you think I am getting somewhere now...??

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Tue Dec 03, 2013 8:44 am
by simonmlewis
Right.
I've done the button.
In the Instant Payments Notifications PayPal screen it is enable and the ipn listener file's URL is in there. The file I have tested on the simulator.

I've made a penny payment live. It's passed me back to my site, but my database hasn't been triggered yet. Can it sometimes take a while to go through?

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Tue Dec 03, 2013 9:55 am
by simonmlewis
Cracked it. It ws because sandbox was 1, not 0.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Tue Dec 03, 2013 6:51 pm
by Eric!
You should stick with the sandbox until you've fully tested the system and make sure it can't be spoofed.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Wed Dec 04, 2013 2:47 am
by simonmlewis
When I used it as the sandbox, it didn't work.
When I set the sandbox 0 to 1 (or the other way around), it did work.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Wed Dec 04, 2013 8:01 am
by simonmlewis
When someone buys something, in the product database table I store the SellersID, and the BuyersID.

How do I update the table with the BuyersID via the PayPal Listener? Will it still be "in session"?? I'm thinking I cannot guarantee it will be in session.

Re: PayPal buttons: how do I protect sellers' sales?

Posted: Wed Dec 04, 2013 11:59 am
by Eric!
simonmlewis wrote:When I used it as the sandbox, it didn't work.
When I set the sandbox 0 to 1 (or the other way around), it did work.
That's because you're posting the form to the live paypal and not the sand box URL
https://www.sandbox.paypal.com/cgi-bin/webscr <---for testing in sandbox
https://www.paypal.com/cgi-bin/webscr <---for live purchases
simonmlewis wrote:When someone buys something, in the product database table I store the SellersID, and the BuyersID.

How do I update the table with the BuyersID via the PayPal Listener? Will it still be "in session"?? I'm thinking I cannot guarantee it will be in session.
Your listener can not access session data. What is the BuyersID? Are you putting that value into the 'custom' variable? There are a lot of ways to solve the problem you are asking. My suggestion was to make every logged in user identified by a hash that you put into the button form field for the 'custom' value. This value comes back to the listener, the listener can then use the 'custom' value to identify who bought it. You can use the Item Number to identify who sold it.