dolibarr 21.0.3
paymentok.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2001-2002 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2006-2013 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2012 Regis Houssin <regis.houssin@inodbox.com>
5 * Copyright (C) 2021-2023 Waël Almoman <info@almoman.com>
6 * Copyright (C) 2021 Maxime Demarest <maxime@indelog.fr>
7 * Copyright (C) 2021 Dorian Vabre <dorian.vabre@gmail.com>
8 * Copyright (C) 2024-2025 Frédéric France <frederic.france@free.fr>
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 3 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with this program. If not, see <https://www.gnu.org/licenses/>.
22 */
23
33if (!defined('NOLOGIN')) {
34 define("NOLOGIN", 1); // This means this output page does not require to be logged.
35}
36if (!defined('NOCSRFCHECK')) {
37 define("NOCSRFCHECK", 1); // We accept to go on this page from external web site.
38}
39if (!defined('NOIPCHECK')) {
40 define('NOIPCHECK', '1'); // Do not check IP defined into conf $dolibarr_main_restrict_ip
41}
42if (!defined('NOBROWSERNOTIF')) {
43 define('NOBROWSERNOTIF', '1');
44}
45
46if (!defined('XFRAMEOPTIONS_ALLOWALL')) {
47 define('XFRAMEOPTIONS_ALLOWALL', '1');
48}
49
50// For MultiCompany module.
51// Do not use GETPOST here, function is not defined and define must be done before including main.inc.php
52// Because 2 entities can have the same ref.
53$entity = (!empty($_GET['e']) ? (int) $_GET['e'] : (!empty($_POST['e']) ? (int) $_POST['e'] : 1));
54if (is_numeric($entity)) {
55 define("DOLENTITY", $entity);
56}
57
58// Load Dolibarr environment
59require '../../main.inc.php';
60require_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
61require_once DOL_DOCUMENT_ROOT.'/core/lib/payments.lib.php';
62require_once DOL_DOCUMENT_ROOT.'/core/lib/security2.lib.php';
63if (isModEnabled('paypal')) {
64 require_once DOL_DOCUMENT_ROOT.'/paypal/lib/paypal.lib.php';
65 require_once DOL_DOCUMENT_ROOT.'/paypal/lib/paypalfunctions.lib.php';
66}
67
78// Hook to be used by external payment modules (ie Payzen, ...)
79$hookmanager = new HookManager($db);
80
81$hookmanager->initHooks(array('newpayment'));
82
83$langs->loadLangs(array("main", "other", "dict", "bills", "companies", "paybox", "paypal", "stripe"));
84
85// Clean parameters
86$PAYPAL_API_USER = "";
87$PAYPAL_API_PASSWORD = "";
88$PAYPAL_API_SIGNATURE = "";
89$PAYPAL_API_SANDBOX = "";
90$PAYPALTOKEN = "";
91$PAYPALPAYERID = "";
92if (isModEnabled('paypal')) {
93 $PAYPAL_API_USER = getDolGlobalString('PAYPAL_API_USER');
94 $PAYPAL_API_PASSWORD = getDolGlobalString('PAYPAL_API_PASSWORD');
95 $PAYPAL_API_SIGNATURE = getDolGlobalString('PAYPAL_API_SIGNATURE');
96 $PAYPAL_API_SANDBOX = getDolGlobalString('PAYPAL_API_SANDBOX');
97
98 $PAYPALTOKEN = GETPOST('TOKEN');
99 if (empty($PAYPALTOKEN)) {
100 $PAYPALTOKEN = GETPOST('token');
101 }
102 $PAYPALPAYERID = GETPOST('PAYERID');
103 if (empty($PAYPALPAYERID)) {
104 $PAYPALPAYERID = GETPOST('PayerID');
105 }
106}
107
108$FULLTAG = GETPOST('FULLTAG');
109if (empty($FULLTAG)) {
110 $FULLTAG = GETPOST('fulltag');
111}
112$source = GETPOST('s', 'alpha') ? GETPOST('s', 'alpha') : GETPOST('source', 'alpha');
113$ref = GETPOST('ref');
114
115$suffix = GETPOST("suffix", 'aZ09');
116$membertypeid = GETPOSTINT("membertypeid");
117
118
119// Detect $paymentmethod
120$paymentmethod = '';
121$reg = array();
122if (preg_match('/PM=([^\.]+)/', $FULLTAG, $reg)) {
123 $paymentmethod = $reg[1];
124}
125if (empty($paymentmethod)) {
126 dol_syslog("***** paymentok.php was called with a non valid parameter FULLTAG=".$FULLTAG, LOG_DEBUG, 0, '_payment');
127 dol_print_error(null, 'The callback url does not contain a parameter fulltag that should help us to find the payment method used');
128 exit;
129}
130
131dol_syslog("***** paymentok.php is called paymentmethod=".$paymentmethod." FULLTAG=".$FULLTAG." REQUEST_URI=".$_SERVER["REQUEST_URI"], LOG_DEBUG, 0, '_payment');
132
133// Detect $ws
134$reg_ws = array();
135$ws = preg_match('/WS=([^\.]+)/', $FULLTAG, $reg_ws) ? $reg_ws[1] : 0;
136if ($ws) {
137 dol_syslog("paymentok.php page is invoked from a website with ref ".$ws.". It performs actions and then redirects back to this website. A page with ref paymentok must be created for this website.", LOG_DEBUG, 0, '_payment');
138}
139
140$validpaymentmethod = getValidOnlinePaymentMethods($paymentmethod);
141
142// Security check
143if (empty($validpaymentmethod)) {
144 httponly_accessforbidden('No valid payment mode');
145}
146
147// Common variables
148$creditor = $mysoc->name;
149$paramcreditor = 'ONLINE_PAYMENT_CREDITOR';
150$paramcreditorlong = 'ONLINE_PAYMENT_CREDITOR_'.$suffix;
151if (getDolGlobalString($paramcreditorlong)) {
152 $creditor = getDolGlobalString($paramcreditorlong); // use label long of the seller to show
153} elseif (getDolGlobalString($paramcreditor)) {
154 $creditor = getDolGlobalString($paramcreditor); // use label short of the seller to show
155}
156
157
158$ispaymentok = false;
159// If payment is ok
160$PAYMENTSTATUS = $TRANSACTIONID = $TAXAMT = $NOTE = '';
161// If payment is ko
162$ErrorCode = $ErrorShortMsg = $ErrorLongMsg = $ErrorSeverityCode = '';
163
164
165$object = new stdClass(); // For triggers
166
167$error = 0;
168
169// Check if we have redirtodomain to do.
170$ws_virtuelhost = null;
171$ws_id = 0;
172$doactionsthenredirect = 0;
173if ($ws) {
174 $doactionsthenredirect = 1;
175 include_once DOL_DOCUMENT_ROOT.'/website/class/website.class.php';
176 $website = new Website($db);
177 $result = $website->fetch(0, $ws);
178 if ($result > 0) {
179 $ws_virtuelhost = $website->virtualhost;
180 $ws_id = $website->id;
181 }
182}
183
184/*
185 * Actions
186 */
187
188// None
189
190
191/*
192 * View
193 */
194
195$now = dol_now();
196
197dol_syslog("Callback url when a payment was done. doactionsthenredirect=".$doactionsthenredirect." query_string=".(empty($_SERVER["QUERY_STRING"]) ? '' : dol_escape_htmltag($_SERVER["QUERY_STRING"]))." script_uri=".(empty($_SERVER["SCRIPT_URI"]) ? '' : dol_escape_htmltag($_SERVER["SCRIPT_URI"])), LOG_DEBUG, 0, '_payment');
198dol_syslog("_SERVER[SERVER_NAME] = ".(empty($_SERVER["SERVER_NAME"]) ? '' : dol_escape_htmltag($_SERVER["SERVER_NAME"])), LOG_DEBUG, 0, '_payment');
199dol_syslog("_SERVER[SERVER_ADDR] = ".(empty($_SERVER["SERVER_ADDR"]) ? '' : dol_escape_htmltag($_SERVER["SERVER_ADDR"])), LOG_DEBUG, 0, '_payment');
200
201$tracepost = "";
202foreach ($_POST as $k => $v) {
203 if (is_scalar($k) && is_scalar($v)) {
204 $tracepost .= "$k - $v\n";
205 }
206}
207dol_syslog("POST=".$tracepost, LOG_DEBUG, 0, '_payment');
208
209$tracesession = "";
210foreach ($_SESSION as $k => $v) {
211 if (is_scalar($k) && is_scalar($v) && in_array($k, array('currencyCodeType', 'errormessage', 'FinalPaymentAmt', 'ipaddress', 'onlinetoken', 'payerID', 'paymentType', 'TRANSACTIONID', 'paymentoksessionkey', 'paymentkosessionkey'))) {
212 $tracesession .= "$k - $v\n";
213 }
214}
215dol_syslog("SESSION=".$tracesession, LOG_DEBUG, 0, '_payment');
216
217dol_syslog("paymentoksessioncode=".GETPOST('paymentoksessioncode')." SESSION['paymentoksessioncode']=".$_SESSION['paymentoksessioncode'], LOG_DEBUG, 0, '_payment');
218
219$head = '';
220if (getDolGlobalString('ONLINE_PAYMENT_CSS_URL')) {
221 $head = '<link rel="stylesheet" type="text/css" href="' . getDolGlobalString('ONLINE_PAYMENT_CSS_URL').'?lang='.$langs->defaultlang.'">'."\n";
222}
223
224$conf->dol_hide_topmenu = 1;
225$conf->dol_hide_leftmenu = 1;
226
227
228// Show header
229if (empty($doactionsthenredirect)) {
230 $replacemainarea = (empty($conf->dol_hide_leftmenu) ? '<div>' : '').'<div>';
231 llxHeader($head, $langs->trans("PaymentForm"), '', '', 0, 0, '', '', '', 'onlinepaymentbody', $replacemainarea);
232
233
234 // Show page content id="dolpaymentdiv"
235 print '<span id="dolpaymentspan"></span>'."\n";
236 print '<div id="dolpaymentdiv" class="center">'."\n";
237
238
239 // Show logo (search order: logo defined by PAYMENT_LOGO_suffix, then PAYMENT_LOGO, then small company logo, large company logo, theme logo, common logo)
240 // Define logo and logosmall
241 $logosmall = $mysoc->logo_small;
242 $logo = $mysoc->logo;
243 $paramlogo = 'ONLINE_PAYMENT_LOGO_'.$suffix;
244 if (getDolGlobalString($paramlogo)) {
245 $logosmall = getDolGlobalString($paramlogo);
246 } elseif (getDolGlobalString('ONLINE_PAYMENT_LOGO')) {
247 $logosmall = getDolGlobalString('ONLINE_PAYMENT_LOGO');
248 }
249 //print '<!-- Show logo (logosmall='.$logosmall.' logo='.$logo.') -->'."\n";
250 // Define urllogo
251 $urllogo = '';
252 $urllogofull = '';
253 if (!empty($logosmall) && is_readable($conf->mycompany->dir_output.'/logos/thumbs/'.$logosmall)) {
254 $urllogo = DOL_URL_ROOT.'/viewimage.php?modulepart=mycompany&amp;entity='.$conf->entity.'&amp;file='.urlencode('logos/thumbs/'.$logosmall);
255 $urllogofull = $dolibarr_main_url_root.'/viewimage.php?modulepart=mycompany&entity='.$conf->entity.'&file='.urlencode('logos/thumbs/'.$logosmall);
256 } elseif (!empty($logo) && is_readable($conf->mycompany->dir_output.'/logos/'.$logo)) {
257 $urllogo = DOL_URL_ROOT.'/viewimage.php?modulepart=mycompany&amp;entity='.$conf->entity.'&amp;file='.urlencode('logos/'.$logo);
258 $urllogofull = $dolibarr_main_url_root.'/viewimage.php?modulepart=mycompany&entity='.$conf->entity.'&file='.urlencode('logos/'.$logo);
259 }
260
261 // Output html code for logo
262 if ($urllogo) {
263 print '<div class="backgreypublicpayment">';
264 print '<div class="logopublicpayment">';
265 print '<img id="dolpaymentlogo" src="'.$urllogo.'"';
266 print '>';
267 print '</div>';
268 if (!getDolGlobalString('MAIN_HIDE_POWERED_BY')) {
269 print '<div class="poweredbypublicpayment opacitymedium right"><a class="poweredbyhref" href="https://www.dolibarr.org?utm_medium=website&utm_source=poweredby" target="dolibarr" rel="noopener">'.$langs->trans("PoweredBy").'<br><img class="poweredbyimg" src="'.DOL_URL_ROOT.'/theme/dolibarr_logo.svg" width="80px"></a></div>';
270 }
271 print '</div>';
272 } elseif ($creditor) {
273 print '<div class="backgreypublicpayment">';
274 print '<div class="logopublicpayment">';
275 print $creditor;
276 print '</div>';
277 print '</div>';
278 }
279 if (getDolGlobalString('MAIN_IMAGE_PUBLIC_PAYMENT')) {
280 print '<div class="backimagepublicpayment">';
281 print '<img id="idMAIN_IMAGE_PUBLIC_PAYMENT" src="' . getDolGlobalString('MAIN_IMAGE_PUBLIC_PAYMENT').'">';
282 print '</div>';
283 }
284
285
286 print '<br><br><br>';
287}
288
289
290// Add steps to validate payment is complete when we enter this page
291
292
293// For Paypal: validate the payment (Paypal need another step after the callback return to validate the payment).
294if (isModEnabled('paypal') && $paymentmethod === 'paypal') { // We call this page only if payment is ok on payment system
295 if (!empty($PAYPALTOKEN)) {
296 // Get on url call
297 $onlinetoken = $PAYPALTOKEN;
298 $fulltag = $FULLTAG;
299 $payerID = !empty($PAYPALPAYERID) ? $PAYPALPAYERID : '';
300 // Set by newpayment.php
301 $ipaddress = $_SESSION['ipaddress'];
302 $currencyCodeType = $_SESSION['currencyCodeType'];
303 $FinalPaymentAmt = $_SESSION["FinalPaymentAmt"];
304 $paymentType = $_SESSION['PaymentType']; // Value can be 'Mark', 'Sole', 'Sale' for example
305
306 dol_syslog("Call paymentok with token=".$onlinetoken." paymentType=".$paymentType." currencyCodeType=".$currencyCodeType." payerID=".$payerID." ipaddress=".$ipaddress." FinalPaymentAmt=".$FinalPaymentAmt." fulltag=".$fulltag, LOG_DEBUG, 0, '_payment');
307
308 // Validate record
309 if (!empty($paymentType)) {
310 dol_syslog("We call GetExpressCheckoutDetails", LOG_DEBUG, 0, '_payment');
311 $resArray = getDetails($onlinetoken);
312 //var_dump($resarray);
313
314 $ack = strtoupper($resArray["ACK"]);
315 if ($ack == "SUCCESS" || $ack == "SUCCESSWITHWARNING") {
316 // Nothing to do
317 dol_syslog("Call to GetExpressCheckoutDetails return ".$ack, LOG_DEBUG, 0, '_payment');
318 } else {
319 dol_syslog("Call to GetExpressCheckoutDetails return error: ".json_encode($resArray), LOG_WARNING, 0, '_payment');
320 }
321
322 dol_syslog("We call DoExpressCheckoutPayment token=".$onlinetoken." paymentType=".$paymentType." currencyCodeType=".$currencyCodeType." payerID=".$payerID." ipaddress=".$ipaddress." FinalPaymentAmt=".$FinalPaymentAmt." fulltag=".$fulltag, LOG_DEBUG, 0, '_payment');
323 $resArray2 = confirmPayment($onlinetoken, $paymentType, $currencyCodeType, $payerID, $ipaddress, $FinalPaymentAmt, $fulltag);
324 //var_dump($resarray);
325
326 $ack = strtoupper($resArray2["ACK"]);
327 if ($ack == "SUCCESS" || $ack == "SUCCESSWITHWARNING") {
328 dol_syslog("Call to GetExpressCheckoutDetails return ".$ack, LOG_DEBUG, 0, '_payment');
329
330 $object->source = $source;
331 $object->ref = $ref;
332 $object->payerID = $payerID;
333 $object->fulltag = $fulltag;
334 $object->resArray = $resArray2;
335
336 // resArray was built from a string like that
337 // TOKEN=EC%2d1NJ057703V9359028&TIMESTAMP=2010%2d11%2d01T11%3a40%3a13Z&CORRELATIONID=1efa8c6a36bd8&ACK=Success&VERSION=56&BUILD=1553277&TRANSACTIONID=9B994597K9921420R&TRANSACTIONTYPE=expresscheckout&PAYMENTTYPE=instant&ORDERTIME=2010%2d11%2d01T11%3a40%3a12Z&AMT=155%2e57&FEEAMT=5%2e54&TAXAMT=0%2e00&CURRENCYCODE=EUR&PAYMENTSTATUS=Completed&PENDINGREASON=None&REASONCODE=None
338 $PAYMENTSTATUS = urldecode($resArray2["PAYMENTSTATUS"]); // Should contains 'Completed'
339 $TRANSACTIONID = urldecode($resArray2["TRANSACTIONID"]);
340 $TAXAMT = urldecode($resArray2["TAXAMT"]);
341 $NOTE = urldecode($resArray2["NOTE"]);
342
343 $ispaymentok = true;
344 } else {
345 dol_syslog("Call to DoExpressCheckoutPayment return error: ".json_encode($resArray2), LOG_WARNING, 0, '_payment');
346
347 //Display a user friendly Error on the page using any of the following error information returned by PayPal
348 $ErrorCode = urldecode($resArray2["L_ERRORCODE0"]);
349 $ErrorShortMsg = urldecode($resArray2["L_SHORTMESSAGE0"]);
350 $ErrorLongMsg = urldecode($resArray2["L_LONGMESSAGE0"]);
351 $ErrorSeverityCode = urldecode($resArray2["L_SEVERITYCODE0"]);
352 }
353 } else {
354 $ErrorCode = "SESSIONEXPIRED";
355 $ErrorLongMsg = "Session expired. Can't retrieve PaymentType. Payment has not been validated.";
356 $ErrorShortMsg = "Session expired";
357
358 dol_syslog($ErrorLongMsg, LOG_WARNING, 0, '_payment');
359 dol_print_error(null, 'Session expired');
360 }
361 } else {
362 $ErrorCode = "PAYPALTOKENNOTDEFINED";
363 $ErrorLongMsg = "The parameter PAYPALTOKEN was not defined. Payment has not been validated.";
364 $ErrorShortMsg = "Parameter PAYPALTOKEN not defined";
365
366 dol_syslog($ErrorLongMsg, LOG_WARNING, 0, '_payment');
367 dol_print_error(null, 'PAYPALTOKEN not defined');
368 }
369}
370
371// For Paybox
372if (isModEnabled('paybox')) {
373 if ($paymentmethod === 'paybox') {
374 // TODO Add a check to validate that payment is ok.
375 $ispaymentok = true; // We call this page only if payment is ok on payment system
376 }
377}
378
379// For Stripe
380if (isModEnabled('stripe')) {
381 if ($paymentmethod === 'stripe') {
382 // Check we are coming from the newpaymentpage
383 if (GETPOST('paymentoksessionkey') == $_SESSION['paymentoksessionkey']) {
384 // We can also request Stripe with payment_intent and payment_intent_client_secret the sameway we do in newpayment after comment "// Get here amount and currency used for payment".
385 $ispaymentok = true; // We call this page only if payment is ok on payment system
386 } else {
387 $ispaymentok = false; // We call this page only if payment is ok on payment system
388 }
389 }
390}
391
392// For other payment modules
393if (!in_array($paymentmethod, array('paypal', 'paybox', 'stripe'))) {
394 // Check status of the object to verify if it is paid by external payment modules
395 $action = '';
396 $parameters = [
397 'paymentmethod' => $paymentmethod,
398 ];
399 $reshook = $hookmanager->executeHooks('isPaymentOK', $parameters, $object, $action);
400 if ($reshook >= 0) {
401 if (isset($hookmanager->resArray['ispaymentok'])) {
402 dol_syslog('ispaymentok overwrite by hook return with value='.$hookmanager->resArray['ispaymentok'], LOG_DEBUG, 0, '_payment');
403 $ispaymentok = $hookmanager->resArray['ispaymentok'];
404 }
405 }
406}
407
408// Get variable into the session env
409if (empty($ipaddress)) {
410 $ipaddress = $_SESSION['ipaddress'];
411}
412if (empty($FinalPaymentAmt)) {
413 $FinalPaymentAmt = empty($_SESSION["FinalPaymentAmt"]) ? '' : $_SESSION["FinalPaymentAmt"];
414}
415if (empty($currencyCodeType)) {
416 $currencyCodeType = empty($_SESSION['currencyCodeType']) ? '' : $_SESSION['currencyCodeType'];
417}
418if (empty($paymentType)) { // Seems used only by Paypal
419 $paymentType = empty($_SESSION["paymentType"]) ? '' : $_SESSION["paymentType"];
420}
421
422if (empty($TRANSACTIONID)) {
423 $TRANSACTIONID = empty($_SESSION['TRANSACTIONID']) ? '' : $_SESSION['TRANSACTIONID']; // pi_... or ch_...
424 if (empty($TRANSACTIONID) && GETPOST('payment_intent', 'alphanohtml')) {
425 // For the case we use STRIPE_USE_INTENT_WITH_AUTOMATIC_CONFIRMATION = 2
426 $TRANSACTIONID = GETPOST('payment_intent', 'alphanohtml');
427 }
428}
429
430$fulltag = $FULLTAG;
431$tmptag = dolExplodeIntoArray($fulltag, '.', '=');
432
433
434dol_syslog("ispaymentok=".$ispaymentok." tmptag=".var_export($tmptag, true), LOG_DEBUG, 0, '_payment');
435
436
437// Set $appli for emails title
438$appli = $mysoc->name;
439
440
441// Make complementary actions (post payment actions if payment is ok)
442$ispostactionok = 0;
443$postactionmessages = array();
444if ($ispaymentok) {
445 // Set permission for the anonymous user
446 if (empty($user->rights->societe)) {
447 $user->rights->societe = new stdClass();
448 }
449 if (empty($user->rights->facture)) {
450 $user->rights->facture = new stdClass();
451 $user->rights->facture->invoice_advance = new stdClass();
452 }
453 if (empty($user->rights->adherent)) {
454 $user->rights->adherent = new stdClass();
455 $user->rights->adherent->cotisation = new stdClass();
456 }
457 $user->rights->societe->creer = 1;
458 $user->rights->facture->creer = 1;
459 $user->rights->facture->invoice_advance->validate = 1;
460 $user->rights->adherent->cotisation->creer = 1;
461
462 if (array_key_exists('MEM', $tmptag) && $tmptag['MEM'] > 0) {
463 // Validate member
464 // Create subscription
465 // Create complementary actions (this include creation of thirdparty)
466 // Send confirmation email
467
468 // Record subscription
469 include_once DOL_DOCUMENT_ROOT.'/adherents/class/adherent.class.php';
470 include_once DOL_DOCUMENT_ROOT.'/adherents/class/adherent_type.class.php';
471 include_once DOL_DOCUMENT_ROOT.'/adherents/class/subscription.class.php';
472 $adht = new AdherentType($db);
473 $object = new Adherent($db);
474
475 $result1 = $object->fetch((int) $tmptag['MEM']);
476 $result2 = $adht->fetch($object->typeid);
477
478 $defaultdelay = !empty($adht->duration_value) ? $adht->duration_value : 1;
479 $defaultdelayunit = !empty($adht->duration_unit) ? $adht->duration_unit : 'y';
480
481 dol_syslog("We have to process member with id=".$tmptag['MEM']." result1=".$result1." result2=".$result2, LOG_DEBUG, 0, '_payment');
482
483 if ($result1 > 0 && $result2 > 0) {
484 $paymentTypeId = 0;
485 if ($paymentmethod == 'paybox') {
486 $paymentTypeId = getDolGlobalInt('PAYBOX_PAYMENT_MODE_FOR_PAYMENTS');
487 }
488 if ($paymentmethod == 'paypal') {
489 $paymentTypeId = getDolGlobalInt('PAYPAL_PAYMENT_MODE_FOR_PAYMENTS');
490 }
491 if ($paymentmethod == 'stripe') {
492 $paymentTypeId = getDolGlobalInt('STRIPE_PAYMENT_MODE_FOR_PAYMENTS');
493 }
494 if (empty($paymentTypeId)) {
495 dol_syslog("paymentType = ".$paymentType, LOG_DEBUG, 0, '_payment');
496
497 if (empty($paymentType)) {
498 $paymentType = 'CB';
499 }
500 // May return nothing when paymentType means nothing
501 // (for example when paymentType is 'Mark', 'Sole', 'Sale', for paypal)
502 $paymentTypeId = dol_getIdFromCode($db, $paymentType, 'c_paiement', 'code', 'id', 1);
503
504 // If previous line has returned nothing, we force to get the ID of payment of Credit Card (hard coded code 'CB').
505 if (empty($paymentTypeId) || $paymentTypeId < 0) {
506 $paymentTypeId = dol_getIdFromCode($db, 'CB', 'c_paiement', 'code', 'id', 1);
507 }
508 }
509
510 dol_syslog("FinalPaymentAmt=".$FinalPaymentAmt." paymentTypeId=".$paymentTypeId." currencyCodeType=".$currencyCodeType, LOG_DEBUG, 0, '_payment');
511
512 // Do action only if $FinalPaymentAmt is set (session variable is cleaned after this page to avoid duplicate actions when page is POST a second time)
513 if (!empty($FinalPaymentAmt) && $paymentTypeId > 0) {
514 // Security protection:
515 if (empty($adht->caneditamount)) { // If we didn't allow members to choose their membership amount (if the amount is allowed in edit mode, no need to check)
516 if ($object->status == $object::STATUS_DRAFT) { // If the member is not yet validated, we check that the amount is the same as expected.
517 $typeid = $object->typeid;
518 $amountbytype = $adht->amountByType(1); // Load the array of amount per type
519
520 // Set amount for the subscription:
521 // - First check the amount of the member type.
522 $amountexpected = empty($amountbytype[$typeid]) ? 0 : $amountbytype[$typeid];
523 // - If not found, take the default amount
524 if (empty($amountexpected) && getDolGlobalString('MEMBER_NEWFORM_AMOUNT')) {
525 $amountexpected = getDolGlobalString('MEMBER_NEWFORM_AMOUNT');
526 }
527 // - If not set, we accept to have amount defined as parameter (for backward compatibility).
528 //if (empty($amount)) {
529 // $amount = (GETPOST('amount') ? price2num(GETPOST('amount', 'alpha'), 'MT', 2) : '');
530 //}
531 // - If a min is set, we take it into account
532 $amountexpected = max(0, (float) $amountexpected, (float) getDolGlobalInt("MEMBER_MIN_AMOUNT"));
533
534 if ($amountexpected && $amountexpected != $FinalPaymentAmt) {
535 $error++;
536 $errmsg = 'Value of FinalPayment ('.$FinalPaymentAmt.') propagated by payment page differs from the expected value for membership ('.$amountexpected.'). May be a hack to try to pay a different amount ?';
537 $postactionmessages[] = $errmsg;
538 $ispostactionok = -1;
539 dol_syslog("Failed to validate member (bad amount check): ".$errmsg, LOG_ERR, 0, '_payment');
540 }
541 }
542 }
543
544 // Security protection:
545 if (getDolGlobalInt('MEMBER_MIN_AMOUNT')) {
546 if ($FinalPaymentAmt < getDolGlobalInt('MEMBER_MIN_AMOUNT')) {
547 $error++;
548 $errmsg = 'Value of FinalPayment ('.$FinalPaymentAmt.') is lower than the minimum allowed (' . getDolGlobalString('MEMBER_MIN_AMOUNT').'). May be a hack to try to pay a different amount ?';
549 $postactionmessages[] = $errmsg;
550 $ispostactionok = -1;
551 dol_syslog("Failed to validate member (amount propagated from payment page is lower than allowed minimum): ".$errmsg, LOG_ERR, 0, '_payment');
552 }
553 }
554
555 // Security protection:
556 if ($currencyCodeType && $currencyCodeType != $conf->currency) { // Check that currency is the good one
557 $error++;
558 $errmsg = 'Value of currencyCodeType ('.$currencyCodeType.') differs from value expected for membership ('.$conf->currency.'). May be a hack to try to pay a different amount ?';
559 $postactionmessages[] = $errmsg;
560 $ispostactionok = -1;
561 dol_syslog("Failed to validate member (bad currency check): ".$errmsg, LOG_ERR, 0, '_payment');
562 }
563
564 if (! $error) {
565 // We validate the member (no effect if it is already validated)
566 $result = ($object->status == $object::STATUS_EXCLUDED) ? -1 : $object->validate($user); // if membre is excluded (status == -2) the new validation is not possible
567 if ($result < 0 || empty($object->datevalid)) {
568 $error++;
569 $errmsg = $object->error;
570 $postactionmessages[] = $errmsg;
571 $postactionmessages = array_merge($postactionmessages, $object->errors);
572 $ispostactionok = -1;
573 dol_syslog("Failed to validate member: ".$errmsg, LOG_ERR, 0, '_payment');
574 }
575 }
576
577 // Guess the subscription start date
578 $datesubscription = $object->datevalid; // By default, the subscription start date is the payment date
579 if ($object->datefin > 0) {
580 $datesubscription = dol_time_plus_duree($object->datefin, 1, 'd');
581 } elseif (getDolGlobalString('MEMBER_SUBSCRIPTION_START_AFTER')) {
582 $datesubscription = dol_time_plus_duree($now, (int) substr(getDolGlobalString('MEMBER_SUBSCRIPTION_START_AFTER'), 0, -1), substr(getDolGlobalString('MEMBER_SUBSCRIPTION_START_AFTER'), -1));
583 }
584 // Now do a correction of the suggested date
585 if (getDolGlobalString('MEMBER_SUBSCRIPTION_START_FIRST_DAY_OF') === "m") {
586 $datesubscription = dol_get_first_day((int) dol_print_date($datesubscription, "%Y"), (int) dol_print_date($datesubscription, "%m"));
587 } elseif (getDolGlobalString('MEMBER_SUBSCRIPTION_START_FIRST_DAY_OF') === "3m") {
588 $datesubscription = dol_time_plus_duree($object->datefin, -3, 'm');
589 $datesubscription = dol_get_first_day((int) dol_print_date($datesubscription, "%Y"), (int) dol_print_date($datesubscription, "%m"));
590 } elseif (getDolGlobalString('MEMBER_SUBSCRIPTION_START_FIRST_DAY_OF') === "Y") {
591 $datesubscription = dol_get_first_day((int) dol_print_date($datesubscription, "%Y"));
592 }
593
594 $datesubend = null;
595 if ($datesubscription && $defaultdelay && $defaultdelayunit) {
596 $datesubend = dol_time_plus_duree($datesubscription, $defaultdelay, $defaultdelayunit);
597 // the new end date of subscription must be in futur
598 while ($datesubend < $now) {
599 $datesubend = dol_time_plus_duree($datesubend, $defaultdelay, $defaultdelayunit);
600 $datesubscription = dol_time_plus_duree($datesubscription, $defaultdelay, $defaultdelayunit);
601 }
602 $datesubend = dol_time_plus_duree($datesubend, -1, 'd');
603 }
604
605 // Set output language
606 $outputlangs = new Translate('', $conf);
607 $outputlangs->setDefaultLang(empty($object->thirdparty->default_lang) ? $mysoc->default_lang : $object->thirdparty->default_lang);
608 $paymentdate = $now;
609 $amount = $FinalPaymentAmt;
610 $formatteddate = dol_print_date($paymentdate, 'dayhour', 'auto', $outputlangs);
611 $label = $langs->trans("OnlineSubscriptionPaymentLine", $formatteddate, $paymentmethod, $ipaddress, $TRANSACTIONID);
612
613 // Payment information
614 $accountid = 0;
615 if ($paymentmethod == 'paybox') {
616 $accountid = getDolGlobalString('PAYBOX_BANK_ACCOUNT_FOR_PAYMENTS');
617 }
618 if ($paymentmethod == 'paypal') {
619 $accountid = getDolGlobalString('PAYPAL_BANK_ACCOUNT_FOR_PAYMENTS');
620 }
621 if ($paymentmethod == 'stripe') {
622 $accountid = getDolGlobalString('STRIPE_BANK_ACCOUNT_FOR_PAYMENTS');
623 }
624
625 //Get bank account for a specific paymentmedthod
626 $parameters = [
627 'paymentmethod' => $paymentmethod,
628 ];
629 $reshook = $hookmanager->executeHooks('getBankAccountPaymentMethod', $parameters, $object, $action);
630 if ($reshook >= 0) {
631 if (isset($hookmanager->resArray['bankaccountid'])) {
632 dol_syslog('accountid overwrite by hook return with value='.$hookmanager->resArray['bankaccountid'], LOG_DEBUG, 0, '_payment');
633 $accountid = $hookmanager->resArray['bankaccountid'];
634 }
635 }
636 if ($accountid < 0) {
637 $error++;
638 $errmsg = 'Setup of bank account to use for payment is not correctly done for payment method '.$paymentmethod;
639 $postactionmessages[] = $errmsg;
640 $ispostactionok = -1;
641 dol_syslog("Failed to get the bank account to record payment: ".$errmsg, LOG_ERR, 0, '_payment');
642 }
643
644 $operation = dol_getIdFromCode($db, $paymentTypeId, 'c_paiement', 'id', 'code', 1); // Payment mode code returned from payment mode id
645 $num_chq = '';
646 $emetteur_nom = '';
647 $emetteur_banque = '';
648 // Define default choice for complementary actions
649 $option = '';
650 if (getDolGlobalString('ADHERENT_BANK_USE') == 'bankviainvoice' && isModEnabled("bank") && isModEnabled("societe") && isModEnabled('invoice')) {
651 $option = 'bankviainvoice';
652 } elseif (getDolGlobalString('ADHERENT_BANK_USE') == 'bankdirect' && isModEnabled("bank")) {
653 $option = 'bankdirect';
654 } elseif (getDolGlobalString('ADHERENT_BANK_USE') == 'invoiceonly' && isModEnabled("bank") && isModEnabled("societe") && isModEnabled('invoice')) {
655 $option = 'invoiceonly';
656 }
657 if (empty($option)) {
658 $option = 'none';
659 }
660 $sendalsoemail = 1;
661
662 // Record the subscription then complementary actions
663 $db->begin();
664
665 // Create subscription
666 if (!$error) {
667 dol_syslog("Call ->subscription to create subscription", LOG_DEBUG, 0, '_payment');
668
669 $crowid = $object->subscription($datesubscription, $amount, $accountid, $operation, $label, $num_chq, $emetteur_nom, $emetteur_banque, $datesubend, $membertypeid);
670 if ($crowid <= 0) {
671 $error++;
672 $errmsg = $object->error;
673 $postactionmessages[] = $errmsg;
674 $ispostactionok = -1;
675 } else {
676 $postactionmessages[] = 'Subscription created (id='.$crowid.')';
677 $ispostactionok = 1;
678 }
679 }
680
681 if (!$error) {
682 dol_syslog("Call ->subscriptionComplementaryActions option=".$option, LOG_DEBUG, 0, '_payment');
683
684 $autocreatethirdparty = 1; // will create thirdparty if member not yet linked to a thirdparty
685
686 $result = $object->subscriptionComplementaryActions($crowid, $option, $accountid, $datesubscription, $paymentdate, $operation, $label, $amount, $num_chq, $emetteur_nom, $emetteur_banque, $autocreatethirdparty, $TRANSACTIONID, $service);
687 if ($result < 0) {
688 dol_syslog("Error ".$object->error." ".implode(',', $object->errors), LOG_DEBUG, 0, '_payment');
689
690 $error++;
691 $postactionmessages[] = $object->error;
692 $postactionmessages = array_merge($postactionmessages, $object->errors);
693 $ispostactionok = -1;
694 } else {
695 if ($option == 'bankviainvoice') {
696 $postactionmessages[] = 'Invoice, payment and bank record created';
697 dol_syslog("Invoice, payment and bank record created", LOG_DEBUG, 0, '_payment');
698 }
699 if ($option == 'bankdirect') {
700 $postactionmessages[] = 'Bank record created';
701 dol_syslog("Bank record created", LOG_DEBUG, 0, '_payment');
702 }
703 if ($option == 'invoiceonly') {
704 $postactionmessages[] = 'Invoice recorded';
705 dol_syslog("Invoice recorded", LOG_DEBUG, 0, '_payment');
706 }
707 $ispostactionok = 1;
708
709 // If an invoice was created, it is into $object->invoice
710 }
711 }
712
713 if (!$error) {
714 // If payment using Strip, save the Stripe payment info into societe_account
715 if ($paymentmethod == 'stripe' && $autocreatethirdparty && $option == 'bankviainvoice') {
716 $thirdparty_id = ($object->socid ? $object->socid : $object->fk_soc);
717
718 dol_syslog("Search existing Stripe customer profile for thirdparty_id=".$thirdparty_id, LOG_DEBUG, 0, '_payment');
719
720 $service = 'StripeTest';
721 $servicestatus = 0;
722 if (getDolGlobalString('STRIPE_LIVE') && !GETPOST('forcesandbox', 'alpha')) {
723 $service = 'StripeLive';
724 $servicestatus = 1;
725 }
726 $stripeacc = null; // No Oauth/connect use for public pages
727
728 $thirdparty = new Societe($db);
729 $thirdparty->fetch($thirdparty_id);
730
731 include_once DOL_DOCUMENT_ROOT.'/stripe/class/stripe.class.php'; // This also set $stripearrayofkeysbyenv
732 $stripe = new Stripe($db);
733 //$stripeacc = $stripe->getStripeAccount($service); Already defined previously
734
735 $customer = $stripe->customerStripe($thirdparty, $stripeacc, $servicestatus, 0);
736
737 if (!$customer && $TRANSACTIONID) { // Not linked to a stripe customer, we make the link
738 dol_syslog("No stripe profile found, so we add it for TRANSACTIONID = ".$TRANSACTIONID, LOG_DEBUG, 0, '_payment');
739
740 try {
741 global $stripearrayofkeysbyenv;
742 \Stripe\Stripe::setApiKey($stripearrayofkeysbyenv[$servicestatus]['secret_key']);
743
744 if (preg_match('/^pi_/', $TRANSACTIONID)) {
745 // This may throw an error if not found.
746 $chpi = \Stripe\PaymentIntent::retrieve($TRANSACTIONID); // payment_intent (pi_...)
747 } else {
748 // This throw an error if not found
749 $chpi = \Stripe\Charge::retrieve($TRANSACTIONID); // old method, contains the charge id (ch_...)
750 }
751
752 if ($chpi) {
753 $stripecu = $chpi->customer; // value 'cus_....'. WARNING: This property may be empty if first payment was recorded before the stripe customer was created.
754
755 if (empty($stripecu)) {
756 // This include the INSERT
757 $customer = $stripe->customerStripe($thirdparty, $stripeacc, $servicestatus, 1);
758
759 // Link this customer to the payment intent
760 if (preg_match('/^pi_/', $TRANSACTIONID) && $customer) {
761 \Stripe\PaymentIntent::update($chpi->id, array('customer' => $customer->id));
762 }
763 } else {
764 $sql = "INSERT INTO ".MAIN_DB_PREFIX."societe_account (fk_soc, login, key_account, site, site_account, status, entity, date_creation, fk_user_creat)";
765 $sql .= " VALUES (".((int) $thirdparty_id).", '', '".$db->escape($stripecu)."', 'stripe', '".$db->escape($stripearrayofkeysbyenv[$servicestatus]['publishable_key'])."', ".((int) $servicestatus).", ".((int) $conf->entity).", '".$db->idate(dol_now())."', 0)";
766 $resql = $db->query($sql);
767 if (!$resql) { // should not happen
768 $error++;
769 $errmsg = 'Failed to insert customer stripe id in database : '.$db->lasterror();
770 dol_syslog($errmsg, LOG_ERR, 0, '_payment');
771 $postactionmessages[] = $errmsg;
772 $ispostactionok = -1;
773 }
774 }
775 } else { // should not happen
776 $error++;
777 $errmsg = 'Failed to retrieve paymentintent or charge from id';
778 dol_syslog($errmsg, LOG_ERR, 0, '_payment');
779 $postactionmessages[] = $errmsg;
780 $ispostactionok = -1;
781 }
782 } catch (Exception $e) { // should not happen
783 $error++;
784 $errmsg = 'Failed to get or save customer stripe id in database : '.$e->getMessage();
785 dol_syslog($errmsg, LOG_ERR, 0, '_payment');
786 $postactionmessages[] = $errmsg;
787 $ispostactionok = -1;
788 }
789 }
790 }
791 }
792
793 if (!$error) {
794 $db->commit();
795 } else {
796 $db->rollback();
797 }
798
799 // Set string to use to send email info
800 $infouserlogin = '';
801
802 // Create external user
803 if (getDolGlobalString('ADHERENT_CREATE_EXTERNAL_USER_LOGIN')) {
804 $nuser = new User($db);
805 $tmpuser = dol_clone($object, 0); // $object is type Adherent
806
807 // Check if a user login already exists for this member or not
808 $found = 0;
809 $sql = "SELECT COUNT(rowid) as nb FROM ".MAIN_DB_PREFIX."user WHERE fk_member = ".((int) $object->id);
810 $resqlcount = $db->query($sql);
811 if ($resqlcount) {
812 $objcount = $db->fetch_object($resqlcount);
813 if ($objcount) {
814 $found = $objcount->nb;
815 }
816 }
817
818 if (!$found) {
819 $result = $nuser->create_from_member($tmpuser, $object->login);
820 $newpassword = $nuser->setPassword($user, '');
821
822 if ($result < 0) {
823 $outputlangs->load("errors");
824 $postactionmessages[] = 'Error in create external user : '.$nuser->error;
825 } else {
826 $infouserlogin = $outputlangs->trans("Login").': '.$nuser->login.' '."\n".$outputlangs->trans("Password").': '.$newpassword;
827 $postactionmessages[] = $langs->trans("NewUserCreated", $nuser->login);
828 }
829 } else {
830 $outputlangs->load("errors");
831 $postactionmessages[] = 'No user created because a user linked to member already exists';
832 }
833 }
834
835 // Send email to member
836 if (!$error) {
837 dol_syslog("Send email to customer to ".$object->email." if we have to (sendalsoemail = ".$sendalsoemail.")", LOG_DEBUG, 0, '_payment');
838
839 // Send confirmation Email
840 if ($object->email && $sendalsoemail) {
841 $subject = '';
842 $msg = '';
843
844 // Send subscription email
845 include_once DOL_DOCUMENT_ROOT.'/core/class/html.formmail.class.php';
846 $formmail = new FormMail($db);
847 // Load traductions files required by page
848 $outputlangs->loadLangs(array("main", "members"));
849 // Get email content from template
850 $arraydefaultmessage = null;
851 $labeltouse = getDolGlobalString('ADHERENT_EMAIL_TEMPLATE_SUBSCRIPTION');
852
853 if (!empty($labeltouse)) {
854 $arraydefaultmessage = $formmail->getEMailTemplate($db, 'member', $user, $outputlangs, 0, 1, $labeltouse);
855 }
856
857 if (!empty($labeltouse) && is_object($arraydefaultmessage) && $arraydefaultmessage->id > 0) {
858 $subject = $arraydefaultmessage->topic;
859 $msg = $arraydefaultmessage->content;
860 }
861
862 $substitutionarray = getCommonSubstitutionArray($outputlangs, 0, null, $object);
863
864 if ($infouserlogin) {
865 $substitutionarray['__MEMBER_USER_LOGIN_INFORMATION__'] = $infouserlogin;
866 }
867
868 complete_substitutions_array($substitutionarray, $outputlangs, $object);
869 $subjecttosend = make_substitutions($subject, $substitutionarray, $outputlangs);
870 $texttosend = make_substitutions(dol_concatdesc($msg, $adht->getMailOnSubscription()), $substitutionarray, $outputlangs);
871
872 // Attach a file ?
873 $file = '';
874 $listofpaths = array();
875 $listofnames = array();
876 $listofmimes = array();
877 if (is_object($object->invoice)) {
878 $invoicediroutput = $conf->facture->dir_output;
879 $fileparams = dol_most_recent_file($invoicediroutput.'/'.$object->invoice->ref, preg_quote($object->invoice->ref, '/').'[^\-]+');
880 $file = $fileparams['fullname'];
881
882 $listofpaths = array($file);
883 $listofnames = array(basename($file));
884 $listofmimes = array(dol_mimetype($file));
885 }
886
887 $moreinheader = 'X-Dolibarr-Info: send_an_email by public/payment/paymentok.php'."\r\n";
888
889 $result = $object->sendEmail($texttosend, $subjecttosend, $listofpaths, $listofmimes, $listofnames, "", "", 0, -1, "", $moreinheader);
890
891 if ($result < 0) {
892 $errmsg = $object->error;
893 $postactionmessages[] = $errmsg;
894 $ispostactionok = -1;
895 } else {
896 if ($file) {
897 $postactionmessages[] = 'Email sent to member (with invoice document attached)';
898 } else {
899 $postactionmessages[] = 'Email sent to member (without any attached document)';
900 }
901
902 // TODO Add actioncomm event
903 }
904 }
905 }
906 } else {
907 $postactionmessages[] = 'Failed to get a valid value for "amount paid" or "payment type" to record the payment of subscription for member '.$tmptag['MEM'].'. May be payment was already recorded.';
908 $ispostactionok = -1;
909 }
910 } else {
911 $postactionmessages[] = 'Member '.$tmptag['MEM'].' for subscription paid was not found';
912 $ispostactionok = -1;
913 }
914 } elseif (array_key_exists('INV', $tmptag) && $tmptag['INV'] > 0) {
915 // Record payment
916 include_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
917 $object = new Facture($db);
918 $result = $object->fetch((int) $tmptag['INV']);
919 if ($result) {
920 $FinalPaymentAmt = $_SESSION["FinalPaymentAmt"];
921
922 $paymentTypeId = 0;
923 if ($paymentmethod === 'paybox') {
924 $paymentTypeId = getDolGlobalInt('PAYBOX_PAYMENT_MODE_FOR_PAYMENTS');
925 }
926 if ($paymentmethod === 'paypal') {
927 $paymentTypeId = getDolGlobalInt('PAYPAL_PAYMENT_MODE_FOR_PAYMENTS');
928 }
929 if ($paymentmethod === 'stripe') {
930 $paymentTypeId = getDolGlobalInt('STRIPE_PAYMENT_MODE_FOR_PAYMENTS');
931 }
932 if (empty($paymentTypeId)) {
933 dol_syslog("paymentType = ".$paymentType, LOG_DEBUG, 0, '_payment');
934
935 if (empty($paymentType)) {
936 $paymentType = 'CB';
937 }
938 // May return nothing when paymentType means nothing
939 // (for example when paymentType is 'Mark', 'Sole', 'Sale', for paypal)
940 $paymentTypeId = dol_getIdFromCode($db, $paymentType, 'c_paiement', 'code', 'id', 1);
941
942 // If previous line has returned nothing, we force to get the ID of payment of Credit Card (hard coded code 'CB').
943 if (empty($paymentTypeId) || $paymentTypeId < 0) {
944 $paymentTypeId = dol_getIdFromCode($db, 'CB', 'c_paiement', 'code', 'id', 1);
945 }
946 }
947
948 dol_syslog("FinalPaymentAmt = ".$FinalPaymentAmt." paymentTypeId = ".$paymentTypeId, LOG_DEBUG, 0, '_payment');
949
950 // Do action only if $FinalPaymentAmt is set (session variable is cleaned after this page to avoid duplicate actions when page is POST a second time)
951 if (!empty($FinalPaymentAmt) && $paymentTypeId > 0) {
952 $db->begin();
953
954 // Creation of payment line
955 include_once DOL_DOCUMENT_ROOT.'/compta/paiement/class/paiement.class.php';
956 $paiement = new Paiement($db);
957 $paiement->datepaye = $now;
958 if ($currencyCodeType == $conf->currency) {
959 $paiement->amounts = array($object->id => $FinalPaymentAmt); // Array with all payments dispatching with invoice id
960 } else {
961 $paiement->multicurrency_amounts = array($object->id => $FinalPaymentAmt); // Array with all payments dispatching
962
963 $postactionmessages[] = 'Payment was done in a currency ('.$currencyCodeType.') other than the expected currency of company ('.$conf->currency.')';
964 $ispostactionok = -1;
965 $error++; // Not yet supported
966 }
967 $paiement->paiementid = $paymentTypeId;
968 $paiement->num_payment = '';
969 $paiement->note_public = 'Online payment '.dol_print_date($now, 'standard').' from '.$ipaddress;
970 $paiement->ext_payment_id = $TRANSACTIONID; // TODO LDR May be we should store py_... instead of pi_... but we started with pi_... so we continue.
971 //$paiement->ext_payment_id = $TRANSACTIONID.':'.$customer->id.'@'.$stripearrayofkeysbyenv[$servicestatus]['publishable_key']; // TODO LDR It would be better if we could store this. Do we have customer->id and publishable_key ?
972 $paiement->ext_payment_site = $service;
973
974 if (!$error) {
975 $paiement_id = $paiement->create($user, 1); // This include closing invoices and regenerating documents
976 if ($paiement_id < 0) {
977 $postactionmessages[] = $paiement->error.' '.implode("<br>\n", $paiement->errors);
978 $ispostactionok = -1;
979 $error++;
980 } else {
981 $postactionmessages[] = 'Payment created';
982 $ispostactionok = 1;
983 }
984 }
985
986 if (!$error && isModEnabled("bank")) {
987 $bankaccountid = 0;
988 if ($paymentmethod == 'paybox') {
989 $bankaccountid = getDolGlobalString('PAYBOX_BANK_ACCOUNT_FOR_PAYMENTS');
990 } elseif ($paymentmethod == 'paypal') {
991 $bankaccountid = getDolGlobalString('PAYPAL_BANK_ACCOUNT_FOR_PAYMENTS');
992 } elseif ($paymentmethod == 'stripe') {
993 $bankaccountid = getDolGlobalString('STRIPE_BANK_ACCOUNT_FOR_PAYMENTS');
994 }
995
996 //Get bank account for a specific paymentmedthod
997 $parameters = [
998 'paymentmethod' => $paymentmethod,
999 ];
1000 $reshook = $hookmanager->executeHooks('getBankAccountPaymentMethod', $parameters, $object, $action);
1001 if ($reshook >= 0) {
1002 if (isset($hookmanager->resArray['bankaccountid'])) {
1003 dol_syslog('bankaccountid overwrite by hook return with value='.$hookmanager->resArray['bankaccountid'], LOG_DEBUG, 0, '_payment');
1004 $bankaccountid = $hookmanager->resArray['bankaccountid'];
1005 }
1006 }
1007 if ($bankaccountid > 0) {
1008 $label = '(CustomerInvoicePayment)';
1009 if ($object->type == Facture::TYPE_CREDIT_NOTE) {
1010 $label = '(CustomerInvoicePaymentBack)'; // Refund of a credit note
1011 }
1012 $result = $paiement->addPaymentToBank($user, 'payment', $label, $bankaccountid, '', '');
1013 if ($result < 0) {
1014 $postactionmessages[] = $paiement->error.' '.implode("<br>\n", $paiement->errors);
1015 $ispostactionok = -1;
1016 $error++;
1017 } else {
1018 $postactionmessages[] = 'Bank transaction of payment created';
1019 $ispostactionok = 1;
1020 }
1021 } else {
1022 $postactionmessages[] = 'Setup of bank account to use in module '.$paymentmethod.' was not set. Your payment was really executed but we failed to record it. Please contact us.';
1023 $ispostactionok = -1;
1024 $error++;
1025 }
1026 }
1027
1028 if (!$error) {
1029 $db->commit();
1030 } else {
1031 $db->rollback();
1032 }
1033 } else {
1034 $postactionmessages[] = 'Failed to get a valid value for "amount paid" ('.$FinalPaymentAmt.') or "payment type id" ('.$paymentTypeId.') to record the payment of invoice '.$tmptag['INV'].'. May be payment was already recorded.';
1035 $ispostactionok = -1;
1036 }
1037 } else {
1038 $postactionmessages[] = 'Invoice paid '.$tmptag['INV'].' was not found';
1039 $ispostactionok = -1;
1040 }
1041 } elseif (array_key_exists('ORD', $tmptag) && $tmptag['ORD'] > 0) {
1042 include_once DOL_DOCUMENT_ROOT . '/commande/class/commande.class.php';
1043 $object = new Commande($db);
1044 $result = $object->fetch((int) $tmptag['ORD']);
1045 if ($result) {
1046 dol_syslog("We have loaded the order id=".$object->id." to use to create the invoice", LOG_DEBUG, 0, '_payment');
1047
1048 $FinalPaymentAmt = $_SESSION["FinalPaymentAmt"];
1049
1050 $paymentTypeId = 0;
1051 if ($paymentmethod == 'paybox') {
1052 $paymentTypeId = getDolGlobalInt('PAYBOX_PAYMENT_MODE_FOR_PAYMENTS');
1053 }
1054 if ($paymentmethod == 'paypal') {
1055 $paymentTypeId = getDolGlobalInt('PAYPAL_PAYMENT_MODE_FOR_PAYMENTS');
1056 }
1057 if ($paymentmethod == 'stripe') {
1058 $paymentTypeId = getDolGlobalInt('STRIPE_PAYMENT_MODE_FOR_PAYMENTS');
1059 }
1060 if (empty($paymentTypeId)) {
1061 dol_syslog("paymentType = ".$paymentType, LOG_DEBUG, 0, '_payment');
1062
1063 if (empty($paymentType)) {
1064 $paymentType = 'CB';
1065 }
1066 // May return nothing when paymentType means nothing
1067 // (for example when paymentType is 'Mark', 'Sole', 'Sale', for paypal)
1068 $paymentTypeId = dol_getIdFromCode($db, $paymentType, 'c_paiement', 'code', 'id', 1);
1069
1070 // If previous line has returned nothing, we force to get the ID of payment of Credit Card (hard coded code 'CB').
1071 if (empty($paymentTypeId) || $paymentTypeId < 0) {
1072 $paymentTypeId = dol_getIdFromCode($db, 'CB', 'c_paiement', 'code', 'id', 1);
1073 }
1074 }
1075
1076 dol_syslog("The payment type id to use is paymentTypeId=".$paymentTypeId." and FinalPaymentAmt=".$FinalPaymentAmt, LOG_DEBUG, 0, '_payment');
1077
1078 // Do action only if $FinalPaymentAmt is set (session variable is cleaned after this page to avoid duplicate actions when page is POST a second time)
1079 if (isModEnabled('invoice')) {
1080 if (!empty($FinalPaymentAmt) && $paymentTypeId > 0) {
1081 $db->begin();
1082
1083 include_once DOL_DOCUMENT_ROOT . '/compta/facture/class/facture.class.php';
1084 $invoice = new Facture($db);
1085 $result = $invoice->createFromOrder($object, $user);
1086 if ($result > 0) {
1087 if ($FinalPaymentAmt != $object->total_ttc) {
1088 // The amount paid can be lower than the order only if the user tried to modified the amount from the payment page. A payment has been received but it is a hack attempt
1089 // We can add a line to reduce the amount of the invoice but with which vat ?
1090 // TODO Test if vat on line is the same everywhere, if yes we can add
1091 // $invoice->addline('Fix amount of invoice', $FinalPaymentAmt - $object->total_ttc, 1, $txtva);
1092 // TODO Send a warning email.
1093 }
1094
1095 $object->classifyBilled($user); // The invoice has been create from the order so total is the same, so we can classify order to billed (even if payment may be partial).
1096
1097 $invoice->validate($user); // This may re-classify all linked orders to billed (done previously) if amount of invoice is ok by triggers, depending on the workflow module setup.
1098
1099 // Creation of payment line (warning: if amount has been modified on page, the payment may be partial)
1100 include_once DOL_DOCUMENT_ROOT . '/compta/paiement/class/paiement.class.php';
1101 $paiement = new Paiement($db);
1102 $paiement->datepaye = $now;
1103 if ($currencyCodeType == $conf->currency) {
1104 $paiement->amounts = array($invoice->id => $FinalPaymentAmt); // Array with all payments dispatching with invoice id
1105 } else {
1106 $paiement->multicurrency_amounts = array($invoice->id => $FinalPaymentAmt); // Array with all payments dispatching
1107
1108 $postactionmessages[] = 'Payment was done in a currency ('.$currencyCodeType.') other than the expected currency of company ('.$conf->currency.')';
1109 $ispostactionok = -1;
1110 $error++;
1111 }
1112 $paiement->paiementid = $paymentTypeId;
1113 $paiement->num_payment = '';
1114 $paiement->note_public = 'Online payment ' . dol_print_date($now, 'standard') . ' from ' . $ipaddress;
1115 $paiement->ext_payment_id = $TRANSACTIONID; // pi_... for Stripe, ...
1116 $paiement->ext_payment_site = $service; // 'StripeLive' or 'Stripe', or ...
1117
1118 if (!$error) {
1119 $paiement_id = $paiement->create($user, 1); // This include closing invoices and regenerating documents
1120 if ($paiement_id < 0) {
1121 $postactionmessages[] = $paiement->error . ' ' . implode("<br>\n", $paiement->errors);
1122 $ispostactionok = -1;
1123 $error++;
1124 } else {
1125 $postactionmessages[] = 'Payment created';
1126 $ispostactionok = 1;
1127 }
1128 }
1129
1130 if (!$error && isModEnabled("bank")) {
1131 $bankaccountid = 0;
1132 if ($paymentmethod == 'paybox') {
1133 $bankaccountid = getDolGlobalString('PAYBOX_BANK_ACCOUNT_FOR_PAYMENTS');
1134 } elseif ($paymentmethod == 'paypal') {
1135 $bankaccountid = getDolGlobalString('PAYPAL_BANK_ACCOUNT_FOR_PAYMENTS');
1136 } elseif ($paymentmethod == 'stripe') {
1137 $bankaccountid = getDolGlobalString('STRIPE_BANK_ACCOUNT_FOR_PAYMENTS');
1138 }
1139
1140 //Get bank account for a specific paymentmedthod
1141 $parameters = [
1142 'paymentmethod' => $paymentmethod,
1143 ];
1144 $reshook = $hookmanager->executeHooks('getBankAccountPaymentMethod', $parameters, $object, $action);
1145 if ($reshook >= 0) {
1146 if (isset($hookmanager->resArray['bankaccountid'])) {
1147 dol_syslog('bankaccountid overwrite by hook return with value='.$hookmanager->resArray['bankaccountid'], LOG_DEBUG, 0, '_payment');
1148 $bankaccountid = $hookmanager->resArray['bankaccountid'];
1149 }
1150 }
1151 if ($bankaccountid > 0) {
1152 $label = '(CustomerInvoicePayment)';
1153 if ($object->type == Facture::TYPE_CREDIT_NOTE) {
1154 $label = '(CustomerInvoicePaymentBack)'; // Refund of a credit note
1155 }
1156 $result = $paiement->addPaymentToBank($user, 'payment', $label, $bankaccountid, '', '');
1157 if ($result < 0) {
1158 $postactionmessages[] = $paiement->error . ' ' . implode("<br>\n", $paiement->errors);
1159 $ispostactionok = -1;
1160 $error++;
1161 } else {
1162 $postactionmessages[] = 'Bank transaction of payment created';
1163 $ispostactionok = 1;
1164 }
1165 } else {
1166 $postactionmessages[] = 'Setup of bank account to use in module ' . $paymentmethod . ' was not set. No way to record the payment.';
1167 $ispostactionok = -1;
1168 $error++;
1169 }
1170 }
1171 } else {
1172 $postactionmessages[] = 'Failed to create invoice form order ' . $tmptag['ORD'] . '.';
1173 $ispostactionok = -1;
1174 $error++;
1175 }
1176
1177 if (!$error) {
1178 $db->commit();
1179 } else {
1180 $db->rollback();
1181 }
1182 } else {
1183 $postactionmessages[] = 'Failed to get a valid value for "amount paid" (' . $FinalPaymentAmt . ') or "payment type id" (' . $paymentTypeId . ') to record the payment of order ' . $tmptag['ORD'] . '. May be payment was already recorded.';
1184 $ispostactionok = -1;
1185 }
1186 } else {
1187 $postactionmessages[] = 'Invoice module is not enable';
1188 $ispostactionok = -1;
1189 }
1190 } else {
1191 $postactionmessages[] = 'Order paid ' . $tmptag['ORD'] . ' was not found';
1192 $ispostactionok = -1;
1193 }
1194 } elseif (array_key_exists('DON', $tmptag) && $tmptag['DON'] > 0) {
1195 include_once DOL_DOCUMENT_ROOT.'/don/class/don.class.php';
1196 $don = new Don($db);
1197 $result = $don->fetch((int) $tmptag['DON']);
1198 if ($result) {
1199 $paymentTypeId = 0;
1200 if ($paymentmethod == 'paybox') {
1201 $paymentTypeId = getDolGlobalInt('PAYBOX_PAYMENT_MODE_FOR_PAYMENTS');
1202 }
1203 if ($paymentmethod == 'paypal') {
1204 $paymentTypeId = getDolGlobalInt('global->PAYPAL_PAYMENT_MODE_FOR_PAYMENTS');
1205 }
1206 if ($paymentmethod == 'stripe') {
1207 $paymentTypeId = getDolGlobalInt('STRIPE_PAYMENT_MODE_FOR_PAYMENTS');
1208 }
1209 if (empty($paymentTypeId)) {
1210 dol_syslog("paymentType = ".$paymentType, LOG_DEBUG, 0, '_payment');
1211
1212 if (empty($paymentType)) {
1213 $paymentType = 'CB';
1214 }
1215 // May return nothing when paymentType means nothing
1216 // (for example when paymentType is 'Mark', 'Sole', 'Sale', for paypal)
1217 $paymentTypeId = dol_getIdFromCode($db, $paymentType, 'c_paiement', 'code', 'id', 1);
1218
1219 // If previous line has returned nothing, we force to get the ID of payment of Credit Card (hard coded code 'CB').
1220 if (empty($paymentTypeId) || $paymentTypeId < 0) {
1221 $paymentTypeId = dol_getIdFromCode($db, 'CB', 'c_paiement', 'code', 'id', 1);
1222 }
1223 }
1224
1225 // Do action only if $FinalPaymentAmt is set (session variable is cleaned after this page to avoid duplicate actions when page is POST a second time)
1226 if (!empty($FinalPaymentAmt) && $paymentTypeId > 0) {
1227 $db->begin();
1228
1229 // Creation of paiement line for donation
1230 include_once DOL_DOCUMENT_ROOT.'/don/class/paymentdonation.class.php';
1231 $paiement = new PaymentDonation($db);
1232
1233 $totalpaid = $FinalPaymentAmt;
1234
1235 if ($currencyCodeType == $conf->currency) {
1236 $paiement->amounts = array($object->id => $totalpaid); // Array with all payments dispatching with donation
1237 } else {
1238 // PaymentDonation does not support multi currency
1239 $postactionmessages[] = 'Payment donation can\'t be paid with different currency than '.$conf->currency;
1240 $ispostactionok = -1;
1241 $error++; // Not yet supported
1242 }
1243
1244 $paiement->fk_donation = $don->id;
1245 $paiement->datep = $now;
1246 $paiement->paymenttype = $paymentTypeId;
1247 $paiement->num_payment = '';
1248 $paiement->note_public = 'Online payment '.dol_print_date($now, 'standard').' from '.$ipaddress;
1249 $paiement->ext_payment_id = $TRANSACTIONID;
1250 $paiement->ext_payment_site = $service;
1251
1252 if (!$error) {
1253 $paiement_id = $paiement->create($user, 1);
1254 if ($paiement_id < 0) {
1255 $postactionmessages[] = $paiement->error.' '.implode("<br>\n", $paiement->errors);
1256 $ispostactionok = -1;
1257 $error++;
1258 } else {
1259 $postactionmessages[] = 'Payment created';
1260 $ispostactionok = 1;
1261
1262 if ($totalpaid >= $don->getRemainToPay()) {
1263 $don->setPaid($don->id);
1264 }
1265 }
1266 }
1267
1268 if (!$error && isModEnabled("bank")) {
1269 $bankaccountid = 0;
1270 if ($paymentmethod == 'paybox') {
1271 $bankaccountid = getDolGlobalString('PAYBOX_BANK_ACCOUNT_FOR_PAYMENTS');
1272 } elseif ($paymentmethod == 'paypal') {
1273 $bankaccountid = getDolGlobalString('PAYPAL_BANK_ACCOUNT_FOR_PAYMENTS');
1274 } elseif ($paymentmethod == 'stripe') {
1275 $bankaccountid = getDolGlobalString('STRIPE_BANK_ACCOUNT_FOR_PAYMENTS');
1276 }
1277
1278 //Get bank account for a specific paymentmedthod
1279 $parameters = [
1280 'paymentmethod' => $paymentmethod,
1281 ];
1282 $reshook = $hookmanager->executeHooks('getBankAccountPaymentMethod', $parameters, $object, $action);
1283 if ($reshook >= 0) {
1284 if (isset($hookmanager->resArray['bankaccountid'])) {
1285 dol_syslog('bankaccountid overwrite by hook return with value='.$hookmanager->resArray['bankaccountid'], LOG_DEBUG, 0, '_payment');
1286 $bankaccountid = $hookmanager->resArray['bankaccountid'];
1287 }
1288 }
1289 if ($bankaccountid > 0) {
1290 $label = '(DonationPayment)';
1291 $result = $paiement->addPaymentToBank($user, 'payment_donation', $label, $bankaccountid, '', '');
1292 if ($result < 0) {
1293 $postactionmessages[] = $paiement->error.' '.implode("<br>\n", $paiement->errors);
1294 $ispostactionok = -1;
1295 $error++;
1296 } else {
1297 $postactionmessages[] = 'Bank transaction of payment created';
1298 $ispostactionok = 1;
1299 }
1300 } else {
1301 $postactionmessages[] = 'Setup of bank account to use in module '.$paymentmethod.' was not set. Your payment was really executed but we failed to record it. Please contact us.';
1302 $ispostactionok = -1;
1303 $error++;
1304 }
1305 }
1306
1307 if (!$error) {
1308 $db->commit();
1309 } else {
1310 $db->rollback();
1311 }
1312 } else {
1313 $postactionmessages[] = 'Failed to get a valid value for "amount paid" ('.$FinalPaymentAmt.') or "payment type id" ('.$paymentTypeId.') to record the payment of donation '.$tmptag['DON'].'. May be payment was already recorded.';
1314 $ispostactionok = -1;
1315 }
1316 } else {
1317 $postactionmessages[] = 'Donation paid '.$tmptag['DON'].' was not found';
1318 $ispostactionok = -1;
1319 }
1320
1321 // TODO send email with acknowledgment for the donation
1322 // (we need first that the donation module is able to generate a pdf document for the cerfa with pre filled content)
1323 } elseif (array_key_exists('ATT', $tmptag) && $tmptag['ATT'] > 0) {
1324 // Record payment for registration to an event for an attendee
1325 require_once DOL_DOCUMENT_ROOT.'/eventorganization/class/conferenceorboothattendee.class.php';
1326 require_once DOL_DOCUMENT_ROOT.'/eventorganization/class/conferenceorbooth.class.php';
1327 include_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
1328 $object = new Facture($db);
1329 $result = $object->fetch($ref);
1330 if ($result) {
1331 $paymentTypeId = 0;
1332 if ($paymentmethod == 'paybox') {
1333 $paymentTypeId = getDolGlobalInt('PAYBOX_PAYMENT_MODE_FOR_PAYMENTS');
1334 }
1335 if ($paymentmethod == 'paypal') {
1336 $paymentTypeId = getDolGlobalInt('PAYPAL_PAYMENT_MODE_FOR_PAYMENTS');
1337 }
1338 if ($paymentmethod == 'stripe') {
1339 $paymentTypeId = getDolGlobalInt('STRIPE_PAYMENT_MODE_FOR_PAYMENTS');
1340 }
1341 if (empty($paymentTypeId)) {
1342 dol_syslog("paymentType = ".$paymentType, LOG_DEBUG, 0, '_payment');
1343
1344 if (empty($paymentType)) {
1345 $paymentType = 'CB';
1346 }
1347 // May return nothing when paymentType means nothing
1348 // (for example when paymentType is 'Mark', 'Sole', 'Sale', for paypal)
1349 $paymentTypeId = dol_getIdFromCode($db, $paymentType, 'c_paiement', 'code', 'id', 1);
1350
1351 // If previous line has returned nothing, we force to get the ID of payment of Credit Card (hard coded code 'CB').
1352 if (empty($paymentTypeId) || $paymentTypeId < 0) {
1353 $paymentTypeId = dol_getIdFromCode($db, 'CB', 'c_paiement', 'code', 'id', 1);
1354 }
1355 }
1356
1357 // Do action only if $FinalPaymentAmt is set (session variable is cleaned after this page to avoid duplicate actions when page is POST a second time)
1358 if (!empty($FinalPaymentAmt) && $paymentTypeId > 0) {
1359 $resultvalidate = $object->validate($user);
1360 if ($resultvalidate < 0) {
1361 $postactionmessages[] = 'Cannot validate invoice';
1362 $ispostactionok = -1;
1363 $error++; // Not yet supported
1364 } else {
1365 $db->begin();
1366
1367 // Creation of payment line
1368 include_once DOL_DOCUMENT_ROOT.'/compta/paiement/class/paiement.class.php';
1369 $paiement = new Paiement($db);
1370 $paiement->datepaye = $now;
1371 if ($currencyCodeType == $conf->currency) {
1372 $paiement->amounts = array($object->id => $FinalPaymentAmt); // Array with all payments dispatching with invoice id
1373 } else {
1374 $paiement->multicurrency_amounts = array($object->id => $FinalPaymentAmt); // Array with all payments dispatching
1375
1376 $postactionmessages[] = 'Payment was done in a currency ('.$currencyCodeType.') other than the expected currency of company ('.$conf->currency.')';
1377 $ispostactionok = -1;
1378 $error++; // Not yet supported
1379 }
1380 $paiement->paiementid = $paymentTypeId;
1381 $paiement->num_payment = '';
1382 $paiement->note_public = 'Online payment '.dol_print_date($now, 'standard').' from '.$ipaddress.' for event registration';
1383 $paiement->ext_payment_id = $TRANSACTIONID;
1384 $paiement->ext_payment_site = $service;
1385
1386 if (!$error) {
1387 $paiement_id = $paiement->create($user, 1); // This include closing invoices and regenerating documents
1388 if ($paiement_id < 0) {
1389 $postactionmessages[] = $paiement->error.' '.implode("<br>\n", $paiement->errors);
1390 $ispostactionok = -1;
1391 $error++;
1392 } else {
1393 $postactionmessages[] = 'Payment created';
1394 $ispostactionok = 1;
1395 }
1396 }
1397
1398 if (!$error && isModEnabled("bank")) {
1399 $bankaccountid = 0;
1400 if ($paymentmethod == 'paybox') {
1401 $bankaccountid = getDolGlobalString('PAYBOX_BANK_ACCOUNT_FOR_PAYMENTS');
1402 } elseif ($paymentmethod == 'paypal') {
1403 $bankaccountid = getDolGlobalString('PAYPAL_BANK_ACCOUNT_FOR_PAYMENTS');
1404 } elseif ($paymentmethod == 'stripe') {
1405 $bankaccountid = getDolGlobalString('STRIPE_BANK_ACCOUNT_FOR_PAYMENTS');
1406 }
1407
1408 //Get bank account for a specific paymentmedthod
1409 $parameters = [
1410 'paymentmethod' => $paymentmethod,
1411 ];
1412 $reshook = $hookmanager->executeHooks('getBankAccountPaymentMethod', $parameters, $object, $action);
1413 if ($reshook >= 0) {
1414 if (isset($hookmanager->resArray['bankaccountid'])) {
1415 dol_syslog('bankaccountid overwrite by hook return with value='.$hookmanager->resArray['bankaccountid'], LOG_DEBUG, 0, '_payment');
1416 $bankaccountid = $hookmanager->resArray['bankaccountid'];
1417 }
1418 }
1419 if ($bankaccountid > 0) {
1420 $label = '(CustomerInvoicePayment)';
1421 if ($object->type == Facture::TYPE_CREDIT_NOTE) {
1422 $label = '(CustomerInvoicePaymentBack)'; // Refund of a credit note
1423 }
1424 $result = $paiement->addPaymentToBank($user, 'payment', $label, $bankaccountid, '', '');
1425 if ($result < 0) {
1426 $postactionmessages[] = $paiement->error.' '.implode("<br>\n", $paiement->errors);
1427 $ispostactionok = -1;
1428 $error++;
1429 } else {
1430 $postactionmessages[] = 'Bank transaction of payment created';
1431 $ispostactionok = 1;
1432 }
1433 } else {
1434 $postactionmessages[] = 'Setup of bank account to use in module '.$paymentmethod.' was not set. Your payment was really executed but we failed to record it. Please contact us.';
1435 $ispostactionok = -1;
1436 $error++;
1437 }
1438 }
1439
1440 $attendeetovalidate = new ConferenceOrBoothAttendee($db);
1441
1442 if (!$error) {
1443 // Validating the attendee
1444 $resultattendee = $attendeetovalidate->fetch((int) $tmptag['ATT']);
1445 if ($resultattendee < 0) {
1446 $error++;
1447 setEventMessages(null, $attendeetovalidate->errors, "errors");
1448 } else {
1449 $attendeetovalidate->validate($user);
1450
1451 $attendeetovalidate->amount = $FinalPaymentAmt;
1452 $attendeetovalidate->date_subscription = dol_now();
1453 $attendeetovalidate->update($user);
1454 }
1455 }
1456
1457 if (!$error) {
1458 $db->commit();
1459 } else {
1460 setEventMessages(null, $postactionmessages, 'warnings');
1461
1462 $db->rollback();
1463 }
1464
1465 if (! $error) {
1466 // Sending mail
1467 $thirdparty = new Societe($db);
1468 $resultthirdparty = $thirdparty->fetch($attendeetovalidate->fk_soc);
1469 if ($resultthirdparty < 0) {
1470 setEventMessages($resultthirdparty->error, $resultthirdparty->errors, "errors");
1471 } else {
1472 require_once DOL_DOCUMENT_ROOT.'/core/class/CMailFile.class.php';
1473 include_once DOL_DOCUMENT_ROOT.'/core/class/html.formmail.class.php';
1474 $formmail = new FormMail($db);
1475 // Set output language
1476 $outputlangs = new Translate('', $conf);
1477 $outputlangs->setDefaultLang(empty($thirdparty->default_lang) ? $mysoc->default_lang : $thirdparty->default_lang);
1478 // Load traductions files required by page
1479 $outputlangs->loadLangs(array("main", "members", "eventorganization"));
1480 // Get email content from template
1481 $arraydefaultmessage = null;
1482
1483 $idoftemplatetouse = getDolGlobalString('EVENTORGANIZATION_TEMPLATE_EMAIL_AFT_SUBS_EVENT'); // Email to send for Event organization registration
1484
1485 if (!empty($idoftemplatetouse)) {
1486 $arraydefaultmessage = $formmail->getEMailTemplate($db, 'conferenceorbooth', $user, $outputlangs, $idoftemplatetouse, 1, '');
1487 }
1488
1489 if (!empty($idoftemplatetouse) && is_object($arraydefaultmessage) && $arraydefaultmessage->id > 0) {
1490 $subject = $arraydefaultmessage->topic;
1491 $msg = $arraydefaultmessage->content;
1492 } else {
1493 $subject = '['.$appli.'] '.$object->ref.' - '.$outputlangs->trans("NewRegistration");
1494 $msg = $outputlangs->trans("OrganizationEventPaymentOfRegistrationWasReceived");
1495 }
1496
1497 $substitutionarray = getCommonSubstitutionArray($outputlangs, 0, null, $thirdparty);
1498 complete_substitutions_array($substitutionarray, $outputlangs, $object);
1499
1500 $subjecttosend = make_substitutions($subject, $substitutionarray, $outputlangs);
1501 $texttosend = make_substitutions($msg, $substitutionarray, $outputlangs);
1502
1503 $sendto = $attendeetovalidate->email;
1504 $cc = '';
1505 if ($thirdparty->email) {
1506 $cc = $thirdparty->email;
1507 }
1508 if ($attendeetovalidate->email_company && $attendeetovalidate->email_company != $thirdparty->email) {
1509 $cc = ($cc ? ', ' : '').$attendeetovalidate->email_company;
1510 }
1511
1512 $from = getDolGlobalString('MAILING_EMAIL_FROM') ? $conf->global->MAILING_EMAIL_FROM : getDolGlobalString("MAIN_MAIL_EMAIL_FROM");
1513
1514 $urlback = $_SERVER["REQUEST_URI"];
1515
1516 $ishtml = dol_textishtml($texttosend); // May contain urls
1517
1518 // Attach a file ?
1519 $file = '';
1520 $listofpaths = array();
1521 $listofnames = array();
1522 $listofmimes = array();
1523 if (is_object($object)) {
1524 $invoicediroutput = $conf->facture->dir_output;
1525 $fileparams = dol_most_recent_file($invoicediroutput.'/'.$object->ref, preg_quote($object->ref, '/').'[^\-]+');
1526 $file = $fileparams['fullname'];
1527
1528 $listofpaths = array($file);
1529 $listofnames = array(basename($file));
1530 $listofmimes = array(dol_mimetype($file));
1531 }
1532
1533 $trackid = 'inv'.$object->id;
1534
1535 $mailfile = new CMailFile($subjecttosend, $sendto, $from, $texttosend, $listofpaths, $listofmimes, $listofnames, $cc, '', 0, ($ishtml ? 1 : 0), '', '', $trackid, '', 'standard');
1536
1537 $result = $mailfile->sendfile();
1538 if ($result) {
1539 dol_syslog("EMail sent to ".$sendto, LOG_DEBUG, 0, '_payment');
1540 } else {
1541 dol_syslog("Failed to send EMail to ".$sendto.' - '.$mailfile->error, LOG_ERR, 0, '_payment');
1542 }
1543 }
1544 }
1545 }
1546 } else {
1547 $postactionmessages[] = 'Failed to get a valid value for "amount paid" ('.$FinalPaymentAmt.') or "payment type id" ('.$paymentTypeId.') to record the payment of invoice '.$tmptag['ATT'].'. May be payment was already recorded.';
1548 $ispostactionok = -1;
1549 }
1550 } else {
1551 $postactionmessages[] = 'Invoice paid '.$tmptag['ATT'].' was not found';
1552 $ispostactionok = -1;
1553 }
1554 } elseif (array_key_exists('BOO', $tmptag) && $tmptag['BOO'] > 0) {
1555 // Record payment for booth or conference
1556 require_once DOL_DOCUMENT_ROOT.'/eventorganization/class/conferenceorboothattendee.class.php';
1557 require_once DOL_DOCUMENT_ROOT.'/eventorganization/class/conferenceorbooth.class.php';
1558 include_once DOL_DOCUMENT_ROOT.'/compta/facture/class/facture.class.php';
1559 $object = new Facture($db);
1560 $result = $object->fetch($ref);
1561 if ($result) {
1562 $FinalPaymentAmt = $_SESSION["FinalPaymentAmt"];
1563
1564 $paymentTypeId = 0;
1565 if ($paymentmethod == 'paybox') {
1566 $paymentTypeId = getDolGlobalInt('PAYBOX_PAYMENT_MODE_FOR_PAYMENTS');
1567 }
1568 if ($paymentmethod == 'paypal') {
1569 $paymentTypeId = getDolGlobalInt('PAYPAL_PAYMENT_MODE_FOR_PAYMENTS');
1570 }
1571 if ($paymentmethod == 'stripe') {
1572 $paymentTypeId = getDolGlobalInt('STRIPE_PAYMENT_MODE_FOR_PAYMENTS');
1573 }
1574 if (empty($paymentTypeId)) {
1575 dol_syslog("paymentType = ".$paymentType, LOG_DEBUG, 0, '_payment');
1576
1577 if (empty($paymentType)) {
1578 $paymentType = 'CB';
1579 }
1580 // May return nothing when paymentType means nothing
1581 // (for example when paymentType is 'Mark', 'Sole', 'Sale', for paypal)
1582 $paymentTypeId = dol_getIdFromCode($db, $paymentType, 'c_paiement', 'code', 'id', 1);
1583
1584 // If previous line has returned nothing, we force to get the ID of payment of Credit Card (hard coded code 'CB').
1585 if (empty($paymentTypeId) || $paymentTypeId < 0) {
1586 $paymentTypeId = dol_getIdFromCode($db, 'CB', 'c_paiement', 'code', 'id', 1);
1587 }
1588 }
1589
1590 // Do action only if $FinalPaymentAmt is set (session variable is cleaned after this page to avoid duplicate actions when page is POST a second time)
1591 if (!empty($FinalPaymentAmt) && $paymentTypeId > 0) {
1592 $resultvalidate = $object->validate($user);
1593 if ($resultvalidate < 0) {
1594 $postactionmessages[] = 'Cannot validate invoice';
1595 $ispostactionok = -1;
1596 $error++; // Not yet supported
1597 } else {
1598 $db->begin();
1599
1600 // Creation of payment line
1601 include_once DOL_DOCUMENT_ROOT.'/compta/paiement/class/paiement.class.php';
1602 $paiement = new Paiement($db);
1603 $paiement->datepaye = $now;
1604 if ($currencyCodeType == $conf->currency) {
1605 $paiement->amounts = array($object->id => $FinalPaymentAmt); // Array with all payments dispatching with invoice id
1606 } else {
1607 $paiement->multicurrency_amounts = array($object->id => $FinalPaymentAmt); // Array with all payments dispatching
1608
1609 $postactionmessages[] = 'Payment was done in a currency ('.$currencyCodeType.') other than the expected currency of company ('.$conf->currency.')';
1610 $ispostactionok = -1;
1611 $error++; // Not yet supported
1612 }
1613 $paiement->paiementid = $paymentTypeId;
1614 $paiement->num_payment = '';
1615 $paiement->note_public = 'Online payment '.dol_print_date($now, 'standard').' from '.$ipaddress;
1616 $paiement->ext_payment_id = $TRANSACTIONID;
1617 $paiement->ext_payment_site = $service;
1618
1619 if (!$error) {
1620 $paiement_id = $paiement->create($user, 1); // This include closing invoices and regenerating documents
1621 if ($paiement_id < 0) {
1622 $postactionmessages[] = $paiement->error.' '.implode("<br>\n", $paiement->errors);
1623 $ispostactionok = -1;
1624 $error++;
1625 } else {
1626 $postactionmessages[] = 'Payment created';
1627 $ispostactionok = 1;
1628 }
1629 }
1630
1631 if (!$error && isModEnabled("bank")) {
1632 $bankaccountid = 0;
1633 if ($paymentmethod == 'paybox') {
1634 $bankaccountid = getDolGlobalString('PAYBOX_BANK_ACCOUNT_FOR_PAYMENTS');
1635 } elseif ($paymentmethod == 'paypal') {
1636 $bankaccountid = getDolGlobalString('PAYPAL_BANK_ACCOUNT_FOR_PAYMENTS');
1637 } elseif ($paymentmethod == 'stripe') {
1638 $bankaccountid = getDolGlobalString('STRIPE_BANK_ACCOUNT_FOR_PAYMENTS');
1639 }
1640
1641 //Get bank account for a specific paymentmedthod
1642 $parameters = [
1643 'paymentmethod' => $paymentmethod,
1644 ];
1645 $reshook = $hookmanager->executeHooks('getBankAccountPaymentMethod', $parameters, $object, $action);
1646 if ($reshook >= 0) {
1647 if (isset($hookmanager->resArray['bankaccountid'])) {
1648 dol_syslog('bankaccountid overwrite by hook return with value='.$hookmanager->resArray['bankaccountid'], LOG_DEBUG, 0, '_payment');
1649 $bankaccountid = $hookmanager->resArray['bankaccountid'];
1650 }
1651 }
1652 if ($bankaccountid > 0) {
1653 $label = '(CustomerInvoicePayment)';
1654 if ($object->type == Facture::TYPE_CREDIT_NOTE) {
1655 $label = '(CustomerInvoicePaymentBack)'; // Refund of a credit note
1656 }
1657 $result = $paiement->addPaymentToBank($user, 'payment', $label, $bankaccountid, '', '');
1658 if ($result < 0) {
1659 $postactionmessages[] = $paiement->error.' '.implode("<br>\n", $paiement->errors);
1660 $ispostactionok = -1;
1661 $error++;
1662 } else {
1663 $postactionmessages[] = 'Bank transaction of payment created';
1664 $ispostactionok = 1;
1665 }
1666 } else {
1667 $postactionmessages[] = 'Setup of bank account to use in module '.$paymentmethod.' was not set. Your payment was really executed but we failed to record it. Please contact us.';
1668 $ispostactionok = -1;
1669 $error++;
1670 }
1671 }
1672
1673 if (!$error) {
1674 // Putting the booth to "suggested" state
1675 require_once DOL_DOCUMENT_ROOT.'/eventorganization/class/conferenceorboothattendee.class.php';
1676 require_once DOL_DOCUMENT_ROOT.'/eventorganization/class/conferenceorbooth.class.php';
1677 $booth = new ConferenceOrBooth($db);
1678 $resultbooth = $booth->fetch((int) $tmptag['BOO']);
1679 if ($resultbooth < 0) {
1680 $error++;
1681 setEventMessages(null, $booth->errors, "errors");
1682 } else {
1683 $booth->status = ConferenceOrBooth::STATUS_SUGGESTED;
1684 $resultboothupdate = $booth->update($user);
1685 if ($resultboothupdate<0) {
1686 // Finding the thirdparty by getting the invoice
1687 $invoice = new Facture($db);
1688 $resultinvoice = $invoice->fetch($ref);
1689 if ($resultinvoice<0) {
1690 $postactionmessages[] = 'Could not find the associated invoice.';
1691 $ispostactionok = -1;
1692 $error++;
1693 } else {
1694 $thirdparty = new Societe($db);
1695 $resultthirdparty = $thirdparty->fetch($invoice->socid);
1696 if ($resultthirdparty<0) {
1697 $error++;
1698 setEventMessages(null, $thirdparty->errors, "errors");
1699 } else {
1700 // TODO Move the send of email out of the db transaction
1701
1702 // Sending mail
1703 require_once DOL_DOCUMENT_ROOT.'/core/class/CMailFile.class.php';
1704 include_once DOL_DOCUMENT_ROOT.'/core/class/html.formmail.class.php';
1705 $formmail = new FormMail($db);
1706 // Set output language
1707 $outputlangs = new Translate('', $conf);
1708 $outputlangs->setDefaultLang(empty($thirdparty->default_lang) ? $mysoc->default_lang : $thirdparty->default_lang);
1709 // Load traductions files required by page
1710 $outputlangs->loadLangs(array("main", "members", "eventorganization"));
1711 // Get email content from template
1712 $arraydefaultmessage = null;
1713
1714 $idoftemplatetouse = getDolGlobalString('EVENTORGANIZATION_TEMPLATE_EMAIL_AFT_SUBS_BOOTH'); // Email sent after registration for a Booth
1715
1716 if (!empty($idoftemplatetouse)) {
1717 $arraydefaultmessage = $formmail->getEMailTemplate($db, 'conferenceorbooth', $user, $outputlangs, $idoftemplatetouse, 1, '');
1718 }
1719
1720 if (!empty($idoftemplatetouse) && is_object($arraydefaultmessage) && $arraydefaultmessage->id > 0) {
1721 $subject = $arraydefaultmessage->topic;
1722 $msg = $arraydefaultmessage->content;
1723 } else {
1724 $subject = '['.$appli.'] '.$booth->ref.' - '.$outputlangs->trans("NewRegistration").']';
1725 $msg = $outputlangs->trans("OrganizationEventPaymentOfBoothWasReceived");
1726 }
1727
1728 $substitutionarray = getCommonSubstitutionArray($outputlangs, 0, null, $thirdparty);
1729 complete_substitutions_array($substitutionarray, $outputlangs, $object);
1730
1731 $subjecttosend = make_substitutions($subject, $substitutionarray, $outputlangs);
1732 $texttosend = make_substitutions($msg, $substitutionarray, $outputlangs);
1733
1734 $sendto = $thirdparty->email;
1735 $from = getDolGlobalString('MAILING_EMAIL_FROM');
1736 $urlback = $_SERVER["REQUEST_URI"];
1737
1738 $ishtml = dol_textishtml($texttosend); // May contain urls
1739 $trackid = 'inv'.$invoice->id;
1740
1741 $mailfile = new CMailFile($subjecttosend, $sendto, $from, $texttosend, array(), array(), array(), '', '', 0, $ishtml ? 1 : 0, '', '', $trackid, '', 'standard');
1742
1743 $result = $mailfile->sendfile();
1744 if ($result) {
1745 dol_syslog("EMail sent to ".$sendto, LOG_DEBUG, 0, '_payment');
1746 } else {
1747 dol_syslog("Failed to send EMail to ".$sendto, LOG_ERR, 0, '_payment');
1748 }
1749 }
1750 }
1751 }
1752 }
1753 }
1754
1755 if (!$error) {
1756 $db->commit();
1757 } else {
1758 $db->rollback();
1759 }
1760 }
1761 } else {
1762 $postactionmessages[] = 'Failed to get a valid value for "amount paid" ('.$FinalPaymentAmt.') or "payment type id" ('.$paymentTypeId.') to record the payment of invoice '.$tmptag['ATT'].'. May be payment was already recorded.';
1763 $ispostactionok = -1;
1764 }
1765 } else {
1766 $postactionmessages[] = 'Invoice paid '.$tmptag['ATT'].' was not found';
1767 $ispostactionok = -1;
1768 }
1769 } elseif (array_key_exists('CON', $tmptag) && $tmptag['CON'] > 0) {
1770 include_once DOL_DOCUMENT_ROOT . '/contrat/class/contrat.class.php';
1771 $object = new Contrat($db);
1772 $result = $object->fetch((int) $tmptag['CON']);
1773 if ($result) {
1774 $FinalPaymentAmt = $_SESSION["FinalPaymentAmt"];
1775
1776 $paymentTypeId = 0;
1777 if ($paymentmethod == 'paybox') {
1778 $paymentTypeId = getDolGlobalInt('PAYBOX_PAYMENT_MODE_FOR_PAYMENTS');
1779 }
1780 if ($paymentmethod == 'paypal') {
1781 $paymentTypeId = getDolGlobalInt('PAYPAL_PAYMENT_MODE_FOR_PAYMENTS');
1782 }
1783 if ($paymentmethod == 'stripe') {
1784 $paymentTypeId = getDolGlobalInt('STRIPE_PAYMENT_MODE_FOR_PAYMENTS');
1785 }
1786 if (empty($paymentTypeId)) {
1787 dol_syslog("paymentType = ".$paymentType, LOG_DEBUG, 0, '_payment');
1788
1789 if (empty($paymentType)) {
1790 $paymentType = 'CB';
1791 }
1792 // May return nothing when paymentType means nothing
1793 // (for example when paymentType is 'Mark', 'Sole', 'Sale', for paypal)
1794 $paymentTypeId = dol_getIdFromCode($db, $paymentType, 'c_paiement', 'code', 'id', 1);
1795
1796 // If previous line has returned nothing, we force to get the ID of payment of Credit Card (hard coded code 'CB').
1797 if (empty($paymentTypeId) || $paymentTypeId < 0) {
1798 $paymentTypeId = dol_getIdFromCode($db, 'CB', 'c_paiement', 'code', 'id', 1);
1799 }
1800 }
1801
1802 $currencyCodeType = $_SESSION['currencyCodeType'];
1803 $contract_lines = (array_key_exists('COL', $tmptag) && $tmptag['COL'] > 0) ? $tmptag['COL'] : null;
1804
1805 // Do action only if $FinalPaymentAmt is set (session variable is cleaned after this page to avoid duplicate actions when page is POST a second time)
1806 if (isModEnabled('invoice')) {
1807 if (!empty($FinalPaymentAmt) && $paymentTypeId > 0) {
1808 $db->begin();
1809
1810 include_once DOL_DOCUMENT_ROOT . '/compta/facture/class/facture.class.php';
1811 $invoice = new Facture($db);
1812 $result = $invoice->createFromContract($object, $user, array((int) $contract_lines));
1813 if ($result > 0) {
1814 // $object->classifyBilled($user);
1815 $invoice->validate($user);
1816 // Creation of payment line
1817 include_once DOL_DOCUMENT_ROOT . '/compta/paiement/class/paiement.class.php';
1818 $paiement = new Paiement($db);
1819 $paiement->datepaye = $now;
1820 if ($currencyCodeType == $conf->currency) {
1821 $paiement->amounts = array($invoice->id => $FinalPaymentAmt); // Array with all payments dispatching with invoice id
1822 } else {
1823 $paiement->multicurrency_amounts = array($invoice->id => $FinalPaymentAmt); // Array with all payments dispatching
1824
1825 $postactionmessages[] = 'Payment was done in a currency ('.$currencyCodeType.') other than the expected currency of company ('.$conf->currency.')';
1826 $ispostactionok = -1;
1827 $error++;
1828 }
1829 $paiement->paiementid = $paymentTypeId;
1830 $paiement->num_payment = '';
1831 $paiement->note_public = 'Online payment ' . dol_print_date($now, 'standard') . ' from ' . $ipaddress;
1832 $paiement->ext_payment_id = $TRANSACTIONID; // pi_... for Stripe, ...
1833 $paiement->ext_payment_site = $service; // 'StripeLive' or 'Stripe', or ...
1834
1835 if (!$error) {
1836 $paiement_id = $paiement->create($user, 1); // This include closing invoices and regenerating documents
1837 if ($paiement_id < 0) {
1838 $postactionmessages[] = $paiement->error . ' ' . implode("<br>\n", $paiement->errors);
1839 $ispostactionok = -1;
1840 $error++;
1841 } else {
1842 $postactionmessages[] = 'Payment created';
1843 $ispostactionok = 1;
1844 }
1845 }
1846
1847 if (!$error && isModEnabled("bank")) {
1848 $bankaccountid = 0;
1849 if ($paymentmethod == 'paybox') {
1850 $bankaccountid = getDolGlobalString('PAYBOX_BANK_ACCOUNT_FOR_PAYMENTS');
1851 } elseif ($paymentmethod == 'paypal') {
1852 $bankaccountid = getDolGlobalString('PAYPAL_BANK_ACCOUNT_FOR_PAYMENTS');
1853 } elseif ($paymentmethod == 'stripe') {
1854 $bankaccountid = getDolGlobalString('STRIPE_BANK_ACCOUNT_FOR_PAYMENTS');
1855 }
1856
1857 //Get bank account for a specific paymentmedthod
1858 $parameters = [
1859 'paymentmethod' => $paymentmethod,
1860 ];
1861 $reshook = $hookmanager->executeHooks('getBankAccountPaymentMethod', $parameters, $object, $action);
1862 if ($reshook >= 0) {
1863 if (isset($hookmanager->resArray['bankaccountid'])) {
1864 dol_syslog('bankaccountid overwrite by hook return with value='.$hookmanager->resArray['bankaccountid'], LOG_DEBUG, 0, '_payment');
1865 $bankaccountid = $hookmanager->resArray['bankaccountid'];
1866 }
1867 }
1868 if ($bankaccountid > 0) {
1869 $label = '(CustomerInvoicePayment)';
1870 if ($object->type == Facture::TYPE_CREDIT_NOTE) {
1871 $label = '(CustomerInvoicePaymentBack)'; // Refund of a credit note
1872 }
1873 $result = $paiement->addPaymentToBank($user, 'payment', $label, $bankaccountid, '', '');
1874 if ($result < 0) {
1875 $postactionmessages[] = $paiement->error . ' ' . implode("<br>\n", $paiement->errors);
1876 $ispostactionok = -1;
1877 $error++;
1878 } else {
1879 $postactionmessages[] = 'Bank transaction of payment created';
1880 $ispostactionok = 1;
1881 }
1882 } else {
1883 $postactionmessages[] = 'Setup of bank account to use in module ' . $paymentmethod . ' was not set. No way to record the payment.';
1884 $ispostactionok = -1;
1885 $error++;
1886 }
1887 }
1888 } else {
1889 $msg = 'Failed to create invoice form contract ' . $tmptag['CON'];
1890 if (!empty($tmptag['COL'])) {
1891 $msg .= ' and col '. $tmptag['COL'] .'.';
1892 }
1893 $postactionmessages[] = $msg;
1894 $ispostactionok = -1;
1895 $error++;
1896 }
1897
1898 if (!$error) {
1899 $db->commit();
1900 } else {
1901 $db->rollback();
1902 }
1903 } else {
1904 $postactionmessages[] = 'Failed to get a valid value for "amount paid" (' . $FinalPaymentAmt . ') or "payment type id" (' . $paymentTypeId . ') to record the payment of contract ' . $tmptag['CON'] .'. Maybe payment was already recorded.';
1905 $ispostactionok = -1;
1906 }
1907 } else {
1908 $postactionmessages[] = 'Invoice module is not enable';
1909 $ispostactionok = -1;
1910 }
1911 } else {
1912 $msg = 'Contract paid ' . $tmptag['CON'] . ' was not found';
1913 if (!empty($tmptag['COL'])) {
1914 $msg .= ' for col '.$tmptag['COL'] .'.';
1915 }
1916 $postactionmessages[] = $msg;
1917 $ispostactionok = -1;
1918 }
1919 } else {
1920 // Nothing done
1921 }
1922}
1923
1924dol_syslog("ispaymentok=".$ispaymentok." ispostactionok=".$ispostactionok." doactionsthenredirect=".$doactionsthenredirect, LOG_DEBUG, 0, '_payment');
1925
1926if ($ispaymentok) {
1927 // Get on url call
1928 $onlinetoken = empty($PAYPALTOKEN) ? $_SESSION['onlinetoken'] : $PAYPALTOKEN;
1929 $payerID = empty($PAYPALPAYERID) ? $_SESSION['payerID'] : $PAYPALPAYERID;
1930 // Set by newpayment.php
1931 $currencyCodeType = empty($_SESSION['currencyCodeType']) ? '' : $_SESSION['currencyCodeType'];
1932 $FinalPaymentAmt = empty($_SESSION["FinalPaymentAmt"]) ? '': $_SESSION["FinalPaymentAmt"];
1933 $paymentType = empty($_SESSION['PaymentType']) ? '' : $_SESSION['PaymentType']; // Seems used by paypal only
1934
1935 if (is_object($object) && method_exists($object, 'call_trigger')) {
1936 // Call trigger
1937 $result = $object->call_trigger('PAYMENTONLINE_PAYMENT_OK', $user);
1938 if ($result < 0) {
1939 $error++;
1940 }
1941 // End call triggers
1942 } elseif (get_class($object) == 'stdClass') {
1943 //In some case $object is not instantiate (for paiement on custom object) We need to deal with payment
1944 include_once DOL_DOCUMENT_ROOT.'/compta/paiement/class/paiement.class.php';
1945 $paiement = new Paiement($db);
1946 $result = $paiement->call_trigger('PAYMENTONLINE_PAYMENT_OK', $user);
1947 if ($result < 0) {
1948 $error++;
1949 }
1950 }
1951}
1952
1953
1954// Show result message
1955if (empty($doactionsthenredirect)) {
1956 if ($ispaymentok) {
1957 print $langs->trans("YourPaymentHasBeenRecorded")."<br>\n";
1958 if ($TRANSACTIONID) {
1959 print $langs->trans("ThisIsTransactionId", $TRANSACTIONID)."<br><br>\n";
1960 }
1961
1962 print '<center>';
1963 print img_picto('', 'tick', 'class="green fa-2x"');
1964 print '</center>';
1965
1966 // Show a custom message
1967 $key = 'ONLINE_PAYMENT_MESSAGE_OK';
1968 if (getDolGlobalString($key)) {
1969 print '<br>';
1970 print getDolGlobalString($key);
1971 }
1972 } else {
1973 print $langs->trans('DoExpressCheckoutPaymentAPICallFailed')."<br>\n";
1974 print $langs->trans('DetailedErrorMessage').": ".$ErrorLongMsg."<br>\n";
1975 print $langs->trans('ShortErrorMessage').": ".$ErrorShortMsg."<br>\n";
1976 print $langs->trans('ErrorCode').": ".$ErrorCode."<br>\n";
1977 print $langs->trans('ErrorSeverityCode').": ".$ErrorSeverityCode."<br>\n";
1978
1979 if ($mysoc->email) {
1980 print "\nPlease, send a screenshot of this page to ".$mysoc->email."<br>\n";
1981 }
1982 }
1983}
1984
1985
1986// Send email
1987if ($ispaymentok) {
1988 $sendemail = getDolGlobalString('ONLINE_PAYMENT_SENDEMAIL');
1989
1990 $tmptag = dolExplodeIntoArray($fulltag, '.', '=');
1991
1992 dol_syslog("Send email to admins if we have to (sendemail = ".$sendemail.")", LOG_DEBUG, 0, '_payment');
1993
1994 // Send an email to the admins
1995 if ($sendemail) {
1996 // Get default language to use for the company for supervision emails
1997 $myCompanyDefaultLang = $mysoc->default_lang;
1998 if (empty($myCompanyDefaultLang) || $myCompanyDefaultLang === 'auto') {
1999 // We must guess the language from the company country. We must not use the language of the visitor. This is a technical email for supervision
2000 // so it must always be into the same language.
2001 $myCompanyDefaultLang = getLanguageCodeFromCountryCode($mysoc->country_code);
2002 }
2003
2004 $companylangs = new Translate('', $conf);
2005 $companylangs->setDefaultLang($myCompanyDefaultLang);
2006 $companylangs->loadLangs(array('main', 'members', 'bills', 'paypal', 'paybox', 'stripe'));
2007
2008 $sendto = $sendemail;
2009 $from = getDolGlobalString('MAIN_MAIL_EMAIL_FROM');
2010 // Define $urlwithroot
2011 $urlwithouturlroot = preg_replace('/'.preg_quote(DOL_URL_ROOT, '/').'$/i', '', trim($dolibarr_main_url_root));
2012 $urlwithroot = $urlwithouturlroot.DOL_URL_ROOT; // This is to use external domain name found into config file
2013 //$urlwithroot=DOL_MAIN_URL_ROOT; // This is to use same domain name than current
2014
2015 // Define link to login card
2016
2017 $urlback = $_SERVER["REQUEST_URI"];
2018 $topic = '['.$appli.'] '.$companylangs->transnoentitiesnoconv("NewOnlinePaymentReceived");
2019 $content = "";
2020 if (array_key_exists('MEM', $tmptag)) {
2021 $url = $urlwithroot."/adherents/subscription.php?rowid=".((int) $tmptag['MEM']);
2022 $content .= '<strong>'.$companylangs->trans("PaymentSubscription")."</strong><br><br>\n";
2023 $content .= $companylangs->trans("MemberId").': <strong>'.$tmptag['MEM']."</strong><br>\n";
2024 $content .= $companylangs->trans("Link").': <a href="'.$url.'">'.$url.'</a>'."<br>\n";
2025 } elseif (array_key_exists('INV', $tmptag)) {
2026 $url = $urlwithroot."/compta/facture/card.php?id=".((int) $tmptag['INV']);
2027 $content .= '<strong>'.$companylangs->trans("Payment")."</strong><br><br>\n";
2028 $content .= $companylangs->trans("InvoiceId").': <strong>'.$tmptag['INV']."</strong><br>\n";
2029 //$content.=$companylangs->trans("ThirdPartyId").': '.$tmptag['CUS']."<br>\n";
2030 $content .= $companylangs->trans("Link").': <a href="'.$url.'">'.$url.'</a>'."<br>\n";
2031 } else {
2032 $content .= $companylangs->transnoentitiesnoconv("NewOnlinePaymentReceived")."<br>\n";
2033 }
2034 $content .= $companylangs->transnoentities("PostActionAfterPayment").' : ';
2035 if ($ispostactionok > 0) {
2036 //$topic.=' ('.$companylangs->transnoentitiesnoconv("Status").' '.$companylangs->transnoentitiesnoconv("OK").')';
2037 $content .= '<span style="color: green">'.$companylangs->transnoentitiesnoconv("OK").'</span>';
2038 } elseif ($ispostactionok == 0) {
2039 $content .= $companylangs->transnoentitiesnoconv("None");
2040 } else {
2041 $topic .= ($ispostactionok ? '' : ' ('.$companylangs->trans("WarningPostActionErrorAfterPayment").')');
2042 $content .= '<span class="star">'.$companylangs->transnoentitiesnoconv("Error").'</span>';
2043 }
2044 $content .= '<br>'."\n";
2045 foreach ($postactionmessages as $postactionmessage) {
2046 $content .= ' * '.$postactionmessage.'<br>'."\n";
2047 }
2048 if ($ispostactionok < 0) {
2049 $content .= $langs->transnoentities("ARollbackWasPerformedOnPostActions");
2050 }
2051 $content .= '<br>'."\n";
2052
2053 $content .= "<br>\n";
2054 $content .= '<u>'.$companylangs->transnoentitiesnoconv("TechnicalInformation").":</u><br>\n";
2055 $content .= $companylangs->transnoentitiesnoconv("OnlinePaymentSystem").': <strong>'.$paymentmethod."</strong><br>\n";
2056 $content .= $companylangs->transnoentitiesnoconv("ThisIsTransactionId").': <strong>'.$TRANSACTIONID."</strong><br>\n";
2057 $content .= $companylangs->transnoentitiesnoconv("ReturnURLAfterPayment").': '.$urlback."<br>\n";
2058 $content .= "<br>\n";
2059 $content .= "tag=".$fulltag."<br>\ntoken=".$onlinetoken."<br>\npaymentType=".$paymentType."<br>\ncurrencycodeType=".$currencyCodeType."<br>\npayerId=".$payerID."<br>\nipaddress=".$ipaddress."<br>\nFinalPaymentAmt=".$FinalPaymentAmt."<br>\n";
2060
2061 if (!empty($ErrorCode)) {
2062 $content .= "ErrorCode = ".$ErrorCode."<br>\n";
2063 }
2064 if (!empty($ErrorShortMsg)) {
2065 $content .= "ErrorShortMsg = ".$ErrorShortMsg."<br>\n";
2066 }
2067 if (!empty($ErrorLongMsg)) {
2068 $content .= "ErrorLongMsg = ".$ErrorLongMsg."<br>\n";
2069 }
2070 if (!empty($ErrorSeverityCode)) {
2071 $content .= "ErrorSeverityCode = ".$ErrorSeverityCode."<br>\n";
2072 }
2073
2074 dol_syslog("Content of email: ".$content, LOG_DEBUG, 0, '_payment');
2075
2076 $ishtml = dol_textishtml($content); // May contain urls
2077 $trackid = '';
2078
2079 require_once DOL_DOCUMENT_ROOT.'/core/class/CMailFile.class.php';
2080 $mailfile = new CMailFile($topic, $sendto, $from, $content, array(), array(), array(), '', '', 0, $ishtml ? 1 : 0, '', '', $trackid, '', 'standard');
2081
2082 $result = $mailfile->sendfile();
2083 if ($result) {
2084 dol_syslog("EMail sent to ".$sendto, LOG_DEBUG, 0, '_payment');
2085 //dol_syslog("EMail sent to ".$sendto, LOG_DEBUG, 0);
2086 } else {
2087 dol_syslog("Failed to send EMail to ".$sendto, LOG_ERR, 0, '_payment');
2088 //dol_syslog("Failed to send EMail to ".$sendto, LOG_ERR, 0);
2089 }
2090 }
2091} else {
2092 $sendemail = getDolGlobalString('ONLINE_PAYMENT_SENDEMAIL');
2093
2094 // Get on url call
2095 $onlinetoken = empty($PAYPALTOKEN) ? $_SESSION['onlinetoken'] : $PAYPALTOKEN;
2096 $payerID = empty($PAYPALPAYERID) ? $_SESSION['payerID'] : $PAYPALPAYERID;
2097 // Set by newpayment.php
2098 $paymentType = $_SESSION['PaymentType'];
2099 $currencyCodeType = $_SESSION['currencyCodeType'];
2100 $FinalPaymentAmt = $_SESSION["FinalPaymentAmt"];
2101
2102 if (is_object($object) && method_exists($object, 'call_trigger')) {
2103 // Call trigger
2104 $result = $object->call_trigger('PAYMENTONLINE_PAYMENT_KO', $user);
2105 if ($result < 0) {
2106 $error++;
2107 }
2108 // End call triggers
2109 }
2110
2111 // Send warning of error to administrator
2112 if ($sendemail) {
2113 $companylangs = new Translate('', $conf);
2114 $companylangs->setDefaultLang($mysoc->default_lang);
2115 $companylangs->loadLangs(array('main', 'members', 'bills', 'paypal', 'paybox', 'stripe'));
2116
2117 $sendto = $sendemail;
2118 $from = getDolGlobalString('MAILING_EMAIL_FROM') ? $conf->global->MAILING_EMAIL_FROM : getDolGlobalString("MAIN_MAIL_EMAIL_FROM");
2119 // Define $urlwithroot
2120 $urlwithouturlroot = preg_replace('/'.preg_quote(DOL_URL_ROOT, '/').'$/i', '', trim($dolibarr_main_url_root));
2121 $urlwithroot = $urlwithouturlroot.DOL_URL_ROOT; // This is to use external domain name found into config file
2122 //$urlwithroot=DOL_MAIN_URL_ROOT; // This is to use same domain name than current
2123
2124 $urlback = $_SERVER["REQUEST_URI"];
2125 $topic = '['.$appli.'] '.$companylangs->transnoentitiesnoconv("ValidationOfPaymentFailed");
2126 $content = "";
2127 $content .= '<span style="color: orange">'.$companylangs->transnoentitiesnoconv("PaymentSystemConfirmPaymentPageWasCalledButFailed")."</span>\n";
2128
2129 $content .= "<br><br>\n";
2130 $content .= '<u>'.$companylangs->transnoentitiesnoconv("TechnicalInformation").":</u><br>\n";
2131 $content .= $companylangs->transnoentitiesnoconv("OnlinePaymentSystem").': <strong>'.$paymentmethod."</strong><br>\n";
2132 $content .= $companylangs->transnoentitiesnoconv("ReturnURLAfterPayment").': '.$urlback."<br>\n";
2133 $content .= "<br>\n";
2134 $content .= "tag=".$fulltag."<br>\ntoken=".$onlinetoken."<br>\npaymentType=".$paymentType."<br>\ncurrencycodeType=".$currencyCodeType."<br>\npayerId=".$payerID."<br>\nipaddress=".$ipaddress."<br>\nFinalPaymentAmt=".$FinalPaymentAmt."<br>\n";
2135
2136
2137 $ishtml = dol_textishtml($content); // May contain urls
2138 $trackid = '';
2139
2140 require_once DOL_DOCUMENT_ROOT.'/core/class/CMailFile.class.php';
2141 $mailfile = new CMailFile($topic, $sendto, $from, $content, array(), array(), array(), '', '', 0, $ishtml ? 1 : 0, '', '', $trackid, '', 'standard');
2142
2143 $result = $mailfile->sendfile();
2144 if ($result) {
2145 dol_syslog("EMail sent to ".$sendto, LOG_DEBUG, 0, '_payment');
2146 } else {
2147 dol_syslog("Failed to send EMail to ".$sendto, LOG_ERR, 0, '_payment');
2148 }
2149 }
2150}
2151
2152
2153// Clean session variables to avoid duplicate actions if post is resent
2154unset($_SESSION["FinalPaymentAmt"]);
2155unset($_SESSION["TRANSACTIONID"]);
2156
2157
2158// Close page content id="dolpaymentdiv"
2159if (empty($doactionsthenredirect)) {
2160 print "\n</div>\n";
2161
2162 print "<!-- Info for payment: FinalPaymentAmt=".dol_escape_htmltag($FinalPaymentAmt)." paymentTypeId=".dol_escape_htmltag($paymentTypeId)." currencyCodeType=".dol_escape_htmltag($currencyCodeType)." -->\n";
2163}
2164
2165
2166// Show footer
2167if (empty($doactionsthenredirect)) {
2168 htmlPrintOnlineFooter($mysoc, $langs, 0, $suffix);
2169
2170 llxFooter('', 'public');
2171}
2172
2173
2174$db->close();
2175
2176
2177// If option to do a redirect somewhere else.
2178if (!empty($doactionsthenredirect)) {
2179 if ($ispaymentok) {
2180 // Redirect to a success page
2181 $randomseckey = getRandomPassword(true, null, 20);
2182 $_SESSION['paymentoksessioncode'] = $randomseckey; // key between paymentok.php to another page like a paymentok of the website.
2183
2184 // Paymentok page must be created for the specific website
2185 if (!defined('USEDOLIBARRSERVER') && !empty($ws_virtuelhost)) {
2186 $ext_urlok = $ws_virtuelhost . '/paymentok.php?paymentoksessioncode='.urlencode($randomseckey).'&fulltag='.$FULLTAG;
2187 } else {
2188 $ext_urlok = DOL_URL_ROOT.'/public/website/index.php?paymentoksessioncode='.urlencode($randomseckey).'&website='.urlencode($ws).'&pageref=paymentok&fulltag='.$FULLTAG;
2189 }
2190
2191 dol_syslog("Now do a redirect using a Location: ".$ext_urlok, LOG_DEBUG, 0, '_payment');
2192 header("Location: ".$ext_urlok);
2193 exit;
2194 } else {
2195 // Redirect to an error page
2196 $randomseckey = getRandomPassword(true, null, 20);
2197 $_SESSION['paymentkosessioncode'] = $randomseckey; // key between paymentok.php to another page like a paymentko of the website.
2198
2199 // Paymentko page must be created for the specific website
2200 if (!defined('USEDOLIBARRSERVER') && !empty($ws_virtuelhost)) {
2201 $ext_urlko = $ws_virtuelhost . '/paymentko.php?paymentkosessioncode='.urlencode($randomseckey).'&fulltag='.$FULLTAG;
2202 } else {
2203 $ext_urlko = DOL_URL_ROOT.'/public/website/index.php?paymentkosessioncode='.urlencode($randomseckey).'&website='.urlencode($ws).'&pageref=paymentko&fulltag='.$FULLTAG;
2204 }
2205
2206 dol_syslog("Now do a redirect using a Location:".$ext_urlko, LOG_DEBUG, 0, '_payment');
2207 header("Location: ".$ext_urlko);
2208 exit;
2209 }
2210}
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:66
llxFooter($comment='', $zone='private', $disabledoutputofmessages=0)
Empty footer.
Definition wrapper.php:87
if(!defined('NOREQUIRESOC')) if(!defined( 'NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined( 'NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined( 'NOREQUIREAJAX')) llxHeader($head='', $title='', $help_url='', $target='', $disablejs=0, $disablehead=0, $arrayofjs='', $arrayofcss='', $morequerystring='', $morecssonbody='', $replacemainareaby='', $disablenofollow=0, $disablenoindex=0)
Empty header.
Definition wrapper.php:71
Class to manage members of a foundation.
Class to manage members type.
Class to send emails (with attachments or not) Usage: $mailfile = new CMailFile($subject,...
Class to manage customers orders.
Class for ConferenceOrBoothAttendee.
Class for ConferenceOrBooth.
Class to manage donations.
Definition don.class.php:41
Class to manage invoices.
const TYPE_CREDIT_NOTE
Credit note invoice.
Class permettant la generation du formulaire html d'envoi de mail unitaire Usage: $formail = new Form...
Class to manage hooks.
Class to manage payments of customer invoices.
Class to manage payments of donations.
Class to manage third parties objects (customers, suppliers, prospects...)
Stripe class @TODO No reason to extends CommonObject.
Class to manage translations.
Class to manage Dolibarr users.
Class Website.
htmlPrintOnlineFooter($fromcompany, $langs, $addformmessage=0, $suffix='', $object=null)
Show footer of company in HTML public pages.
dol_get_first_day($year, $month=1, $gm=false)
Return GMT time for first day of a month or year.
Definition date.lib.php:600
dol_time_plus_duree($time, $duration_value, $duration_unit, $ruleforendofmonth=0)
Add a delay to a date.
Definition date.lib.php:125
dol_most_recent_file($dir, $regexfilter='', $excludefilter=array('(\.meta|_preview.*\.png) $', '^\.'), $nohook=0, $mode=0)
Return file(s) into a directory (by default most recent)
dol_getIdFromCode($db, $key, $tablename, $fieldkey='code', $fieldid='id', $entityfilter=0, $filters='', $useCache=true)
Return an id or code from a code or id.
getLanguageCodeFromCountryCode($countrycode)
Return default language from country code.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0, $attop=0)
Set event messages in dol_events session object.
dolExplodeIntoArray($string, $delimiter=';', $kv='=')
Split a string with 2 keys into key array.
img_picto($titlealt, $picto, $moreatt='', $pictoisfullpath=0, $srconly=0, $notitle=0, $alt='', $morecss='', $marginleftonlyshort=2, $allowothertags=array())
Show picto whatever it's its name (generic function)
dol_mimetype($file, $default='application/octet-stream', $mode=0)
Return MIME type of a file from its name with extension.
GETPOSTINT($paramname, $method=0)
Return the value of a $_GET or $_POST supervariable, converted into integer.
dol_now($mode='auto')
Return date for now.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
dol_print_date($time, $format='', $tzoutput='auto', $outputlangs=null, $encodetooutput=false)
Output date in a string format according to outputlangs (or langs if not defined).
dol_concatdesc($text1, $text2, $forxml=false, $invert=false)
Concat 2 descriptions with a new line between them (second operand after first one with appropriate n...
complete_substitutions_array(&$substitutionarray, $outputlangs, $object=null, $parameters=null, $callfunc="completesubstitutionarray")
Complete the $substitutionarray with more entries coming from external module that had set the "subst...
make_substitutions($text, $substitutionarray, $outputlangs=null, $converttextinhtmlifnecessary=0)
Make substitution into a text string, replacing keys with vals from $substitutionarray (oldval=>newva...
dol_textishtml($msg, $option=0)
Return if a text is a html content.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
dol_clone($object, $native=2)
Create a clone of instance of object (new instance with same value for each properties) With native =...
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
getCommonSubstitutionArray($outputlangs, $onlykey=0, $exclude=null, $object=null, $include=null)
Return array of possible common substitutions.
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0, $cleanalsojavascript=0)
Returns text escaped for inclusion in HTML alt or title or value tags, or into values of HTML input f...
global $conf
The following vars must be defined: $type2label $form $conf, $lang, The following vars may also be de...
Definition member.php:79
confirmPayment($token, $paymentType, $currencyCodeType, $payerID, $ipaddress, $FinalPaymentAmt, $tag)
Validate payment.
getDetails($token)
Prepares the parameters for the GetExpressCheckoutDetails API Call.
getRandomPassword($generic=false, $replaceambiguouschars=null, $length=32)
Return a generated password using default module.
httponly_accessforbidden($message='1', $http_response_code=403, $stringalreadysanitized=0)
Show a message to say access is forbidden and stop program.