001
014
015 package com.liferay.portlet.messageboards.service.impl;
016
017 import com.liferay.portal.kernel.dao.orm.QueryDefinition;
018 import com.liferay.portal.kernel.exception.PortalException;
019 import com.liferay.portal.kernel.exception.SystemException;
020 import com.liferay.portal.kernel.increment.BufferedIncrement;
021 import com.liferay.portal.kernel.increment.NumberIncrement;
022 import com.liferay.portal.kernel.json.JSONFactoryUtil;
023 import com.liferay.portal.kernel.json.JSONObject;
024 import com.liferay.portal.kernel.lar.ExportImportThreadLocal;
025 import com.liferay.portal.kernel.search.Field;
026 import com.liferay.portal.kernel.search.Hits;
027 import com.liferay.portal.kernel.search.Indexer;
028 import com.liferay.portal.kernel.search.IndexerRegistryUtil;
029 import com.liferay.portal.kernel.search.SearchContext;
030 import com.liferay.portal.kernel.search.Sort;
031 import com.liferay.portal.kernel.systemevent.SystemEvent;
032 import com.liferay.portal.kernel.util.StringUtil;
033 import com.liferay.portal.kernel.util.Validator;
034 import com.liferay.portal.kernel.workflow.WorkflowConstants;
035 import com.liferay.portal.model.Group;
036 import com.liferay.portal.model.ResourceConstants;
037 import com.liferay.portal.model.SystemEventConstants;
038 import com.liferay.portal.model.User;
039 import com.liferay.portal.portletfilerepository.PortletFileRepositoryUtil;
040 import com.liferay.portal.service.ServiceContext;
041 import com.liferay.portal.util.PortletKeys;
042 import com.liferay.portlet.asset.model.AssetEntry;
043 import com.liferay.portlet.documentlibrary.model.DLFolderConstants;
044 import com.liferay.portlet.messageboards.NoSuchCategoryException;
045 import com.liferay.portlet.messageboards.SplitThreadException;
046 import com.liferay.portlet.messageboards.model.MBCategory;
047 import com.liferay.portlet.messageboards.model.MBCategoryConstants;
048 import com.liferay.portlet.messageboards.model.MBMessage;
049 import com.liferay.portlet.messageboards.model.MBMessageDisplay;
050 import com.liferay.portlet.messageboards.model.MBThread;
051 import com.liferay.portlet.messageboards.model.MBThreadConstants;
052 import com.liferay.portlet.messageboards.model.MBTreeWalker;
053 import com.liferay.portlet.messageboards.service.base.MBThreadLocalServiceBaseImpl;
054 import com.liferay.portlet.messageboards.util.MBUtil;
055 import com.liferay.portlet.social.model.SocialActivityConstants;
056 import com.liferay.portlet.trash.model.TrashEntry;
057 import com.liferay.portlet.trash.model.TrashVersion;
058
059 import java.util.ArrayList;
060 import java.util.Date;
061 import java.util.HashSet;
062 import java.util.List;
063 import java.util.Set;
064
065
069 public class MBThreadLocalServiceImpl extends MBThreadLocalServiceBaseImpl {
070
071 @Override
072 public MBThread addThread(
073 long categoryId, MBMessage message, ServiceContext serviceContext)
074 throws PortalException, SystemException {
075
076
077
078 Date now = new Date();
079
080 long threadId = message.getThreadId();
081
082 if (!message.isRoot() || (threadId <= 0)) {
083 threadId = counterLocalService.increment();
084 }
085
086 MBThread thread = mbThreadPersistence.create(threadId);
087
088 thread.setUuid(serviceContext.getUuid());
089 thread.setGroupId(message.getGroupId());
090 thread.setCompanyId(message.getCompanyId());
091 thread.setUserId(message.getUserId());
092 thread.setUserName(message.getUserName());
093 thread.setCreateDate(serviceContext.getCreateDate(now));
094 thread.setModifiedDate(serviceContext.getModifiedDate(now));
095 thread.setCategoryId(categoryId);
096 thread.setRootMessageId(message.getMessageId());
097 thread.setRootMessageUserId(message.getUserId());
098
099 if (message.isAnonymous()) {
100 thread.setLastPostByUserId(0);
101 }
102 else {
103 thread.setLastPostByUserId(message.getUserId());
104 }
105
106 thread.setLastPostDate(message.getCreateDate());
107
108 if (message.getPriority() != MBThreadConstants.PRIORITY_NOT_GIVEN) {
109 thread.setPriority(message.getPriority());
110 }
111
112 thread.setStatus(message.getStatus());
113 thread.setStatusByUserId(message.getStatusByUserId());
114 thread.setStatusByUserName(message.getStatusByUserName());
115 thread.setStatusDate(message.getStatusDate());
116
117 mbThreadPersistence.update(thread);
118
119
120
121 if (categoryId >= 0) {
122 assetEntryLocalService.updateEntry(
123 message.getUserId(), message.getGroupId(),
124 thread.getStatusDate(), thread.getLastPostDate(),
125 MBThread.class.getName(), thread.getThreadId(),
126 thread.getUuid(), 0, new long[0], new String[0], false, null,
127 null, null, null, String.valueOf(thread.getRootMessageId()),
128 null, null, null, null, 0, 0, null, false);
129 }
130
131 return thread;
132 }
133
134 @Override
135 public void deleteThread(long threadId)
136 throws PortalException, SystemException {
137
138 MBThread thread = mbThreadPersistence.findByPrimaryKey(threadId);
139
140 mbThreadLocalService.deleteThread(thread);
141 }
142
143 @Override
144 @SystemEvent(
145 action = SystemEventConstants.ACTION_SKIP, send = false,
146 type = SystemEventConstants.TYPE_DELETE)
147 public void deleteThread(MBThread thread)
148 throws PortalException, SystemException {
149
150 MBMessage rootMessage = mbMessagePersistence.findByPrimaryKey(
151 thread.getRootMessageId());
152
153
154
155 Indexer messageIndexer = IndexerRegistryUtil.nullSafeGetIndexer(
156 MBMessage.class);
157
158 messageIndexer.delete(thread);
159
160
161
162 long folderId = thread.getAttachmentsFolderId();
163
164 if (folderId != DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
165 PortletFileRepositoryUtil.deleteFolder(folderId);
166 }
167
168
169
170 subscriptionLocalService.deleteSubscriptions(
171 thread.getCompanyId(), MBThread.class.getName(),
172 thread.getThreadId());
173
174
175
176 mbThreadFlagPersistence.removeByThreadId(thread.getThreadId());
177
178
179
180 List<MBMessage> messages = mbMessagePersistence.findByThreadId(
181 thread.getThreadId());
182
183 for (MBMessage message : messages) {
184
185
186
187 ratingsStatsLocalService.deleteStats(
188 message.getWorkflowClassName(), message.getMessageId());
189
190
191
192 assetEntryLocalService.deleteEntry(
193 message.getWorkflowClassName(), message.getMessageId());
194
195
196
197 if (!message.isDiscussion()) {
198 resourceLocalService.deleteResource(
199 message.getCompanyId(), message.getWorkflowClassName(),
200 ResourceConstants.SCOPE_INDIVIDUAL, message.getMessageId());
201 }
202
203
204
205 mbMessagePersistence.remove(message);
206
207
208
209 if (!message.isDiscussion()) {
210 mbStatsUserLocalService.updateStatsUser(
211 message.getGroupId(), message.getUserId());
212 }
213
214
215
216 workflowInstanceLinkLocalService.deleteWorkflowInstanceLink(
217 message.getCompanyId(), message.getGroupId(),
218 message.getWorkflowClassName(), message.getMessageId());
219 }
220
221
222
223 if ((rootMessage.getCategoryId() !=
224 MBCategoryConstants.DEFAULT_PARENT_CATEGORY_ID) &&
225 (rootMessage.getCategoryId() !=
226 MBCategoryConstants.DISCUSSION_CATEGORY_ID)) {
227
228 try {
229 MBCategory category = mbCategoryPersistence.findByPrimaryKey(
230 thread.getCategoryId());
231
232 MBUtil.updateCategoryStatistics(
233 category.getCompanyId(), category.getCategoryId());
234 }
235 catch (NoSuchCategoryException nsce) {
236 if (!thread.isInTrash()) {
237 throw nsce;
238 }
239 }
240 }
241
242
243
244 AssetEntry assetEntry = assetEntryLocalService.fetchEntry(
245 MBThread.class.getName(), thread.getThreadId());
246
247 if (assetEntry != null) {
248 assetEntry.setTitle(rootMessage.getSubject());
249
250 assetEntryLocalService.updateAssetEntry(assetEntry);
251 }
252
253 assetEntryLocalService.deleteEntry(
254 MBThread.class.getName(), thread.getThreadId());
255
256
257
258 trashEntryLocalService.deleteEntry(
259 MBThread.class.getName(), thread.getThreadId());
260
261
262
263 Indexer threadIndexer = IndexerRegistryUtil.nullSafeGetIndexer(
264 MBThread.class);
265
266 threadIndexer.delete(thread);
267
268
269
270 mbThreadPersistence.remove(thread);
271 }
272
273 @Override
274 public void deleteThreads(long groupId, long categoryId)
275 throws PortalException, SystemException {
276
277 deleteThreads(groupId, categoryId, true);
278 }
279
280 @Override
281 public void deleteThreads(
282 long groupId, long categoryId, boolean includeTrashedEntries)
283 throws PortalException, SystemException {
284
285 List<MBThread> threads = mbThreadPersistence.findByG_C(
286 groupId, categoryId);
287
288 for (MBThread thread : threads) {
289 if (includeTrashedEntries || !thread.isInTrash()) {
290 mbThreadLocalService.deleteThread(thread);
291 }
292 }
293
294 if (mbThreadPersistence.countByGroupId(groupId) == 0) {
295 PortletFileRepositoryUtil.deletePortletRepository(
296 groupId, PortletKeys.MESSAGE_BOARDS);
297 }
298 }
299
300 @Override
301 public MBThread fetchThread(long threadId) throws SystemException {
302 return mbThreadPersistence.fetchByPrimaryKey(threadId);
303 }
304
305 @Override
306 public int getCategoryThreadsCount(
307 long groupId, long categoryId, int status)
308 throws SystemException {
309
310 if (status == WorkflowConstants.STATUS_ANY) {
311 return mbThreadPersistence.countByG_C(groupId, categoryId);
312 }
313 else {
314 return mbThreadPersistence.countByG_C_S(
315 groupId, categoryId, status);
316 }
317 }
318
319
323 @Override
324 public List<MBThread> getGroupThreads(
325 long groupId, int status, int start, int end)
326 throws SystemException {
327
328 QueryDefinition queryDefinition = new QueryDefinition(
329 status, start, end, null);
330
331 return getGroupThreads(groupId, queryDefinition);
332 }
333
334 @Override
335 public List<MBThread> getGroupThreads(
336 long groupId, long userId, boolean subscribed,
337 boolean includeAnonymous, QueryDefinition queryDefinition)
338 throws SystemException {
339
340 if (userId <= 0) {
341 return getGroupThreads(groupId, queryDefinition);
342 }
343
344 if (subscribed) {
345 return mbThreadFinder.findByS_G_U_C(
346 groupId, userId, null, queryDefinition);
347 }
348 else {
349 if (includeAnonymous) {
350 return mbThreadFinder.findByG_U_C(
351 groupId, userId, null, queryDefinition);
352 }
353 else {
354 return mbThreadFinder.findByG_U_C_A(
355 groupId, userId, null, false, queryDefinition);
356 }
357 }
358 }
359
360 @Override
361 public List<MBThread> getGroupThreads(
362 long groupId, long userId, boolean subscribed,
363 QueryDefinition queryDefinition)
364 throws SystemException {
365
366 return getGroupThreads(
367 groupId, userId, subscribed, true, queryDefinition);
368 }
369
370
374 @Override
375 public List<MBThread> getGroupThreads(
376 long groupId, long userId, int status, boolean subscribed,
377 boolean includeAnonymous, int start, int end)
378 throws SystemException {
379
380 QueryDefinition queryDefinition = new QueryDefinition(
381 status, start, end, null);
382
383 return getGroupThreads(
384 groupId, userId, subscribed, includeAnonymous, queryDefinition);
385 }
386
387
391 @Override
392 public List<MBThread> getGroupThreads(
393 long groupId, long userId, int status, boolean subscribed,
394 int start, int end)
395 throws SystemException {
396
397 QueryDefinition queryDefinition = new QueryDefinition(
398 status, start, end, null);
399
400 return getGroupThreads(groupId, userId, subscribed, queryDefinition);
401 }
402
403
407 @Override
408 public List<MBThread> getGroupThreads(
409 long groupId, long userId, int status, int start, int end)
410 throws SystemException {
411
412 QueryDefinition queryDefinition = new QueryDefinition(
413 status, start, end, null);
414
415 return getGroupThreads(groupId, userId, false, queryDefinition);
416 }
417
418 @Override
419 public List<MBThread> getGroupThreads(
420 long groupId, long userId, QueryDefinition queryDefinition)
421 throws SystemException {
422
423 return getGroupThreads(groupId, userId, false, queryDefinition);
424 }
425
426 @Override
427 public List<MBThread> getGroupThreads(
428 long groupId, QueryDefinition queryDefinition)
429 throws SystemException {
430
431 if (queryDefinition.isExcludeStatus()) {
432 return mbThreadPersistence.findByG_NotC_NotS(
433 groupId, MBCategoryConstants.DISCUSSION_CATEGORY_ID,
434 queryDefinition.getStatus(), queryDefinition.getStart(),
435 queryDefinition.getEnd());
436 }
437 else {
438 return mbThreadPersistence.findByG_NotC_S(
439 groupId, MBCategoryConstants.DISCUSSION_CATEGORY_ID,
440 queryDefinition.getStatus(), queryDefinition.getStart(),
441 queryDefinition.getEnd());
442 }
443 }
444
445
449 @Override
450 public int getGroupThreadsCount(long groupId, int status)
451 throws SystemException {
452
453 QueryDefinition queryDefinition = new QueryDefinition(status);
454
455 return getGroupThreadsCount(groupId, queryDefinition);
456 }
457
458 @Override
459 public int getGroupThreadsCount(
460 long groupId, long userId, boolean subscribed,
461 boolean includeAnonymous, QueryDefinition queryDefinition)
462 throws SystemException {
463
464 if (userId <= 0) {
465 return getGroupThreadsCount(groupId, queryDefinition);
466 }
467
468 if (subscribed) {
469 return mbThreadFinder.countByS_G_U_C(
470 groupId, userId, null, queryDefinition);
471 }
472 else {
473 if (includeAnonymous) {
474 return mbThreadFinder.countByG_U_C(
475 groupId, userId, null, queryDefinition);
476 }
477 else {
478 return mbThreadFinder.countByG_U_C_A(
479 groupId, userId, null, false, queryDefinition);
480 }
481 }
482 }
483
484 @Override
485 public int getGroupThreadsCount(
486 long groupId, long userId, boolean subscribed,
487 QueryDefinition queryDefinition)
488 throws SystemException {
489
490 return getGroupThreadsCount(
491 groupId, userId, subscribed, true, queryDefinition);
492 }
493
494
498 @Override
499 public int getGroupThreadsCount(long groupId, long userId, int status)
500 throws SystemException {
501
502 QueryDefinition queryDefinition = new QueryDefinition(status);
503
504 return getGroupThreadsCount(groupId, userId, false, queryDefinition);
505 }
506
507
511 @Override
512 public int getGroupThreadsCount(
513 long groupId, long userId, int status, boolean subscribed)
514 throws SystemException {
515
516 QueryDefinition queryDefinition = new QueryDefinition(status);
517
518 return getGroupThreadsCount(
519 groupId, userId, subscribed, true, queryDefinition);
520 }
521
522
526 @Override
527 public int getGroupThreadsCount(
528 long groupId, long userId, int status, boolean subscribed,
529 boolean includeAnonymous)
530 throws SystemException {
531
532 QueryDefinition queryDefinition = new QueryDefinition(status);
533
534 return getGroupThreadsCount(
535 groupId, userId, subscribed, includeAnonymous, queryDefinition);
536 }
537
538 @Override
539 public int getGroupThreadsCount(
540 long groupId, long userId, QueryDefinition queryDefinition)
541 throws SystemException {
542
543 return getGroupThreadsCount(groupId, userId, false, queryDefinition);
544 }
545
546 @Override
547 public int getGroupThreadsCount(
548 long groupId, QueryDefinition queryDefinition)
549 throws SystemException {
550
551 if (queryDefinition.isExcludeStatus()) {
552 return mbThreadPersistence.countByG_NotC_NotS(
553 groupId, MBCategoryConstants.DISCUSSION_CATEGORY_ID,
554 queryDefinition.getStatus());
555 }
556 else {
557 return mbThreadPersistence.countByG_NotC_S(
558 groupId, MBCategoryConstants.DISCUSSION_CATEGORY_ID,
559 queryDefinition.getStatus());
560 }
561 }
562
563 @Override
564 public List<MBThread> getNoAssetThreads() throws SystemException {
565 return mbThreadFinder.findByNoAssets();
566 }
567
568 @Override
569 public List<MBThread> getPriorityThreads(long categoryId, double priority)
570 throws PortalException, SystemException {
571
572 return getPriorityThreads(categoryId, priority, false);
573 }
574
575 @Override
576 public List<MBThread> getPriorityThreads(
577 long categoryId, double priority, boolean inherit)
578 throws PortalException, SystemException {
579
580 if (!inherit) {
581 return mbThreadPersistence.findByC_P(categoryId, priority);
582 }
583
584 List<MBThread> threads = new ArrayList<MBThread>();
585
586 while ((categoryId != MBCategoryConstants.DEFAULT_PARENT_CATEGORY_ID) &&
587 (categoryId != MBCategoryConstants.DISCUSSION_CATEGORY_ID)) {
588
589 threads.addAll(
590 0, mbThreadPersistence.findByC_P(categoryId, priority));
591
592 MBCategory category = mbCategoryPersistence.findByPrimaryKey(
593 categoryId);
594
595 categoryId = category.getParentCategoryId();
596 }
597
598 return threads;
599 }
600
601 @Override
602 public MBThread getThread(long threadId)
603 throws PortalException, SystemException {
604
605 return mbThreadPersistence.findByPrimaryKey(threadId);
606 }
607
608 @Override
609 public List<MBThread> getThreads(
610 long groupId, long categoryId, int status, int start, int end)
611 throws SystemException {
612
613 if (status == WorkflowConstants.STATUS_ANY) {
614 return mbThreadPersistence.findByG_C(
615 groupId, categoryId, start, end);
616 }
617 else {
618 return mbThreadPersistence.findByG_C_S(
619 groupId, categoryId, status, start, end);
620 }
621 }
622
623 @Override
624 public int getThreadsCount(long groupId, long categoryId, int status)
625 throws SystemException {
626
627 if (status == WorkflowConstants.STATUS_ANY) {
628 return mbThreadPersistence.countByG_C(groupId, categoryId);
629 }
630 else {
631 return mbThreadPersistence.countByG_C_S(
632 groupId, categoryId, status);
633 }
634 }
635
636 @Override
637 public boolean hasAnswerMessage(long threadId) throws SystemException {
638 int count = mbMessagePersistence.countByT_A(threadId, true);
639
640 if (count > 0) {
641 return true;
642 }
643 else {
644 return false;
645 }
646 }
647
648 @BufferedIncrement(
649 configuration = "MBThread", incrementClass = NumberIncrement.class)
650 @Override
651 public MBThread incrementViewCounter(long threadId, int increment)
652 throws PortalException, SystemException {
653
654 MBThread thread = mbThreadPersistence.findByPrimaryKey(threadId);
655
656 if (ExportImportThreadLocal.isImportInProcess()) {
657 return thread;
658 }
659
660 thread.setViewCount(thread.getViewCount() + increment);
661
662 mbThreadPersistence.update(thread);
663
664 return thread;
665 }
666
667 @Override
668 public void moveDependentsToTrash(
669 long groupId, long threadId, long trashEntryId)
670 throws PortalException, SystemException {
671
672 Set<Long> userIds = new HashSet<Long>();
673
674 List<MBMessage> messages = mbMessageLocalService.getThreadMessages(
675 threadId, WorkflowConstants.STATUS_ANY);
676
677 for (MBMessage message : messages) {
678
679
680
681 if (message.isDiscussion()) {
682 continue;
683 }
684
685 int oldStatus = message.getStatus();
686
687 message.setStatus(WorkflowConstants.STATUS_IN_TRASH);
688
689 mbMessagePersistence.update(message);
690
691 userIds.add(message.getUserId());
692
693
694
695 int status = oldStatus;
696
697 if (oldStatus == WorkflowConstants.STATUS_PENDING) {
698 status = WorkflowConstants.STATUS_DRAFT;
699 }
700
701 if (oldStatus != WorkflowConstants.STATUS_APPROVED) {
702 trashVersionLocalService.addTrashVersion(
703 trashEntryId, MBMessage.class.getName(),
704 message.getMessageId(), status);
705 }
706
707
708
709 if (oldStatus == WorkflowConstants.STATUS_APPROVED) {
710 assetEntryLocalService.updateVisible(
711 MBMessage.class.getName(), message.getMessageId(), false);
712 }
713
714
715
716 Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
717 MBMessage.class);
718
719 indexer.reindex(message);
720
721
722
723 if (oldStatus == WorkflowConstants.STATUS_PENDING) {
724 workflowInstanceLinkLocalService.deleteWorkflowInstanceLink(
725 message.getCompanyId(), message.getGroupId(),
726 MBMessage.class.getName(), message.getMessageId());
727 }
728 }
729
730
731
732 for (long userId : userIds) {
733 mbStatsUserLocalService.updateStatsUser(groupId, userId);
734 }
735 }
736
737 @Override
738 public MBThread moveThread(long groupId, long categoryId, long threadId)
739 throws PortalException, SystemException {
740
741 MBThread thread = mbThreadPersistence.findByPrimaryKey(threadId);
742
743 long oldCategoryId = thread.getCategoryId();
744
745 MBCategory oldCategory = null;
746
747 if (oldCategoryId != MBCategoryConstants.DEFAULT_PARENT_CATEGORY_ID) {
748 oldCategory = mbCategoryPersistence.fetchByPrimaryKey(
749 oldCategoryId);
750 }
751
752 MBCategory category = null;
753
754 if (categoryId != MBCategoryConstants.DEFAULT_PARENT_CATEGORY_ID) {
755 category = mbCategoryPersistence.fetchByPrimaryKey(categoryId);
756 }
757
758
759
760 thread.setModifiedDate(new Date());
761 thread.setCategoryId(categoryId);
762
763 mbThreadPersistence.update(thread);
764
765
766
767 List<MBMessage> messages = mbMessagePersistence.findByG_C_T(
768 groupId, oldCategoryId, thread.getThreadId());
769
770 for (MBMessage message : messages) {
771 message.setCategoryId(categoryId);
772
773 mbMessagePersistence.update(message);
774
775
776
777 if (!message.isDiscussion()) {
778 Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
779 MBMessage.class);
780
781 indexer.reindex(message);
782 }
783 }
784
785
786
787 if ((oldCategory != null) && (categoryId != oldCategoryId)) {
788 MBUtil.updateCategoryStatistics(
789 oldCategory.getCompanyId(), oldCategory.getCategoryId());
790 }
791
792 if ((category != null) && (categoryId != oldCategoryId)) {
793 MBUtil.updateCategoryStatistics(
794 category.getCompanyId(), category.getCategoryId());
795 }
796
797
798
799 Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
800 MBThread.class);
801
802 indexer.reindex(thread);
803
804 return thread;
805 }
806
807 @Override
808 public MBThread moveThreadFromTrash(
809 long userId, long categoryId, long threadId)
810 throws PortalException, SystemException {
811
812 MBThread thread = mbThreadPersistence.findByPrimaryKey(threadId);
813
814 TrashEntry trashEntry = thread.getTrashEntry();
815
816 if (trashEntry.isTrashEntry(MBThread.class, threadId)) {
817 restoreThreadFromTrash(userId, threadId);
818 }
819 else {
820
821
822
823 TrashVersion trashVersion =
824 trashVersionLocalService.fetchVersion(
825 trashEntry.getEntryId(), MBThread.class.getName(),
826 thread.getThreadId());
827
828 int status = WorkflowConstants.STATUS_APPROVED;
829
830 if (trashVersion != null) {
831 status = trashVersion.getStatus();
832 }
833
834 updateStatus(userId, threadId, status);
835
836
837
838 if (trashVersion != null) {
839 trashVersionLocalService.deleteTrashVersion(trashVersion);
840 }
841
842
843
844 restoreDependentsFromTrash(
845 thread.getGroupId(), threadId, trashEntry.getEntryId());
846 }
847
848 return moveThread(thread.getGroupId(), categoryId, threadId);
849 }
850
851 @Override
852 public void moveThreadsToTrash(long groupId, long userId)
853 throws PortalException, SystemException {
854
855 List<MBThread> threads = mbThreadPersistence.findByGroupId(groupId);
856
857 for (MBThread thread : threads) {
858 moveThreadToTrash(userId, thread);
859 }
860 }
861
862 @Override
863 public MBThread moveThreadToTrash(long userId, long threadId)
864 throws PortalException, SystemException {
865
866 MBThread thread = mbThreadPersistence.findByPrimaryKey(threadId);
867
868 return moveThreadToTrash(userId, thread);
869 }
870
871 @Override
872 public MBThread moveThreadToTrash(long userId, MBThread thread)
873 throws PortalException, SystemException {
874
875
876
877 if (thread.getCategoryId() ==
878 MBCategoryConstants.DISCUSSION_CATEGORY_ID) {
879
880 return thread;
881 }
882
883 int oldStatus = thread.getStatus();
884
885 if (oldStatus == WorkflowConstants.STATUS_PENDING) {
886 thread.setStatus(WorkflowConstants.STATUS_DRAFT);
887
888 mbThreadPersistence.update(thread);
889 }
890
891 thread = updateStatus(
892 userId, thread.getThreadId(), WorkflowConstants.STATUS_IN_TRASH);
893
894
895
896 TrashEntry trashEntry = trashEntryLocalService.addTrashEntry(
897 userId, thread.getGroupId(), MBThread.class.getName(),
898 thread.getThreadId(), thread.getUuid(), null, oldStatus, null,
899 null);
900
901
902
903 moveDependentsToTrash(
904 thread.getGroupId(), thread.getThreadId(), trashEntry.getEntryId());
905
906
907
908 MBMessage message = mbMessageLocalService.getMBMessage(
909 thread.getRootMessageId());
910
911 JSONObject extraDataJSONObject = JSONFactoryUtil.createJSONObject();
912
913 extraDataJSONObject.put("rootMessageId", thread.getRootMessageId());
914 extraDataJSONObject.put("title", message.getSubject());
915
916 socialActivityLocalService.addActivity(
917 userId, thread.getGroupId(), MBThread.class.getName(),
918 thread.getThreadId(), SocialActivityConstants.TYPE_MOVE_TO_TRASH,
919 extraDataJSONObject.toString(), 0);
920
921 return thread;
922 }
923
924 @Override
925 public void restoreDependentsFromTrash(
926 long groupId, long threadId, long trashEntryId)
927 throws PortalException, SystemException {
928
929 Set<Long> userIds = new HashSet<Long>();
930
931 List<MBMessage> messages = mbMessageLocalService.getThreadMessages(
932 threadId, WorkflowConstants.STATUS_ANY);
933
934 for (MBMessage message : messages) {
935
936
937
938 if (message.isDiscussion()) {
939 continue;
940 }
941
942 TrashVersion trashVersion = trashVersionLocalService.fetchVersion(
943 trashEntryId, MBMessage.class.getName(),
944 message.getMessageId());
945
946 int oldStatus = WorkflowConstants.STATUS_APPROVED;
947
948 if (trashVersion != null) {
949 oldStatus = trashVersion.getStatus();
950 }
951
952 message.setStatus(oldStatus);
953
954 mbMessagePersistence.update(message);
955
956 userIds.add(message.getUserId());
957
958
959
960 if (trashVersion != null) {
961 trashVersionLocalService.deleteTrashVersion(trashVersion);
962 }
963
964
965
966 if (oldStatus == WorkflowConstants.STATUS_APPROVED) {
967 assetEntryLocalService.updateVisible(
968 MBMessage.class.getName(), message.getMessageId(), true);
969 }
970
971
972
973 Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
974 MBMessage.class);
975
976 indexer.reindex(message);
977 }
978
979
980
981 for (long userId : userIds) {
982 mbStatsUserLocalService.updateStatsUser(groupId, userId);
983 }
984 }
985
986 @Override
987 public void restoreThreadFromTrash(long userId, long threadId)
988 throws PortalException, SystemException {
989
990
991
992 MBThread thread = getThread(threadId);
993
994 if (thread.getCategoryId() ==
995 MBCategoryConstants.DISCUSSION_CATEGORY_ID) {
996
997 return;
998 }
999
1000 TrashEntry trashEntry = trashEntryLocalService.getEntry(
1001 MBThread.class.getName(), threadId);
1002
1003 updateStatus(userId, threadId, trashEntry.getStatus());
1004
1005
1006
1007 restoreDependentsFromTrash(
1008 thread.getGroupId(), threadId, trashEntry.getEntryId());
1009
1010
1011
1012 trashEntryLocalService.deleteEntry(trashEntry.getEntryId());
1013
1014
1015
1016 MBMessage message = mbMessageLocalService.getMBMessage(
1017 thread.getRootMessageId());
1018
1019 JSONObject extraDataJSONObject = JSONFactoryUtil.createJSONObject();
1020
1021 extraDataJSONObject.put("rootMessageId", thread.getRootMessageId());
1022 extraDataJSONObject.put("title", message.getSubject());
1023
1024 socialActivityLocalService.addActivity(
1025 userId, thread.getGroupId(), MBThread.class.getName(),
1026 thread.getThreadId(),
1027 SocialActivityConstants.TYPE_RESTORE_FROM_TRASH,
1028 extraDataJSONObject.toString(), 0);
1029 }
1030
1031 @Override
1032 public Hits search(
1033 long groupId, long userId, long creatorUserId, int status,
1034 int start, int end)
1035 throws PortalException, SystemException {
1036
1037 return search(groupId, userId, creatorUserId, 0, 0, status, start, end);
1038 }
1039
1040 @Override
1041 public Hits search(
1042 long groupId, long userId, long creatorUserId, long startDate,
1043 long endDate, int status, int start, int end)
1044 throws PortalException, SystemException {
1045
1046 Indexer indexer = IndexerRegistryUtil.getIndexer(
1047 MBThread.class.getName());
1048
1049 SearchContext searchContext = new SearchContext();
1050
1051 searchContext.setAttribute(Field.STATUS, status);
1052
1053 if (endDate > 0) {
1054 searchContext.setAttribute("endDate", endDate);
1055 }
1056
1057 searchContext.setAttribute("paginationType", "none");
1058
1059 if (creatorUserId > 0) {
1060 searchContext.setAttribute(
1061 "participantUserId", String.valueOf(creatorUserId));
1062 }
1063
1064 if (startDate > 0) {
1065 searchContext.setAttribute("startDate", startDate);
1066 }
1067
1068 Group group = groupLocalService.getGroup(groupId);
1069
1070 searchContext.setCompanyId(group.getCompanyId());
1071
1072 searchContext.setEnd(end);
1073 searchContext.setGroupIds(new long[] {groupId});
1074 searchContext.setSorts(new Sort("lastPostDate", true));
1075 searchContext.setStart(start);
1076 searchContext.setUserId(userId);
1077
1078 return indexer.search(searchContext);
1079 }
1080
1081 @Override
1082 public MBThread splitThread(
1083 long messageId, String subject, ServiceContext serviceContext)
1084 throws PortalException, SystemException {
1085
1086 MBMessage message = mbMessagePersistence.findByPrimaryKey(messageId);
1087
1088 if (message.isRoot()) {
1089 throw new SplitThreadException();
1090 }
1091
1092 MBCategory category = message.getCategory();
1093 MBThread oldThread = message.getThread();
1094 MBMessage rootMessage = mbMessagePersistence.findByPrimaryKey(
1095 oldThread.getRootMessageId());
1096
1097
1098
1099 mbMessageLocalService.updateAnswer(message, false, true);
1100
1101
1102
1103 MBThread thread = addThread(
1104 message.getCategoryId(), message, serviceContext);
1105
1106 oldThread.setModifiedDate(serviceContext.getModifiedDate(new Date()));
1107
1108 mbThreadPersistence.update(oldThread);
1109
1110
1111
1112 if (Validator.isNotNull(subject)) {
1113 MBMessageDisplay messageDisplay =
1114 mbMessageService.getMessageDisplay(
1115 messageId, WorkflowConstants.STATUS_ANY,
1116 MBThreadConstants.THREAD_VIEW_TREE, false);
1117
1118 MBTreeWalker treeWalker = messageDisplay.getTreeWalker();
1119
1120 List<MBMessage> messages = treeWalker.getMessages();
1121
1122 int[] range = treeWalker.getChildrenRange(message);
1123
1124 for (int i = range[0]; i < range[1]; i++) {
1125 MBMessage curMessage = messages.get(i);
1126
1127 String oldSubject = message.getSubject();
1128 String curSubject = curMessage.getSubject();
1129
1130 if (oldSubject.startsWith("RE: ")) {
1131 curSubject = StringUtil.replace(
1132 curSubject, rootMessage.getSubject(), subject);
1133 }
1134 else {
1135 curSubject = StringUtil.replace(
1136 curSubject, oldSubject, subject);
1137 }
1138
1139 curMessage.setSubject(curSubject);
1140
1141 mbMessagePersistence.update(curMessage);
1142 }
1143
1144 message.setSubject(subject);
1145 }
1146
1147 message.setThreadId(thread.getThreadId());
1148 message.setRootMessageId(thread.getRootMessageId());
1149 message.setParentMessageId(0);
1150
1151 mbMessagePersistence.update(message);
1152
1153
1154
1155 if (!message.isDiscussion()) {
1156 Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
1157 MBMessage.class);
1158
1159 indexer.reindex(message);
1160 }
1161
1162
1163
1164 moveChildrenMessages(message, category, oldThread.getThreadId());
1165
1166
1167
1168 MBUtil.updateThreadMessageCount(
1169 thread.getCompanyId(), thread.getThreadId());
1170
1171
1172
1173 MBUtil.updateThreadMessageCount(
1174 oldThread.getCompanyId(), oldThread.getThreadId());
1175
1176
1177
1178 if ((message.getCategoryId() !=
1179 MBCategoryConstants.DEFAULT_PARENT_CATEGORY_ID) &&
1180 (message.getCategoryId() !=
1181 MBCategoryConstants.DISCUSSION_CATEGORY_ID)) {
1182
1183 MBUtil.updateCategoryThreadCount(
1184 category.getCompanyId(), category.getCategoryId());
1185 }
1186
1187
1188
1189 Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
1190 MBThread.class);
1191
1192 indexer.reindex(oldThread);
1193 indexer.reindex(message.getThread());
1194
1195 return thread;
1196 }
1197
1198 @Override
1199 public void updateQuestion(long threadId, boolean question)
1200 throws PortalException, SystemException {
1201
1202 MBThread thread = mbThreadPersistence.findByPrimaryKey(threadId);
1203
1204 if (thread.isQuestion() == question) {
1205 return;
1206 }
1207
1208 thread.setQuestion(question);
1209
1210 mbThreadPersistence.update(thread);
1211
1212 if (!question) {
1213 MBMessage message = mbMessagePersistence.findByPrimaryKey(
1214 thread.getRootMessageId());
1215
1216 mbMessageLocalService.updateAnswer(message, false, true);
1217 }
1218 }
1219
1220 @Override
1221 public MBThread updateStatus(long userId, long threadId, int status)
1222 throws PortalException, SystemException {
1223
1224 MBThread thread = mbThreadPersistence.findByPrimaryKey(threadId);
1225
1226
1227
1228 User user = userPersistence.findByPrimaryKey(userId);
1229
1230 Date now = new Date();
1231
1232 thread.setModifiedDate(now);
1233 thread.setStatus(status);
1234 thread.setStatusByUserId(user.getUserId());
1235 thread.setStatusByUserName(user.getFullName());
1236 thread.setStatusDate(now);
1237
1238 mbThreadPersistence.update(thread);
1239
1240
1241
1242 if (thread.getCategoryId() !=
1243 MBCategoryConstants.DEFAULT_PARENT_CATEGORY_ID) {
1244
1245
1246
1247 MBCategory category = mbCategoryPersistence.fetchByPrimaryKey(
1248 thread.getCategoryId());
1249
1250 if (category != null) {
1251 MBUtil.updateCategoryStatistics(
1252 category.getCompanyId(), category.getCategoryId());
1253 }
1254 }
1255
1256
1257
1258 Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
1259 MBThread.class);
1260
1261 indexer.reindex(thread);
1262
1263 return thread;
1264 }
1265
1266
1270 @Override
1271 public MBThread updateThread(long threadId, int viewCount)
1272 throws PortalException, SystemException {
1273
1274 MBThread thread = mbThreadPersistence.findByPrimaryKey(threadId);
1275
1276 thread.setViewCount(viewCount);
1277
1278 mbThreadPersistence.update(thread);
1279
1280 return thread;
1281 }
1282
1283 protected void moveChildrenMessages(
1284 MBMessage parentMessage, MBCategory category, long oldThreadId)
1285 throws PortalException, SystemException {
1286
1287 List<MBMessage> messages = mbMessagePersistence.findByT_P(
1288 oldThreadId, parentMessage.getMessageId());
1289
1290 for (MBMessage message : messages) {
1291 message.setCategoryId(parentMessage.getCategoryId());
1292 message.setThreadId(parentMessage.getThreadId());
1293 message.setRootMessageId(parentMessage.getRootMessageId());
1294
1295 mbMessagePersistence.update(message);
1296
1297 if (!message.isDiscussion()) {
1298 Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
1299 MBMessage.class);
1300
1301 indexer.reindex(message);
1302 }
1303
1304 moveChildrenMessages(message, category, oldThreadId);
1305 }
1306 }
1307
1308 }