Squiz Matrix  4.12.2
 All Data Structures Namespaces Functions Variables Pages
payment_gateway_datacash.inc
1 <?php
18 require_once dirname(__FILE__).'/../../payment_gateway/payment_gateway.inc';
19 require_once dirname(__FILE__).'/datacash_processor.inc';
20 
21 
34 {
35 
36 
41  private $_redirect_info = NULL;
42 
47  private $_pass_through_vars = NULL;
48 
49 
56  function __construct($assetid=0)
57  {
58  parent::__construct($assetid);
59 
60  }//end constructor
61 
62 
73  function _createAdditional(&$link)
74  {
75  if (!parent::_createAdditional($link)) return FALSE;
76 
77  return ($this->_createBodycopy('display_format', translate('default_bodycopy_content')) && $this->_createBodycopy('card_holder_verification', translate('card_holder_verification_bodycopy_content')));
78 
79  }//end _createAdditional()
80 
81 
91  function _createBodycopy($link_value, $content)
92  {
93  $GLOBALS['SQ_SYSTEM']->am->includeAsset('bodycopy');
94  $bodycopy = new Bodycopy();
95  $copy_link = Array('asset' => &$this, 'link_type' => SQ_LINK_TYPE_2, 'is_dependant' => 1, 'is_exclusive' => 1, 'value' => $link_value);
96 
97  $bodycopy->setAttrValue('name', ucwords(str_replace('_',' ', $link_value)));
98  $args = Array('content' => $content);
99  if ($bodycopy->create($copy_link, $args)) {
100  $child_bodycopy = $GLOBALS['SQ_SYSTEM']->am->getLink($bodycopy->id, SQ_LINK_TYPE_2, 'bodycopy_div');
101  $GLOBALS['SQ_SYSTEM']->am->releaseLock($child_bodycopy['minorid'], 'attributes');
102  return TRUE;
103  }
104  return FALSE;
105 
106  }//end _createBodycopy()
107 
108 
116  function _getAllowedLinks()
117  {
118  $page_links = parent::_getAllowedLinks();
119  $page_links[SQ_LINK_TYPE_2]['bodycopy'] = Array('card' => 2, 'exclusive' => TRUE);
120  return $page_links;
121 
122  }//end _getAllowedLinks()
123 
124 
139  {
140  $keywords = parent::getAvailableKeywords();
141 
142  $keywords['card_number'] = 'Card Number';
143  $keywords['card_start_month'] = 'Card Start Month';
144  $keywords['card_start_year'] = 'Card Start Year';
145  $keywords['card_expiry_month'] = 'Card Expiry Month';
146  $keywords['card_expiry_year'] = 'Card Expiry Year';
147  $keywords['card_issue_number'] = 'Card Issue Number';
148  $keywords['card_cv2'] = 'Card CV2';
149 
150  $keywords['street_address1'] = 'Street Address 1';
151  $keywords['street_address2'] = 'Street Address 2';
152  $keywords['street_address3'] = 'Street Address 3';
153  $keywords['street_address4'] = 'Street Address 4';
154  $keywords['postcode'] = 'Postcode';
155 
156  $keywords['transaction_amount'] = 'Transaction Amount';
157  $keywords['transaction_currency'] = 'Transaction Currency';
158  $keywords['processing_error'] = 'Processing Error (empty if no error)';
159  $keywords['submit_button'] = 'Submit Button';
160  $keywords['cancel_button'] = 'Cancel Button';
161  $keywords['reset_button'] = 'Reset Button';
162  $keywords['card_holder_verification_form'] = 'Card Holder Verification Form';
163 
164  return $keywords;
165 
166  }//end getAvailableKeywords()
167 
168 
179  function onRequestKeywords(&$broadcaster, $vars=Array())
180  {
181  $keywords = $this->getAvailableKeywords();
182  $vars['keywords'] = array_merge($vars['keywords'], $keywords);
183 
184  }//end onRequestKeywords()
185 
186 
193  function printBody()
194  {
195  //this page is redirected to by the child iframe with unknown reference error
196  if (array_get_index($_GET, 'unknown_referer', FALSE)) {
197  trigger_error('Unknown caller reference');
198  exit;
199  }
200 
201  //this page is redirected to by the child iframe with an error message
202  if (array_get_index($_GET, 'error_message', FALSE)) {
203  $this->_setError($_GET['error_message']);
204  }
205 
206  $success = FALSE;
207  $is_in_frame = FALSE; //indicates whether this page is in the iframe after it is redirected to by the ACS
208 
209  if (empty($_POST['PaRes']) || empty($_POST['MD'])) {
210  //THIS PAGE IS REDIRECTED TO BY DELIVERY METHOD OR FORM ECOMMERCE ASSET NOT BY THE ACS
211  $amount = array_get_index($_SESSION,'SQ_ECOM_AMOUNT', 0);
212  $card_info = array_get_index($_REQUEST, $this->getPrefix().'_card', FALSE);
213  $action = array_get_index($_REQUEST, $this->getPrefix().'_action', FALSE);
214 
215  if ($action == 'Cancel') {
216  $this->returnToCaller('CANCEL');
217 
218  } else if (empty($amount)) {
219  unset($_SESSION['SQ_ECOM_AMOUNT']);
220  $this->_unsetCurrency();
221  //clear pass through variables
222  if (isset($_SESSION['SQ_ECOM_PASS_THROUGH_VARS'])) {
223  unset($_SESSION['SQ_ECOM_PASS_THROUGH_VARS']);
224  }
225 
226  $this->appendPendingOrderAuditLog(translate('ecom_payment_no_amount'));
227 
228  $this->returnToCaller('SUCCESS');
229 
230  } else if ($card_info) {
231  $this->appendPendingOrderAuditLog(translate('ecom_payment_attempted_gateway_contacted'));
232 
233  $success = $this->processPayment($card_info);
234  //if success = 2, redirect to the Access Control Server (ACS) for Card Holder Verification
235  if ($success === 2) {
236  //store the Datacash reference number to authorize payment after the card holder verify himself
237  $_SESSION['SQ_ECOM_TRANSACTION_REF_NO'] = $this->_redirect_info['TRANSACTION'];
238  //print the Card Holder Verification bodycopy
239  $this->printBodycopy('card_holder_verification');
240  return;
241  }
242  }
243 
244  } else if (!empty($_SESSION['SQ_ECOM_TRANSACTION_REF_NO']) && ($_POST['MD'] == md5($_SESSION['SQ_ECOM_REF_NO']))) {
245  //THIS PAGE IS REDIRECTED TO BY THE ACCESS CONTROL SERVER (ACS) OF ISSUEING BANK AFTER CARD HOLDER VERIFICATION PROCESS
246  $is_in_frame = TRUE;
247  $datacash_ref = $_SESSION['SQ_ECOM_TRANSACTION_REF_NO'];
248  unset($_SESSION['SQ_ECOM_TRANSACTION_REF_NO']);
249  $success = $this->authorizePayment($datacash_ref, $_POST['PaRes']);
250  if ($success === FALSE) {
251  //transaction fails, redirect the parent document of the iframe and display error
252  $this->_redirectParent($this->getURL().'?error_message='.urlencode($this->_tmp['error_message'][0]));
253  }
254  }
255 
256  //if transaction is accepted, redirect the user to the success page
257  if ($success === 1) {
258  unset($_SESSION['SQ_ECOM_AMOUNT']);
259  $this->_unsetCurrency();
260  //clear pass through variables
261  if (isset($_SESSION['SQ_ECOM_PASS_THROUGH_VARS'])) {
262  unset($_SESSION['SQ_ECOM_PASS_THROUGH_VARS']);
263  }
264  //broadcast payment completed trigger event before return
265  if (isset($_SESSION['SQ_ECOM_PAYMENT_COMPLETED_BROADCASTER_ASSETID'])) {
266  $broadcaster = $GLOBALS['SQ_SYSTEM']->am->getAsset($_SESSION['SQ_ECOM_PAYMENT_COMPLETED_BROADCASTER_ASSETID']);
267  if (!empty($broadcaster)) {
268  //put all returned variables in $_SESSION['SQ_ECOM_RESPONSE'] to $_POST array so that the listening trigger can use them
269  $response = array_get_index($_SESSION, 'SQ_ECOM_RESPONSE', FALSE);
270  if ($response) {
271  $_POST['transaction_reference'] = $response['TRANSACTION'];
272  $_POST['transaction_time'] = $response['TIME'];
273  $_POST['transaction_status'] = $response['STATUS'];
274  $_POST['transaction_card_number'] = $response['CARDNO'];
275  $_POST['transaction_amount'] = $response['AMOUNT'];
276  $_POST['transaction_currency'] = $response['CURRENCY'];
277  }
278  $GLOBALS['SQ_SYSTEM']->broadcastTriggerEvent('trigger_event_ecommerce_payment_completed', $broadcaster);
279  }
280  }
281 
282  $this->appendPendingOrderAuditLog(translate('ecom_payment_succeeded'));
283 
284  $this->returnToCaller('SUCCESS', $is_in_frame);
285  } else {
286  // Notify that the payment was declined
287  if ($card_info) {
288  $this->appendPendingOrderAuditLog(translate('ecom_payment_declined'));
289  }
290  }
291 
292  //print default bodycopy
293  $this->printBodycopy('display_format');
294 
295  }//end printBody()
296 
297 
304  function printBodycopy($link_value)
305  {
306  $bodycopy = $this->getBodycopy($link_value);
307  if (is_null($bodycopy)) return;
308 
309  $keywords = $bodycopy->getKeywords();
310  $replacements = Array();
311  foreach ($keywords as $word) {
312  $replacements[$word] = $this->getKeywordReplacement($word);
313  }
314  $bodycopy->setKeywordReplacements($replacements);
315 
316  //OUTPUT HERE
317  if ($link_value == 'display_format') {
318  //the default body copy with card input
319  $datapath = sq_web_path('data').'/asset_types/payment_gateway_datacash/files';
320  $card = $this->getPrefix().'_card';
321 
322  if ($this->attr('test_mode')) {
323  echo '<h2 class="gateway-test-mode" style="color: white; background-color: #C00; padding: 5px">TEST MODE</h2>';
324  }
325 
326  ?>
327  <script src="<?php echo $datapath; ?>/loader.js"></script>
328  <script>
329  var Loader = new Loader('<?php echo $card; ?>','#FFFFFF','Processing Transaction...','<?php echo $datapath; ?>/loader.gif');
330  Loader.print();
331  </script>
332  <form method="post" action="<?php echo $this->getURL(); ?>" onsubmit="Loader.show();">
333  <?php
334  $bodycopy->printBody();
335  echo '</form>';
336  } else {
337  //the card holder verification bodycopy
338  $bodycopy->printBody();
339  }
340 
341  }//end printBodycopy()
342 
343 
350  function getBodycopy($link_value)
351  {
352  $link = $GLOBALS['SQ_SYSTEM']->am->getLink($this->id, SQ_LINK_TYPE_2, 'bodycopy', TRUE, $link_value);
353  if (empty($link)) return NULL;
354  $bodycopy = $GLOBALS['SQ_SYSTEM']->am->getAsset($link['minorid'], $link['minor_type_code']);
355  return $bodycopy;
356 
357  }//end getBodycopy()
358 
359 
368  function processPayment($card_info)
369  {
370  if (!$card_info) return FALSE;
371 
372  $amount = $_SESSION['SQ_ECOM_AMOUNT'];
373 
374  $processor = new Datacash_Processor($this->attr('client'), $this->attr('password'), $this->attr('datacash_api_path'), $this->attr('cardinfo_dir_path'), $this->attr('timeout'), $this->attr('test_mode'));
375 
376  //SET AMOUNT
377  if (empty($amount)) {
378  $this->_setError(translate('datacash_amount_not_specified'));
379  } else {
380  $processor->setAmount($amount, $this->_getCurrency());
381  }
382 
383  //SET MERCHANT REFERENCE
384  //merchant reference number should be generated here instead of inside default_delivery_method.inc or form_ecommerce.inc
385  //because the customer can try to pay many times until his card is accepted. So each time a payment transaction
386  //is sent to Datacash, a new merchant reference number should be used because using the old reference number can
387  //cause the "duplicate reference" error. We can see that Datacash reference number is different in every response
388  $processor->setMerchantReference(md5(session_id().time()));
389  //get the merchant reference number back, it was changed because Datacash requires that merchant reference number length must be between 6 and 30 alphanumeric characters
390  $_SESSION['SQ_ECOM_REF_NO'] = $processor->getMerchantReference();
391 
392  //store the merchant reference number to the pending order asset before processing
393  $this->setPendingOrderMerchantReference($_SESSION['SQ_ECOM_REF_NO']);
394 
395  //SET CARD NUMBER
396  if (empty($card_info['number'])) {
397  $this->_setError(translate('datacash_card_number_not_specified'));
398  } else {
399  $card_info['number'] = str_replace(Array(' ', "\t"), '', $card_info['number']);
400  $processor->setCardNumber($card_info['number']);
401  }
402 
403  //SET CARD EXPIRY DATE
404  if ($this->_isValidDate(array_get_index($card_info, 'expiry_month', ''), array_get_index($card_info, 'expiry_year', ''))) {
405  $processor->setCardExpiryDate($card_info['expiry_month'], $card_info['expiry_year']);
406  } else {
407  $this->_setError(translate('datacash_expiry_date_invalid'));
408  }
409 
410  //SET CARD START DATE IF SPECIFIED BECAUSE START DATE IS ONLY REQUIRED FOR SOME CARD TYPES, E.G. SOLO
411  if (!empty($card_info['start_month']) || !empty($card_info['start_year'])) {
412  if ($this->_isValidDate(array_get_index($card_info, 'start_month', ''), array_get_index($card_info, 'start_year', ''))) {
413  $processor->setCardStartDate($card_info['start_month'], $card_info['start_year']);
414  } else {
415  $this->_setError(translate('datacash_start_date_invalid'));
416  }
417  }
418 
419  //SET CARD ISSUE NUMBER, IF SPECIFIED
420  if (!empty($card_info['issue_number'])) {
421  if ($this->_isValidIssueNumber($card_info['issue_number'])) {
422  $processor->setCardIssueNumber($card_info['issue_number']);
423  } else {
424  $this->_setError(translate('datacash_issue_number_invalid'));
425  }
426  }
427 
428  //SET CARD CV2, IF SPECIFIED
429  if (!empty($card_info['cv2'])) {
430  if ($this->_isValidCV2($card_info['cv2'])) {
431  $processor->setCardCV2($card_info['cv2']);
432  } else {
433  $this->_setError(translate('datacash_card_cv2_invalid'));
434  }
435  }
436 
437  $addr = '';
438  //SET STREET ADDRESS (1 - 4)
439  for ($i = 1; $i < 5; $i++) {
440  if (!empty($card_info['street_address'.$i])) {
441  $addr .= $card_info['street_address'.$i]."\n";
442  $processor->setStreetAddress($i, $card_info['street_address'.$i]);
443  }
444  }
445 
446  //SET POSTCODE
447  if (!empty($card_info['postcode'])) {
448  $addr .= $card_info['postcode']."\n";
449  $processor->setPostcode($card_info['postcode']);
450  }
451 
452  //SET TRANSACTION TYPE AS "AUTH" (ONE STAGE PROCESSING)
453  $processor->setTransactionTypeAuth();
454 
455  //SET 3-D SECURE PARAMETERS
456  $nonthreed_card_types = $this->attr('nonthreed_card_types');
457  $processor->setThreeDSecureParams($this->attr('merchant_url'), $this->attr('purchase_desc'), time(), empty($nonthreed_card_types)? Array() : explode('|', $nonthreed_card_types));
458 
459  //SET AVS/CV2
460  $policy = $this->attr('avscv2_standard_policy');
461  if ($policy != 0) {
462  $processor->setStandardPolicy($policy);
463 
464  if (($policy == 2) || ($policy == 3) || ($policy == 6) || ($policy == 7)) {
465  if (empty($card_info['cv2'])) {
466  $this->_setError(translate('datacash_card_cv2_not_specified'));
467  }
468  }
469 
470  if (($policy == 1) || ($policy == 3) || ($policy == 5) || ($policy == 7)) {
471  if (empty($card_info['street_address1']) && empty($card_info['street_address2']) && empty($card_info['street_address3']) && empty($card_info['street_address4'])) {
472  $this->_setError(translate('datacash_street_address_not_specified'));
473  }
474 
475  if (empty($card_info['postcode'])) {
476  $this->_setError(translate('datacash_postcode_not_specified'));
477  }
478  }
479 
480  }
481 
482  //CHECK IF THERE IS ERROR BEFORE SENDING DATA TO DATACASH SERVER, RETURN FALSE
483  if ($this->isError()) {
484  return FALSE;
485  }
486 
487  $success = $processor->process();
488 
489  //GET RESPONSE
490  $response = $processor->getResponse();
491 
492  //if success is 1 (payment is accepted) or 2 (redirect)
493  if ($success) {
494  //store the last 4 digits of card number to display it later in Form Ecommerce or Delivery Method through the Session variable SQ_ECOM_RESPONSE
495  $_SESSION['SQ_ECOM_FORMATTED_CARD_NUMBER'] = $this->_getFormattedCardNumber($card_info['number']);
496  //store the billing address to store in the Order asset of Form Ecommerce
497  $_SESSION['SQ_ECOM_ORDER_BILLING_ADDR'] = $addr;
498  }
499 
500  //if $success = 2, redirect user for card holder verification
501  if ($success === 2) {
502  $this->_redirect_info = $response;
503  } else {
504  //success = 1 or FALSE
505  $this->_setTransactionResult($success, $response);
506  }
507 
508  return $success;
509 
510  }//end processPayment()
511 
512 
522  function authorizePayment($datacash_ref, $pares)
523  {
524  $processor = new Datacash_Processor($this->attr('client'), $this->attr('password'), $this->attr('datacash_api_path'), $this->attr('cardinfo_dir_path'), $this->attr('timeout'), $this->attr('test_mode'));
525 
526  $success = $processor->authorize($datacash_ref, $pares);
527 
528  //get response
529  $response = $processor->getResponse();
530 
531  $this->_setTransactionResult($success, $response);
532 
533  return $success;
534 
535  }//end authorizePayment()
536 
537 
547  private function _setTransactionResult($success, $response)
548  {
549  if ($success === FALSE) {
550  $this->_setError($response['STATUS']);
551  } else { //success = 1
552  if ($this->attr('test_mode')) {
553  $response['STATUS'] = '!!!ATTENTION!!! TEST MODE (transaction not performed) -- '.$response['STATUS'];
554  }
555 
556  $card_no = '';
557  if (isset($_SESSION['SQ_ECOM_FORMATTED_CARD_NUMBER'])) {
558  $card_no = $_SESSION['SQ_ECOM_FORMATTED_CARD_NUMBER'];
559  unset($_SESSION['SQ_ECOM_FORMATTED_CARD_NUMBER']);
560  }
561 
562  $response['CARDNO'] = $card_no;
563  $response['AMOUNT'] = $_SESSION['SQ_ECOM_AMOUNT'];
564  $response['CURRENCY'] = $this->_getCurrency();
565 
566  $billing_addr = '';
567  if (isset($_SESSION['SQ_ECOM_ORDER_BILLING_ADDR'])) {
568  $billing_addr = $_SESSION['SQ_ECOM_ORDER_BILLING_ADDR'];
569  unset($_SESSION['SQ_ECOM_ORDER_BILLING_ADDR']);
570  }
571  $response['BILLING_ADDR'] = $billing_addr;
572 
573  $_SESSION['SQ_ECOM_RESPONSE'] = $response;
574  }
575 
576  }//end _setTransactionResult()
577 
578 
587  private function _getFormattedCardNumber($card_number)
588  {
589  $card_no = $card_number;
590  $card_len = strlen($card_no);
591  if ($card_len == 16) {
592  $card_no = '****-****-****-'.substr($card_no, -4);
593  } else {
594  $card_no = str_pad(substr($card_no, -4), $card_len, '*', STR_PAD_LEFT);
595  }
596 
597  return $card_no;
598 
599  }//end _getFormattedCardNumber()
600 
601 
610  function returnToCaller($state='SUCCESS', $is_in_frame = FALSE)
611  {
612  $back_url = NULL;
613 
614  if ($state == 'SUCCESS') {
615  $back_url = array_get_index($_SESSION, 'SQ_ECOM_SUCCESS_URL');
616  } else if ($state == 'CANCEL') {
617  $back_url = array_get_index($_SESSION, 'SQ_ECOM_CANCEL_URL');
618  }
619 
620  unset($_SESSION['SQ_ECOM_SUCCESS_URL']);
621  unset($_SESSION['SQ_ECOM_CANCEL_URL']);
622 
623  if (is_null($back_url)) {
624  if ($is_in_frame) {
625  $this->_redirectParent($this->getURL().'?unknown_referer=1');
626  } else {
627  trigger_error('Unknown caller reference');
628  exit;
629  }
630  } else {
631  if ($is_in_frame) {
632  $this->_redirectParent($back_url);
633  }else {
634  header('Location: '.$back_url);
635  exit;
636  }
637  }
638 
639  }//end returnToCaller()
640 
641 
650  private function _redirectParent($url)
651  {
652  $string = <<<HEREDOC
653 <script type="text/javascript">
654  if (parent != self) {
655  parent.location = "{$url}";
656  }
657 </script>
658 HEREDOC;
659 
660  echo $string;
661  exit;
662 
663  }//end _redirectParent()
664 
665 
673  {
674  $prefix = $this->getPrefix();
675  $card = $prefix.'_card';
676 
677  // set variables for test mode
678  if ($this->attr('test_mode')) {
679  $test_card_numbers = Datacash_Processor::getTestCardNumbers();
680  $card_number = '<select name="'.$card.'[number]">';
681  foreach ($test_card_numbers as $number => $label) {
682  $card_number .= '<option value="'.$number.'" >'.$label.'</option>';
683  }
684  $card_number .= '</select>';
685  } else {
686  $card_number = '<input name="'.$card.'[number]" autocomplete="off" />';
687  }
688 
689  return $card_number;
690 
691  }//end getCardNumberKeywordReplacement()
692 
693 
701  {
702  $card = $this->getPrefix().'_card';
703 
704  $string = '<input name="'.$card.'[start_month]" size="2" autocomplete="off" />';
705 
706  return $string;
707 
708  }//end getCardStartMonthKeywordReplacement()
709 
710 
718  {
719  $card = $this->getPrefix().'_card';
720 
721  $string = '<input name="'.$card.'[start_year]" size="2" autocomplete="off" />';
722 
723  return $string;
724 
725  }//end getCardStartYearKeywordReplacement()
726 
727 
735  {
736  $card = $this->getPrefix().'_card';
737 
738  $string = '<input name="'.$card.'[expiry_month]" size="2" autocomplete="off" />';
739 
740  return $string;
741 
742  }//end getCardExpiryMonthKeywordReplacement()
743 
744 
752  {
753  $card = $this->getPrefix().'_card';
754 
755  $string = '<input name="'.$card.'[expiry_year]" size="2" autocomplete="off" />';
756 
757  return $string;
758 
759  }//end getCardExpiryYearKeywordReplacement()
760 
761 
769  {
770  $card = $this->getPrefix().'_card';
771 
772  $string = '<input name="'.$card.'[issue_number]" size="4" autocomplete="off" />';
773 
774  return $string;
775 
776  }//end getCardIssueNumberKeywordReplacement()
777 
778 
786  {
787  $card = $this->getPrefix().'_card';
788 
789  $string = '<input name="'.$card.'[cv2]" size="4" autocomplete="off" />';
790 
791  return $string;
792 
793  }//end getCardCv2KeywordReplacement()
794 
795 
803  {
804  ob_start();
805  $card = $this->getPrefix().'_card';
806  text_box($card.'[street_address1]', $this->_getDefaultInputFromPassThroughAttribute('addr1_var_name'));
807 
808  return ob_get_clean();
809 
810  }//end getStreetAddress1KeywordReplacement()
811 
812 
820  {
821  ob_start();
822  $card = $this->getPrefix().'_card';
823  text_box($card.'[street_address2]', $this->_getDefaultInputFromPassThroughAttribute('addr2_var_name'));
824 
825  return ob_get_clean();
826 
827  }//end getStreetAddress2KeywordReplacement()
828 
829 
837  {
838  ob_start();
839  $card = $this->getPrefix().'_card';
840  text_box($card.'[street_address3]', $this->_getDefaultInputFromPassThroughAttribute('addr3_var_name'));
841 
842  return ob_get_clean();
843 
844  }//end getStreetAddress3KeywordReplacement()
845 
846 
854  {
855  ob_start();
856  $card = $this->getPrefix().'_card';
857  text_box($card.'[street_address4]', $this->_getDefaultInputFromPassThroughAttribute('addr4_var_name'));
858 
859  return ob_get_clean();
860 
861  }//end getStreetAddress4KeywordReplacement()
862 
863 
871  {
872  ob_start();
873  $card = $this->getPrefix().'_card';
874  text_box($card.'[postcode]', $this->_getDefaultInputFromPassThroughAttribute('postcode_var_name'));
875 
876  return ob_get_clean();
877 
878  }//end getPostcodeKeywordReplacement()
879 
880 
888  {
889  $amount = array_get_index($_SESSION,'SQ_ECOM_AMOUNT', 0);
890 
891  return $amount;
892 
893  }//end getTransactionAmountKeywordReplacement()
894 
895 
903  {
904  return $this->_getCurrency();
905 
906  }//end getTransactionAmountKeywordReplacement()
907 
908 
916  {
917  if ($this->isError()) {
918  return '<span class="payment-gateway-transaction-error">'.$this->getErrorMessage().'</span>';
919  }
920 
921  return '';
922 
923  }//end getProcessingErrorKeywordReplacement()
924 
925 
933  {
934  $button_text = $this->attr('submit_text');
935  if (empty($button_text)) $button_text = 'Submit';
936 
937  return '<input type="submit" value="'.$button_text.'" />';
938 
939  }//end getSubmitButtonKeywordReplacement()
940 
941 
949  {
950  $button_text = $this->attr('reset_text');
951  if (empty($button_text)) $button_text = 'Reset';
952 
953  return '<input type="reset" value="'.$button_text.'" />';
954 
955  }//end getResetButtonKeywordReplacement()
956 
957 
965  {
966  $button_text = $this->attr('cancel_text');
967  if (empty($button_text)) $button_text = 'Cancel';
968 
969  return '<input type="submit" name="'.$this->getPrefix().'_action" value="'.$button_text.'" />';
970 
971  }//end getCancelButtonKeywordReplacement()
972 
973 
981  {
982  $md = md5($_SESSION['SQ_ECOM_REF_NO']);
983 
984  $string = <<<HEREDOC
985 <form name="PARequestForm" action="{$this->_redirect_info['ACS_URL']}" method="POST">
986  <input type="hidden" name="PaReq" value="{$this->_redirect_info['PAREQ_MESSAGE']}">
987  <input type="hidden" name="TermUrl" value="{$this->getURL()}">
988  <input type="hidden" name="MD" value="{$md}">
989 </form>
990 <iframe name="ACSframe" width="390" height="400" frameborder="0">
991  <b>Your browser does not support iframes</b>
992 </iframe>
993 <script type="text/javascript">
994  window.onload = function()
995  {
996  document.PARequestForm.target = "ACSframe";
997  document.PARequestForm.submit();
998  }
999 </script>
1000 HEREDOC;
1001 
1002  return $string;
1003 
1004  }//end getCardHolderVerificationFormKeywordReplacement()
1005 
1006 
1014  private function _setError($err_message)
1015  {
1016  $this->_tmp['is_error'] = TRUE;
1017  $this->_tmp['error_message'][] = $err_message;
1018 
1019  }//end _setError()
1020 
1021 
1030  private function _isValidDate($month, $year)
1031  {
1032  $valid = FALSE;
1033 
1034  $two_digits_pattern = '/^\d{2}$/';
1035  //month and year must have 2 digit pattern mm/yy
1036  if (preg_match($two_digits_pattern, $month) && preg_match($two_digits_pattern, $year)) {
1037  //month must be in 1 and 12
1038  if ((0 < $month) && ($month < 13)) {
1039  $valid = TRUE;
1040  }
1041  }
1042 
1043  return $valid;
1044 
1045  }//end _isValidDate()
1046 
1047 
1056  private function _isValidIssueNumber($issue_no)
1057  {
1058  $valid = FALSE;
1059 
1060  $pattern = '/^\d{1,2}$/';
1061  //issue number must be one or two digits long
1062  if (preg_match($pattern, $issue_no)) {
1063  $valid = TRUE;
1064  }
1065 
1066  return $valid;
1067 
1068  }//end _isValidIssueNumber()
1069 
1070 
1079  private function _isValidCV2($cv2)
1080  {
1081  $valid = FALSE;
1082 
1083  $pattern = '/^\d{3,4}$/';
1084  //cv2 must be three or four (AMEX card only) digits long
1085  if (preg_match($pattern, $cv2)) {
1086  $valid = TRUE;
1087  }
1088 
1089  return $valid;
1090 
1091  }//end _isValidCV2()
1092 
1093 
1094  private function _getPassThroughVariable($var_name, $default)
1095  {
1096  if (is_null($this->_pass_through_vars)) {
1097  $this->_pass_through_vars = array_get_index($_SESSION, 'SQ_ECOM_PASS_THROUGH_VARS', Array());
1098  }
1099 
1100  return array_get_index($this->_pass_through_vars, $var_name, $default);
1101 
1102  }//end _getPassThroughVariable()
1103 
1104 
1105  private function _getDefaultInputFromPassThroughAttribute($attr_name)
1106  {
1107  $result = '';
1108  $var_name = $this->attr($attr_name);
1109  if (!empty($var_name)) {
1110  $result = $this->_getPassThroughVariable($var_name, '');
1111  }
1112 
1113  return $result;
1114 
1115  }//end _getDefaultInputFromPassThroughAttribute()
1116 
1117 
1124  private function _getCurrency()
1125  {
1126  return isset($_SESSION['SQ_ECOM_CURRENCY'])? $_SESSION['SQ_ECOM_CURRENCY'] : $this->attr('currency');
1127 
1128  }//end _getCurrency()
1129 
1130 
1137  private function _unsetCurrency()
1138  {
1139  if (isset($_SESSION['SQ_ECOM_CURRENCY'])) {
1140  unset($_SESSION['SQ_ECOM_CURRENCY']);
1141  }
1142 
1143  }//end _unsetCurrency()
1144 
1145 
1152  public function isError()
1153  {
1154  return array_get_index($this->_tmp, 'is_error', FALSE);
1155 
1156  }//end isError()
1157 
1158 
1165  public function getErrorMessage()
1166  {
1167  $err_message = '';
1168  $errors = array_get_index($this->_tmp, 'error_message', Array());
1169  foreach ($errors as $error) {
1170  $err_message .= "<li>$error </li>";
1171  }
1172 
1173  return '<ul>'.$err_message.'</ul>';
1174 
1175  }//end getErrorMessage()
1176 
1177 
1178 }//end class
1179 
1180 ?>