开发者

How do i integrate PayPal IPN in my Joomla Custom Component?

开发者 https://www.devze.com 2023-03-28 05:56 出处:网络
I am not sure the title of this question covers what I mean. In this Joomla component I am writing I have built in the ability for customers to buy via PayPal. At first I wrote a seperate view for the

I am not sure the title of this question covers what I mean. In this Joomla component I am writing I have built in the ability for customers to buy via PayPal. At first I wrote a seperate view for the IPN, but even though the script worked without a flaw, it kept sending a 503 back to IPN (probably because the ipn-url was something like www.example.com/index.php?option=com_component&view=paypal) so i rewro开发者_开发百科te part of the script and now the IPN-url is www.example.com/paypal.php. Since this is an actual page it now correctly sends a 200 instead of a 503 back to PayPal. But...now I don't know how to call the rest of my script which handles all the emailing and database storing of a payment. Since this paypal.php is called directly (and not via index.php) it works completely seperate from Joomla so I cannot call in a Model (or at least I don't know how to do that).

This is my paypal.php file:

<?php
$header = "";
$req = 'cmd=_notify-validate';
$get_magic_quotes_exists = false;
if (function_exists('get_magic_quotes_gpc')) {
  $get_magic_quotes_exists = true;
}
foreach ($_POST as $key => $value) {
  if ($get_magic_quotes_exists == true && get_magic_quotes_gpc() == 1) {
    $value = urlencode(stripslashes($value));
  }
  else {
     $value = urlencode($value);
     $req .= "&$key=$value";
  }
}
// Post back to PayPal to validate
$header .= "POST /cgi-bin/webscr HTTP/1.0\r\n";
$header .= "Content-Type: application/x-www-form-urlencoded\r\n";
$header .= "Content-Length: " . strlen($req) . "\r\n\r\n";
$fp = fsockopen('ssl://www.sandbox.paypal.com', 443, $errno, $errstr, 30);


if ($fp) {
  fputs($fp, $header . $req);
  while (!feof($fp)) {
     $res = fgets($fp, 1024);
     if (strcmp($res, "VERIFIED") == 0) {
        // Here I must process the payment (emails, database, etc.)
     }
     else {
        // Error
     }
  }
}
fclose($fp);

Now at the place where it says 'Here I must process payment' I must be able to get data from the database and store data into the database. So how do I make it so this file acts as part of my component so I can call methods from my Model(s)? Or is there some other way I can integrate IPN into my model while ensuring a 200 instead of a 503.

UPDATE: Someone mentioned using curl so i tried that. The handler now looks like this:

  <?php
  $header = "";
  $req = 'cmd=_notify-validate';
  $postData = 'option=com_component&view=buy&layout=paypal';
  $get_magic_quotes_exists = false;
  if (function_exists('get_magic_quotes_gpc')) {
     $get_magic_quotes_exists = true;
  }
  foreach ($_POST as $key => $value) {
     if ($get_magic_quotes_exists == true && get_magic_quotes_gpc() == 1) {
        $value = urlencode(stripslashes($value));
     }
     else {
        $value = urlencode($value);
        $req .= "&$key=$value";
        $postData .= "&$key=$value";
     }
  }

  $header .= "POST /cgi-bin/webscr HTTP/1.0\r\n";
  $header .= "Content-Type: application/x-www-form-urlencoded\r\n";
  $header .= "Content-Length: " . strlen($req) . "\r\n\r\n";
  $fp = fsockopen('ssl://www.sandbox.paypal.com', 443, $errno, $errstr, 30);


  if ($fp) {
     fputs($fp, $header . $req);
     while (!feof($fp)) {
        $res = fgets($fp, 1024);
        if (strcmp($res, "VERIFIED") == 0) {

           $ch = curl_init("http://www.example.com/index.php");
           curl_setopt($ch, CURLOPT_POST, true);
           curl_setopt($ch, CURLOPT_POSTFIELDS, $postData);
           $output = curl_exec($ch);
           if ($output == FALSE) {
              // Error
           }
           curl_close($ch);
        }
        else {
           // Error
        }
     }
  }
  fclose($fp);

The IPN still works fine, but the component is not 'executed'. I never used curl before so maybe it is a fault in the script?


Got it myself finally; so somewhere I found out that to be able to access most of the basic functionality of Joomla from any file you simply need to include 2 files:

/includes/defines.php
/includes/framework.php

Then you simply initialise the framework like so:

$framework = & JFactory::getApplication('site');
$framework->initialise();

And then I import the model which contains all the database/email functionality:

JLoader::import('joomla.application.component.model');
JLoader::import('modelname', 'path_to_my/models');

$model= JModel::getInstance('ModelName', 'ComponentnameModel');

And now I can access the methods from that model (and thus the database) from my IPN-handler.


I just had a similar issue with a paypal component on my website and figured out where the 503 notification originated from.

This issue could have to do with the online/offline status of your website. If your website is offline (meaning you have to log in as admin to have a look at your website) and you're not logged in (PayPal isn't logged in as well) Joomla is generating a standard message displaying a message like"

This site is down for maintenance. Please check back again soon.

This message is send with a 503 notification.

Depending on how your component is developed, the ipn message from PayPal can be processed by your website, while still sending a 503 error to PayPal.

Hope this helps you out.


For a component com_mycomponent, your mycomponent.php should look like

// Require the com_content helper library
require_once (JPATH_COMPONENT.DS.'controller.php');

// Create the controller
$controller = new MyComponentController();

// Perform the Request task
$controller->execute(JRequest::geCmd('task'));

// Redirect if set by the controller
$controller->redirect();

In controller.php, then use

class MyComponentCOntroller extends JController{

    function processPaypalPayment(){

        //paste your code here
    }

}

In Paypal set your IPN to:

http://mysite.com/?option=com_mycomponent&task=processPaypalPayment
0

精彩评论

暂无评论...
验证码 换一张
取 消