dolibarr 25.0.0-alpha
card.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2004 Rodolphe Quiedeville <rodolphe@quiedeville.org>
3 * Copyright (C) 2005-2019 Laurent Destailleur <eldy@users.sourceforge.net>
4 * Copyright (C) 2005-2016 Regis Houssin <regis.houssin@inodbox.com>
5 * Copyright (C) 2021 Waël Almoman <info@almoman.com>
6 * Copyright (C) 2024-2026 MDW <mdeweerd@users.noreply.github.com>
7 * Copyright (C) 2025 Jon Bendtsen <jon.bendtsen.github@jonb.dk>
8 * Copyright (C) 2024-2026 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
30if (!defined('NOSTYLECHECK')) {
31 define('NOSTYLECHECK', '1');
32}
33
34// Load Dolibarr environment
35require '../../main.inc.php';
46require_once DOL_DOCUMENT_ROOT.'/core/lib/emailing.lib.php';
47require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
48require_once DOL_DOCUMENT_ROOT.'/core/class/CMailFile.class.php';
49require_once DOL_DOCUMENT_ROOT.'/core/lib/functions2.lib.php';
50require_once DOL_DOCUMENT_ROOT.'/comm/mailing/class/mailing.class.php';
51require_once DOL_DOCUMENT_ROOT.'/core/class/html.formother.class.php';
52require_once DOL_DOCUMENT_ROOT.'/core/class/html.formmail.class.php';
53if (isModEnabled('project')) {
54 require_once DOL_DOCUMENT_ROOT . '/projet/class/project.class.php';
55 require_once DOL_DOCUMENT_ROOT . '/core/class/html.formprojet.class.php';
56}
57
58// Load translation files required by the page
59$langs->loadLangs(array("mails", "admin"));
60
61$id = (GETPOSTINT('mailid') ? GETPOSTINT('mailid') : GETPOSTINT('id'));
62
63$action = GETPOST('action', 'aZ09');
64$confirm = GETPOST('confirm', 'alpha');
65$cancel = GETPOST('cancel', 'alpha');
66$projectid = GETPOSTINT('projectid');
67$urlfrom = GETPOST('urlfrom');
68$backtopage = GETPOST('backtopage');
69$backtopageforcancel = GETPOST('backtopageforcancel');
70
71// Initialize a technical objects
72$object = new Mailing($db);
73$hookmanager->initHooks(array('mailingcard', 'globalcard'));
74
75// Fetch optionals attributes and labels
76$extrafields->fetch_name_optionals_label($object->table_element);
77
78// Load object
79include DOL_DOCUMENT_ROOT.'/core/actions_fetchobject.inc.php'; // Must be 'include', not 'include_once'.
80
81// Load object->fk_project
82if (isset($object->fk_project) && $object->fk_project > 0 ) {
83 dol_syslog('isset($object->fk_project)='.$object->fk_project, LOG_DEBUG);
84 $ret = $object->fetchProject();
85 if ($ret <= 0) {
86 setEventMessages($object->error, $object->errors, 'errors');
87 $action = '';
88 }
89}
90
91
92// Array of possible substitutions (See also file mailing-send.php that should manage same substitutions)
93$object->substitutionarray = FormMail::getAvailableSubstitKey('emailing');
94
95
96// Set $object->substitutionarrayfortest
97$signature = ((!empty($user->signature) && !getDolGlobalString('MAIN_MAIL_DO_NOT_USE_SIGN')) ? $user->signature : '');
98
99$targetobject = null; // Not defined with mass emailing
100
101$parameters = array('mode' => 'emailing');
102$substitutionarray = FormMail::getAvailableSubstitKey('emailing', $targetobject);
103
104$object->substitutionarrayfortest = $substitutionarray;
105
106// List of sending methods
107$listofmethods = array();
108//$listofmethods['default'] = $langs->trans('DefaultOutgoingEmailSetup');
109$listofmethods['mail'] = 'PHP mail function';
110//$listofmethods['simplemail']='Simplemail class';
111$listofmethods['smtps'] = 'SMTP/SMTPS socket library';
112if (version_compare(phpversion(), '7.0', '>=')) {
113 $listofmethods['swiftmailer'] = 'Swift Mailer socket library';
114}
115
116// Security check
117if (!$user->hasRight('mailing', 'lire') || (!getDolGlobalString('EXTERNAL_USERS_ARE_AUTHORIZED') && $user->socid > 0)) {
119}
120if (empty($action) && empty($object->id)) {
121 accessforbidden('Object not found');
122}
123
124$upload_dir = $conf->mailing->dir_output."/".get_exdir($object->id, getDolGlobalInt('MAILING_USE_NEW_PATH_FOR_FILES') ? 0 : 2, 0, 1, $object, 'mailing');
125
126//$permissiontoread = $user->hasRight('maling', 'read');
127$permissiontocreate = $user->hasRight('mailing', 'creer');
128$permissiontovalidatesend = $user->hasRight('mailing', 'valider');
129$permissiontodelete = $user->hasRight('mailing', 'supprimer');
130
131
132/*
133 * Actions
134 */
135
136$parameters = array();
137$reshook = $hookmanager->executeHooks('doActions', $parameters, $object, $action); // Note that $action and $object may have been modified by some hooks
138if ($reshook < 0) {
139 setEventMessages($hookmanager->error, $hookmanager->errors, 'errors');
140}
141
142if (empty($reshook)) {
143 $error = 0;
144
145 $backurlforlist = DOL_URL_ROOT.'/comm/mailing/list.php';
146
147 if (empty($backtopage) || ($cancel && empty($id))) {
148 if (empty($backtopage) || ($cancel && strpos($backtopage, '__ID__'))) {
149 if (empty($id) && (($action != 'add' && $action != 'create') || $cancel)) {
150 $backtopage = $backurlforlist;
151 } else {
152 $backtopage = DOL_URL_ROOT.'/comm/mailing/card.php?id='.((!empty($id) && $id > 0) ? $id : '__ID__');
153 }
154 }
155 }
156
157 if ($cancel) {
158 /*var_dump($cancel);var_dump($backtopage);var_dump($backtopageforcancel);exit;*/
159 if (!empty($backtopageforcancel)) {
160 header("Location: ".$backtopageforcancel);
161 exit;
162 } elseif (!empty($backtopage)) {
163 header("Location: ".$backtopage);
164 exit;
165 }
166 $action = '';
167 }
168
169 // Action clone object
170 if ($action == 'confirm_clone' && $confirm == 'yes' && $permissiontocreate) {
171 if (!GETPOST("clone_content", 'alpha') && !GETPOST("clone_receivers", 'alpha')) {
172 setEventMessages($langs->trans("NoCloneOptionsSpecified"), null, 'errors');
173 } else {
174 $result = $object->createFromClone($user, $object->id, GETPOST("clone_content") ? 1 : 0, GETPOST("clone_receivers") ? 1 : 0);
175 if ($result > 0) {
176 header("Location: ".$_SERVER['PHP_SELF'].'?id='.$result);
177 exit;
178 } else {
179 setEventMessages($object->error, $object->errors, 'errors');
180 }
181 }
182 $action = '';
183 }
184
185 // Action send emailing for everybody
186 if ($action == 'sendallconfirmed' && $confirm == 'yes' && $permissiontovalidatesend) {
187 if (!getDolGlobalString('MAILING_LIMIT_SENDBYWEB')) {
188 // As security measure, we don't allow send from the GUI
189 setEventMessages($langs->trans("MailingNeedCommand"), null, 'warnings');
190 setEventMessages('<textarea cols="70" rows="'.ROWS_2.'" wrap="soft">php ./scripts/emailings/mailing-send.php '.$object->id.'</textarea>', null, 'warnings');
191 setEventMessages($langs->trans("MailingNeedCommand2"), null, 'warnings');
192 $action = '';
193 } elseif (getDolGlobalInt('MAILING_LIMIT_SENDBYWEB') < 0) {
194 setEventMessages($langs->trans("NotEnoughPermissions"), null, 'warnings');
195 $action = '';
196 } else {
197 if ($object->status == 0) {
198 dol_print_error(null, 'ErrorMailIsNotValidated');
199 exit;
200 }
201
202 $id = $object->id;
203 $subject = $object->sujet;
204 $message = $object->body;
205 $email_from = $object->email_from;
206 $replyto = $object->email_replyto;
207 $errorsto = $object->email_errorsto;
208 // Is the message in html
209 $msgishtml = -1; // Unknown by default
210 if (preg_match('/[\s\t]*<html>/i', $message)) {
211 $msgishtml = 1;
212 }
213
214 // Warning, we must not use begin-commit transaction here
215 // because we want to save update for each mail sent.
216
217 $nbok = 0;
218 $nbko = 0;
219
220 // We choose mails not already sent for this mailing (statut=0)
221 // or sent in error (statut=-1)
222 $sql = "SELECT mc.rowid, mc.fk_mailing, mc.lastname, mc.firstname, mc.email, mc.other, mc.source_url, mc.source_id, mc.source_type, mc.tag";
223 $sql .= " FROM ".MAIN_DB_PREFIX."mailing_cibles as mc";
224 $sql .= " WHERE mc.statut < 1 AND mc.fk_mailing = ".((int) $object->id);
225 $sql .= " ORDER BY mc.statut DESC"; // first status 0, then status -1
226
227 dol_syslog("card.php: select targets", LOG_DEBUG);
228 $resql = $db->query($sql);
229 if ($resql) {
230 $num = $db->num_rows($resql); // Number of possible recipients
231
232 if ($num) {
233 dol_syslog("comm/mailing/card.php: nb of targets = ".$num, LOG_DEBUG);
234
235 $now = dol_now();
236
237 // Positioning date of start sending
238 $sql = "UPDATE ".MAIN_DB_PREFIX."mailing SET date_envoi='".$db->idate($now)."' WHERE rowid=".((int) $object->id);
239 $resql2 = $db->query($sql);
240 if (!$resql2) {
241 dol_print_error($db);
242 }
243
244 $thirdpartystatic = new Societe($db);
245 // Loop on each email and send it
246 $iforemailloop = 0;
247
248 while ($iforemailloop < $num && $iforemailloop < $conf->global->MAILING_LIMIT_SENDBYWEB) {
249 // Here code is common with same loop ino mailing-send.php
250 $res = 1;
251 $now = dol_now();
252
253 $obj = $db->fetch_object($resql);
254
255 // sendto en RFC2822
256 $sendto = str_replace(',', ' ', dolGetFirstLastname($obj->firstname, $obj->lastname))." <".$obj->email.">";
257
258 // Make substitutions on topic and body. From (AA=YY;BB=CC;...) we keep YY, CC, ...
259 $other = explode(';', $obj->other);
260 $tmpfield = explode('=', $other[0], 2);
261 $other1 = (isset($tmpfield[1]) ? $tmpfield[1] : $tmpfield[0]);
262 $tmpfield = explode('=', $other[1], 2);
263 $other2 = (isset($tmpfield[1]) ? $tmpfield[1] : $tmpfield[0]);
264 $tmpfield = explode('=', $other[2], 2);
265 $other3 = (isset($tmpfield[1]) ? $tmpfield[1] : $tmpfield[0]);
266 $tmpfield = explode('=', $other[3], 2);
267 $other4 = (isset($tmpfield[1]) ? $tmpfield[1] : $tmpfield[0]);
268 $tmpfield = explode('=', $other[4], 2);
269 $other5 = (isset($tmpfield[1]) ? $tmpfield[1] : $tmpfield[0]);
270
271 $signature = ((!empty($user->signature) && !getDolGlobalString('MAIN_MAIL_DO_NOT_USE_SIGN')) ? $user->signature : '');
272
273 $parameters = array('mode' => 'emailing');
274 $substitutionarray = getCommonSubstitutionArray($langs, 0, array('object', 'objectamount'), $targetobject); // Note: On mass emailing, this is null because be don't know object
275
276 // Array of possible substitutions (See also file mailing-send.php that should manage same substitutions)
277 $substitutionarray['__ID__'] = $obj->source_id;
278 $substitutionarray['__EMAIL__'] = $obj->email;
279 $substitutionarray['__LASTNAME__'] = $obj->lastname;
280 $substitutionarray['__FIRSTNAME__'] = $obj->firstname;
281 $substitutionarray['__MAILTOEMAIL__'] = '<a href="mailto:'.$obj->email.'">'.$obj->email.'</a>';
282 $substitutionarray['__OTHER1__'] = $other1;
283 $substitutionarray['__OTHER2__'] = $other2;
284 $substitutionarray['__OTHER3__'] = $other3;
285 $substitutionarray['__OTHER4__'] = $other4;
286 $substitutionarray['__OTHER5__'] = $other5;
287
288 if ($obj->source_type == "thirdparty") {
289 $result = $thirdpartystatic->fetch($obj->source_id);
290 if ($result > 0) {
291 $substitutionarray['__THIRDPARTY_CUSTOMER_CODE__'] = $thirdpartystatic->code_client;
292 } else {
293 $substitutionarray['__THIRDPARTY_CUSTOMER_CODE__'] = '';
294 }
295 }
296
297 $substitutionarray['__USER_SIGNATURE__'] = $signature; // Signature is empty when ran from command line or taken from user in parameter)
298 $substitutionarray['__SENDEREMAIL_SIGNATURE__'] = $signature; // Signature is empty when ran from command line or taken from user in parameter)
299 $substitutionarray['__CHECK_READ__'] = '<img src="'.DOL_MAIN_URL_ROOT.'/public/emailing/mailing-read.php?tag='.urlencode($obj->tag).'&securitykey='.dol_hash(getDolGlobalString('MAILING_EMAIL_UNSUBSCRIBE_KEY').'-'.$obj->tag.'-'.$obj->email.'-'.$obj->rowid, "md5").'&email='.urlencode($obj->email).'&mtid='.((int) $obj->rowid).'" width="1" height="1" style="width:1px;height:1px" border="0"/>';
300 $substitutionarray['__UNSUBSCRIBE__'] = '<a href="'.DOL_MAIN_URL_ROOT.'/public/emailing/mailing-unsubscribe.php?tag='.urlencode($obj->tag).'&unsuscrib=1&securitykey='.dol_hash(getDolGlobalString('MAILING_EMAIL_UNSUBSCRIBE_KEY').'-'.$obj->tag.'-'.$obj->email.'-'.$obj->rowid, "md5").'&email='.urlencode($obj->email).'&mtid='.((int) $obj->rowid).'" target="_blank" rel="noopener noreferrer">'.$langs->trans("MailUnsubcribe").'</a>';
301 $substitutionarray['__UNSUBSCRIBE_URL__'] = DOL_MAIN_URL_ROOT.'/public/emailing/mailing-unsubscribe.php?tag='.urlencode($obj->tag).'&unsuscrib=1&securitykey='.dol_hash(getDolGlobalString('MAILING_EMAIL_UNSUBSCRIBE_KEY').'-'.$obj->tag.'-'.$obj->email.'-'.$obj->rowid, "md5").'&email='.urlencode($obj->email).'&mtid='.((int) $obj->rowid);
302
303 $onlinepaymentenabled = 0;
304 if (isModEnabled('paypal')) {
305 $onlinepaymentenabled++;
306 }
307 if (isModEnabled('stripe')) {
308 $onlinepaymentenabled++;
309 }
310 if ($onlinepaymentenabled && getDolGlobalString('PAYMENT_SECURITY_TOKEN')) {
311 require_once DOL_DOCUMENT_ROOT.'/core/lib/payments.lib.php';
312 $substitutionarray['__ONLINEPAYMENTLINK_MEMBER__'] = getHtmlOnlinePaymentLink('member', $obj->source_id);
313 $substitutionarray['__ONLINEPAYMENTLINK_DONATION__'] = getHtmlOnlinePaymentLink('donation', $obj->source_id);
314 $substitutionarray['__ONLINEPAYMENTLINK_ORDER__'] = getHtmlOnlinePaymentLink('order', $obj->source_id);
315 $substitutionarray['__ONLINEPAYMENTLINK_INVOICE__'] = getHtmlOnlinePaymentLink('invoice', $obj->source_id);
316 $substitutionarray['__ONLINEPAYMENTLINK_CONTRACTLINE__'] = getHtmlOnlinePaymentLink('contractline', $obj->source_id);
317
318 $substitutionarray['__SECUREKEYPAYMENT__'] = dol_hash(getDolGlobalString('PAYMENT_SECURITY_TOKEN'), '2');
319 $substitutionarray['__SECUREKEYPAYMENT_MEMBER__'] = dol_hash(getDolGlobalString('PAYMENT_SECURITY_TOKEN') . 'member'.$obj->source_id, '2');
320 $substitutionarray['__SECUREKEYPAYMENT_DONATION__'] = dol_hash(getDolGlobalString('PAYMENT_SECURITY_TOKEN') . 'donation'.$obj->source_id, '2');
321 $substitutionarray['__SECUREKEYPAYMENT_ORDER__'] = dol_hash(getDolGlobalString('PAYMENT_SECURITY_TOKEN') . 'order'.$obj->source_id, '2');
322 $substitutionarray['__SECUREKEYPAYMENT_INVOICE__'] = dol_hash(getDolGlobalString('PAYMENT_SECURITY_TOKEN') . 'invoice'.$obj->source_id, '2');
323 $substitutionarray['__SECUREKEYPAYMENT_CONTRACTLINE__'] = dol_hash(getDolGlobalString('PAYMENT_SECURITY_TOKEN') . 'contractline'.$obj->source_id, '2');
324 }
325 if (getDolGlobalString('MEMBER_ENABLE_PUBLIC')) {
326 $substitutionarray['__PUBLICLINK_NEWMEMBERFORM__'] = '<a target="_blank" rel="noopener noreferrer" href="'.DOL_MAIN_URL_ROOT.'/public/members/new.php'.((isModEnabled('multicompany')) ? '?entity='.$conf->entity : '').'">'.$langs->trans('BlankSubscriptionForm'). '</a>';
327 }
328 /* For backward compatibility, deprecated */
329 if (isModEnabled('paypal') && getDolGlobalString('PAYPAL_SECURITY_TOKEN')) {
330 $substitutionarray['__SECUREKEYPAYPAL__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN'), '2');
331
332 if (!getDolGlobalString('PAYPAL_SECURITY_TOKEN_UNIQUE')) {
333 $substitutionarray['__SECUREKEYPAYPAL_MEMBER__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN'), '2');
334 } else {
335 $substitutionarray['__SECUREKEYPAYPAL_MEMBER__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN') . 'membersubscription'.$obj->source_id, '2');
336 }
337
338 if (!getDolGlobalString('PAYPAL_SECURITY_TOKEN_UNIQUE')) {
339 $substitutionarray['__SECUREKEYPAYPAL_ORDER__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN'), '2');
340 } else {
341 $substitutionarray['__SECUREKEYPAYPAL_ORDER__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN') . 'order'.$obj->source_id, '2');
342 }
343
344 if (!getDolGlobalString('PAYPAL_SECURITY_TOKEN_UNIQUE')) {
345 $substitutionarray['__SECUREKEYPAYPAL_INVOICE__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN'), '2');
346 } else {
347 $substitutionarray['__SECUREKEYPAYPAL_INVOICE__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN') . 'invoice'.$obj->source_id, '2');
348 }
349
350 if (!getDolGlobalString('PAYPAL_SECURITY_TOKEN_UNIQUE')) {
351 $substitutionarray['__SECUREKEYPAYPAL_CONTRACTLINE__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN'), '2');
352 } else {
353 $substitutionarray['__SECUREKEYPAYPAL_CONTRACTLINE__'] = dol_hash(getDolGlobalString('PAYPAL_SECURITY_TOKEN') . 'contractline'.$obj->source_id, '2');
354 }
355 }
356 //$substitutionisok=true;
357
358 complete_substitutions_array($substitutionarray, $langs);
359 $newsubject = make_substitutions($subject, $substitutionarray);
360 $newmessage = make_substitutions($message, $substitutionarray, null, 0);
361
362 $moreinheader = '';
363 if (preg_match('/__UNSUBSCRIBE_(_|URL_)/', $message)) {
364 $moreinheader = "List-Unsubscribe: <__UNSUBSCRIBE_URL__>\n";
365 $moreinheader = make_substitutions($moreinheader, $substitutionarray);
366 }
367
368 $arr_file = array();
369 $arr_mime = array();
370 $arr_name = array();
371 $arr_css = array();
372
373 $listofpaths = dol_dir_list($upload_dir, 'all', 0, '', '', 'name', SORT_ASC, 0);
374 if (count($listofpaths)) {
375 foreach ($listofpaths as $key => $val) {
376 $arr_file[] = $listofpaths[$key]['fullname'];
377 $arr_mime[] = dol_mimetype($listofpaths[$key]['name']);
378 $arr_name[] = $listofpaths[$key]['name'];
379 }
380 }
381
382 // Mail making
383 $trackid = 'emailing-'.$obj->fk_mailing.'-'.$obj->rowid;
384 $upload_dir_tmp = $upload_dir;
385 $mail = new CMailFile($newsubject, $sendto, $email_from, $newmessage, $arr_file, $arr_mime, $arr_name, '', '', 0, $msgishtml, $errorsto, $arr_css, $trackid, $moreinheader, 'emailing', $replyto, $upload_dir_tmp);
386
387 if ($mail->error) {
388 $res = 0;
389 }
390 /*if (! $substitutionisok)
391 {
392 $mail->error='Some substitution failed';
393 $res=0;
394 }*/
395
396 // Send mail
397 if ($res) {
398 $res = $mail->sendfile();
399 }
400
401 if ($res) {
402 // Mail successful
403 $nbok++;
404
405 dol_syslog("comm/mailing/card.php: ok for #".$iforemailloop.($mail->error ? ' - '.$mail->error : ''), LOG_DEBUG);
406
407 $sql = "UPDATE ".MAIN_DB_PREFIX."mailing_cibles";
408 $sql .= " SET statut=1, date_envoi = '".$db->idate($now)."' WHERE rowid=".((int) $obj->rowid);
409 $resql2 = $db->query($sql);
410 if (!$resql2) {
411 dol_print_error($db);
412 } else {
413 //if check read is use then update prospect contact status
414 if (strpos($message, '__CHECK_READ__') !== false) {
415 //Update status communication of thirdparty prospect
416 $sql = "UPDATE ".MAIN_DB_PREFIX."societe SET fk_stcomm=2 WHERE rowid IN (SELECT source_id FROM ".MAIN_DB_PREFIX."mailing_cibles WHERE rowid=".((int) $obj->rowid).")";
417 dol_syslog("card.php: set prospect thirdparty status", LOG_DEBUG);
418 $resql2 = $db->query($sql);
419 if (!$resql2) {
420 dol_print_error($db);
421 }
422
423 //Update status communication of contact prospect
424 $sql = "UPDATE ".MAIN_DB_PREFIX."societe SET fk_stcomm=2 WHERE rowid IN (SELECT sc.fk_soc FROM ".MAIN_DB_PREFIX."socpeople AS sc INNER JOIN ".MAIN_DB_PREFIX."mailing_cibles AS mc ON mc.rowid=".((int) $obj->rowid)." AND mc.source_type = 'contact' AND mc.source_id = sc.rowid)";
425 dol_syslog("card.php: set prospect contact status", LOG_DEBUG);
426
427 $resql2 = $db->query($sql);
428 if (!$resql2) {
429 dol_print_error($db);
430 }
431 }
432 }
433
434 if (getDolGlobalString('MAILING_DELAY')) {
435 dol_syslog("Wait a delay of MAILING_DELAY=".((float) $conf->global->MAILING_DELAY));
436 usleep((int) ((float) $conf->global->MAILING_DELAY * 1000000));
437 }
438
439 //test if CHECK READ change statut prospect contact
440 } else {
441 // Mail failed
442 $nbko++;
443
444 dol_syslog("comm/mailing/card.php: error for #".$iforemailloop.($mail->error ? ' - '.$mail->error : ''), LOG_WARNING);
445
446 $sql = "UPDATE ".MAIN_DB_PREFIX."mailing_cibles";
447 $sql .= " SET statut=-1, error_text='".$db->escape(dol_trunc($mail->error, 250))."', date_envoi='".$db->idate($now)."' WHERE rowid=".((int) $obj->rowid);
448 $resql2 = $db->query($sql);
449 if (!$resql2) {
450 dol_print_error($db);
451 }
452 }
453
454 $iforemailloop++;
455 }
456 } else {
457 setEventMessages($langs->transnoentitiesnoconv("NoMoreRecipientToSendTo"), null, 'mesgs');
458 }
459
460 // Loop finished, set global statut of mail
461 if ($nbko > 0) {
462 $statut = 2; // Status 'sent partially' (because at least one error)
463 setEventMessages($langs->transnoentitiesnoconv("EMailSentToNRecipients", (string) $nbok), null, 'mesgs');
464 } else {
465 if ($nbok >= $num) {
466 $statut = 3; // Send to everybody
467 } else {
468 $statut = 2; // Status 'sent partially' (because not send to everybody)
469 }
470 setEventMessages($langs->transnoentitiesnoconv("EMailSentToNRecipients", (string) $nbok), null, 'mesgs');
471 }
472
473 $sql = "UPDATE ".MAIN_DB_PREFIX."mailing SET statut=".((int) $statut)." WHERE rowid = ".((int) $object->id);
474 dol_syslog("comm/mailing/card.php: update global status", LOG_DEBUG);
475 $resql2 = $db->query($sql);
476 if (!$resql2) {
477 dol_print_error($db);
478 }
479 } else {
480 dol_syslog($db->error());
481 dol_print_error($db);
482 }
483 $object->fetch($id);
484 $action = '';
485 }
486 }
487
488 // Action send test emailing
489 if ($action == 'send' && ! $cancel && $permissiontovalidatesend) {
490 $error = 0;
491
492 $upload_dir = $conf->mailing->dir_output."/".get_exdir($object->id, getDolGlobalInt('MAILING_USE_NEW_PATH_FOR_FILES') ? 0 : 2, 0, 1, $object, 'mailing');
493
494 $object->sendto = GETPOST("sendto", 'alphawithlgt');
495 if (!$object->sendto) {
496 setEventMessages($langs->trans("ErrorFieldRequired", $langs->transnoentitiesnoconv("MailTo")), null, 'errors');
497 $error++;
498 }
499
500 if (!$error) {
501 // Is the message in html
502 $msgishtml = -1; // Unknown = autodetect by default
503 if (preg_match('/[\s\t]*<html>/i', $object->body)) {
504 $msgishtml = 1;
505 }
506
507 $signature = ((!empty($user->signature) && !getDolGlobalString('MAIN_MAIL_DO_NOT_USE_SIGN')) ? $user->signature : '');
508
509 $parameters = array('mode' => 'emailing');
510 $substitutionarray = getCommonSubstitutionArray($langs, 0, array('object', 'objectamount'), $targetobject); // Note: On mass emailing, this is null because be don't know object
511
512 // other are set at begin of page
513 $substitutionarray['__EMAIL__'] = $object->sendto;
514 $substitutionarray['__MAILTOEMAIL__'] = '<a href="mailto:'.$object->sendto.'">'.$object->sendto.'</a>';
515 $substitutionarray['__CHECK_READ__'] = '<img src="'.DOL_MAIN_URL_ROOT.'/public/emailing/mailing-read.php?tag=undefinedintestmode&securitykey='.dol_hash(getDolGlobalString('MAILING_EMAIL_UNSUBSCRIBE_KEY')."-undefinedintestmode-".$object->sendto."-0", 'md5').'&email='.urlencode($object->sendto).'&mtid=0" width="1" height="1" style="width:1px;height:1px" border="0"/>';
516 $substitutionarray['__UNSUBSCRIBE__'] = '<a href="'.DOL_MAIN_URL_ROOT.'/public/emailing/mailing-unsubscribe.php?tag=undefinedintestmode&unsuscrib=1&securitykey='.dol_hash(getDolGlobalString('MAILING_EMAIL_UNSUBSCRIBE_KEY')."-undefinedintestmode-".$object->sendto."-0", 'md5').'&email='.urlencode($object->sendto).'&mtid=0" target="_blank" rel="noopener noreferrer">'.$langs->trans("MailUnsubcribe").'</a>';
517 $substitutionarray['__UNSUBSCRIBE_URL__'] = DOL_MAIN_URL_ROOT.'/public/emailing/mailing-unsubscribe.php?tag=undefinedintestmode&unsuscrib=1&securitykey='.dol_hash(getDolGlobalString('MAILING_EMAIL_UNSUBSCRIBE_KEY')."-undefinedintestmode-".$object->sendto."-0", 'md5').'&email='.urlencode($object->sendto).'&mtid=0';
518
519 // Subject and message substitutions
520 complete_substitutions_array($substitutionarray, $langs, $targetobject);
521
522 $tmpsujet = make_substitutions($object->sujet, $substitutionarray);
523 $tmpbody = make_substitutions($object->body, $substitutionarray);
524
525 $arr_file = array();
526 $arr_mime = array();
527 $arr_name = array();
528 $arr_css = array();
529
530 // Add CSS
531 if (!empty($object->bgcolor)) {
532 $arr_css['bgcolor'] = (preg_match('/^#/', $object->bgcolor) ? '' : '#').$object->bgcolor;
533 }
534 if (!empty($object->bgimage)) {
535 $arr_css['bgimage'] = $object->bgimage;
536 }
537
538 // Attached files
539 $listofpaths = dol_dir_list($upload_dir, 'all', 0, '', '', 'name', SORT_ASC, 0);
540 if (count($listofpaths)) {
541 foreach ($listofpaths as $key => $val) {
542 $arr_file[] = $listofpaths[$key]['fullname'];
543 $arr_mime[] = dol_mimetype($listofpaths[$key]['name']);
544 $arr_name[] = $listofpaths[$key]['name'];
545 }
546 }
547
548 $trackid = 'emailing-test';
549 $upload_dir_tmp = $upload_dir;
550 $mailfile = new CMailFile($tmpsujet, $object->sendto, $object->email_from, $tmpbody, $arr_file, $arr_mime, $arr_name, '', '', 0, $msgishtml, $object->email_errorsto, $arr_css, $trackid, '', 'emailing', $object->email_replyto, $upload_dir_tmp);
551
552 $result = $mailfile->sendfile();
553 if ($result) {
554 setEventMessages($langs->trans("MailSuccessfulySent", $mailfile->getValidAddress($object->email_from, 2), $mailfile->getValidAddress($object->sendto, 2)), null, 'mesgs');
555 $action = '';
556 } else {
557 setEventMessages($langs->trans("ResultKo").'<br>'.$mailfile->error.' '.json_encode($result), null, 'errors');
558 $action = 'test';
559 }
560 }
561 }
562
563 $mesgs = array();
564 // Action add emailing
565 if ($action == 'add' && $permissiontocreate) {
566 $object->messtype = (string) GETPOST("messtype");
567 if ($object->messtype == 'sms') {
568 $object->email_from = (string) GETPOST("from_phone", 'alphawithlgt'); // Must allow 'name <email>'
569 } else {
570 $object->email_from = (string) GETPOST("from", 'alphawithlgt'); // Must allow 'name <email>'
571 }
572 $object->email_replyto = (string) GETPOST("replyto", 'alphawithlgt'); // Must allow 'name <email>'
573 $object->email_errorsto = (string) GETPOST("errorsto", 'alphawithlgt'); // Must allow 'name <email>'
574 $object->title = (string) GETPOST("title");
575 $object->sujet = (string) GETPOST("subject");
576 $object->body = (string) GETPOST("bodyemail", 'restricthtml');
577 $object->bgcolor = preg_replace('/^#/', '', (string) GETPOST("bgcolor"));
578 $object->bgimage = (string) GETPOST("bgimage");
579 $object->fk_project = GETPOSTINT('projectid');
580
581 if (!$object->title) {
582 $mesgs[] = $langs->trans("ErrorFieldRequired", $langs->transnoentities("MailTitle"));
583 }
584 if ($object->messtype != 'sms' && !$object->sujet) {
585 $mesgs[] = $langs->trans("ErrorFieldRequired", $langs->transnoentities("MailTopic"));
586 }
587 if (!$object->body) {
588 $mesgs[] = $langs->trans("ErrorFieldRequired", $langs->transnoentities("MailMessage"));
589 }
590
591 if (!count($mesgs)) {
592 if ($object->create($user) >= 0) {
593 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
594 exit;
595 }
596 $mesgs[] = $object->error;
597 $mesgs = array_merge($mesgs, $object->errors);
598 }
599
600 setEventMessages('', $mesgs, 'errors');
601 $action = "create";
602 }
603
604 if ($action == 'classin' && $permissiontocreate) {
605 $mesgs = array();
606 $setResult = $object->setProject(GETPOSTINT('projectid'));
607 dol_syslog('Mailing card, action classin, setProject', LOG_DEBUG);
608 if ($setResult) {
609 $result = $object->update($user);
610 if ($result >= 0) {
611 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
612 exit;
613 }
614 $mesg = $object->error;
615 setEventMessages($mesg, $mesgs, 'errors');
616 } else {
617 setEventMessages(null, $mesgs, 'errors');
618 }
619
620 $action = "";
621 }
622
623 // Action update description of emailing
624 if (($action == 'settitle' || $action == 'setemail_from' || $action == 'setemail_replyto' || $action == 'setreplyto' || $action == 'setemail_errorsto' || $action == 'setevenunsubscribe') && $permissiontovalidatesend) {
625 $upload_dir = $conf->mailing->dir_output."/".get_exdir($object->id, getDolGlobalInt('MAILING_USE_NEW_PATH_FOR_FILES') ? 0 : 2, 0, 1, $object, 'mailing');
626
627 if ($action == 'settitle') { // Test on permission already done
628 $object->title = trim(GETPOST('title', 'alpha'));
629 if (empty($object->title)) {
630 $mesg = $langs->trans("ErrorFieldRequired", $langs->transnoentities("MailTitle"));
631 }
632 } elseif ($action == 'setemail_from') { // Test on permission already done
633 $object->email_from = trim(GETPOST('email_from', 'alphawithlgt')); // Must allow 'name <email>'
634 if (empty($object->email_from)) {
635 $mesg = $langs->trans("ErrorFieldRequired", $langs->transnoentities("MailFrom"));
636 }
637 } elseif ($action == 'setemail_replyto') { // Test on permission already done
638 $object->email_replyto = trim(GETPOST('email_replyto', 'alphawithlgt')); // Must allow 'name <email>'
639 } elseif ($action == 'setemail_errorsto') { // Test on permission already done
640 $object->email_errorsto = trim(GETPOST('email_errorsto', 'alphawithlgt')); // Must allow 'name <email>'
641 } elseif ($action == 'setevenunsubscribe') { // Test on permission already done
642 $object->evenunsubscribe = (GETPOST('evenunsubscribe') ? 1 : 0);
643 }
644
645 if (empty($mesg)) {
646 $result = $object->update($user);
647 if ($result >= 0) {
648 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
649 exit;
650 }
651 $mesg = $object->error;
652 }
653 setEventMessages($mesg, $mesgs, 'errors');
654 $action = "";
655 }
656
657 /*
658 * Action of adding a file in email form
659 */
660 if (GETPOST('addfile') && $permissiontocreate) {
661 $upload_dir = $conf->mailing->dir_output."/".get_exdir($object->id, getDolGlobalInt('MAILING_USE_NEW_PATH_FOR_FILES') ? 0 : 2, 0, 1, $object, 'mailing');
662
663 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
664
665 // Set tmp user directory
666 dol_add_file_process($upload_dir, 0, 0, 'addedfile', '', null, '', 0);
667
668 $action = "edit";
669 }
670
671 // Action of file remove
672 if (GETPOSTINT("removedfile") && $permissiontocreate) {
673 $upload_dir = $conf->mailing->dir_output."/".get_exdir($object->id, getDolGlobalInt('MAILING_USE_NEW_PATH_FOR_FILES') ? 0 : 2, 0, 1, $object, 'mailing');
674
675 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
676
677 dol_remove_file_process(GETPOSTINT('removedfile'), 0, 0); // We really delete file linked to mailing
678
679 $action = "edit";
680 }
681
682 // Action of emailing update
683 if ($action == 'update' && !GETPOSTINT("removedfile") && !$cancel && $permissiontocreate) {
684 require_once DOL_DOCUMENT_ROOT.'/core/lib/files.lib.php';
685
686 $isupload = 0;
687
688 if (!$isupload) {
689 $mesgs = array();
690
691 //$object->messtype = (string) GETPOST("messtype"); // We must not be able to change the messtype
692 $object->sujet = (string) GETPOST("subject");
693 $object->body = (string) GETPOST("bodyemail", 'restricthtml');
694 $object->bgcolor = preg_replace('/^#/', '', (string) GETPOST("bgcolor"));
695 $object->bgimage = (string) GETPOST("bgimage");
696
697 if ($object->messtype != 'sms' && !$object->sujet) {
698 $mesgs[] = $langs->trans("ErrorFieldRequired", $langs->transnoentities("MailTopic"));
699 }
700 if (!$object->body) {
701 $mesgs[] = $langs->trans("ErrorFieldRequired", $langs->transnoentities("MailMessage"));
702 }
703
704 if (!count($mesgs)) {
705 if ($object->update($user) >= 0) {
706 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
707 exit;
708 }
709 $mesgs[] = $object->error;
710 $mesgs = array_merge($mesgs, $object->errors);
711 }
712
713 setEventMessages('', $mesgs, 'errors');
714 $action = "edit";
715 } else {
716 $action = "edit";
717 }
718 }
719
720 // Action of validation confirmation
721 if ($action == 'confirm_valid' && $confirm == 'yes' && $permissiontovalidatesend) {
722 if ($object->id > 0) {
723 $object->valid($user);
724 setEventMessages($langs->trans("MailingSuccessfullyValidated"), null, 'mesgs');
725 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
726 exit;
727 } else {
728 dol_print_error($db);
729 }
730 }
731
732 // Action of validation confirmation
733 if ($action == 'confirm_settodraft' && $confirm == 'yes' && $permissiontocreate) {
734 if ($object->id > 0) {
735 $result = $object->setStatut(0);
736 if ($result > 0) {
737 //setEventMessages($langs->trans("MailingSuccessfullyValidated"), null, 'mesgs');
738 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
739 exit;
740 } else {
741 setEventMessages($object->error, $object->errors, 'errors');
742 }
743 } else {
744 dol_print_error($db);
745 }
746 }
747
748 // Resend
749 if ($action == 'confirm_reset' && $confirm == 'yes' && $permissiontocreate) {
750 if ($object->id > 0) {
751 $db->begin();
752
753 $result = $object->valid($user);
754 if ($result > 0) {
755 $result = $object->reset_targets_status($user);
756 }
757
758 if ($result > 0) {
759 $db->commit();
760 header("Location: ".$_SERVER['PHP_SELF']."?id=".$object->id);
761 exit;
762 } else {
763 setEventMessages($object->error, $object->errors, 'errors');
764 $db->rollback();
765 }
766 } else {
767 dol_print_error($db);
768 }
769 }
770
771 // Action of delete confirmation
772 if ($action == 'confirm_delete' && $confirm == 'yes' && $permissiontodelete) {
773 $object->oldcopy = dol_clone($object, 2); // @phan-suppress-current-line PhanTypeMismatchProperty
774 if ($object->delete($user) > 0) {
775 $url = (!empty($urlfrom) ? $urlfrom : 'list.php');
776 header("Location: ".$url);
777 exit;
778 } else {
779 setEventMessages($object->error, $object->errors, 'errors');
780 }
781 }
782
783 if ($cancel) {
784 $action = '';
785 }
786}
787
788
789/*
790 * View
791 */
792
793$form = new Form($db);
794$htmlother = new FormOther($db);
795$formproject = null;
796if (isModEnabled('project')) {
797 $formproject = new FormProjets($db);
798}
799
800// Same check as the email templates editor in admin/mails_templates.php so the
801// local media browser is shown consistently in both places.
802$acceptlocallinktomedia = (acceptLocalLinktoMedia() > 0 ? 1 : 0);
803
804$help_url = 'EN:Module_EMailing|FR:Module_Mailing|ES:M&oacute;dulo_Mailing';
806 '',
807 $langs->trans("Mailing"),
808 $help_url,
809 '',
810 0,
811 0,
812 array(
813 '/includes/ace/src/ace.js',
814 '/includes/ace/src/ext-statusbar.js',
815 '/includes/ace/src/ext-language_tools.js',
816 //'/includes/ace/src/ext-chromevox.js'
817 ),
818 array()
819);
820
821
822if ($action == 'create') { // aaa
823 // EMailing in creation mode
824 print '<form name="new_mailing" action="'.$_SERVER['PHP_SELF'].'" method="POST">'."\n";
825 print '<input type="hidden" name="token" value="'.newToken().'">';
826 print '<input type="hidden" name="action" value="add">';
827
828 $htmltext = '<i>'.$langs->trans("FollowingConstantsWillBeSubstituted").':<br><br><span class="small">';
829 foreach ($object->substitutionarray as $key => $val) {
830 $htmltext .= $key.' = '.$langs->trans($val).'<br>';
831 }
832 $htmltext .= '</span></i>';
833
834 $availablelink = '<span class="opacitymedium hideonsmartphone small">'.$form->textwithpicto($langs->trans("AvailableVariables"), $htmltext, 1, 'helpclickable', '', 0, 2, 'availvar').'</span>';
835
836 // Print mail form
837 print load_fiche_titre($langs->trans("NewMailing"), $availablelink, 'object_email');
838
839 print dol_get_fiche_head(array(), '', '', -3, '', 0, '', 'noborderbottom');
840
841 print '<table class="border centpercent">';
842
843 $title = GETPOST('title');
844 if (empty($title)) {
845 $title = $langs->transnoentities("MailingOf", dol_print_date(dol_now(), 'dayrfc'));
846 }
847 print '<tr><td class="fieldrequired titlefieldcreate">'.$langs->trans("MailTitle").'</td><td><input class="flat minwidth300" id="title" name="title" value="'.dolPrintHTMLForAttribute($title).'" autofocus="autofocus" spellcheck="false"></td></tr>';
848
849 // Project
850 if (isModEnabled('project')) {
851 // Link mailing to project
852 if (GETPOST('origin', 'alpha') == 'project') {
853 $projectid = GETPOSTINT('originid');
854 } else {
855 $projectid = GETPOSTINT('projectid');
856 }
857 if ($projectid > 0) {
858 $object->setProject($projectid);
859 }
860 $langs->load("projects");
861 print '<tr class="field_projectid">';
862 print '<td class="titlefieldcreate">' . $langs->trans("Project") . '</td><td class="valuefieldcreate">';
863 print img_picto('', 'project', 'class="pictofixedwidth"') . $formproject->select_projects(-1, (string) $projectid, 'projectid', 0, 0, 1, 1, 0, 0, 0, '', 1, 0, 'maxwidth500 widthcentpercentminusxx');
864 print ' <a href="' . DOL_URL_ROOT . '/projet/card.php?action=create&status=1&backtopage=' . urlencode($_SERVER["PHP_SELF"] . '?action=create') . '"><span class="fa fa-plus-circle valignmiddle paddingleft" title="' . $langs->trans("AddProject") . '"></span></a>';
865 print '</td>';
866 print '</tr>';
867 }
868
869 if (getDolGlobalInt('EMAILINGS_SUPPORT_ALSO_SMS')) {
870 $arrayoftypes = array("email" => "Email", "sms" => "SMS");
871 print '<tr><td class="fieldrequired titlefieldcreate">'.$langs->trans("Type").'</td><td>';
872 print $form->selectarray('messtype', $arrayoftypes, (GETPOSTISSET('messtype') ? GETPOST('messtype') : 'email'), 0, 0);
873
874 print '<script>
875 $( document ).ready(function() {
876 jQuery("#messtype").on("change", function() {
877 console.log("We change the message ttpe");
878 if (jQuery("#messtype").val() == "email") {
879 jQuery(".fieldsforsms").hide();
880 jQuery(".fieldsforemail").show();
881 }
882 if (jQuery("#messtype").val() == "sms") {
883 jQuery(".fieldsforsms").show();
884 jQuery(".fieldsforemail").hide();
885 }
886 });
887 jQuery("#messtype").change();
888 })
889 </script>';
890
891 print '</td></tr>';
892 }
893 print '</table>';
894
895 print '<br>';
896
897 print '<table class="border centpercent">';
898
899 print '<tr class="fieldsforemail"><td class="fieldrequired titlefieldcreate">'.$langs->trans("MailFrom").'</td>';
900 print '<td>'.img_picto('', 'email', 'class="pictofixedwidth"').'<input class="flat minwidth200" name="from" value="'.(GETPOSTISSET('from') ? GETPOST('from') : getDolGlobalString('MAILING_EMAIL_FROM')).'" spellcheck="false"></td></tr>';
901
902 print '<tr class="fieldsforsms hidden"><td class="fieldrequired titlefieldcreate">'.$langs->trans("PhoneFrom").'</td>';
903 print '<td>'.img_picto('', 'email', 'class="pictofixedwidth"').'<input class="flat minwidth200" name="fromphone" value="'.(GETPOSTISSET('fromphone') ? GETPOST('fromphone') : getDolGlobalString('MAILING_SMS_FROM')).'" placeholder="+123..."></td></tr>';
904
905 print '<tr class="fieldsforemail"><td>'.$langs->trans("MailErrorsTo").'</td>';
906 print '<td>'.img_picto('', 'email', 'class="pictofixedwidth"').'<input class="flat minwidth200" name="errorsto" value="'.getDolGlobalString('MAILING_EMAIL_ERRORSTO', getDolGlobalString('MAIN_MAIL_ERRORS_TO')).'"></td></tr>';
907
908 print '<tr class="fieldsforemail"><td>'.$langs->trans("MailReply").'</td>';
909 print '<td>'.img_picto('', 'email', 'class="pictofixedwidth"').'<input class="flat minwidth200" name="replyto" value="'.getDolGlobalString('MAILING_EMAIL_REPLYTO', getDolGlobalString('MAIN_MAIL_REPLY_TO')).'"></td></tr>';
910
911 // Other attributes
912 $parameters = array();
913 $reshook = $hookmanager->executeHooks('formObjectOptions', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
914 print $hookmanager->resPrint;
915 if (empty($reshook)) {
916 print $object->showOptionals($extrafields, 'create');
917 }
918
919 print '</table>';
920
921 print '<br>';
922
923 print '<table class="border centpercent">';
924
925 $subject = GETPOST('subject');
926 if (empty($subject)) {
927 $subject = '['.$mysoc->name.'] '.$langs->trans("Information");
928 }
929
930 print '<tr class="fieldsforemail"><td class="fieldrequired titlefieldcreate">'.$langs->trans("MailTopic").'</td>';
931 print '<td><input id="subject" class="flat minwidth200 quatrevingtpercent" name="subject" id="subject" value="'.dolPrintHTMLForAttributeUrl($subject).'" spellcheck="false"></td></tr>';
932
933 // Background color
934 /* if (getDolGlobalString('EMAILING_CAN_EDIT_BACKGROUND_COLOR')) {
935 print '<tr class="fieldsforemail"><td>'.$langs->trans("BackgroundColorByDefault").'</td><td colspan="3">';
936 print $htmlother->selectColor(GETPOST('bgcolor'), 'bgcolor', '', 0);
937 print '</td></tr>';
938 } */
939
940 $formmail = new FormMail($db);
941 $formmail->withfckeditor = 1;
942 $formmail->withlayout = 'emailing';
943 $formmail->withaiprompt = 'html';
944
945 print '<tr class="fieldsforemail"><td></td><td class="tdtop"></td></tr>';
946
947 print '<tr class="fieldsforemail"><td class="tdtop" colspan="2">';
948
949 $out = '';
950 $showlinktolayout = ($formmail->withfckeditor ? $formmail->withlayout : '');
951 $showlinktolayoutlabel = $langs->trans("FillMessageWithALayout");
952 $showlinktoai = ($formmail->withaiprompt && isModEnabled('ai')) ? 'textgenerationemail' : '';
953 $showlinktoailabel = $langs->trans("FillMessageWithAIContent");
954 $formatforouput = 'html';
955 $htmlname = 'bodyemail';
956
957 // Fill $out
958 include DOL_DOCUMENT_ROOT.'/core/tpl/formlayoutai.tpl.php';
959
960 print $out;
961
962 print '</td></tr>';
963 print '</table>';
964
965
966 print '<div style="padding-top: 10px">';
967 // wysiwyg editor
968 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
969 $doleditor = new DolEditor('bodyemail', GETPOST('bodyemail', 'restricthtmlallowunvalid'), '', 600, 'dolibarr_mailings', '', true, $acceptlocallinktomedia, getDolGlobalInt('FCKEDITOR_ENABLE_MAILING'), 20, '100%');
970 $doleditor->Create();
971 print '</div>';
972
973 print dol_get_fiche_end();
974
975 print $form->buttonsSaveCancel("Create", 'Cancel');
976
977 print '</form>';
978} else {
979 if ($object->id > 0) {
980 $upload_dir = $conf->mailing->dir_output."/".get_exdir($object->id, getDolGlobalInt('MAILING_USE_NEW_PATH_FOR_FILES') ? 0 : 2, 0, 1, $object, 'mailing');
981
982 $head = emailing_prepare_head($object);
983
984 if ($action == 'settodraft') {
985 // Confirmation back to draft
986 print $form->formconfirm($_SERVER["PHP_SELF"]."?id=".$object->id, $langs->trans("SetToDraft"), $langs->trans("ConfirmUnvalidateEmailing"), "confirm_settodraft", '', '', 1);
987 } elseif ($action == 'valid') {
988 // Confirmation of mailing validation
989 print $form->formconfirm($_SERVER["PHP_SELF"]."?id=".$object->id, $langs->trans("ValidMailing"), $langs->trans("ConfirmValidMailing"), "confirm_valid", '', '', 1);
990 } elseif ($action == 'reset') {
991 // Confirm reset
992 print $form->formconfirm($_SERVER["PHP_SELF"]."?id=".$object->id, $langs->trans("ResetMailing"), $langs->trans("ConfirmResetMailing", $object->ref), "confirm_reset", '', '', 2);
993 } elseif ($action == 'delete') {
994 // Confirm delete
995 print $form->formconfirm($_SERVER["PHP_SELF"]."?id=".$object->id.(!empty($urlfrom) ? '&urlfrom='.urlencode($urlfrom) : ''), $langs->trans("DeleteMailing"), $langs->trans("ConfirmDeleteMailing"), "confirm_delete", '', '', 1);
996 }
997
998 if ($action != 'edit' && $action != 'edittxt' && $action != 'edithtml') {
999 print dol_get_fiche_head($head, 'card', $langs->trans("Mailing"), -1, $object->picto);
1000
1001 // View mode mailing
1002 if ($action == 'sendall') {
1003 // Define message to recommend from command line
1004 $sendingmode = getDolGlobalString('EMAILING_MAIL_SENDMODE');
1005 if (empty($sendingmode)) {
1006 $sendingmode = getDolGlobalString('MAIN_MAIL_SENDMODE');
1007 }
1008 if (empty($sendingmode)) {
1009 $sendingmode = 'mail'; // If not defined, we use php mail function
1010 }
1011
1012 // MAILING_NO_USING_PHPMAIL may be defined or not.
1013 // MAILING_LIMIT_SENDBYWEB is always defined to something != 0 (-1=forbidden).
1014 // MAILING_LIMIT_SENDBYCLI may be defined or not (-1=forbidden, 0 or undefined=no limit).
1015 // MAILING_LIMIT_SENDBYDAY may be defined or not (0 or undefined=no limit).
1016 if (getDolGlobalString('MAILING_NO_USING_PHPMAIL') && $sendingmode == 'mail') {
1017 // EMailing feature may be a spam problem, so when you host several users/instance, having this option may force each user to use their own SMTP agent.
1018 // You ensure that every user is using its own SMTP server when using the mass emailing module.
1019 $linktoadminemailbefore = '<a href="'.DOL_URL_ROOT.'/admin/mails_emailing.php">';
1020 $linktoadminemailend = '</a>';
1021 setEventMessages($langs->trans("MailSendSetupIs", $listofmethods[$sendingmode]), null, 'warnings');
1022 $messagetoshow = $langs->trans("MailSendSetupIs2", '{s1}', '{s2}', '{s3}', '{s4}');
1023 $messagetoshow = str_replace('{s1}', $linktoadminemailbefore, $messagetoshow);
1024 $messagetoshow = str_replace('{s2}', $linktoadminemailend, $messagetoshow);
1025 $messagetoshow = str_replace('{s3}', $langs->transnoentitiesnoconv("MAIN_MAIL_SENDMODE"), $messagetoshow);
1026 $messagetoshow = str_replace('{s4}', $listofmethods['smtps'], $messagetoshow);
1027 setEventMessages($messagetoshow, null, 'warnings');
1028
1029 if (getDolGlobalString('MAILING_SMTP_SETUP_EMAILS_FOR_QUESTIONS')) {
1030 setEventMessages($langs->trans("MailSendSetupIs3", getDolGlobalString('MAILING_SMTP_SETUP_EMAILS_FOR_QUESTIONS')), null, 'warnings');
1031 }
1032 $action = '';
1033 } elseif (getDolGlobalInt('MAILING_LIMIT_SENDBYWEB') < 0) {
1034 if (getDolGlobalString('MAILING_LIMIT_WARNING_PHPMAIL') && $sendingmode == 'mail') {
1035 setEventMessages($langs->transnoentitiesnoconv($conf->global->MAILING_LIMIT_WARNING_PHPMAIL), null, 'warnings');
1036 }
1037 if (getDolGlobalString('MAILING_LIMIT_WARNING_NOPHPMAIL') && $sendingmode != 'mail') {
1038 setEventMessages($langs->transnoentitiesnoconv($conf->global->MAILING_LIMIT_WARNING_NOPHPMAIL), null, 'warnings');
1039 }
1040
1041 // The feature is forbidden from GUI, we show just message to use from command line.
1042 setEventMessages($langs->trans("MailingNeedCommand"), null, 'warnings');
1043 setEventMessages('<textarea cols="60" rows="'.ROWS_1.'" wrap="soft">php ./scripts/emailings/mailing-send.php '.$object->id.'</textarea>', null, 'warnings');
1044 if ($conf->file->mailing_limit_sendbyweb != '-1') { // MAILING_LIMIT_SENDBYWEB was set to -1 in database, but it is allowed to increase it.
1045 setEventMessages($langs->trans("MailingNeedCommand2"), null, 'warnings'); // You can send online with constant...
1046 }
1047 $action = '';
1048 } else {
1049 if (getDolGlobalString('MAILING_LIMIT_WARNING_PHPMAIL') && $sendingmode == 'mail') {
1050 setEventMessages($langs->transnoentitiesnoconv($conf->global->MAILING_LIMIT_WARNING_PHPMAIL), null, 'warnings');
1051 }
1052 if (getDolGlobalString('MAILING_LIMIT_WARNING_NOPHPMAIL') && $sendingmode != 'mail') {
1053 setEventMessages($langs->transnoentitiesnoconv($conf->global->MAILING_LIMIT_WARNING_NOPHPMAIL), null, 'warnings');
1054 }
1055
1056 $text = '';
1057
1058 if (getDolGlobalInt('MAILING_LIMIT_SENDBYDAY') > 0) {
1059 $text .= $langs->trans('WarningLimitSendByDay', getDolGlobalInt('MAILING_LIMIT_SENDBYDAY'));
1060 $text .= '<br><br>';
1061 }
1062 $text .= $langs->trans('ConfirmSendingEmailing').'<br>';
1063 $text .= $langs->trans('LimitSendingEmailing', getDolGlobalString('MAILING_LIMIT_SENDBYWEB'));
1064
1065 if (!isset($conf->global->MAILING_LIMIT_SENDBYCLI) || getDolGlobalInt('MAILING_LIMIT_SENDBYCLI') >= 0) {
1066 $text .= '<br><br>';
1067 $text .= '<u>'.$langs->trans("AdvancedAlternative").':</u> '.$langs->trans("MailingNeedCommand");
1068 $text .= '<br><textarea class="quatrevingtpercent" rows="'.ROWS_2.'" wrap="soft" disabled>php ./scripts/emailings/mailing-send.php '.$object->id.' '.$user->login.'</textarea>';
1069 }
1070
1071 $labelbuttonyes = $langs->transnoentities('Confirm');
1072 $labelbuttonno = $langs->transnoentities('Cancel');
1073
1074 print $form->formconfirm($_SERVER['PHP_SELF'].'?id='.$object->id, $langs->trans('SendMailing'), $text, 'sendallconfirmed', '', '', 1, 380, 660, 0, $labelbuttonyes, $labelbuttonno);
1075 }
1076 }
1077
1078 $linkback = '<a href="'.DOL_URL_ROOT.'/comm/mailing/list.php?restore_lastsearch_values=1">'.$langs->trans("BackToList").'</a>';
1079
1080 $morehtmlref = '<div class="refidno">';
1081 // Ref customer
1082 $morehtmlref .= $form->editfieldkey("", 'title', $object->title, $object, $user->hasRight('mailing', 'creer'), 'string', '', 0, 1);
1083 $morehtmlref .= $form->editfieldval("", 'title', $object->title, $object, $user->hasRight('mailing', 'creer'), 'string', '', null, null, '', 1);
1084
1085 $morehtmlstatus = '';
1086 $nbtry = $nbok = 0;
1087 if ($object->status == $object::STATUS_SENTPARTIALY || $object->status == $object::STATUS_SENTCOMPLETELY) {
1088 $nbtry = $object->countNbOfTargets('alreadysent');
1089 $nbko = $object->countNbOfTargets('alreadysentko');
1090
1091 $morehtmlstatus .= ' ('.$nbtry.'/'.$object->nbemail;
1092 if ($nbko) {
1093 $morehtmlstatus .= ' - '.$nbko.' '.$langs->trans("Error");
1094 }
1095 $morehtmlstatus .= ') &nbsp; ';
1096 }
1097 // Project
1098 if (isModEnabled('project')) {
1099 $langs->load("projects");
1100 $morehtmlref .= '<br>';
1101 if ($permissiontocreate) {
1102 $morehtmlref .= img_picto($langs->trans("Project"), 'project', 'class="pictofixedwidth"');
1103 if ($action != 'classify') {
1104 $morehtmlref .= '<a class="editfielda" href="' . $_SERVER['PHP_SELF'] . '?action=classify&token=' . newToken() . '&id=' . $object->id . '">' . img_edit($langs->transnoentitiesnoconv('SetProject')) . '</a> ';
1105 }
1106 $morehtmlref .= $form->form_project($_SERVER['PHP_SELF'] . '?id=' . $object->id, -1, (string) $object->fk_project, ($action == 'classify' ? 'projectid' : 'none'), 0, 0, 0, 1, '', 'maxwidth300', '');
1107 } else {
1108 if (!empty($object->fk_project)) {
1109 $proj = new Project($db);
1110 $proj->fetch($object->fk_project);
1111 $morehtmlref .= $proj->getNomUrl(1, 'mailing');
1112 if ($proj->title) {
1113 $morehtmlref .= '<span class="opacitymedium"> - ' . dol_escape_htmltag($proj->title) . '</span>';
1114 }
1115 }
1116 }
1117 if (!getDolGlobalString('MAIN_DISABLE_OTHER_LINK') && $object->fk_project > 0 && $action != 'classify') {
1118 $proj = new Project($db);
1119 $proj->fetch($object->fk_project);
1120 $morehtmlref .= ' <small>(<a href="' . DOL_URL_ROOT . '/comm/mailing/list.php?projectid='.$object->fk_project.'">'.$langs->trans("OtherEMailingsForProject").'</a>)</small>';
1121 }
1122 }
1123 $morehtmlref .= '</div>';
1124
1125 dol_banner_tab($object, 'id', $linkback, 1, 'rowid', 'ref', $morehtmlref, '', 0, '', $morehtmlstatus);
1126
1127 print '<div class="fichecenter">';
1128 print '<div class="fichehalfleft">';
1129 print '<div class="underbanner clearboth"></div>';
1130
1131 print '<table class="border centpercent tableforfield">'."\n";
1132
1133 // From
1134 print '<tr><td class="titlefield">';
1135 print $form->editfieldkey("MailFrom", 'email_from', $object->email_from, $object, (int) ($user->hasRight('mailing', 'creer') && $object->status < $object::STATUS_SENTCOMPLETELY), 'string');
1136 print '</td><td>';
1137 print $form->editfieldval("MailFrom", 'email_from', $object->email_from, $object, $user->hasRight('mailing', 'creer') && $object->status < $object::STATUS_SENTCOMPLETELY, 'string');
1138 if ($action != 'editemail_from') {
1139 $email = CMailFile::getValidAddress($object->email_from, 2);
1140 if ($email && !isValidEmail($email)) {
1141 $langs->load("errors");
1142 print img_warning($langs->transnoentitiesnoconv("ErrorBadEMail", $email));
1143 } elseif ($email && !isValidMailDomain($email)) {
1144 $langs->load("errors");
1145 print img_warning($langs->transnoentitiesnoconv("ErrorBadMXDomain", $email));
1146 }
1147 }
1148 print '</td></tr>';
1149
1150 // Errors to
1151 if ($object->messtype != 'sms') {
1152 print '<tr><td>';
1153 print $form->editfieldkey("MailErrorsTo", 'email_errorsto', $object->email_errorsto, $object, (int) ($user->hasRight('mailing', 'creer') && $object->status < $object::STATUS_SENTCOMPLETELY), 'string');
1154 print '</td><td>';
1155 print $form->editfieldval("MailErrorsTo", 'email_errorsto', $object->email_errorsto, $object, $user->hasRight('mailing', 'creer') && $object->status < $object::STATUS_SENTCOMPLETELY, 'string');
1156
1157 $emailarray = CMailFile::getArrayAddress($object->email_errorsto);
1158 foreach ($emailarray as $email => $name) {
1159 if ($name != $email) {
1160 if ($action != 'editemail_errorsto') {
1161 if ($email && !isValidEmail($email)) {
1162 $langs->load("errors");
1163 print img_warning($langs->transnoentitiesnoconv("ErrorBadEMail", $email));
1164 } elseif ($email && !isValidMailDomain($email)) {
1165 $langs->load("errors");
1166 print img_warning($langs->transnoentitiesnoconv("ErrorBadMXDomain", $email));
1167 }
1168 }
1169 } else {
1170 if ($object->email_errorsto) {
1171 print dol_print_email($object->email_errorsto, 0, 0, 0, 0, 1);
1172 }
1173 }
1174 }
1175 print '</td></tr>';
1176 }
1177
1178 // Reply to
1179 if ($object->messtype != 'sms') {
1180 print '<tr><td>';
1181 print $form->editfieldkey("MailReply", 'email_replyto', $object->email_replyto, $object, (int) ($user->hasRight('mailing', 'creer') && $object->status < $object::STATUS_SENTCOMPLETELY), 'string');
1182 print '</td><td>';
1183 print $form->editfieldval("MailReply", 'email_replyto', $object->email_replyto, $object, $user->hasRight('mailing', 'creer') && $object->status < $object::STATUS_SENTCOMPLETELY, 'string');
1184 $email = CMailFile::getValidAddress($object->email_replyto, 2);
1185 if ($action != 'editemail_replyto') {
1186 if ($email && !isValidEmail($email)) {
1187 $langs->load("errors");
1188 print img_warning($langs->trans("ErrorBadEMail", $email));
1189 } elseif ($email && !isValidMailDomain($email)) {
1190 $langs->load("errors");
1191 print img_warning($langs->trans("ErrorBadMXDomain", $email));
1192 }
1193 }
1194 print '</td></tr>';
1195 }
1196
1197 print '</table>';
1198 print '</div>';
1199
1200 print '<div class="fichehalfright">';
1201 print '<div class="underbanner clearboth"></div>';
1202
1203 print '<table class="border centpercent tableforfield">';
1204
1205 // Number of distinct emails
1206 print '<tr><td>';
1207 print $langs->trans("TotalNbOfDistinctRecipients");
1208 print '</td><td>';
1209 $nbemail = ($object->nbemail ? $object->nbemail : 0);
1210 if (is_numeric($nbemail)) {
1211 $htmltooltip = '';
1212 if ((getDolGlobalString('MAILING_LIMIT_SENDBYWEB') && getDolGlobalInt('MAILING_LIMIT_SENDBYWEB') < $nbemail) && ($object->status == 1 || ($object->status == 2 && $nbtry < $nbemail))) {
1213 if (getDolGlobalInt('MAILING_LIMIT_SENDBYWEB') > 0) {
1214 $htmltooltip .= $langs->trans('LimitSendingEmailing', getDolGlobalString('MAILING_LIMIT_SENDBYWEB'));
1215 } else {
1216 $htmltooltip .= $langs->trans('SendingFromWebInterfaceIsNotAllowed');
1217 }
1218 }
1219 if (empty($nbemail)) {
1220 $nbemail .= ' '.img_warning('').' <span class="warning">'.$langs->trans("NoTargetYet").'</span>';
1221 }
1222 if ($htmltooltip) {
1223 print $form->textwithpicto($nbemail, $htmltooltip, 1, 'info');
1224 } else {
1225 print $nbemail;
1226 }
1227 }
1228 print '</td></tr>';
1229
1230 print '<tr><td>';
1231 print $langs->trans("MAIN_MAIL_SENDMODE");
1232 print '</td><td>';
1233 if ($object->messtype != 'sms') {
1234 if (getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING') && getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING') != 'default') {
1235 $text = $listofmethods[getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING')];
1236 } elseif (getDolGlobalString('MAIN_MAIL_SENDMODE')) {
1237 $text = $listofmethods[getDolGlobalString('MAIN_MAIL_SENDMODE')];
1238 } else {
1239 $text = $listofmethods['mail'];
1240 }
1241 print $text;
1242 if (getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING') != 'default') {
1243 if (getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING') != 'mail') {
1244 print ' <span class="opacitymedium">('.getDolGlobalString('MAIN_MAIL_SMTP_SERVER_EMAILING', getDolGlobalString('MAIN_MAIL_SMTP_SERVER')).')</span>';
1245 }
1246 } elseif (getDolGlobalString('MAIN_MAIL_SENDMODE') != 'mail' && getDolGlobalString('MAIN_MAIL_SMTP_SERVER')) {
1247 print ' <span class="opacitymedium">('.getDolGlobalString('MAIN_MAIL_SMTP_SERVER').')</span>';
1248 }
1249 } else {
1250 print 'SMS ';
1251 print ' <span class="opacitymedium">('.getDolGlobalString('MAIN_MAIL_SMTP_SERVER').')</span>';
1252 }
1253 print '</td></tr>';
1254
1255 // Other attributes. Fields from hook formObjectOptions and Extrafields.
1256 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_view.tpl.php';
1257
1258 print '</table>';
1259 print '</div>';
1260 print '</div>';
1261
1262 print '<div class="clearboth"></div>';
1263
1264 print dol_get_fiche_end();
1265
1266
1267 // Clone confirmation
1268 if ($action == 'clone') {
1269 // Create an array for form
1270 $formquestion = array(
1271 'text' => $langs->trans("ConfirmClone"),
1272 0 => array('type' => 'checkbox', 'name' => 'clone_content', 'label' => $langs->trans("CloneContent"), 'value' => 1),
1273 1 => array('type' => 'checkbox', 'name' => 'clone_receivers', 'label' => $langs->trans("CloneReceivers"), 'value' => 0)
1274 );
1275 // Incomplete payment. On demande si motif = escompte ou autre
1276 print $form->formconfirm($_SERVER["PHP_SELF"].'?id='.$object->id, $langs->trans('ToClone'), $langs->trans('ConfirmCloneEMailing', $object->ref), 'confirm_clone', $formquestion, 'yes', 2, 0);
1277 }
1278
1279 // Actions Buttons
1280 if (GETPOST('cancel', 'alpha') || $confirm == 'no' || $action == '' || in_array($action, array('settodraft', 'valid', 'delete', 'sendall', 'clone', 'test', 'editevenunsubscribe'))) {
1281 print "\n\n<div class=\"tabsAction\">\n";
1282
1283 $reshook = $hookmanager->executeHooks('addMoreActionsButtons', $parameters, $object, $action);
1284
1285
1286 if (($object->status == 1) && ($user->hasRight('mailing', 'valider') || $object->user_validation_id == $user->id)) {
1287 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?action=settodraft&token='.newToken().'&id='.$object->id.'">'.$langs->trans("SetToDraft").'</a>';
1288 }
1289
1290 if (($object->status == 0 || $object->status == 1 || $object->status == 2) && $user->hasRight('mailing', 'creer')) {
1291 if (isModEnabled('fckeditor') && getDolGlobalInt('FCKEDITOR_ENABLE_MAILING') && $object->messtype != 'sms') {
1292 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?action=edit&token='.newToken().'&id='.$object->id.'">'.$langs->trans("Edit").'</a>';
1293 } else {
1294 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?action=edittxt&token='.newToken().'&id='.$object->id.'">'.$langs->trans("EditWithTextEditor").'</a>';
1295 }
1296
1297 if (!getDolGlobalInt('EMAILINGS_SUPPORT_ALSO_SMS')) {
1298 if (!empty($conf->use_javascript_ajax)) {
1299 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?action=edithtml&token='.newToken().'&id='.$object->id.'">'.$langs->trans("EditHTMLSource").'</a>';
1300 }
1301 }
1302 }
1303
1304 //print '<a class="butAction" href="card.php?action=test&amp;id='.$object->id.'">'.$langs->trans("PreviewMailing").'</a>';
1305
1306 if (getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !$user->hasRight('mailing', 'mailing_advance', 'send')) {
1307 print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NotEnoughPermissions")).'">'.$langs->trans("TestMailing").'</a>';
1308 } else {
1309 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?action=test&token='.newToken().'&id='.$object->id.'">'.$langs->trans("TestMailing").'</a>';
1310 }
1311
1312 if ($object->status == 0) {
1313 if ($object->nbemail <= 0) {
1314 print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NoTargetYet")).'">'.$langs->trans("Validate").'</a>';
1315 } elseif (!$user->hasRight('mailing', 'valider')) {
1316 print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NotEnoughPermissions")).'">'.$langs->trans("Validate").'</a>';
1317 } else {
1318 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?action=valid&amp;token='.newToken().'&amp;id='.$object->id.'">'.$langs->trans("Validate").'</a>';
1319 }
1320 }
1321
1322 if (($object->status == 1 || $object->status == 2) && $object->nbemail > 0 && $user->hasRight('mailing', 'valider')) {
1323 if (getDolGlobalInt('MAILING_LIMIT_SENDBYWEB') < 0) {
1324 print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("SendingFromWebInterfaceIsNotAllowed")).'">'.$langs->trans("SendMailing").'</a>';
1325 } elseif (getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !$user->hasRight('mailing', 'mailing_advance', 'send')) {
1326 print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NotEnoughPermissions")).'">'.$langs->trans("SendMailing").'</a>';
1327 } else {
1328 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?action=sendall&amp;token='.newToken().'&amp;id='.$object->id.'">'.$langs->trans("SendMailing").'</a>';
1329 }
1330 }
1331
1332 if ($user->hasRight('mailing', 'creer')) {
1333 print dolGetButtonAction($langs->trans("ToClone"), $langs->trans("ToClone"), 'clone', $_SERVER['PHP_SELF'].'?action=clone&token='.newToken().'&object=emailing&id='.$object->id, '', true, array('attr' => array('class' => 'reposition')));
1334 }
1335
1336 if (($object->status == 2 || $object->status == 3) && $user->hasRight('mailing', 'valider')) {
1337 if (getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !$user->hasRight('mailing', 'mailing_advance', 'send')) {
1338 print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NotEnoughPermissions")).'">'.$langs->trans("ResetMailing").'</a>';
1339 } else {
1340 print '<a class="butAction" href="'.$_SERVER['PHP_SELF'].'?action=reset&amp;token='.newToken().'&amp;id='.$object->id.'">'.$langs->trans("ResetMailing").'</a>';
1341 }
1342 }
1343
1344 if (($object->status <= 1 && $user->hasRight('mailing', 'creer')) || $user->hasRight('mailing', 'supprimer')) {
1345 if ($object->status > 0 && (getDolGlobalString('MAIN_USE_ADVANCED_PERMS') && !$user->hasRight('mailing', 'mailing_advance', 'delete'))) {
1346 print '<a class="butActionRefused classfortooltip" href="#" title="'.dol_escape_htmltag($langs->transnoentitiesnoconv("NotEnoughPermissions")).'">'.$langs->trans("Delete").'</a>';
1347 } else {
1348 print dolGetButtonAction($langs->trans("Delete"), $langs->trans("Delete"), 'delete', $_SERVER['PHP_SELF'].'?action=delete&token='.newToken().'&id='.$object->id.(!empty($urlfrom) ? '&urlfrom='.$urlfrom : ''), '', true, array('attr' => array('class' => 'reposition')))."\n";
1349 }
1350 }
1351
1352 print '</div>';
1353 }
1354
1355 // Display of the TEST form
1356 if ($action == 'test') {
1357 print '<div id="formmailbeforetitle" name="formmailbeforetitle"></div>';
1358 print load_fiche_titre($langs->trans("TestMailing"));
1359
1360 print dol_get_fiche_head([], '', '', -1);
1361
1362 // Create mail form object
1363 include_once DOL_DOCUMENT_ROOT.'/core/class/html.formmail.class.php';
1364 $formmail = new FormMail($db);
1365 $formmail->fromname = $object->email_from;
1366 $formmail->frommail = $object->email_from;
1367 $formmail->withsubstit = 0;
1368 $formmail->withfrom = 0;
1369 $formmail->withto = $user->email ? $user->email : 1;
1370 $formmail->withtocc = 0;
1371 $formmail->withtoccc = getDolGlobalString('MAIN_EMAIL_USECCC');
1372 $formmail->withtopic = 0;
1373 $formmail->withtopicreadonly = 1;
1374 $formmail->withfile = 0;
1375 $formmail->withlayout = '';
1376 $formmail->withaiprompt = '';
1377 $formmail->withbody = 0;
1378 $formmail->withbodyreadonly = 1;
1379 $formmail->withcancel = 1;
1380 $formmail->withdeliveryreceipt = 0;
1381 // Table of substitutions
1382 $formmail->substit = $object->substitutionarrayfortest;
1383 // Table of post's complementary params
1384 $formmail->param["action"] = "send";
1385 $formmail->param["models"] = 'none';
1386 $formmail->param["mailid"] = $object->id;
1387 $formmail->param["returnurl"] = $_SERVER['PHP_SELF']."?id=".$object->id;
1388
1389 print $formmail->get_form();
1390
1391 print '<br>';
1392
1393 print dol_get_fiche_end();
1394
1395 dol_set_focus('#sendto');
1396 }
1397
1398
1399 $htmltext = '<i>'.$langs->trans("FollowingConstantsWillBeSubstituted").':<br><br><span class="small">';
1400 foreach ($object->substitutionarray as $key => $val) {
1401 $htmltext .= $key.' = '.$langs->trans($val).'<br>';
1402 }
1403 $htmltext .= '</span></i>';
1404
1405 $availablelink = '<span class="opacitymedium hideonsmartphone">'.$form->textwithpicto($langs->trans("AvailableVariables"), $htmltext, 1, 'helpclickable', '', 0, 3, 'emailsubstitionhelp').'</span>';
1406
1407 // Print mail content
1408 print load_fiche_titre($langs->trans("EMail"), $availablelink, 'generic');
1409
1410 print dol_get_fiche_head([], '', '', -1);
1411
1412 print '<table class="bordernooddeven tableforfield centpercent">';
1413
1414 // Subject
1415 if ($object->messtype != 'sms') {
1416 print '<tr><td class="titlefield">'.$langs->trans("MailTopic").'</td><td colspan="3">'.$object->sujet.'</td></tr>';
1417 }
1418
1419 // Joined files
1420 if ($object->messtype != 'sms') {
1421 print '<tr><td>'.$langs->trans("MailFile").'</td><td colspan="3">';
1422 // List of files
1423 $listofpaths = dol_dir_list($upload_dir, 'all', 0, '', '', 'name', SORT_ASC, 0);
1424 if (count($listofpaths)) {
1425 foreach ($listofpaths as $key => $val) {
1426 print img_mime($listofpaths[$key]['name']).' '.$listofpaths[$key]['name'];
1427 print '<br>';
1428 }
1429 } else {
1430 print '<span class="opacitymedium">'.$langs->trans("NoAttachedFiles").'</span><br>';
1431 }
1432 print '</td></tr>';
1433 }
1434
1435 // Background color
1436 /* if (getDolGlobalString('EMAILING_CAN_EDIT_BACKGROUND_COLOR')) {
1437 print '<tr><td width="15%">'.$langs->trans("BackgroundColorByDefault").'</td><td colspan="3">';
1438 print $htmlother->selectColor($object->bgcolor,'bgcolor','',0);
1439 print '</td></tr>';
1440 }*/
1441
1442 print '</table>';
1443
1444 // Message
1445 print '<div class="previewemail" style="padding-top: 10px; background: '.($object->bgcolor ? (preg_match('/^#/', $object->bgcolor) ? '' : '#').$object->bgcolor : 'white').'">';
1446 if (empty($object->bgcolor) || strtolower($object->bgcolor) == 'ffffff') { // CKEditor does not apply the color of the div into its content area
1447 $readonly = 1;
1448 // wysiwyg editor
1449 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
1450 $doleditor = new DolEditor('bodyemail', $object->body, '', 600, 'dolibarr_mailings', '', false, $acceptlocallinktomedia, getDolGlobalInt('FCKEDITOR_ENABLE_MAILING'), 20, '100%', $readonly);
1451 $doleditor->Create();
1452 } else {
1453 print dol_htmlentitiesbr($object->body);
1454 }
1455 print '</div>';
1456
1457 print dol_get_fiche_end();
1458 } else {
1459 /*
1460 * Edition mode mailing (CKeditor or HTML source)
1461 */
1462
1463 print dol_get_fiche_head($head, 'card', $langs->trans("Mailing"), -1, $object->picto);
1464
1465 $linkback = '<a href="'.DOL_URL_ROOT.'/comm/mailing/list.php?restore_lastsearch_values=1">'.$langs->trans("BackToList").'</a>';
1466
1467 $morehtmlref = '<div class="refidno">';
1468 // Ref customer
1469 $morehtmlref .= $form->editfieldkey("", 'title', $object->title, $object, $user->hasRight('mailing', 'creer'), 'string', '', 0, 1);
1470 $morehtmlref .= $form->editfieldval("", 'title', $object->title, $object, $user->hasRight('mailing', 'creer'), 'string', '', null, null, '', 1);
1471
1472 $morehtmlstatus = '';
1473 $nbtry = $nbok = 0;
1474 if ($object->status == 2 || $object->status == 3) {
1475 $nbtry = $object->countNbOfTargets('alreadysent');
1476 $nbko = $object->countNbOfTargets('alreadysentko');
1477
1478 $morehtmlstatus .= ' ('.$nbtry.'/'.$object->nbemail;
1479 if ($nbko) {
1480 $morehtmlstatus .= ' - '.$nbko.' '.$langs->trans("Error");
1481 }
1482 $morehtmlstatus .= ') &nbsp; ';
1483 }
1484
1485 // Project
1486 if (isModEnabled('project')) {
1487 $langs->load("projects");
1488 $morehtmlref .= '<br>';
1489 if ($permissiontocreate) {
1490 $morehtmlref .= img_picto($langs->trans("Project"), 'project', 'class="pictofixedwidth"');
1491 $morehtmlref .= '<a class="editfielda" href="' . $_SERVER['PHP_SELF'] . '?action=classify&token=' . newToken() . '&id=' . $object->id . '">' . img_edit($langs->transnoentitiesnoconv('SetProject')) . '</a> ';
1492 $morehtmlref .= $form->form_project($_SERVER['PHP_SELF'] . '?id=' . $object->id, -1, (string) $object->fk_project, 'none', 0, 0, 0, 1, '', 'maxwidth300', '');
1493 } else {
1494 if (!empty($object->fk_project)) {
1495 $proj = new Project($db);
1496 $proj->fetch($object->fk_project);
1497 $morehtmlref .= $proj->getNomUrl(1, 'mailing');
1498 if ($proj->title) {
1499 $morehtmlref .= '<span class="opacitymedium"> - ' . dol_escape_htmltag($proj->title) . '</span>';
1500 }
1501 }
1502 }
1503 if (!getDolGlobalString('MAIN_DISABLE_OTHER_LINK')) {
1504 $proj = new Project($db);
1505 $proj->fetch($object->fk_project);
1506 $morehtmlref .= '<!-- Edit mode, so we open url in new window -->';
1507 $morehtmlref .= ' <small>(<a href="' . DOL_URL_ROOT . '/comm/mailing/list.php?projectid='.$object->fk_project.'" target="_blank">' .$langs->trans("Other").' '.$langs->trans("EMailings").' for '.$langs->trans("Project").': '. $proj->title. '</a>)</small>';
1508 }
1509 }
1510 $morehtmlref .= '</div>';
1511
1512 dol_banner_tab($object, 'id', $linkback, 1, 'rowid', 'ref', $morehtmlref, '', 0, '', $morehtmlstatus);
1513
1514 print '<div class="fichecenter">';
1515 print '<div class="fichehalfleft">';
1516 print '<div class="underbanner clearboth"></div>';
1517
1518 print '<table class="border centpercent tableforfield">';
1519
1520 /*
1521 print '<tr><td class="titlefield">'.$langs->trans("Ref").'</td>';
1522 print '<td colspan="3">';
1523 print $form->showrefnav($object,'id', $linkback);
1524 print '</td></tr>';
1525 */
1526
1527 // From
1528 print '<tr><td class="titlefield">';
1529 print $langs->trans("MailFrom");
1530 print '</td><td>'.dol_print_email($object->email_from, 0, 0, 0, 0, 1).'</td></tr>';
1531 // To
1532 if ($object->messtype != 'sms') {
1533 print '<tr><td>'.$langs->trans("MailErrorsTo").'</td><td>'.dol_print_email($object->email_errorsto, 0, 0, 0, 0, 1).'</td></tr>';
1534 print '<tr><td>'.$langs->trans("MailReply").'</td><td>'.dol_print_email($object->email_replyto, 0, 0, 0, 0, 1).'</td></tr>';
1535 }
1536
1537 print '</table>';
1538 print '</div>';
1539
1540
1541 print '<div class="fichehalfright">';
1542 print '<div class="underbanner clearboth"></div>';
1543
1544 print '<table class="border centpercent tableforfield">';
1545
1546 // Number of distinct emails
1547 print '<tr><td>';
1548 print $langs->trans("TotalNbOfDistinctRecipients");
1549 print '</td><td>';
1550 $nbemail = ($object->nbemail ? $object->nbemail : 0);
1551 if (is_numeric($nbemail)) {
1552 $htmltooltip = '';
1553 // MAILING_LIMIT_SENDBYWEB can be 'default'
1554 if ((getDolGlobalString('MAILING_LIMIT_SENDBYWEB') && getDolGlobalInt('MAILING_LIMIT_SENDBYWEB') < $nbemail) && ($object->status == 1 || $object->status == 2)) {
1555 if (getDolGlobalInt('MAILING_LIMIT_SENDBYWEB') > 0) {
1556 $htmltooltip .= $langs->trans('LimitSendingEmailing', getDolGlobalString('MAILING_LIMIT_SENDBYWEB'));
1557 } else {
1558 $htmltooltip .= $langs->trans('SendingFromWebInterfaceIsNotAllowed');
1559 }
1560 }
1561 if (empty($nbemail)) {
1562 $nbemail .= ' '.img_warning('').' <span class="warning">'.$langs->trans("NoTargetYet").'</span>';
1563 }
1564 if ($htmltooltip) {
1565 print $form->textwithpicto($nbemail, $htmltooltip, 1, 'warning');
1566 } else {
1567 print $nbemail;
1568 }
1569 }
1570 print '</td></tr>';
1571
1572 print '<tr><td>';
1573 print $langs->trans("MAIN_MAIL_SENDMODE");
1574 print '</td><td>';
1575 if ($object->messtype != 'sms') {
1576 if (getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING') && getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING') != 'default') {
1577 $text = $listofmethods[getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING')];
1578 } elseif (getDolGlobalString('MAIN_MAIL_SENDMODE')) {
1579 $text = $listofmethods[getDolGlobalString('MAIN_MAIL_SENDMODE')];
1580 } else {
1581 $text = $listofmethods['mail'];
1582 }
1583 print $text;
1584 if (getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING') != 'default') {
1585 if (getDolGlobalString('MAIN_MAIL_SENDMODE_EMAILING') != 'mail') {
1586 print ' <span class="opacitymedium">('.getDolGlobalString('MAIN_MAIL_SMTP_SERVER_EMAILING', getDolGlobalString('MAIN_MAIL_SMTP_SERVER')).')</span>';
1587 }
1588 } elseif (getDolGlobalString('MAIN_MAIL_SENDMODE') != 'mail' && getDolGlobalString('MAIN_MAIL_SMTP_SERVER')) {
1589 print ' <span class="opacitymedium">('.getDolGlobalString('MAIN_MAIL_SMTP_SERVER').')</span>';
1590 }
1591 } else {
1592 print 'SMS ';
1593 print ' <span class="opacitymedium">('.getDolGlobalString('MAIN_MAIL_SMTP_SERVER').')</span>';
1594 }
1595 print '</td></tr>';
1596
1597
1598 // Other attributes
1599 $parameters = array();
1600 $reshook = $hookmanager->executeHooks('formObjectOptions', $parameters, $object, $action); // Note that $action and $object may have been modified by hook
1601 print $hookmanager->resPrint;
1602 if (empty($reshook)) {
1603 print $object->showOptionals($extrafields, 'edit', $parameters);
1604 }
1605
1606 print '</table>';
1607 print '</div>';
1608 print '</div>';
1609
1610 print '<div class="clearboth"></div>';
1611
1612 print dol_get_fiche_end();
1613
1614
1615 print "<br><br>\n";
1616
1617 print '<form name="edit_mailing" action="card.php" method="post" enctype="multipart/form-data">'."\n";
1618 print '<input type="hidden" name="token" value="'.newToken().'">';
1619 print '<input type="hidden" name="action" value="update">';
1620 print '<input type="hidden" name="id" value="'.$object->id.'">';
1621 print '<input type="hidden" name="page_y" value="">';
1622
1623 $htmltext = '<i>'.$langs->trans("FollowingConstantsWillBeSubstituted").':<br><br><span class="small">';
1624 foreach ($object->substitutionarray as $key => $val) {
1625 $htmltext .= $key.' = '.$langs->trans($val).'<br>';
1626 }
1627 $htmltext .= '</span></i>';
1628
1629 $availablelink = '<span class="opacitymedium small">'.$form->textwithpicto($langs->trans("AvailableVariables"), $htmltext, 1, 'helpclickable', '', 0, 2, 'emailsubstitionhelp').'</span>';
1630
1631 // Print mail content
1632 print load_fiche_titre($langs->trans("EMail"), $availablelink, 'generic');
1633
1634 print dol_get_fiche_head([], '', '', -1);
1635
1636 print '<table class="bordernooddeven centpercent">';
1637
1638 // Subject
1639 if ($object->messtype != 'sms') {
1640 print '<tr><td class="fieldrequired titlefield">';
1641 print $form->textwithpicto($langs->trans("MailTopic"), $htmltext, 1, 'help', '', 0, 2, 'emailsubstitionhelp');
1642 print '</td><td colspan="3"><input class="flat quatrevingtpercent" type="text" id="subject" name="subject" value="'.$object->sujet.'" spellcheck="false"></td></tr>';
1643 }
1644
1645 $trackid = ''; // TODO To avoid conflicts with 2 mass emailing, we should set a trackid here, even if we use another one into email header.
1646 dol_init_file_process($upload_dir, $trackid);
1647
1648 // Joined files
1649 if ($object->messtype != 'sms') {
1650 $addfileaction = 'addfile';
1651 print '<tr><td>'.$langs->trans("MailFile").'</td>';
1652 print '<td colspan="3">';
1653 // List of files
1654 $listofpaths = dol_dir_list($upload_dir, 'all', 0, '', '', 'name', SORT_ASC, 0);
1655 $out = '';
1656
1657 // TODO Trick to have param removedfile containing nb of image to delete. But this does not works without javascript
1658 $out .= '<input type="hidden" class="removedfilehidden" name="removedfile" value="">'."\n";
1659 $out .= '<script type="text/javascript">';
1660 $out .= 'jQuery(document).ready(function () {';
1661 $out .= ' jQuery(".removedfile").click(function() {';
1662 $out .= ' jQuery(".removedfilehidden").val(jQuery(this).val());';
1663 $out .= ' });';
1664 $out .= '})';
1665 $out .= '</script>'."\n";
1666 if (count($listofpaths)) {
1667 foreach ($listofpaths as $key => $val) {
1668 $out .= '<div id="attachfile_'.$key.'">';
1669 $out .= img_mime($listofpaths[$key]['name']).' '.$listofpaths[$key]['name'];
1670 $out .= ' <input type="image" style="border: 0px;" src="'.img_picto($langs->trans("Search"), 'delete', '', 0, 1).'" value="'.($key + 1).'" class="removedfile" id="removedfile_'.$key.'" name="removedfile_'.$key.'" />';
1671 $out .= '<br></div>';
1672 }
1673 } else {
1674 //$out .= '<span class="opacitymedium">'.$langs->trans("NoAttachedFiles").'</span><br>';
1675 }
1676
1677 // Add link to add file
1678 $maxfilesizearray = getMaxFileSizeArray();
1679 $maxmin = $maxfilesizearray['maxmin'];
1680 if ($maxmin > 0) {
1681 $out .= '<input type="hidden" name="MAX_FILE_SIZE" value="'.($maxmin * 1024).'">'; // MAX_FILE_SIZE must precede the field type=file
1682 }
1683 $out .= '<input type="file" class="flat" id="addedfile" name="addedfile" value="'.$langs->trans("Upload").'" />';
1684 $out .= ' ';
1685 $out .= '<input type="submit" class="button smallpaddingimp" id="'.$addfileaction.'" name="'.$addfileaction.'" value="'.$langs->trans("MailingAddFile").'" />';
1686 print $out;
1687 print '</td></tr>';
1688
1689 // Background color
1690 print '<tr><td>'.$langs->trans("BackgroundColorByDefault").'</td><td colspan="3">';
1691 print $htmlother->selectColor($object->bgcolor, 'bgcolor', '', 0);
1692 print '</td></tr>';
1693 }
1694
1695
1696 // Add editor assistants
1697 $out = '';
1698 $out .= '<tr>';
1699 $out .= '<td class="tdtop">';
1700 $out .= $form->textwithpicto($langs->trans('MailText'), $htmltext, 1, 'help', '', 0, 2, 'substittooltipfrombody');
1701 $out .= '</td>';
1702 $out .= '<td class="tdtop">';
1703
1704 //$formmail = $this;
1705 $showlinktolayout = getDolGlobalInt('MAIN_EMAIL_USE_LAYOUT') ? 'emailing' : '';
1706 $showlinktolayoutlabel = $langs->trans("FillMessageWithALayout");
1707 $showlinktoai = isModEnabled('ai') ? 'textgenerationemail' : '';
1708 $showlinktoailabel = $langs->trans("AIEnhancements");
1709 $formatforouput = '';
1710 $htmlname = 'bodyemail';
1711 //$formai->substit = $this->substit;
1712 //$formai->substit_lines = $this->substit_lines;
1713
1714 // Fill $out
1715 include DOL_DOCUMENT_ROOT.'/core/tpl/formlayoutai.tpl.php';
1716
1717 $out .= '</td>';
1718 $out .= '</tr>';
1719
1720 print $out;
1721
1722 print '</table>';
1723
1724
1725 // Message
1726 print '<div style="padding-top: 10px">';
1727
1728 if ($action == 'edit') {
1729 // wysiwyg editor
1730 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
1731 if ($object->bgcolor) {
1732 if (!preg_match('/^<div style="background-color: #'.$object->bgcolor.'">/', $object->body)) {
1733 $object->body = '<div style="background-color: #'.$object->bgcolor.'; margin-bottom:-20px; margin-left:-10px; margin-right:-10px; margin-top:-10px; padding: 10px;">'.$object->body.'</div>';
1734 }
1735 }
1736 $doleditor = new DolEditor('bodyemail', $object->body, '', 600, 'dolibarr_mailings', '', true, $acceptlocallinktomedia, getDolGlobalInt('FCKEDITOR_ENABLE_MAILING'), 20, '100%');
1737 $doleditor->Create();
1738 }
1739 if ($action == 'edittxt') {
1740 // wysiwyg editor
1741 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
1742 $doleditor = new DolEditor('bodyemail', $object->body, '', 600, 'dolibarr_mailings', '', true, $acceptlocallinktomedia, 0, 20, '100%');
1743 $doleditor->Create();
1744 }
1745 if ($action == 'edithtml') {
1746 // HTML source editor
1747 require_once DOL_DOCUMENT_ROOT.'/core/class/doleditor.class.php';
1748 $doleditor = new DolEditor('bodyemail', $object->body, '', 600, 'dolibarr_mailings', '', true, $acceptlocallinktomedia, 'ace', 20, '100%');
1749 $doleditor->Create(0, '', false, 'HTML Source', 'php');
1750 }
1751
1752 print '</div>';
1753
1754 print dol_get_fiche_end();
1755
1756 print '<div class="center">';
1757 print '<input type="submit" class="button buttonforacesave button-save" value="'.$langs->trans("Save").'" name="save">';
1758 print '&nbsp; &nbsp; &nbsp;';
1759 print '<input type="submit" class="button button-cancel" value="'.$langs->trans("Cancel").'" name="cancel">';
1760 print '</div>';
1761
1762 print '</form>';
1763 print '<br>';
1764 }
1765 } else {
1766 dol_print_error($db, $object->error);
1767 }
1768}
1769
1770// End of page
1771llxFooter();
1772$db->close();
$id
Support class for third parties, contacts, members, users or resources.
Definition account.php:47
if(! $sortfield) if(! $sortorder) $object
Definition account.php:100
llxFooter($comment='', $zone='private', $disabledoutputofmessages=0)
Empty footer.
Definition wrapper.php:91
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:73
Class to send emails (with attachments or not) Usage: $mailfile = new CMailFile($subject,...
static getValidAddress($address, $format, $encode=0, $maxnumberofemail=0)
Return a formatted address string for SMTP protocol.
static getArrayAddress($address)
Return a formatted array of address string for SMTP protocol.
Class to manage a WYSIWYG editor.
Class to manage generation of HTML components Only common components must be here.
Class to manage a HTML form to send a unitary email Usage: $formail = new FormMail($db) $formmail->pr...
static getAvailableSubstitKey($mode='formemail', $object=null)
Get list of substitution keys available for emails.
Class to help generate other html components Only common components are here.
Class to manage building of HTML components.
Class to manage emailings module.
Class to manage projects.
Class to manage third parties objects (customers, suppliers, prospects...)
emailing_prepare_head(Mailing $object)
Prepare array with list of tabs.
if(!isModEnabled('ai')||!getDolGlobalString('AI_ASSISTANT_ENABLED')) global $conf
The main.inc.php has been included so the following variable are now defined:
dol_add_file_process($upload_dir, $allowoverwrite=0, $updatesessionordb=0, $keyforsourcefile='addedfile', $savingdocmask='', $link=null, $trackid='', $generatethumbs=1, $object=null, $forceFullTextIndexation='', $mode=0)
Get and save an upload file (for example after submitting a new file in a mail form).
dol_init_file_process($pathtoscan='', $trackid='')
Scan a directory and init $_SESSION to manage uploaded files with list of all found files.
dol_remove_file_process($filenb, $donotupdatesession=0, $donotdeletefile=1, $trackid='')
Remove an uploaded file (for example after submitting a new file a mail form).
dol_dir_list($utf8_path, $types="all", $recursive=0, $filter="", $excludefilter=null, $sortcriteria="name", $sortorder=SORT_ASC, $mode=0, $nohook=0, $relativename="", $donotfollowsymlinks=0, $nbsecondsold=0)
Scan a directory and return a list of files/directories.
Definition files.lib.php:65
acceptLocalLinktoMedia()
Check the syntax of some PHP code.
isValidMailDomain($mail)
Return true if email has a domain name that can be resolved to MX type.
dol_now($mode='gmt')
Return date for now.
dol_print_email($email, $contactid=0, $socid=0, $addlink=0, $max=0, $showinvalid=2, $withpicto=0, $morecss='paddingrightonly')
Show EMail link formatted for HTML output.
dol_mimetype($file, $default='application/octet-stream', $mode=0)
Return MIME type of a file from its name with extension.
getDolGlobalInt($key, $default=0)
Return a Dolibarr global constant int value.
newToken()
Return the value of token currently saved into session with name 'newtoken'.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0, $nodefault=0)
Return value of a param into GET or POST supervariable.
dolGetFirstLastname($firstname, $lastname, $nameorder=-1)
Return firstname and lastname in correct order.
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...
GETPOSTINT($paramname, $method=0, $nodefault=0)
Return the value of a $_GET or $_POST supervariable, converted into integer.
dol_clone($srcobject, $native=2)
Create a clone of instance of object (new instance with same value for each properties) With native =...
dol_print_date($time, $format='', $tzoutput='auto', $outputlangs=null, $encodetooutput=false, $decorate=0)
Output date in a string format according to outputlangs (or langs if not defined).
dol_trunc($string, $size=40, $trunc='right', $stringencoding='UTF-8', $nodot=0, $display=0)
Truncate a string to a particular length adding '...' if string larger than length.
GETPOSTISSET($paramname)
Return true if we are in a context of submitting the parameter $paramname from a POST of a form.
dol_htmlentitiesbr($stringtoencode, $nl2brmode=0, $pagecodefrom='UTF-8', $removelasteolbr=1)
This function is called to encode a string into a HTML string but differs from htmlentities because a...
isValidEmail($address, $acceptsupervisorkey=0, $acceptuserkey=0)
Return true if email syntax is ok.
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
isModEnabled($module)
Is Dolibarr module enabled.
get_exdir($num, $level, $alpha, $withoutslash, $object, $modulepart='')
Return a path to have a the directory according to object where files are stored.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
dol_get_fiche_head($links=array(), $active='', $title='', $notab=0, $picto='', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limittoshow=0, $moretabssuffix='', $dragdropfile=0, $morecssdiv='')
Show tabs of a record.
Definition html.lib.php:540
dol_get_fiche_end($notab=0)
Return tab footer of a card.
Definition html.lib.php:738
img_mime($file, $titlealt='', $morecss='')
Show MIME img of a file.
dol_set_focus($selector)
Set focus onto field with selector (similar behaviour of 'autofocus' HTML5 tag)
load_fiche_titre($title, $morehtmlright='', $picto='generic', $pictoisfullpath=0, $id='', $morecssontable='', $morehtmlcenter='', $morecssonpicto='widthpictotitle')
Load a title with picto.
dol_escape_htmltag($stringtoescape, $keepb=0, $keepn=0, $noescapetags='', $escapeonlyhtmltags=0, $cleanalsojavascript=0)
Definition html.lib.php:181
getMaxFileSizeArray()
Return the max allowed for file upload.
accessforbidden($message='', $printheader=1, $printfooter=1, $showonlymessage=0, $params=null)
Show a message to say access is forbidden and stop program.
dol_hash($chain, $type='0', $nosalt=0, $mode=0)
Returns a hash (non reversible encryption) of a string.