1<?php
2// +-----------------------------------------------------------------------+
3// | This file is part of Piwigo.                                          |
4// |                                                                       |
5// | For copyright and license information, please view the COPYING.txt    |
6// | file that was distributed with this source code.                      |
7// +-----------------------------------------------------------------------+
8
9/* nbm_global_var */
10$env_nbm = array
11          (
12            'start_time' => get_moment(),
13            'sendmail_timeout' => (intval(ini_get('max_execution_time')) * $conf['nbm_max_treatment_timeout_percent']),
14            'is_sendmail_timeout' => false
15          );
16
17if
18  (
19    (!isset($env_nbm['sendmail_timeout'])) or
20    (!is_numeric($env_nbm['sendmail_timeout'])) or
21    ($env_nbm['sendmail_timeout'] <= 0)
22  )
23{
24  $env_nbm['sendmail_timeout'] = $conf['nbm_treatment_timeout_default'];
25}
26
27/*
28 * Search an available check_key
29 *
30 * It's a copy of function find_available_feed_id
31 *
32 * @return string nbm identifier
33 */
34function find_available_check_key()
35{
36  while (true)
37  {
38    $key = generate_key(16);
39    $query = '
40select
41  count(*)
42from
43  '.USER_MAIL_NOTIFICATION_TABLE.'
44where
45  check_key = \''.$key.'\';';
46
47    list($count) = pwg_db_fetch_row(pwg_query($query));
48    if ($count == 0)
49    {
50      return $key;
51    }
52  }
53}
54
55/*
56 * Check sendmail timeout state
57 *
58 * @return true, if it's timeout
59 */
60function check_sendmail_timeout()
61{
62  global $env_nbm;
63
64  $env_nbm['is_sendmail_timeout'] = ((get_moment() - $env_nbm['start_time']) > $env_nbm['sendmail_timeout']);
65
66  return $env_nbm['is_sendmail_timeout'];
67}
68
69
70/*
71 * Add quote to all elements of check_key_list
72 *
73 * @return quoted check key list
74 */
75function quote_check_key_list($check_key_list = array())
76{
77  return array_map(function($s) { return  '\''.$s.'\'';   } , $check_key_list);
78}
79
80/*
81 * Execute all main queries to get list of user
82 *
83 * Type are the type of list 'subscribe', 'send'
84 *
85 * return array of users
86 */
87function get_user_notifications($action, $check_key_list = array(), $enabled_filter_value = '')
88{
89  global $conf;
90
91  $data_users = array();
92
93  if (in_array($action, array('subscribe', 'send')))
94  {
95    $quoted_check_key_list = quote_check_key_list($check_key_list);
96    if (count($quoted_check_key_list) != 0 )
97    {
98      $query_and_check_key = ' and
99    check_key in ('.implode(",", $quoted_check_key_list).') ';
100    }
101    else
102    {
103      $query_and_check_key = '';
104    }
105
106    $query = '
107select
108  N.user_id,
109  N.check_key,
110  U.'.$conf['user_fields']['username'].' as username,
111  U.'.$conf['user_fields']['email'].' as mail_address,
112  N.enabled,
113  N.last_send,
114  UI.status
115from '.USER_MAIL_NOTIFICATION_TABLE.' as N
116  JOIN '.USERS_TABLE.' as U on N.user_id =  U.'.$conf['user_fields']['id'].'
117  JOIN '.USER_INFOS_TABLE.' as UI on UI.user_id = N.user_id
118where 1=1';
119
120    if ($action == 'send')
121    {
122      // No mail empty and all users enabled
123      $query .= ' and
124  N.enabled = \'true\' and
125  U.'.$conf['user_fields']['email'].' is not null';
126    }
127
128    $query .= $query_and_check_key;
129
130    if (isset($enabled_filter_value) and ($enabled_filter_value != ''))
131    {
132      $query .= ' and
133        N.enabled = \''.boolean_to_string($enabled_filter_value).'\'';
134    }
135
136    $query .= '
137order by';
138
139    if ($action == 'send')
140    {
141      $query .= '
142  last_send, username;';
143    }
144    else
145    {
146      $query .= '
147  username';
148    }
149
150    $query .= ';';
151
152    $result = pwg_query($query);
153    if (!empty($result))
154    {
155      while ($nbm_user = pwg_db_fetch_assoc($result))
156      {
157        $data_users[] = $nbm_user;
158      }
159    }
160  }
161  return $data_users;
162}
163
164/*
165 * Begin of use nbm environment
166 * Prepare and save current environment and initialize data in order to send mail
167 *
168 * Return none
169 */
170function begin_users_env_nbm($is_to_send_mail = false)
171{
172  global $user, $lang, $lang_info, $conf, $env_nbm;
173
174  // Save $user, $lang_info and $lang arrays (include/user.inc.php has been executed)
175  $env_nbm['save_user'] = $user;
176  // Save current language to stack, necessary because $user change during NBM
177  switch_lang_to($user['language']);
178
179  $env_nbm['is_to_send_mail'] = $is_to_send_mail;
180
181  if ($is_to_send_mail)
182  {
183    // Init mail configuration
184    $env_nbm['email_format'] = get_str_email_format($conf['nbm_send_html_mail']);
185    $env_nbm['send_as_name'] = ((isset($conf['nbm_send_mail_as']) and !empty($conf['nbm_send_mail_as'])) ? $conf['nbm_send_mail_as'] : get_mail_sender_name());
186    $env_nbm['send_as_mail_address'] = get_webmaster_mail_address();
187    $env_nbm['send_as_mail_formated'] = format_email($env_nbm['send_as_name'], $env_nbm['send_as_mail_address']);
188    // Init mail counter
189    $env_nbm['error_on_mail_count'] = 0;
190    $env_nbm['sent_mail_count'] = 0;
191    // Save sendmail message info and error in the original language
192    $env_nbm['msg_info'] = l10n('Mail sent to %s [%s].');
193    $env_nbm['msg_error'] = l10n('Error when sending email to %s [%s].');
194  }
195}
196
197/*
198 * End of use nbm environment
199 * Restore environment
200 *
201 * Return none
202 */
203function end_users_env_nbm()
204{
205  global $user, $lang, $lang_info, $env_nbm;
206
207  // Restore $user, $lang_info and $lang arrays (include/user.inc.php has been executed)
208  $user = $env_nbm['save_user'];
209  // Restore current language to stack, necessary because $user change during NBM
210  switch_lang_back();
211
212  if ($env_nbm['is_to_send_mail'])
213  {
214    unset($env_nbm['email_format']);
215    unset($env_nbm['send_as_name']);
216    unset($env_nbm['send_as_mail_address']);
217    unset($env_nbm['send_as_mail_formated']);
218    // Don t unset counter
219    //unset($env_nbm['error_on_mail_count']);
220    //unset($env_nbm['sent_mail_count']);
221    unset($env_nbm['msg_info']);
222    unset($env_nbm['msg_error']);
223  }
224
225  unset($env_nbm['save_user']);
226  unset($env_nbm['is_to_send_mail']);
227}
228
229/*
230 * Set user on nbm enviromnent
231 *
232 * Return none
233 */
234function set_user_on_env_nbm(&$nbm_user, $is_action_send)
235{
236  global $user, $lang, $lang_info, $env_nbm;
237
238  $user = build_user( $nbm_user['user_id'], true );
239
240  switch_lang_to($user['language']);
241
242  if ($is_action_send)
243  {
244    $env_nbm['mail_template'] = get_mail_template($env_nbm['email_format']);
245    $env_nbm['mail_template']->set_filename('notification_by_mail', 'notification_by_mail.tpl');
246  }
247}
248
249/*
250 * Unset user on nbm enviromnent
251 *
252 * Return none
253 */
254function unset_user_on_env_nbm()
255{
256  global $env_nbm;
257
258  switch_lang_back();
259  unset($env_nbm['mail_template']);
260}
261
262/*
263 * Inc Counter success
264 *
265 * Return none
266 */
267function inc_mail_sent_success($nbm_user)
268{
269  global $page, $env_nbm;
270
271  $env_nbm['sent_mail_count'] += 1;
272  $page['infos'][] = sprintf($env_nbm['msg_info'], stripslashes($nbm_user['username']), $nbm_user['mail_address']);
273}
274
275/*
276 * Inc Counter failed
277 *
278 * Return none
279 */
280function inc_mail_sent_failed($nbm_user)
281{
282  global $page, $env_nbm;
283
284  $env_nbm['error_on_mail_count'] += 1;
285  $page['errors'][] = sprintf($env_nbm['msg_error'], stripslashes($nbm_user['username']), $nbm_user['mail_address']);
286}
287
288/*
289 * Display Counter Info
290 *
291 * Return none
292 */
293function display_counter_info()
294{
295  global $page, $env_nbm;
296
297  if ($env_nbm['error_on_mail_count'] != 0)
298  {
299    $page['errors'][] = l10n_dec(
300      '%d mail was not sent.', '%d mails were not sent.',
301      $env_nbm['error_on_mail_count']
302      );
303
304    if ($env_nbm['sent_mail_count'] != 0)
305    {
306      $page['infos'][] = l10n_dec(
307        '%d mail was sent.', '%d mails were sent.',
308        $env_nbm['sent_mail_count']
309        );
310    }
311  }
312  else
313  {
314    if ($env_nbm['sent_mail_count'] == 0)
315    {
316      $page['infos'][] = l10n('No mail to send.');
317    }
318    else
319    {
320      $page['infos'][] = l10n_dec(
321        '%d mail was sent.', '%d mails were sent.',
322        $env_nbm['sent_mail_count']
323        );
324    }
325  }
326}
327
328function assign_vars_nbm_mail_content($nbm_user)
329{
330  global $env_nbm;
331
332  set_make_full_url();
333
334  $env_nbm['mail_template']->assign
335  (
336    array
337    (
338      'USERNAME' => stripslashes($nbm_user['username']),
339
340      'SEND_AS_NAME' => $env_nbm['send_as_name'],
341
342      'UNSUBSCRIBE_LINK' => add_url_params(get_gallery_home_url().'/nbm.php', array('unsubscribe' => $nbm_user['check_key'])),
343      'SUBSCRIBE_LINK' => add_url_params(get_gallery_home_url().'/nbm.php', array('subscribe' => $nbm_user['check_key'])),
344      'CONTACT_EMAIL' => $env_nbm['send_as_mail_address']
345    )
346  );
347
348  unset_make_full_url();
349}
350
351/*
352 * Subscribe or unsubscribe notification by mail
353 *
354 * is_subscribe define if action=subscribe or unsubscribe
355 * check_key list where action will be done
356 *
357 * @return check_key list treated
358 */
359function do_subscribe_unsubscribe_notification_by_mail($is_admin_request, $is_subscribe = false, $check_key_list = array())
360{
361  global $conf, $page, $env_nbm, $conf;
362
363  set_make_full_url();
364
365  $check_key_treated = array();
366  $updated_data_count = 0;
367  $error_on_updated_data_count = 0;
368
369  if ($is_subscribe)
370  {
371    $msg_info = l10n('User %s [%s] was added to the subscription list.');
372    $msg_error = l10n('User %s [%s] was not added to the subscription list.');
373  }
374  else
375  {
376    $msg_info = l10n('User %s [%s] was removed from the subscription list.');
377    $msg_error = l10n('User %s [%s] was not removed from the subscription list.');
378  }
379
380  if (count($check_key_list) != 0)
381  {
382    $updates = array();
383    $enabled_value = boolean_to_string($is_subscribe);
384    $data_users = get_user_notifications('subscribe', $check_key_list, !$is_subscribe);
385
386    // Prepare message after change language
387    $msg_break_timeout = l10n('Time to send mail is limited. Others mails are skipped.');
388
389    // Begin nbm users environment
390    begin_users_env_nbm(true);
391
392    foreach ($data_users as $nbm_user)
393    {
394      if (check_sendmail_timeout())
395      {
396        // Stop fill list on 'send', if the quota is override
397        $page['errors'][] = $msg_break_timeout;
398        break;
399      }
400
401      // Fill return list
402      $check_key_treated[] = $nbm_user['check_key'];
403
404      $do_update = true;
405      if ($nbm_user['mail_address'] != '')
406      {
407        // set env nbm user
408        set_user_on_env_nbm($nbm_user, true);
409
410        $subject = '['.$conf['gallery_title'].'] '.($is_subscribe ? l10n('Subscribe to notification by mail'): l10n('Unsubscribe from notification by mail'));
411
412        // Assign current var for nbm mail
413        assign_vars_nbm_mail_content($nbm_user);
414
415        $section_action_by = ($is_subscribe ? 'subscribe_by_' : 'unsubscribe_by_');
416        $section_action_by .= ($is_admin_request ? 'admin' : 'himself');
417        $env_nbm['mail_template']->assign
418        (
419          array
420          (
421            $section_action_by => true,
422            'GOTO_GALLERY_TITLE' => $conf['gallery_title'],
423            'GOTO_GALLERY_URL' => get_gallery_home_url(),
424          )
425        );
426
427        $ret = pwg_mail(
428          array(
429            'name' => stripslashes($nbm_user['username']),
430            'email' => $nbm_user['mail_address'],
431            ),
432          array(
433            'from' => $env_nbm['send_as_mail_formated'],
434            'subject' => $subject,
435            'email_format' => $env_nbm['email_format'],
436            'content' => $env_nbm['mail_template']->parse('notification_by_mail', true),
437            'content_format' => $env_nbm['email_format'],
438            )
439          );
440
441        if ($ret)
442        {
443          inc_mail_sent_success($nbm_user);
444        }
445        else
446        {
447          inc_mail_sent_failed($nbm_user);
448          $do_update = false;
449        }
450
451        // unset env nbm user
452        unset_user_on_env_nbm();
453
454      }
455
456      if ($do_update)
457      {
458        $updates[] = array(
459          'check_key' => $nbm_user['check_key'],
460          'enabled' => $enabled_value
461          );
462        $updated_data_count += 1;
463        $page['infos'][] = sprintf($msg_info, stripslashes($nbm_user['username']), $nbm_user['mail_address']);
464      }
465      else
466      {
467        $error_on_updated_data_count += 1;
468        $page['errors'][] = sprintf($msg_error, stripslashes($nbm_user['username']), $nbm_user['mail_address']);
469      }
470
471    }
472
473    // Restore nbm environment
474    end_users_env_nbm();
475
476    display_counter_info();
477
478    mass_updates(
479      USER_MAIL_NOTIFICATION_TABLE,
480      array(
481        'primary' => array('check_key'),
482        'update' => array('enabled')
483      ),
484      $updates
485    );
486
487  }
488
489  $page['infos'][] = l10n_dec(
490    '%d user was updated.', '%d users were updated.',
491    $updated_data_count
492    );
493
494  if ($error_on_updated_data_count != 0)
495  {
496    $page['errors'][] = l10n_dec(
497      '%d user was not updated.', '%d users were not updated.',
498      $error_on_updated_data_count
499      );
500  }
501
502  unset_make_full_url();
503
504  return $check_key_treated;
505}
506
507/*
508 * Unsubscribe notification by mail
509 *
510 * check_key list where action will be done
511 *
512 * @return check_key list treated
513 */
514function unsubscribe_notification_by_mail($is_admin_request, $check_key_list = array())
515{
516  return do_subscribe_unsubscribe_notification_by_mail($is_admin_request, false, $check_key_list);
517}
518
519/*
520 * Subscribe notification by mail
521 *
522 * check_key list where action will be done
523 *
524 * @return check_key list treated
525 */
526function subscribe_notification_by_mail($is_admin_request, $check_key_list = array())
527{
528  return do_subscribe_unsubscribe_notification_by_mail($is_admin_request, true, $check_key_list);
529}
530
531?>
532