/**
  * Validate this is valid for this transaction type.
  *
  * - If valid returns the subscription and member IDs we are going to process.
  */
 public function precheck()
 {
     global $modSettings, $txt;
     // Is this the right hash?
     if (empty($modSettings['2co_password']) || $_POST['x_MD5_Hash'] !== strtoupper(md5($modSettings['2co_password'] . $modSettings['2co_id'] . $_POST['x_trans_id'] . $_POST['x_amount']))) {
         generateSubscriptionError($txt['2co_password_wrong']);
     }
     // Verify the currency
     list(, $currency) = explode(':', $_POST['x_invoice_num']);
     // Verify the currency!
     if (strtolower($currency) != $modSettings['currency_code']) {
         exit;
     }
     // Return the ID_SUB/ID_MEMBER
     return explode('+', $_POST['x_invoice_num']);
 }
 public function precheck()
 {
     global $modSettings, $txt;
     // Put this to some default value.
     if (!isset($_POST['txn_type'])) {
         $_POST['txn_type'] = '';
     }
     // Build the request string - starting with the minimum requirement.
     $requestString = 'cmd=_notify-validate';
     // Now my dear, add all the posted bits.
     foreach ($_POST as $k => $v) {
         $requestString .= '&' . $k . '=' . urlencode($v);
     }
     // Can we use curl?
     if (function_exists('curl_init') && ($curl = curl_init('http://www.', !empty($modSettings['paidsubs_test']) ? 'sandbox.' : '', 'paypal.com/cgi-bin/webscr'))) {
         // Set the post data.
         curl_setopt($curl, CURLOPT_POST, true);
         curl_setopt($curl, CURLOPT_POSTFIELDSIZE, 0);
         curl_setopt($curl, CURLOPT_POSTFIELDS, $requestString);
         // Fetch the data returned as a string.
         curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
         // Fetch the data.
         $this->return_data = curl_exec($curl);
         // Close the session.
         curl_close($curl);
     } else {
         // Setup the headers.
         $header = 'POST /cgi-bin/webscr HTTP/1.0' . "\r\n";
         $header .= 'Content-Type: application/x-www-form-urlencoded' . "\r\n";
         $header .= 'Content-Length: ' . strlen($requestString) . "\r\n\r\n";
         // Open the connection.
         $fp = fsockopen('www.' . (!empty($modSettings['paidsubs_test']) ? 'sandbox.' : '') . 'paypal.com', 80, $errno, $errstr, 30);
         // Did it work?
         if (!$fp) {
             generateSubscriptionError($txt['paypal_could_not_connect']);
         }
         // Put the data to the port.
         fputs($fp, $header . $requestString);
         // Get the data back...
         while (!feof($fp)) {
             $this->return_data = fgets($fp, 1024);
             if (strcmp($this->return_data, 'VERIFIED') == 0) {
                 break;
             }
         }
         // Clean up.
         fclose($fp);
     }
     // If this isn't verified then give up...
     // !! This contained a comment "send an email", but we don't appear to send any?
     if (strcmp($this->return_data, 'VERIFIED') != 0) {
         exit;
     }
     // Check that this is intended for us.
     if ($modSettings['paypal_email'] != $_POST['business'] && (empty($modSettings['paypal_additional_emails']) || !in_array($_POST['business'], explode(',', $modSettings['paypal_additional_emails'])))) {
         exit;
     }
     // Is this a subscription - and if so it's it a secondary payment that we need to process?
     if ($this->isSubscription() && (empty($_POST['item_number']) || strpos($_POST['item_number'], '+') === false)) {
         // Calculate the subscription it relates to!
         $this->_findSubscription();
     }
     // Verify the currency!
     if (strtolower($_POST['mc_currency']) != $modSettings['paid_currency_code']) {
         exit;
     }
     // Can't exist if it doesn't contain anything.
     if (empty($_POST['item_number'])) {
         exit;
     }
     // Return the id_sub and id_member
     return explode('+', $_POST['item_number']);
 }
