dolibarr 22.0.5
view.php
Go to the documentation of this file.
1<?php
2/* Copyright (C) 2020 Laurent Destailleur <eldy@users.sourceforge.net>
3 * Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
4 * Copyright (C) 2024-2025 MDW <mdeweerd@users.noreply.github.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 3 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <https://www.gnu.org/licenses/>.
18 */
19
26if (!defined('NOLOGIN')) {
27 define("NOLOGIN", 1); // This means this output page does not require to be logged.
28}
29if (!defined('NOCSRFCHECK')) {
30 define("NOCSRFCHECK", 1); // We accept to go on this page from external web site.
31}
32if (!defined('NOIPCHECK')) {
33 define('NOIPCHECK', '1'); // Do not check IP defined into conf $dolibarr_main_restrict_ip
34}
35if (!defined('NOBROWSERNOTIF')) {
36 define('NOBROWSERNOTIF', '1');
37}
38
39// Load Dolibarr environment
40require '../../main.inc.php';
41require_once DOL_DOCUMENT_ROOT.'/recruitment/class/recruitmentjobposition.class.php';
42require_once DOL_DOCUMENT_ROOT.'/recruitment/class/recruitmentcandidature.class.php';
43require_once DOL_DOCUMENT_ROOT.'/core/class/CMailFile.class.php';
44require_once DOL_DOCUMENT_ROOT.'/core/lib/security.lib.php';
45require_once DOL_DOCUMENT_ROOT.'/core/lib/company.lib.php';
46require_once DOL_DOCUMENT_ROOT.'/core/lib/payments.lib.php';
47require_once DOL_DOCUMENT_ROOT . '/core/lib/public.lib.php';
48require_once DOL_DOCUMENT_ROOT.'/core/class/extrafields.class.php';
49
58// Load translation files required by the page
59$langs->loadLangs(array("companies", "other", "recruitment"));
60
61// Get parameters
62$action = GETPOST('action', 'aZ09');
63$cancel = GETPOST('cancel', 'alpha');
64$email = GETPOST('email', 'alpha');
65$firstname = GETPOST('firstname', 'alpha');
66$lastname = GETPOST('lastname', 'alpha');
67$birthday = GETPOST('birthday', 'alpha');
68$phone = GETPOST('phone', 'alpha');
69$message = GETPOST('message', 'alpha');
70$requestedremuneration = GETPOST('requestedremuneration', 'alpha');
71
72$ref = GETPOST('ref', 'alpha');
73
74if (GETPOST('btn_view')) {
75 unset($_SESSION['email_customer']);
76}
77if (isset($_SESSION['email_customer'])) {
78 $email = $_SESSION['email_customer'];
79}
80
82
83if (!$ref) {
84 print $langs->trans('ErrorBadParameters')." - ref missing";
85 exit;
86}
87
88
89// Define $urlwithroot
90//$urlwithouturlroot=preg_replace('/'.preg_quote(DOL_URL_ROOT,'/').'$/i','',trim($dolibarr_main_url_root));
91//$urlwithroot=$urlwithouturlroot.DOL_URL_ROOT; // This is to use external domain name found into config file
92$urlwithroot = DOL_MAIN_URL_ROOT; // This is to use same domain name than current. For Paypal payment, we can use internal URL like localhost.
93$backtopage = $urlwithroot.'/public/recruitment/index.php';
94
95// Security check
96if (!isModEnabled("recruitment")) {
97 httponly_accessforbidden('Module Recruitment not enabled');
98}
99
100// Done before the actions, so no application can be recorded when the public interface is disabled
101if (!getDolGlobalInt('RECRUITMENT_ENABLE_PUBLIC_INTERFACE')) {
102 $langs->load("errors");
103 print '<div class="error">'.$langs->trans('ErrorPublicInterfaceNotEnabled').'</div>';
104 $db->close();
105 exit();
106}
107
108$object->fetch(0, $ref);
109// A draft job position is not published, it must not be shown nor receive applications
110if ($object->id <= 0 || $object->status == RecruitmentJobPosition::STATUS_DRAFT) {
111 $langs->load("errors");
112 httponly_accessforbidden($langs->trans('ErrorRecordNotFound'), 404);
113}
114$user->loadDefaultValues();
115$errmsg = "";
116
117$extrafields = new ExtraFields($db);
118
119/*
120 * Actions
121 */
122
123if ($cancel) {
124 if (!empty($backtopage)) {
125 header("Location: ".$backtopage);
126 exit;
127 }
128}
129
130if ($action == "dosubmit") { // Test on permission not required here (anonymous action protected by mitigation of /public/... urls)
131 $error = 0;
132 $db->begin();
133 if (!strlen($ref)) {
134 $error++;
135 array_push($object->errors, $langs->trans("ErrorFieldRequired", $langs->transnoentities("Ref")));
136 $action = 'view';
137 }
138 // Only a job position still open can receive an application
140 $error++;
141 array_push($object->errors, $langs->trans($object->status == RecruitmentJobPosition::STATUS_RECRUITED ? "JobClosedTextCandidateFound" : "JobClosedTextCanceled"));
142 $action = 'view';
143 }
144 if (!strlen($email)) {
145 $error++;
146 array_push($object->errors, $langs->trans("ErrorFieldRequired", $langs->transnoentities("Email")));
147 $action = 'view';
148 } else {
149 if (!isValidEmail($email)) {
150 $error++;
151 array_push($object->errors, $langs->trans("ErrorEmailInvalid"));
152 $action = 'view';
153 }
154 }
155 if (!strlen($lastname)) {
156 $error++;
157 array_push($object->errors, $langs->trans("ErrorFieldRequired", $langs->transnoentities("Lastname")));
158 $action = 'view';
159 }
160
161 if (!$error) {
162 $sql = "SELECT rrc.rowid FROM ".MAIN_DB_PREFIX."recruitment_recruitmentcandidature as rrc";
163 $sql .= " WHERE rrc.email = '". $db->escape($email)."'";
164 $sql .= " AND rrc.entity IN (". getEntity($object->element, 0).")";
165 $resql = $db->query($sql);
166 if ($resql) {
167 $num = $db->num_rows($resql);
168 if ($num > 0) {
169 $error++;
170 setEventMessages($langs->trans("ErrorRecruitmmentCandidatureAlreadyExists", $email), null, 'errors');
171 }
172 } else {
173 dol_print_error($db);
174 $error++;
175 }
176 }
177
178 if (!$error) { // Test on permission not required here (anonymous action protected by mitigation of /public/... urls)
179 $candidature = new RecruitmentCandidature($db);
180
181 $candidature->firstname = GETPOST('firstname', 'alpha');
182 $candidature->lastname = GETPOST('lastname', 'alpha');
183 $candidature->email = GETPOST('email', 'alpha');
184 $candidature->phone = GETPOST('phone', 'alpha');
185 $candidature->date_birth = GETPOST('birthday', 'alpha');
186 $candidature->requestedremuneration = GETPOST('requestedremuneration', 'alpha');
187 $candidature->description = GETPOST('message', 'alpha');
188 $candidature->fk_recruitmentjobposition = $object->id;
189
190 $candidature->ip = getUserRemoteIP();
191
192 // Test MAIN_SECURITY_MAX_POST_ON_PUBLIC_PAGES_BY_IP_ADDRESS
193 $nb_post_max = getDolGlobalInt("MAIN_SECURITY_MAX_POST_ON_PUBLIC_PAGES_BY_IP_ADDRESS", 200);
194
195 if (checkNbPostsForASpeceificIp($candidature, $nb_post_max) <= 0) {
196 $error++;
197 $errmsg .= implode('<br>', $candidature->errors);
198 }
199
200 // Fill array 'array_options' with data from add form
201 $extrafields->fetch_name_optionals_label($candidature->table_element);
202 $ret = $extrafields->setOptionalsFromPost(null, $candidature);
203 if ($ret < 0) {
204 $error++;
205 $errmsg .= $candidature->error;
206 }
207
208 if (!$error) {
209 $result = $candidature->create($user);
210 if ($result <= 0) {
211 $error++;
212 $errmsg .= implode('<br>', $candidature->errors);
213 }
214 }
215 if (!$error) {
216 $candidature->validate($user);
217 if ($result <= 0) {
218 $error++;
219 $errmsg .= implode('<br>', $candidature->errors);
220 }
221 }
222 }
223
224 if (!$error) {
225 $db->commit();
226 setEventMessages($langs->trans("RecruitmentCandidatureSaved"), null);
227 header("Location: " . $backtopage);
228 exit;
229 } else {
230 $db->rollback();
231 $action = "view";
232 }
233}
234
235// Actions to send emails (for ticket, we need to manage the addfile and removefile only)
236$triggersendname = 'CANDIDATURE_SENTBYMAIL';
237$paramname = 'id';
238$autocopy = 'MAIN_MAIL_AUTOCOPY_CANDIDATURE_TO'; // used to know the automatic BCC to add
239$trackid = 'recruitmentcandidature'.$object->id;
240include DOL_DOCUMENT_ROOT.'/core/actions_sendmails.inc.php';
241
242
243
244/*
245 * View
246 */
247
248$form = new Form($db);
249$now = dol_now();
250
251$head = '';
252if (getDolGlobalString('MAIN_RECRUITMENT_CSS_URL')) {
253 $head = '<link rel="stylesheet" type="text/css" href="' . getDolGlobalString('MAIN_RECRUITMENT_CSS_URL').'?lang='.$langs->defaultlang.'">'."\n";
254}
255
256$conf->dol_hide_topmenu = 1;
257$conf->dol_hide_leftmenu = 1;
258
259$arrayofjs = array();
260$arrayofcss = array();
261
262$replacemainarea = (empty($conf->dol_hide_leftmenu) ? '<div>' : '').'<div>';
263llxHeader($head, $langs->trans("PositionToBeFilled"), '', '', 0, 0, '', '', '', 'onlinepaymentbody', $replacemainarea, 1, 1);
264dol_htmloutput_errors($errmsg);
265
266print '<span id="dolpaymentspan"></span>'."\n";
267print '<div class="center">'."\n";
268print '<form id="dolpaymentform" class="center" name="paymentform" action="'.$_SERVER["PHP_SELF"].'" method="POST">'."\n";
269print '<input type="hidden" name="token" value="'.newToken().'">'."\n";
270print '<input type="hidden" name="action" value="dosubmit">'."\n";
271print '<input type="hidden" name="tag" value="'.GETPOST("tag", 'alpha').'">'."\n";
272print '<input type="hidden" name="suffix" value="'.GETPOST("suffix", 'alpha').'">'."\n";
273print '<input type="hidden" name="securekey" value="'.$SECUREKEY.'">'."\n";
274print '<input type="hidden" name="entity" value="'.$entity.'" />';
275print "\n";
276print '<!-- Form to view job -->'."\n";
277
278// Show logo (search order: logo defined by ONLINE_SIGN_LOGO_suffix, then ONLINE_SIGN_LOGO_, then small company logo, large company logo, theme logo, common logo)
279// Define logo and logosmall
280$logosmall = $mysoc->logo_small;
281$logo = $mysoc->logo;
282$paramlogo = 'ONLINE_RECRUITMENT_LOGO_'.$suffix;
283if (getDolGlobalString($paramlogo)) {
284 $logosmall = getDolGlobalString($paramlogo);
285} elseif (getDolGlobalString('ONLINE_RECRUITMENT_LOGO')) {
286 $logosmall = getDolGlobalString('ONLINE_RECRUITMENT_LOGO');
287}
288//print '<!-- Show logo (logosmall='.$logosmall.' logo='.$logo.') -->'."\n";
289// Define urllogo
290$urllogo = '';
291$urllogofull = '';
292if (!empty($logosmall) && is_readable($conf->mycompany->dir_output.'/logos/thumbs/'.$logosmall)) {
293 $urllogo = DOL_URL_ROOT.'/viewimage.php?modulepart=mycompany&amp;entity='.$conf->entity.'&amp;file='.urlencode('logos/thumbs/'.$logosmall);
294 $urllogofull = $dolibarr_main_url_root.'/viewimage.php?modulepart=mycompany&entity='.$conf->entity.'&file='.urlencode('logos/thumbs/'.$logosmall);
295} elseif (!empty($logo) && is_readable($conf->mycompany->dir_output.'/logos/'.$logo)) {
296 $urllogo = DOL_URL_ROOT.'/viewimage.php?modulepart=mycompany&amp;entity='.$conf->entity.'&amp;file='.urlencode('logos/'.$logo);
297 $urllogofull = $dolibarr_main_url_root.'/viewimage.php?modulepart=mycompany&entity='.$conf->entity.'&file='.urlencode('logos/'.$logo);
298}
299// Output html code for logo
300if ($urllogo) {
301 print '<div class="backgreypublicpayment">';
302 print '<div class="logopublicpayment">';
303 if (!empty($mysoc->url)) {
304 print '<a href="'.$mysoc->url.'" target="_blank" rel="noopener">';
305 }
306 print '<img id="dolpaymentlogo" src="'.$urllogofull.'">';
307 if (!empty($mysoc->url)) {
308 print '</a>';
309 }
310 print '</div>';
311 if (!getDolGlobalString('MAIN_HIDE_POWERED_BY')) {
312 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>';
313 }
314 print '</div>';
315}
316
317if (getDolGlobalString('RECRUITMENT_IMAGE_PUBLIC_INTERFACE')) {
318 print '<div class="backimagepublicrecruitment">';
319 print '<img id="idRECRUITMENT_IMAGE_PUBLIC_INTERFACE" src="' . getDolGlobalString('RECRUITMENT_IMAGE_PUBLIC_INTERFACE').'">';
320 print '</div>';
321}
322
323
324print '<table id="dolpaymenttable" summary="Job position offer" class="center">'."\n";
325
326// Output introduction text
327$text = '';
328if (getDolGlobalString('RECRUITMENT_NEWFORM_TEXT')) {
329 $reg = array();
330 if (preg_match('/^\‍((.*)\‍)$/', $conf->global->RECRUITMENT_NEWFORM_TEXT, $reg)) {
331 $text .= $langs->trans($reg[1])."<br>\n";
332 } else {
333 $text .= getDolGlobalString('RECRUITMENT_NEWFORM_TEXT') . "<br>\n";
334 }
335 $text = '<tr><td align="center"><br>'.$text.'<br></td></tr>'."\n";
336}
337if (empty($text)) {
338 $text .= '<tr><td class="textpublicpayment" colspan=2><br>'.$langs->trans("JobOfferToBeFilled", $mysoc->name);
339 $text .= ' &nbsp; - &nbsp; <strong>'.$mysoc->name.'</strong>';
340 $text .= ' &nbsp; - &nbsp; <span class="nowraponall"><span class="fa fa-calendar secondary"></span> '.dol_print_date($object->date_creation).'</span>';
341 $text .= '</td></tr>'."\n";
342 $text .= '<tr><td class="textpublicpayment" colspan=2><h1 class="paddingleft paddingright">'.$object->label.'</h1><br></td></tr>'."\n";
343}
344print $text;
345
346// Output payment summary form
347print '<tr><td class="left" colspan=2>';
348
349print '<div with="100%" id="tablepublicpayment">';
350print '<div class="opacitymedium">'.$langs->trans("ThisIsInformationOnJobPosition").' :</div>'."\n";
351
352$error = 0;
353$found = true;
354
355print '<br>';
356
357// Label
358print $langs->trans("Label").' : ';
359print '<b>'.dol_escape_htmltag($object->label).'</b><br>';
360
361// Date
362print $langs->trans("DateExpected").' : ';
363print '<b>';
364if ($object->date_planned > $now) {
365 print dol_print_date($object->date_planned, 'day');
366} else {
367 print $langs->trans("ASAP");
368}
369print '</b><br>';
370
371// Remuneration
372print $langs->trans("Remuneration").' : ';
373print '<b>';
374print dol_escape_htmltag($object->remuneration_suggested);
375print '</b><br>';
376
377// Contact
378$tmpuser = new User($db);
379$tmpuser->fetch($object->fk_user_recruiter);
380
381print $langs->trans("ContactForRecruitment").' : ';
382$emailforcontact = $object->email_recruiter;
383if (empty($emailforcontact)) {
384 $emailforcontact = $tmpuser->email ?? '';
385 if (empty($emailforcontact)) {
386 $emailforcontact = $mysoc->email ?? '';
387 }
388}
389print '<b class="wordbreak">';
390print $tmpuser->getFullName($langs);
391print ' &nbsp; '.dol_print_email($emailforcontact, 0, 0, 1, 0, 0, 'envelope');
392print '</b>';
393print '</b><br>';
394
396 print info_admin($langs->trans("JobClosedTextCandidateFound"), 0, 0, '0', 'warning');
397}
399 print info_admin($langs->trans("JobClosedTextCanceled"), 0, 0, '0', 'warning');
400}
401
402print '<br>';
403
404// Description
405
406$text = $object->description;
407print $text;
408print '<input type="hidden" name="ref" value="'.$object->ref.'">';
409
410print '</div>'."\n";
411print "\n";
412
413
414if ($action != 'dosubmit') {
415 if ($found && !$error) {
416 // We are in a management option and no error
417 print '</td></tr>'."\n";
418 print '<tr><td class="titlefieldcreate fieldrequired left">'.$langs->trans("Lastname").'</td><td class="left">';
419 print '<input type="text" class="flat minwidth400 --success" name="lastname" maxlength="128" value="'.$lastname.'">';
420 print '</td></tr>'."\n";
421
422 print '<tr><td class="titlefieldcreate left">'.$langs->trans("Firstname").'</td><td class="left">';
423 print '<input type="text" class="flat minwidth400 --success" name="firstname" maxlength="128" value="'.$firstname.'">';
424 print '</td></tr>'."\n";
425
426 print '<tr><td class="titlefieldcreate fieldrequired left">'.$langs->trans("Email").'</td><td class="left">';
427 print img_picto("", "email").'<input type="text" class="flat minwidth100 --success" name="email" value="'.$email.'">';
428 print '</td></tr>'."\n";
429
430 print '<tr><td class="titlefieldcreate left">'.$langs->trans("Phone").'</td><td class="left">';
431 print img_picto("", "phone").'<input type="text" class="flat minwidth100 --success" name="phone" value="'.$phone.'">';
432 print '</td></tr>'."\n";
433
434 print '<tr><td class="titlefieldcreate left minwidth300">'.$langs->trans("DateOfBirth").'</td><td class="left">';
435 print $form->selectDate($birthday, 'birthday', 0, 0, 1, "", 1, 0);
436 print '</td></tr>'."\n";
437
438 print '<tr><td class="titlefieldcreate left">'.$langs->trans("RequestedRemuneration").'</td><td class="left">';
439 print '<input type="text" class="flat minwidth100 --success" name="requestedremuneration" value="'.$requestedremuneration.'">';
440 print '</td></tr>'."\n";
441
442 // Other attributes
444 $parameters['tpl_context'] = 'public'; // define template context to public
445 $parameters['tdclass'] = 'left';
446 $extrafields->fetch_name_optionals_label("recruitment_recruitmentcandidature");
447 include DOL_DOCUMENT_ROOT.'/core/tpl/extrafields_add.tpl.php';
448
449 print '<tr><td class="titlefieldcreate left">'.$langs->trans("Message").'</td><td class="left">';
450 print '<textarea class="flat quatrevingtpercent" rows="'.ROWS_5.'" name="message">'.$message.'</textarea>';
451 print '</td></tr>'."\n";
452
453 print '<tr><td colspan=2>';
454 print $form->buttonsSaveCancel('Submit', 'Cancel');
455 print '</td></tr>'."\n";
456 } else {
457 dol_print_error_email('ERRORSUBMITAPPLICATION');
458 }
459} else {
460 // Print
461}
462
463print '</td></tr>'."\n";
464
465print '</table>'."\n";
466
467print '</form>'."\n";
468print '</div>'."\n";
469print '<br>';
470
471
472htmlPrintOnlineFooter($mysoc, $langs);
473
474llxFooter('', 'public');
475
476$db->close();
if( $user->socid > 0) if(! $user->hasRight('accounting', 'chartofaccount')) $object
Definition card.php:67
global $dolibarr_main_url_root
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 manage standard extra fields.
Class to manage generation of HTML components Only common components must be here.
Class for RecruitmentCandidature.
Class for RecruitmentJobPosition.
Class to manage Dolibarr users.
htmlPrintOnlineFooter($fromcompany, $langs, $addformmessage=0, $suffix='', $object=null)
Show footer of company in HTML public pages.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0, $attop=0)
Set event messages in dol_events session object.
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_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).
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
dol_print_error_email($prefixcode, $errormessage='', $errormessages=array(), $morecss='error', $email='')
Show a public email and error code to contact if technical error.
getUserRemoteIP($trusted=0)
Return the real IP of remote user.
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
isValidEmail($address, $acceptsupervisorkey=0, $acceptuserkey=0)
Return true if email syntax is ok.
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
info_admin($text, $infoonimgalt=0, $nodiv=0, $admin='1', $morecss='hideonsmartphone', $textfordropdown='', $picto='')
Show information in HTML for admin users or standard users.
dol_htmloutput_errors($mesgstring='', $mesgarray=array(), $keepembedded=0)
Print formatted error messages to output (Used to show messages on html output).
getEntity($element, $shared=1, $currentobject=null)
Get list of entity id to use.
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
checkNbPostsForASpeceificIp($object, $nb_post_max)
Check if the object exceeded the number of posts for a specific ip in the same week.
httponly_accessforbidden($message='1', $http_response_code=403, $stringalreadysanitized=0)
Show a message to say access is forbidden and stop program.