ILIAS  release_5-3 Revision v5.3.23-19-g915713cf615
class.ilObjForum.php
Go to the documentation of this file.
1 <?php
2 /* Copyright (c) 1998-2012 ILIAS open source, Extended GPL, see docs/LICENSE */
3 
4 require_once 'Services/Object/classes/class.ilObject.php';
5 require_once 'Modules/Forum/classes/class.ilForum.php';
6 require_once 'Modules/Forum/classes/class.ilFileDataForum.php';
7 require_once 'Modules/Forum/classes/class.ilForumProperties.php';
8 
18 class ilObjForum extends ilObject
19 {
25  public $Forum;
26 
27  // private $objProperties = null;
28 
33  protected static $obj_id_to_forum_id_cache = array();
34 
39  protected static $ref_id_to_forum_id_cache = array();
40 
45  protected static $forum_statistics_cache = array();
46 
51  protected static $forum_last_post_cache = array();
52 
53  private $settings;
54  private $rbac;
55  private $ilBench;
56  private $user;
57  private $logger;
58 
65  public function __construct($a_id = 0, $a_call_by_reference = true)
66  {
67  global $DIC;
68  $this->settings = $DIC->settings();
69  $this->rbac = $DIC->rbac();
70  $this->db = $DIC->database();
71  $this->ilBench = $DIC['ilBench'];
72  $this->user = $DIC->user();
73  $this->logger = $DIC->logger()->root();
74 
75  $this->type = 'frm';
76  parent::__construct($a_id, $a_call_by_reference);
77 
78  /*
79  * this constant is used for the information if a single post is marked as new
80  * All threads/posts created before this date are never marked as new
81  * Default is 8 weeks
82  *
83  */
84  $new_deadline = time() - 60 * 60 * 24 * 7 * ($this->settings->get('frm_store_new') ?
85  $this->settings->get('frm_store_new') :
86  8);
87  define('NEW_DEADLINE', $new_deadline);
88 
89  // TODO: needs to rewrite scripts that are using Forum outside this class
90  $this->Forum = new ilForum();
91  }
92 
96  public function create()
97  {
98  $id = parent::create();
99 
100  require_once 'Modules/Forum/classes/class.ilForumProperties.php';
101  $properties = ilForumProperties::getInstance($this->getId());
102  $properties->setDefaultView(1);
103  $properties->setAnonymisation(0);
104  $properties->setStatisticsStatus(0);
105  $properties->setPostActivation(0);
106  $properties->setThreadSorting(0);
107  $properties->insert();
108 
109  $this->createSettings();
110 
111  $this->saveData();
112 
113  return $id;
114  }
115 
119  public function setPermissions($a_ref_id)
120  {
121  parent::setPermissions($a_ref_id);
122 
123  // ...finally assign moderator role to creator of forum object
124  $roles = array(ilObjForum::_lookupModeratorRole($this->getRefId()));
125  $this->rbac->admin()->assignUser($roles[0], $this->getOwner(), 'n');
126  $this->updateModeratorRole($roles[0]);
127  }
128 
132  public function updateModeratorRole($role_id)
133  {
134  $this->db->manipulate('UPDATE frm_data SET top_mods = ' . $this->db->quote($role_id, 'integer') . ' WHERE top_frm_fk = ' . $this->db->quote($this->getId(), 'integer'));
135  }
136 
142  public function getDiskUsage()
143  {
144  require_once("./Modules/File/classes/class.ilObjFileAccess.php");
145  return ilObjForumAccess::_lookupDiskUsage($this->id);
146  }
147 
148  public static function _lookupThreadSubject($a_thread_id)
149  {
150  global $DIC;
151  $ilDB = $DIC->database();
152 
153  $res = $ilDB->queryf(
154  '
155  SELECT thr_subject FROM frm_threads WHERE thr_pk = %s',
156  array('integer'),
157  array($a_thread_id)
158  );
159 
160  while ($row = $ilDB->fetchObject($res)) {
161  return $row->thr_subject;
162  }
163  return '';
164  }
165 
166  // METHODS FOR UN-READ STATUS
167  public function getCountUnread($a_usr_id, $a_thread_id = 0)
168  {
169  $a_frm_id = $this->getId();
170 
171  $this->ilBench->start("Forum", 'getCountRead');
172  if (!$a_thread_id) {
173  // Get topic_id
174  $res = $this->db->queryf(
175  '
176  SELECT top_pk FROM frm_data WHERE top_frm_fk = %s',
177  array('integer'),
178  array($a_frm_id)
179  );
180 
181 
182  while ($row = $this->db->fetchObject($res)) {
183  $topic_id = $row->top_pk;
184  }
185 
186  // Get number of posts
187  $res = $this->db->queryf(
188  '
189  SELECT COUNT(pos_pk) num_posts FROM frm_posts
190  WHERE pos_top_fk = %s',
191  array('integer'),
192  array($topic_id)
193  );
194 
195  while ($row = $this->db->fetchObject($res)) {
196  $num_posts = $row->num_posts;
197  }
198 
199  $res = $this->db->queryf(
200  '
201  SELECT COUNT(post_id) count_read FROM frm_user_read
202  WHERE obj_id = %s
203  AND usr_id = %s',
204  array('integer', 'integer'),
205  array($a_frm_id, $a_usr_id)
206  );
207 
208  while ($row = $this->db->fetchObject($res)) {
209  $count_read = $row->count_read;
210  }
211  $unread = $num_posts - $count_read;
212 
213  $this->ilBench->stop("Forum", 'getCountRead');
214  return $unread > 0 ? $unread : 0;
215  } else {
216  $res = $this->db->queryf(
217  '
218  SELECT COUNT(pos_pk) num_posts FROM frm_posts
219  WHERE pos_thr_fk = %s',
220  array('integer'),
221  array($a_thread_id)
222  );
223 
224  $row = $this->db->fetchObject($res);
225  $num_posts = $row->num_posts;
226 
227  $res = $this->db->queryf(
228  '
229  SELECT COUNT(post_id) count_read FROM frm_user_read
230  WHERE obj_id = %s
231  AND usr_id = %s
232  AND thread_id = %s',
233  array('integer', 'integer', 'integer'),
234  array($a_frm_id, $a_frm_id, $a_thread_id)
235  );
236 
237  $row = $this->db->fetchObject($res);
238  $count_read = $row->count_read;
239 
240  $unread = $num_posts - $count_read;
241 
242  $this->ilBench->stop("Forum", 'getCountRead');
243  return $unread > 0 ? $unread : 0;
244  }
245  $this->ilBench->stop("Forum", 'getCountRead');
246  return false;
247  }
248 
249 
250  public function markThreadRead($a_usr_id, $a_thread_id)
251  {
252  // Get all post ids
253  $res = $this->db->queryf(
254  '
255  SELECT * FROM frm_posts WHERE pos_thr_fk = %s',
256  array('integer'),
257  array($a_thread_id)
258  );
259 
260  while ($row = $this->db->fetchObject($res)) {
261  $this->markPostRead($a_usr_id, $a_thread_id, $row->pos_pk);
262  }
263  return true;
264  }
265 
266  public function markAllThreadsRead($a_usr_id)
267  {
268  $res = $this->db->queryf(
269  '
270  SELECT * FROM frm_data, frm_threads
271  WHERE top_frm_fk = %s
272  AND top_pk = thr_top_fk',
273  array('integer'),
274  array($this->getId())
275  );
276 
277  while ($row = $this->db->fetchObject($res)) {
278  $this->markThreadRead($a_usr_id, $row->thr_pk);
279  }
280 
281  return true;
282  }
283 
284 
285  public function markPostRead($a_usr_id, $a_thread_id, $a_post_id)
286  {
287  // CHECK IF ENTRY EXISTS
288  $res = $this->db->queryf(
289  '
290  SELECT * FROM frm_user_read
291  WHERE usr_id = %s
292  AND obj_id = %s
293  AND thread_id = %s
294  AND post_id = %s',
295  array('integer', 'integer', 'integer', 'integer'),
296  array($a_usr_id, $this->getId(), $a_thread_id, $a_post_id)
297  );
298 
299  if ($this->db->numRows($res)) {
300  return true;
301  }
302 
303  $this->db->manipulateF(
304  '
305  INSERT INTO frm_user_read
306  ( usr_id,
307  obj_id,
308  thread_id,
309  post_id
310  )
311  VALUES (%s,%s,%s,%s)',
312  array('integer', 'integer', 'integer', 'integer'),
313  array($a_usr_id, $this->getId(), $a_thread_id, $a_post_id)
314  );
315 
316  return true;
317  }
318 
319  public function markPostUnread($a_user_id, $a_post_id)
320  {
321  $this->db->manipulateF(
322  '
323  DELETE FROM frm_user_read
324  WHERE usr_id = %s
325  AND post_id = %s',
326  array('integer', 'integer'),
327  array($a_user_id, $a_post_id)
328  );
329  }
330 
331  public function isRead($a_usr_id, $a_post_id)
332  {
333  $res = $this->db->queryf(
334  '
335  SELECT * FROM frm_user_read
336  WHERE usr_id = %s
337  AND post_id = %s',
338  array('integer', 'integer'),
339  array($a_usr_id, $a_post_id)
340  );
341 
342  return $this->db->numRows($res) ? true : false;
343  }
344 
345  public function updateLastAccess($a_usr_id, $a_thread_id)
346  {
347  $res = $this->db->queryf(
348  '
349  SELECT * FROM frm_thread_access
350  WHERE usr_id = %s
351  AND obj_id = %s
352  AND thread_id = %s',
353  array('integer', 'integer', 'integer'),
354  array($a_usr_id, $this->getId(), $a_thread_id)
355  );
356  $data = $this->db->fetchAssoc($res);
357 
358  $this->db->replace(
359  'frm_thread_access',
360  array(
361  'usr_id' => array('integer', $a_usr_id),
362  'obj_id' => array('integer', $this->getId()),
363  'thread_id' => array('integer', $a_thread_id)
364  ),
365  array(
366  'access_last' => array('integer', time()),
367  'access_old' => array('integer', isset($data['access_old']) ? $data['access_old'] : 0),
368  'access_old_ts' => array('timestamp', $data['access_old_ts'])
369  )
370  );
371 
372  return true;
373  }
374 
379  public static function _updateOldAccess($a_usr_id)
380  {
381  global $DIC;
382  $ilDB = $DIC->database();
383 
384  $ilDB->manipulateF(
385  '
386  UPDATE frm_thread_access
387  SET access_old = access_last
388  WHERE usr_id = %s',
389  array('integer'),
390  array($a_usr_id)
391  );
392 
393  $set = $ilDB->query(
394  "SELECT * FROM frm_thread_access " .
395  " WHERE usr_id = " . $ilDB->quote($a_usr_id, "integer")
396  );
397  while ($rec = $ilDB->fetchAssoc($set)) {
398  $ilDB->manipulate(
399  "UPDATE frm_thread_access SET " .
400  " access_old_ts = " . $ilDB->quote(date('Y-m-d H:i:s', $rec["access_old"]), "timestamp") .
401  " WHERE usr_id = " . $ilDB->quote($rec["usr_id"], "integer") .
402  " AND obj_id = " . $ilDB->quote($rec["obj_id"], "integer") .
403  " AND thread_id = " . $ilDB->quote($rec["thread_id"], "integer")
404  );
405  }
406 
407  $new_deadline = time() - 60 * 60 * 24 * 7 * ($DIC->settings()->get('frm_store_new') ?
408  $DIC->settings()->get('frm_store_new') :
409  8);
410 
411  $ilDB->manipulateF(
412  '
413  DELETE FROM frm_thread_access WHERE access_last < %s',
414  array('integer'),
415  array($new_deadline)
416  );
417  }
418 
419  public static function _deleteUser($a_usr_id)
420  {
421  global $DIC;
422  $ilDB = $DIC->database();
423 
424  $data = array($a_usr_id);
425 
426  $ilDB->manipulateF(
427  '
428  DELETE FROM frm_user_read WHERE usr_id = %s',
429  array('integer'),
430  $data
431  );
432 
433  $ilDB->manipulateF(
434  '
435  DELETE FROM frm_thread_access WHERE usr_id = %s',
436  array('integer'),
437  $data
438  );
439 
440  // delete notifications of deleted user
441  $ilDB->manipulateF(
442  '
443  DELETE FROM frm_notification WHERE user_id = %s',
444  array('integer'),
445  $data
446  );
447 
448  return true;
449  }
450 
451 
452  public static function _deleteReadEntries($a_post_id)
453  {
454  global $DIC;
455  $ilDB = $DIC->database();
456 
457  $ilDB->manipulateF(
458  '
459  DELETE FROM frm_user_read WHERE post_id = %s',
460  array('integer'),
461  array($a_post_id)
462  );
463 
464  return true;
465  }
466 
467  public static function _deleteAccessEntries($a_thread_id)
468  {
469  global $DIC;
470  $ilDB = $DIC->database();
471  $ilDB->manipulateF(
472  '
473  DELETE FROM frm_thread_access WHERE thread_id = %s',
474  array('integer'),
475  array($a_thread_id)
476  );
477 
478  return true;
479  }
480 
485  public function update($a_update_user_id = 0)
486  {
487  if (!$a_update_user_id) {
488  $a_update_user_id = $this->user->getId();
489  }
490 
491  if (parent::update()) {
492  $this->db->manipulateF(
493  '
494  UPDATE frm_data
495  SET top_name = %s,
496  top_description = %s,
497  top_update = %s,
498  update_user = %s
499  WHERE top_frm_fk =%s',
500  array('text', 'text', 'timestamp', 'integer', 'integer'),
501  array(
502  $this->getTitle(),
503  $this->getDescription(),
504  date("Y-m-d H:i:s"),
505  (int) $a_update_user_id,
506  (int) $this->getId()
507  )
508  );
509 
510  return true;
511  }
512 
513  return false;
514  }
515 
522  public function cloneObject($a_target_id, $a_copy_id = 0, $a_omit_tree = false)
523  {
525  $new_obj = parent::cloneObject($a_target_id, $a_copy_id, $a_omit_tree);
526  $this->cloneAutoGeneratedRoles($new_obj);
527 
528  ilForumProperties::getInstance($this->getId())->copy($new_obj->getId());
529  $this->Forum->setMDB2WhereCondition('top_frm_fk = %s ', array('integer'), array($this->getId()));
530  $topData = $this->Forum->getOneTopic();
531 
532  $this->db->update('frm_data', array(
533  'top_name' => array('text', $topData['top_name']),
534  'top_description' => array('text', $topData['top_description']),
535  'top_num_posts' => array('integer', $topData['top_num_posts']),
536  'top_num_threads' => array('integer', $topData['top_num_threads']),
537  'top_last_post' => array('text', $topData['top_last_post']),
538  'top_date' => array('timestamp', $topData['top_date']),
539  'visits' => array('integer', $topData['visits']),
540  'top_update' => array('timestamp', $topData['top_update']),
541  'update_user' => array('integer', $topData['update_user']),
542  'top_usr_id' => array('integer', $topData['top_usr_id'])
543  ), array(
544  'top_frm_fk' => array('integer', $new_obj->getId())
545  ));
546 
547  // read options
548  include_once('Services/CopyWizard/classes/class.ilCopyWizardOptions.php');
549 
550  $cwo = ilCopyWizardOptions::_getInstance($a_copy_id);
551  $options = $cwo->getOptions($this->getRefId());
552 
553  $options['threads'] = $this->Forum->_getThreads($this->getId());
554 
555  // Generate starting threads
556  include_once('Modules/Forum/classes/class.ilFileDataForum.php');
557 
558  $new_frm = $new_obj->Forum;
559  $new_frm->setMDB2WhereCondition('top_frm_fk = %s ', array('integer'), array($new_obj->getId()));
560 
561  $new_frm->setForumId($new_obj->getId());
562  $new_frm->setForumRefId($new_obj->getRefId());
563 
564  $new_topic = $new_frm->getOneTopic();
565  foreach ($options['threads'] as $thread_id => $thread_subject) {
566  $this->Forum->setMDB2WhereCondition('thr_pk = %s ', array('integer'), array($thread_id));
567 
568  $old_thread = $this->Forum->getOneThread();
569 
570  $old_post_id = $this->Forum->getFirstPostByThread($old_thread['thr_pk']);
571  $old_post = $this->Forum->getOnePost($old_post_id);
572 
573  $newThread = new ilForumTopic(0, true, true);
574  $newThread->setSticky($old_thread['is_sticky']);
575  $newThread->setForumId($new_topic['top_pk']);
576  $newThread->setThrAuthorId($old_thread['thr_author_id']);
577  $newThread->setDisplayUserId($old_thread['thr_display_user_id']);
578  $newThread->setSubject($old_thread['thr_subject']);
579  $newThread->setUserAlias($old_thread['thr_usr_alias']);
580  $newThread->setCreateDate($old_thread['thr_date']);
581 
582  $newPostId = $new_frm->generateThread(
583  $newThread,
584  ilForum::_lookupPostMessage($old_post_id),
585  $old_post['notify'],
586  0
587  );
588 
589  $old_forum_files = new ilFileDataForum($this->getId(), $old_post_id);
590  $old_forum_files->ilClone($new_obj->getId(), $newPostId);
591  }
592 
593  $sourceRefId = $this->getRefId();
594  $targetRefId = $new_obj->getRefId();
595 
596  if (
597  $sourceRefId > 0 && $targetRefId > 0 &&
598  $this->tree->getParentId($sourceRefId) === $this->tree->getParentId($targetRefId)
599  ) {
600  $grpRefId = $this->tree->checkForParentType($targetRefId, 'grp');
601  $crsRefId = $this->tree->checkForParentType($targetRefId, 'crs');
602 
603  if ($grpRefId > 0 || $crsRefId > 0) {
604  $notifications = new \ilForumNotification($targetRefId);
605  $notifications->cloneFromSource((int) $sourceRefId);
606  }
607  }
608 
609  return $new_obj;
610  }
611 
618  public function cloneAutoGeneratedRoles($new_obj)
619  {
620  $moderator = ilObjForum::_lookupModeratorRole($this->getRefId());
621  $new_moderator = ilObjForum::_lookupModeratorRole($new_obj->getRefId());
622 
623  if (!$moderator || !$new_moderator || !$this->getRefId() || !$new_obj->getRefId()) {
624  $this->logger->write(__METHOD__ . ' : Error cloning auto generated role: il_frm_moderator');
625  }
626  $this->rbac->admin()->copyRolePermissions($moderator, $this->getRefId(), $new_obj->getRefId(), $new_moderator, true);
627  $this->logger->write(__METHOD__ . ' : Finished copying of role il_frm_moderator.');
628 
629  include_once './Modules/Forum/classes/class.ilForumModerators.php';
630  $obj_mods = new ilForumModerators($this->getRefId());
631 
632  $old_mods = $obj_mods->getCurrentModerators();
633  foreach ($old_mods as $user_id) {
634  // The object owner is already member of the moderator role when this method is called
635  // Since the new static caches are introduced with ILIAS 5.0, a database error occurs if we try to assign the user here.
636  if ($this->getOwner() != $user_id) {
637  $this->rbac->admin()->assignUser($new_moderator, $user_id);
638  }
639  }
640  }
641 
647  public function delete()
648  {
649  // always call parent delete function first!!
650  if (!parent::delete()) {
651  return false;
652  }
653 
654  // delete attachments
655  $tmp_file_obj = new ilFileDataForum($this->getId());
656  $tmp_file_obj->delete();
657  unset($tmp_file_obj);
658 
659  $this->Forum->setMDB2WhereCondition('top_frm_fk = %s ', array('integer'), array($this->getId()));
660 
661  $topData = $this->Forum->getOneTopic();
662 
663  $threads = $this->Forum->getAllThreads($topData['top_pk']);
664  foreach ($threads['items'] as $thread) {
665  $thread_ids_to_delete[$thread->getId()] = $thread->getId();
666  }
667 
668  // delete tree
669  $this->db->manipulate('DELETE FROM frm_posts_tree WHERE ' . $this->db->in('thr_fk', $thread_ids_to_delete, false, 'integer'));
670 
671  // delete posts
672  $this->db->manipulate('DELETE FROM frm_posts WHERE ' . $this->db->in('pos_thr_fk', $thread_ids_to_delete, false, 'integer'));
673 
674  // delete threads
675  $this->db->manipulate('DELETE FROM frm_threads WHERE ' . $this->db->in('thr_pk', $thread_ids_to_delete, false, 'integer'));
676 
677  $obj_id = array($this->getId());
678  // delete forum
679  $this->db->manipulateF(
680  'DELETE FROM frm_data WHERE top_frm_fk = %s',
681  array('integer'),
682  $obj_id
683  );
684 
685  // delete settings
686  $this->db->manipulateF(
687  'DELETE FROM frm_settings WHERE obj_id = %s',
688  array('integer'),
689  $obj_id
690  );
691 
692  // delete read infos
693  $this->db->manipulateF(
694  'DELETE FROM frm_user_read WHERE obj_id = %s',
695  array('integer'),
696  $obj_id
697  );
698 
699  // delete thread access entries
700  $this->db->manipulateF(
701  'DELETE FROM frm_thread_access WHERE obj_id = %s',
702  array('integer'),
703  $obj_id
704  );
705 
706  //delete thread notifications
707  $this->db->manipulate('DELETE FROM frm_notification WHERE ' . $this->db->in('thread_id', $thread_ids_to_delete, false, 'integer'));
708 
709  //delete forum notifications
710  $this->db->manipulateF('DELETE FROM frm_notification WHERE frm_id = %s', array('integer'), $obj_id);
711 
712  // delete posts_deleted entries
713  $this->db->manipulateF('DELETE FROM frm_posts_deleted WHERE obj_id = %s', array('integer'), $obj_id);
714 
715  //delete drafts
716  $this->deleteDraftsByForumId((int) $topData['top_pk']);
717 
718  return true;
719  }
720 
724  private function deleteDraftsByForumId($forum_id)
725  {
726  $res = $this->db->queryF(
727  'SELECT draft_id FROM frm_posts_drafts WHERE forum_id = %s',
728  array('integer'),
729  array((int) $forum_id)
730  );
731 
732  $draft_ids = array();
733  while ($row = $this->db->fetchAssoc($res)) {
734  $draft_ids[] = $row['draft_id'];
735  }
736 
737  if (count($draft_ids) > 0) {
738  require_once 'Modules/Forum/classes/class.ilForumDraftsHistory.php';
739  $historyObj = new ilForumDraftsHistory();
740  $historyObj->deleteHistoryByDraftIds($draft_ids);
741 
742  require_once 'Modules/Forum/classes/class.ilForumPostDraft.php';
743  $draftObj = new ilForumPostDraft();
744  $draftObj->deleteDraftsByDraftIds($draft_ids);
745  }
746  }
747 
753  public function initDefaultRoles()
754  {
755  include_once './Services/AccessControl/classes/class.ilObjRole.php';
757  'il_frm_moderator_' . $this->getRefId(),
758  "Moderator of forum obj_no." . $this->getId(),
759  'il_frm_moderator',
760  $this->getRefId()
761  );
762  return array();
763  }
764 
772  public static function _lookupModeratorRole($a_ref_id)
773  {
774  global $DIC;
775  $ilDB = $DIC->database();
776 
777  $mod_title = 'il_frm_moderator_' . $a_ref_id;
778 
779  $res = $ilDB->queryf(
780  '
781  SELECT * FROM object_data WHERE title = %s',
782  array('text'),
783  array($mod_title)
784  );
785 
786  while ($row = $ilDB->fetchObject($res)) {
787  return $row->obj_id;
788  }
789  return 0;
790  }
791 
792 
793  public function createSettings()
794  {
795  // news settings (public notifications yes/no)
796  include_once("./Services/News/classes/class.ilNewsItem.php");
797  $default_visibility = ilNewsItem::_getDefaultVisibilityForRefId($_GET["ref_id"]);
798  if ($default_visibility == "public") {
799  ilBlockSetting::_write("news", "public_notifications", 1, 0, $this->getId());
800  }
801 
802  return true;
803  }
804 
805  public function saveData($a_roles = array())
806  {
807  $nextId = $this->db->nextId('frm_data');
808 
809  $top_data = array(
810  'top_frm_fk' => $this->getId(),
811  'top_name' => $this->getTitle(),
812  'top_description' => $this->getDescription(),
813  'top_num_posts' => 0,
814  'top_num_threads' => 0,
815  'top_last_post' => null,
816  'top_mods' => !is_numeric($a_roles[0]) ? 0 : $a_roles[0],
817  'top_usr_id' => $this->user->getId(),
818  'top_date' => ilUtil::now()
819  );
820 
821  $this->db->manipulateF(
822  '
823  INSERT INTO frm_data
824  (
825  top_pk,
826  top_frm_fk,
827  top_name,
828  top_description,
829  top_num_posts,
830  top_num_threads,
831  top_last_post,
832  top_mods,
833  top_date,
834  top_usr_id
835  )
836  VALUES(%s, %s, %s, %s, %s, %s, %s, %s, %s, %s)',
837  array('integer', 'integer', 'text', 'text', 'integer', 'integer', 'text', 'integer', 'timestamp', 'integer'),
838  array(
839  $nextId,
840  $top_data['top_frm_fk'],
841  $top_data['top_name'],
842  $top_data['top_description'],
843  $top_data['top_num_posts'],
844  $top_data['top_num_threads'],
845  $top_data['top_last_post'],
846  $top_data['top_mods'],
847  $top_data['top_date'],
848  $top_data['top_usr_id']
849  )
850  );
851  }
852 
853  public function setThreadSorting($a_thr_pk, $a_sorting_value)
854  {
855  $this->db->update(
856  'frm_threads',
857  array('thread_sorting' => array('integer',$a_sorting_value)),
858  array('thr_pk' => array('integer', $a_thr_pk))
859  );
860  }
861 
862 
868  public static function lookupForumIdByObjId($obj_id)
869  {
870  if (array_key_exists($obj_id, self::$obj_id_to_forum_id_cache)) {
871  return (int) self::$obj_id_to_forum_id_cache[$obj_id];
872  }
873 
874  self::preloadForumIdsByObjIds(array($obj_id));
875 
876  return (int) self::$obj_id_to_forum_id_cache[$obj_id];
877  }
878 
884  public static function lookupForumIdByRefId($ref_id)
885  {
886  if (array_key_exists($ref_id, self::$ref_id_to_forum_id_cache)) {
887  return (int) self::$ref_id_to_forum_id_cache[$ref_id];
888  }
889 
890  self::preloadForumIdsByRefIds(array($ref_id));
891 
892  return (int) self::$ref_id_to_forum_id_cache[$ref_id];
893  }
894 
899  public static function preloadForumIdsByObjIds(array $obj_ids)
900  {
901  global $DIC;
902  $ilDB = $DIC->database();
903 
904  if (count($obj_ids) == 1) {
905  $in = " objr.obj_id = " . $ilDB->quote(current($obj_ids), 'integer') . " ";
906  } else {
907  $in = $ilDB->in('objr.obj_id', $obj_ids, false, 'integer');
908  }
909  $query = "
910  SELECT frmd.top_pk, objr.ref_id, objr.obj_id
911  FROM object_reference objr
912  INNER JOIN frm_data frmd ON frmd.top_frm_fk = objr.obj_id
913  WHERE $in
914  ";
915  $res = $ilDB->query($query);
916 
917  // Prepare cache array
918  foreach ($obj_ids as $obj_id) {
919  self::$obj_id_to_forum_id_cache[$obj_id] = null;
920  }
921 
922  while ($row = $ilDB->fetchAssoc($res)) {
923  self::$obj_id_to_forum_id_cache[$row['obj_id']] = $row['top_pk'];
924  self::$ref_id_to_forum_id_cache[$row['ref_id']] = $row['top_pk'];
925  }
926  }
927 
932  public static function preloadForumIdsByRefIds(array $ref_ids)
933  {
934  global $DIC;
935  $ilDB = $DIC->database();
936 
937  if (count($ref_ids) == 1) {
938  $in = " objr.ref_id = " . $ilDB->quote(current($ref_ids), 'integer') . " ";
939  } else {
940  $in = $ilDB->in('objr.ref_id', $ref_ids, false, 'integer');
941  }
942  $query = "
943  SELECT frmd.top_pk, objr.ref_id, objr.obj_id
944  FROM object_reference objr
945  INNER JOIN frm_data frmd ON frmd.top_frm_fk = objr.obj_id
946  WHERE $in
947  ";
948  $res = $ilDB->query($query);
949 
950  // Prepare cache array
951  foreach ($ref_ids as $ref_id) {
952  self::$ref_id_to_forum_id_cache[$ref_id] = null;
953  }
954 
955  while ($row = $ilDB->fetchAssoc($res)) {
956  self::$obj_id_to_forum_id_cache[$row['obj_id']] = $row['top_pk'];
957  self::$ref_id_to_forum_id_cache[$row['ref_id']] = $row['top_pk'];
958  }
959  }
960 
966  public static function lookupStatisticsByRefId($ref_id)
967  {
968  global $DIC;
969  $ilAccess = $DIC->access();
970  $ilUser = $DIC->user();
971  $ilDB = $DIC->database();
972  $ilSetting = $DIC->settings();
973 
974  if (isset(self::$forum_statistics_cache[$ref_id])) {
975  return self::$forum_statistics_cache[$ref_id];
976  }
977 
978  $statistics = array(
979  'num_posts' => 0,
980  'num_unread_posts' => 0,
981  'num_new_posts' => 0
982  );
983 
984  $forumId = self::lookupForumIdByRefId($ref_id);
985  if (!$forumId) {
986  self::$forum_statistics_cache[$ref_id] = $statistics;
987  return self::$forum_statistics_cache[$ref_id];
988  }
989 
991  $is_post_activation_enabled = $objProperties->isPostActivationEnabled();
992 
993  $act_clause = '';
994 
995  if ($is_post_activation_enabled && !$ilAccess->checkAccess('moderate_frm', '', $ref_id)) {
996  $act_clause .= " AND (frm_posts.pos_status = " . $ilDB->quote(1, "integer") . " OR frm_posts.pos_author_id = " . $ilDB->quote($ilUser->getId(), "integer") . ") ";
997  }
998 
999  $new_deadline = date('Y-m-d H:i:s', time() - 60 * 60 * 24 * 7 * ($ilSetting->get('frm_store_new') ? $ilSetting->get('frm_store_new') : 8));
1000 
1001  if (!$ilUser->isAnonymous()) {
1002  $query = "
1003  (SELECT COUNT(frm_posts.pos_pk) cnt
1004  FROM frm_posts
1005  INNER JOIN frm_threads ON frm_posts.pos_thr_fk = frm_threads.thr_pk
1006  WHERE frm_threads.thr_top_fk = %s $act_clause)
1007 
1008  UNION ALL
1009 
1010  (SELECT COUNT(DISTINCT(frm_user_read.post_id)) cnt
1011  FROM frm_user_read
1012  INNER JOIN frm_posts ON frm_user_read.post_id = frm_posts.pos_pk
1013  INNER JOIN frm_threads ON frm_threads.thr_pk = frm_posts.pos_thr_fk
1014  WHERE frm_user_read.usr_id = %s AND frm_posts.pos_top_fk = %s $act_clause)
1015  ";
1016 
1017  $types = array('integer', 'integer', 'integer');
1018  $values = array($forumId, $ilUser->getId(), $forumId);
1019 
1020  $forum_overview_setting = (int) $ilSetting::_lookupValue('frma', 'forum_overview');
1021  if ($forum_overview_setting == ilForumProperties::FORUM_OVERVIEW_WITH_NEW_POSTS) {
1022  $news_types = array('integer', 'integer', 'integer', 'timestamp', 'integer');
1023  $news_values = array($ilUser->getId(), $ilUser->getId(), $forumId, $new_deadline, $ilUser->getId());
1024 
1025  $query .= "
1026  UNION ALL
1027 
1028  (SELECT COUNT(frm_posts.pos_pk) cnt
1029  FROM frm_posts
1030  LEFT JOIN frm_user_read ON (post_id = frm_posts.pos_pk AND frm_user_read.usr_id = %s)
1031  LEFT JOIN frm_thread_access ON (frm_thread_access.thread_id = frm_posts.pos_thr_fk AND frm_thread_access.usr_id = %s)
1032  WHERE frm_posts.pos_top_fk = %s
1033  AND ( (frm_posts.pos_update > frm_thread_access.access_old_ts)
1034  OR (frm_thread_access.access_old IS NULL AND frm_posts.pos_update > %s)
1035  )
1036  AND frm_posts.pos_author_id != %s
1037  AND frm_user_read.usr_id IS NULL $act_clause)";
1038 
1039  $types = array_merge($types, $news_types);
1040  $values = array_merge($values, $news_values);
1041  }
1042 
1043  $mapping = array_keys($statistics);
1044  $res = $ilDB->queryF(
1045  $query,
1046  $types,
1047  $values
1048  );
1049  for ($i = 0; $i <= 2; $i++) {
1050  $row = $ilDB->fetchAssoc($res);
1051 
1052  $statistics[$mapping[$i]] = (int) $row['cnt'];
1053 
1054  if ($i == 1) {
1055  // unread = all - read
1056  $statistics[$mapping[$i]] = $statistics[$mapping[$i - 1]] - $statistics[$mapping[$i]];
1057  }
1058  }
1059  } else {
1060  $query = "
1061  SELECT COUNT(frm_posts.pos_pk) cnt
1062  FROM frm_posts
1063  INNER JOIN frm_threads ON frm_posts.pos_thr_fk = frm_threads.thr_pk
1064  WHERE frm_threads.thr_top_fk = %s $act_clause
1065  ";
1066  $types = array('integer');
1067  $values = array($forumId);
1068  $res = $ilDB->queryF(
1069  $query,
1070  $types,
1071  $values
1072  );
1073  $row = $ilDB->fetchAssoc($res);
1074 
1075  $statistics = array(
1076  'num_posts' => $row['cnt'],
1077  'num_unread_posts' => $row['cnt'],
1078  'num_new_posts' => $row['cnt']
1079  );
1080  }
1081 
1082  self::$forum_statistics_cache[$ref_id] = $statistics;
1083 
1084  return self::$forum_statistics_cache[$ref_id];
1085  }
1086 
1092  public static function lookupLastPostByRefId($ref_id)
1093  {
1094  global $DIC;
1095  $ilAccess = $DIC->access();
1096  $ilUser = $DIC->user();
1097  $ilDB = $DIC->database();
1098 
1099  if (isset(self::$forum_last_post_cache[$ref_id])) {
1100  return self::$forum_last_post_cache[$ref_id];
1101  }
1102 
1103  $forumId = self::lookupForumIdByRefId($ref_id);
1104  if (!$forumId) {
1105  self::$forum_last_post_cache[$ref_id] = array();
1106  return self::$forum_last_post_cache[$ref_id];
1107  }
1108 
1109  $act_clause = '';
1110  if (!$ilAccess->checkAccess('moderate_frm', '', $ref_id)) {
1111  $act_clause .= " AND (frm_posts.pos_status = " . $ilDB->quote(1, "integer") . " OR frm_posts.pos_author_id = " . $ilDB->quote($ilUser->getId(), "integer") . ") ";
1112  }
1113 
1114  $ilDB->setLimit(1, 0);
1115  $query = "
1116  SELECT *
1117  FROM frm_posts
1118  WHERE pos_top_fk = %s $act_clause
1119  ORDER BY pos_date DESC
1120  ";
1121  $res = $ilDB->queryF(
1122  $query,
1123  array('integer'),
1124  array($forumId)
1125  );
1126 
1127  $data = $ilDB->fetchAssoc($res);
1128 
1129  self::$forum_last_post_cache[$ref_id] = is_array($data) ? $data : array();
1130 
1131  return self::$forum_last_post_cache[$ref_id];
1132  }
1133 
1140  public static function getUserIdsOfLastPostsByRefIdAndThreadIds($ref_id, array $thread_ids)
1141  {
1142  global $DIC;
1143  $ilAccess = $DIC->access();
1144  $ilUser = $DIC->user();
1145  $ilDB = $DIC->database();
1146 
1147  $act_clause = '';
1148  $act_inner_clause = '';
1149  if (!$ilAccess->checkAccess('moderate_frm', '', $ref_id)) {
1150  $act_clause .= " AND (t1.pos_status = " . $ilDB->quote(1, "integer") . " OR t1.pos_author_id = " . $ilDB->quote($ilUser->getId(), "integer") . ") ";
1151  $act_inner_clause .= " AND (t3.pos_status = " . $ilDB->quote(1, "integer") . " OR t3.pos_author_id = " . $ilDB->quote($ilUser->getId(), "integer") . ") ";
1152  }
1153 
1154  $in = $ilDB->in("t1.pos_thr_fk", $thread_ids, false, 'integer');
1155  $inner_in = $ilDB->in("t3.pos_thr_fk", $thread_ids, false, 'integer');
1156  //@todo fix this query 'group by ... '
1157  $query = "
1158  SELECT t1.pos_display_user_id, t1.update_user
1159  FROM frm_posts t1
1160  INNER JOIN (
1161  SELECT t3.pos_thr_fk, MAX(t3.pos_date) pos_date
1162  FROM frm_posts t3
1163  WHERE $inner_in $act_inner_clause
1164  GROUP BY t3.pos_thr_fk
1165  ) t2 ON t2.pos_thr_fk = t1.pos_thr_fk AND t2.pos_date = t1.pos_date
1166  WHERE $in $act_clause
1167  GROUP BY t1.pos_thr_fk, t1.pos_display_user_id, t1.update_user
1168  ";
1170  $usr_ids = array();
1171 
1172  $res = $ilDB->query($query);
1173  while ($row = $ilDB->fetchAssoc($res)) {
1174  if ((int) $row['pos_display_user_id']) {
1175  $usr_ids[] = (int) $row['pos_display_user_id'];
1176  }
1177  if ((int) $row['update_user']) {
1178  $usr_ids[] = (int) $row['update_user'];
1179  }
1180  }
1181 
1182  return array_unique($usr_ids);
1183  }
1184 
1185  public static function mergeForumUserRead($merge_source_thread_id, $merge_target_thread_id)
1186  {
1187  global $DIC;
1188  $ilDB = $DIC->database();
1189 
1190  $ilDB->update(
1191  'frm_user_read',
1192  array('thread_id' => array('integer', $merge_target_thread_id)),
1193  array('thread_id' => array('integer',$merge_source_thread_id))
1194  );
1195  }
1196 }
static $forum_last_post_cache
markAllThreadsRead($a_usr_id)
Class ilForumPostDraft.
static mergeForumUserRead($merge_source_thread_id, $merge_target_thread_id)
Class Forum core functions for forum.
static _write($a_type, $a_setting, $a_value, $a_user=0, $a_block_id=0)
Write setting to database.
update($a_update_user_id=0)
update forum data public
static _lookupPostMessage($a_id)
setThreadSorting($a_thr_pk, $a_sorting_value)
static lookupForumIdByObjId($obj_id)
global $DIC
Definition: saml.php:7
$_GET["client_id"]
getCountUnread($a_usr_id, $a_thread_id=0)
static lookupForumIdByRefId($ref_id)
static $obj_id_to_forum_id_cache
initDefaultRoles()
init default roles settings public
deleteDraftsByForumId($forum_id)
markPostRead($a_usr_id, $a_thread_id, $a_post_id)
markThreadRead($a_usr_id, $a_thread_id)
static preloadForumIdsByObjIds(array $obj_ids)
setPermissions($a_ref_id)
getOwner()
get object owner
static now()
Return current timestamp in Y-m-d H:i:s format.
user()
Definition: user.php:4
static createDefaultRole($a_title, $a_description, $a_tpl_name, $a_ref_id)
Class ilForumDraftHistory.
markPostUnread($a_user_id, $a_post_id)
saveData($a_roles=array())
static _lookupObjectId($a_ref_id)
lookup object id
updateLastAccess($a_usr_id, $a_thread_id)
static _deleteReadEntries($a_post_id)
static getInstance($a_obj_id=0)
static _getInstance($a_copy_id)
Get instance of copy wizard options.
updateModeratorRole($role_id)
static _lookupThreadSubject($a_thread_id)
foreach($_POST as $key=> $value) $res
getId()
get object id public
static _lookupDiskUsage($a_obj_id)
Returns the number of bytes used on the harddisk by the specified forum.
static _lookupModeratorRole($a_ref_id)
Lookup moderator role public.
date( 'd-M-Y', $objPHPExcel->getProperties() ->getCreated())
getTitle()
get object title public
getDescription()
get object description
$ilUser
Definition: imgupload.php:18
$query
static _updateOldAccess($a_usr_id)
Create styles array
The data for the language used.
if(php_sapi_name() !='cli') $in
Definition: Utf8Test.php:37
update($pash, $contents, Config $config)
static _deleteAccessEntries($a_thread_id)
static $forum_statistics_cache
settings()
Definition: settings.php:2
static _deleteUser($a_usr_id)
isRead($a_usr_id, $a_post_id)
global $ilSetting
Definition: privfeed.php:17
This class handles all operations on files for the forum object.
global $ilDB
static _getDefaultVisibilityForRefId($a_ref_id)
Get default visibility for reference id.
$i
Definition: disco.tpl.php:19
getRefId()
get reference id public
static lookupStatisticsByRefId($ref_id)
__construct($a_id=0, $a_call_by_reference=true)
Constructor public.
Add data(end) time
Method that wraps PHPs time in order to allow simulations with the workflow.
static $ref_id_to_forum_id_cache
Class ilObjForum.
cloneAutoGeneratedRoles($new_obj)
Clone forum moderator role public.
static getUserIdsOfLastPostsByRefIdAndThreadIds($ref_id, array $thread_ids)
Class ilForumModerators.
static preloadForumIdsByRefIds(array $ref_ids)
getDiskUsage()
Gets the disk usage of the object in bytes.
static lookupLastPostByRefId($ref_id)
if(!isset($_REQUEST['ReturnTo'])) if(!isset($_REQUEST['AuthId'])) $options
Definition: as_login.php:20