Monday, October 24, 2011

PayPal Instant Payment Notification (IPN)

Lets start.

WHAT IS PayPal?
PayPal is a service that enables you to pay, send money, and accept payments without revealing your financial information.


WHAT IS IPN?
Instant Payment Notification (IPN) is a message service that notifies you of events related to PayPal transactions. You can use it to automate back-office and administrative functions, such as fulfilling orders, tracking customers, and providing status and other information related to a transaction.


The Following diagram shows requests and responses, which are the result of processing button clicks or API operations on PayPal. PayPal sends an IPN message when it sends a response to a request. The IPN message is not actually part of the response sent to your website. Rather, the IPN message is sent to the your listener, which allows you to take actions that are not directly tied to the operation of your website.





HOW WE CAN TEST THIS BEFORE RUN IT IN PRODUCTION SERVER?
First go to www.developer.paypal.com and if u haven't any account on this site (PayPal Sandbox) click Sign Up button after registration type your E-mail Address, Password and Log In. Then u'll see menu at the left side. Click Test Accounts link. Click on link Preconfigured and create two account 
  1. Select Buyer (Use to represent your customer's experience) as Account Type
  2. Select Seller (Use to represent yourself as the merchant) as Account Type
After completion set  Business Account radio checked and click Enter Sandbox Test Site and login with your account which u have created above (see 2) select Merchant Services tab and click Buy Now Button to create it. After completion simple copy and past this form to your web site page.
Now we must enable IPN notification:
Click My Account tab Profile sub tab under Selling Preferences (My selling tools in real account)  select Instant payment notifications 

-> click Update button 
-> click the Choose IPN Settings button
-> click Receive IPN messages (Enabled)
write Notification URL: http://yourdomainorip:port/yourIpnlistener


NOTE:  If your listener is java servlet or jsp (in my case it was servlet) u must be sure your listener works in port standard 80, last night I did hard work for this with no payment expectation. When admin changed port from 8080 to 80 it worked perfectly :)


Now U can go to your web page and click Buy Now Button it redirect u to paypal page when paypal receives a payment immediately notifies your listener about payment. And after this your listener can VERIFY this. My code here:

<%@ page language="java" contentType="text/html; charset=UTF-8"
 pageEncoding="UTF-8"%>

<%@ page import="java.util.*"%>
<%@ page import="java.net.*"%>
<%@ page import="java.io.*"%>

<%
// read post from PayPal system and add 'cmd'
Enumeration en = request.getParameterNames();
String str = "cmd=_notify-validate";
while(en.hasMoreElements()){
String paramName = (String)en.nextElement();
String paramValue = request.getParameter(paramName);
str = str + "&" + paramName + "=" + URLEncoder.encode(paramValue, "UTF-8");
}

// post back to PayPal system to validate
// NOTE: change http: to https: in the following URL to verify using SSL (for increased security).
// using HTTPS requires either Java 1.4 or greater, or Java Secure Socket Extension (JSSE)
// and configured for older versions.
URL u = new URL("https://www.sandbox.paypal.com/cgi-bin/webscr");
URLConnection uc = u.openConnection();
uc.setDoOutput(true);
uc.setRequestProperty("Content-Type","application/x-www-form-urlencoded");
PrintWriter pw = new PrintWriter(uc.getOutputStream());
pw.println(str);
pw.close();

BufferedReader in = new BufferedReader(
new InputStreamReader(uc.getInputStream()));
String res = in.readLine();
in.close();

// assign posted variables to local variables
String itemName = request.getParameter("item_name");
String itemNumber = request.getParameter("item_number");
String paymentStatus = request.getParameter("payment_status");
String paymentAmount = request.getParameter("mc_gross");
String paymentCurrency = request.getParameter("mc_currency");
String txnId = request.getParameter("txn_id");
String receiverEmail = request.getParameter("receiver_email");
String payerEmail = request.getParameter("payer_email");

//check notification validation
if(res.equals("VERIFIED")) {
// check that paymentStatus=Completed
// check that txnId has not been previously processed
// check that receiverEmail is your Primary PayPal email
// check that paymentAmount/paymentCurrency are correct
// process payment
System.out.println("oleyyyyyyyyyyyyy VERIFIED :) ");
System.out.println("You can write to DB");
}
else if(res.equals("INVALID")) {
// log for investigation
System.out.println("opsss INVALID :( ");
}
else {
 System.out.println("ERROR :(((( ");
}
%>
If everything goes normal u can see "oleyyyyyyyyyyyyy VERIFIED :)" and "You can write to DB" lines.


HOW I CAN TEST MY LISTENER?
in the your sandbox page click Test Tools link and write your listener URL here and click Send IPN button your listener must get request and verified it for you :)


If u find this post useful don't forget leave comment :)
For more information read: 

  1. Introducing IPN
  2. IPN Operations on PayPal

4 comments:

  1. Hey, that is a great script. Can you integrate it with my project - http://www.etherfeed.com . It also uses paypal ipn notification

    ReplyDelete
    Replies
    1. Thanks.
      How can I integrate this with your project?

      Delete
  2. Thanks for the nice instructions. We integrated this with our merchant capital project

    ReplyDelete