Exemple #3
0
			AND id_member = {int:current_member}
			AND status = {int:status}', array('current_time' => $subscription_act, 'current_subscription' => $subscription_id, 'current_member' => $member_id, 'status' => $status));
    // Receipt?
    if (!empty($modSettings['paid_email']) && $modSettings['paid_email'] == 2) {
        $replacements = array('NAME' => $subscription_info['name'], 'REFUNDNAME' => $member_info['member_name'], 'REFUNDUSER' => $member_info['real_name'], 'PROFILELINK' => $scripturl . '?action=profile;u=' . $member_id, 'DATE' => timeformat(time(), false));
        emailAdmins('paid_subscription_refund', $replacements, $notify_users);
    }
} elseif ($gatewayClass->isPayment() || $gatewayClass->isSubscription()) {
    $cost = unserialize($subscription_info['cost']);
    $total_cost = $gatewayClass->getCost();
    $notify = false;
    // For one off's we want to only capture them once!
    if (!$gatewayClass->isSubscription()) {
        $real_details = @unserialize($subscription_info['pending_details']);
        if (empty($real_details)) {
            generateSubscriptionError(sprintf($txt['paid_count_not_find_outstanding_payment'], $member_id, $subscription_id));
        }
        // Now we just try to find anything pending.
        // We don't really care which it is as security happens later.
        foreach ($real_details as $id => $detail) {
            unset($real_details[$id]);
            if ($detail[3] == 'payback' && $subscription_info['payments_pending']) {
                $subscription_info['payments_pending']--;
            }
            break;
        }
        $subscription_info['pending_details'] = empty($real_details) ? '' : serialize($real_details);
        $smcFunc['db_query']('', '
			UPDATE {db_prefix}log_subscribed
			SET payments_pending = {int:payments_pending}, pending_details = {string:pending_details}
			WHERE id_sublog = {int:current_subscription_item}', array('payments_pending' => $subscription_info['payments_pending'], 'current_subscription_item' => $subscription_info['id_sublog'], 'pending_details' => $subscription_info['pending_details']));
 /**
  * Post the IPN data received back to paypal for validation
  *
  * - Sends the complete unaltered message back to PayPal.
  * - The message must contain the same fields in the same order and be encoded in the same way as the original message
  * - PayPal will respond back with a single word, which is either VERIFIED if the message originated with PayPal or INVALID
  * - If valid returns the subscription and member IDs we are going to process if it passes
  *
  * @return string
  */
 public function precheck()
 {
     global $modSettings, $txt;
     $my_post = array();
     // Reading POSTed data directly from $_POST may causes serialization issues with array data
     // in the POST. Instead, read raw POST data from the input stream.
     $raw_post_data = file_get_contents('php://input');
     $raw_post_array = explode('&', $raw_post_data);
     // Process it
     foreach ($raw_post_array as $keyval) {
         $keyval = explode('=', $keyval);
         if (count($keyval) === 2) {
             $my_post[$keyval[0]] = urldecode($keyval[1]);
         }
     }
     // Put this to some default value.
     if (!isset($my_post['txn_type'])) {
         $my_post['txn_type'] = '';
     }
     // Build the request string - starting with the minimum requirement.
     $requestString = 'cmd=_notify-validate';
     // Now my dear, add all the posted bits back in the exact order we got them
     foreach ($my_post as $key => $value) {
         $requestString .= '&' . $key . '=' . urlencode($value);
     }
     // Post IPN data back to PayPal to validate the IPN data is genuine
     // First we try cURL
     if (function_exists('curl_init') && ($curl = curl_init((!empty($modSettings['paidsubs_test']) ? 'https://www.sandbox.' : 'http://www.') . 'paypal.com/cgi-bin/webscr'))) {
         // Set the post data.
         curl_setopt($curl, CURLOPT_POST, true);
         curl_setopt($curl, CURLOPT_POSTFIELDSIZE, 0);
         curl_setopt($curl, CURLOPT_POSTFIELDS, $requestString);
         // Set up the headers so paypal will accept the post
         curl_setopt($curl, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_1);
         curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, 1);
         curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, 2);
         curl_setopt($curl, CURLOPT_FORBID_REUSE, 1);
         // Set TCP timeout to 30 seconds
         curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, 30);
         // Set the http headers
         curl_setopt($curl, CURLOPT_HTTPHEADER, array('Content-Type: application/x-www-form-urlencoded', 'Content-Length: ' . strlen($requestString), 'Host: www.' . (!empty($modSettings['paidsubs_test']) ? 'sandbox.' : '') . 'paypal.com', 'Connection: close'));
         // The data returned as a string.
         curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
         // Fetch the data.
         $this->return_data = curl_exec($curl);
         // Close the session.
         curl_close($curl);
     } else {
         // Setup the headers.
         $header = 'POST /cgi-bin/webscr HTTP/1.1' . "\r\n";
         $header .= 'Content-Type: application/x-www-form-urlencoded' . "\r\n";
         $header .= 'Host: www.' . (!empty($modSettings['paidsubs_test']) ? 'sandbox.' : '') . 'paypal.com' . "\r\n";
         $header .= 'Content-Length: ' . strlen($requestString) . "\r\n";
         $header .= 'Connection: close' . "\r\n\r\n";
         // Open the connection.
         if (!empty($modSettings['paidsubs_test'])) {
             $fp = fsockopen('ssl://www.sandbox.paypal.com', 443, $errno, $errstr, 30);
         } else {
             $fp = fsockopen('www.paypal.com', 80, $errno, $errstr, 30);
         }
         // Did it work?
         if (!$fp) {
             generateSubscriptionError($txt['paypal_could_not_connect']);
         }
         // Put the data to the port.
         fputs($fp, $header . $requestString);
         // Get the data back...
         while (!feof($fp)) {
             $this->return_data = fgets($fp, 1024);
             if (strcmp(trim($this->return_data), 'VERIFIED') === 0) {
                 break;
             }
         }
         // Clean up.
         fclose($fp);
     }
     // If PayPal IPN does not return verified then give up...
     if (strcmp(trim($this->return_data), 'VERIFIED') !== 0) {
         exit;
     }
     // Now that we have received a VERIFIED response from PayPal, we perform some checks
     // before we assume that the IPN is legitimate. First check that this is intended for us.
     if ($modSettings['paypal_email'] !== $_POST['business'] && (empty($modSettings['paypal_additional_emails']) || !in_array($_POST['business'], explode(',', $modSettings['paypal_additional_emails'])))) {
         exit;
     }
     // Is this a subscription - and if so is it a secondary payment that we need to process?
     if ($this->isSubscription() && (empty($_POST['item_number']) || strpos($_POST['item_number'], '+') === false)) {
         // Calculate the subscription it relates to!
         $this->_findSubscription();
     }
     // Verify the currency!
     if (trim(strtolower($_POST['mc_currency'])) !== strtolower($modSettings['paid_currency_code'])) {
         generateSubscriptionError(sprintf($txt['paypal_currency_unkown'], $_POST['mc_currency'], $modSettings['paid_currency_code']));
     }
     // Can't exist if it doesn't contain anything.
     if (empty($_POST['item_number'])) {
         exit;
     }
     // Return the id_sub and id_member
     return explode('+', $_POST['item_number']);
 }