001
014
015 package com.liferay.portlet.bookmarks.service.impl;
016
017 import com.liferay.portal.kernel.exception.PortalException;
018 import com.liferay.portal.kernel.exception.SystemException;
019 import com.liferay.portal.kernel.json.JSONFactoryUtil;
020 import com.liferay.portal.kernel.json.JSONObject;
021 import com.liferay.portal.kernel.log.Log;
022 import com.liferay.portal.kernel.log.LogFactoryUtil;
023 import com.liferay.portal.kernel.search.Field;
024 import com.liferay.portal.kernel.search.Hits;
025 import com.liferay.portal.kernel.search.Indexable;
026 import com.liferay.portal.kernel.search.IndexableType;
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.util.ArrayUtil;
032 import com.liferay.portal.kernel.util.ContentTypes;
033 import com.liferay.portal.kernel.util.OrderByComparator;
034 import com.liferay.portal.kernel.util.StringPool;
035 import com.liferay.portal.kernel.util.Validator;
036 import com.liferay.portal.kernel.workflow.WorkflowConstants;
037 import com.liferay.portal.model.Group;
038 import com.liferay.portal.model.ResourceConstants;
039 import com.liferay.portal.model.User;
040 import com.liferay.portal.service.ServiceContext;
041 import com.liferay.portal.service.ServiceContextUtil;
042 import com.liferay.portal.util.Portal;
043 import com.liferay.portal.util.PortletKeys;
044 import com.liferay.portal.util.SubscriptionSender;
045 import com.liferay.portlet.asset.model.AssetEntry;
046 import com.liferay.portlet.asset.model.AssetLinkConstants;
047 import com.liferay.portlet.bookmarks.EntryURLException;
048 import com.liferay.portlet.bookmarks.model.BookmarksEntry;
049 import com.liferay.portlet.bookmarks.model.BookmarksFolder;
050 import com.liferay.portlet.bookmarks.model.BookmarksFolderConstants;
051 import com.liferay.portlet.bookmarks.service.base.BookmarksEntryLocalServiceBaseImpl;
052 import com.liferay.portlet.bookmarks.social.BookmarksActivityKeys;
053 import com.liferay.portlet.bookmarks.util.BookmarksUtil;
054 import com.liferay.portlet.bookmarks.util.comparator.EntryModifiedDateComparator;
055 import com.liferay.portlet.social.model.SocialActivityConstants;
056 import com.liferay.portlet.trash.model.TrashEntry;
057
058 import java.util.ArrayList;
059 import java.util.Date;
060 import java.util.List;
061 import java.util.Locale;
062 import java.util.Map;
063
064 import javax.portlet.PortletPreferences;
065
066
071 public class BookmarksEntryLocalServiceImpl
072 extends BookmarksEntryLocalServiceBaseImpl {
073
074 @Indexable(type = IndexableType.REINDEX)
075 @Override
076 public BookmarksEntry addEntry(
077 long userId, long groupId, long folderId, String name, String url,
078 String description, ServiceContext serviceContext)
079 throws PortalException, SystemException {
080
081
082
083 User user = userPersistence.findByPrimaryKey(userId);
084
085 if (Validator.isNull(name)) {
086 name = url;
087 }
088
089 Date now = new Date();
090
091 validate(url);
092
093 long entryId = counterLocalService.increment();
094
095 BookmarksEntry entry = bookmarksEntryPersistence.create(entryId);
096
097 entry.setUuid(serviceContext.getUuid());
098 entry.setGroupId(groupId);
099 entry.setCompanyId(user.getCompanyId());
100 entry.setUserId(user.getUserId());
101 entry.setUserName(user.getFullName());
102 entry.setCreateDate(serviceContext.getCreateDate(now));
103 entry.setModifiedDate(serviceContext.getModifiedDate(now));
104 entry.setFolderId(folderId);
105 entry.setName(name);
106 entry.setUrl(url);
107 entry.setDescription(description);
108 entry.setExpandoBridgeAttributes(serviceContext);
109
110 bookmarksEntryPersistence.update(entry);
111
112
113
114 resourceLocalService.addModelResources(entry, serviceContext);
115
116
117
118 updateAsset(
119 userId, entry, serviceContext.getAssetCategoryIds(),
120 serviceContext.getAssetTagNames(),
121 serviceContext.getAssetLinkEntryIds());
122
123
124
125 JSONObject extraDataJSONObject = JSONFactoryUtil.createJSONObject();
126
127 extraDataJSONObject.put("title", entry.getName());
128
129 socialActivityLocalService.addActivity(
130 userId, groupId, BookmarksEntry.class.getName(), entryId,
131 BookmarksActivityKeys.ADD_ENTRY, extraDataJSONObject.toString(), 0);
132
133
134
135 notifySubscribers(entry, serviceContext);
136
137 return entry;
138 }
139
140 @Override
141 public void deleteEntries(long groupId, long folderId)
142 throws PortalException, SystemException {
143
144 deleteEntries(groupId, folderId, true);
145 }
146
147 @Override
148 public void deleteEntries(
149 long groupId, long folderId, boolean includeTrashedEntries)
150 throws PortalException, SystemException {
151
152 List<BookmarksEntry> entries = bookmarksEntryPersistence.findByG_F(
153 groupId, folderId);
154
155 for (BookmarksEntry entry : entries) {
156 if (includeTrashedEntries || !entry.isInTrash()) {
157 bookmarksEntryLocalService.deleteEntry(entry);
158 }
159 }
160 }
161
162 @Indexable(type = IndexableType.DELETE)
163 @Override
164 public BookmarksEntry deleteEntry(BookmarksEntry entry)
165 throws PortalException, SystemException {
166
167
168
169 bookmarksEntryPersistence.remove(entry);
170
171
172
173 resourceLocalService.deleteResource(
174 entry, ResourceConstants.SCOPE_INDIVIDUAL);
175
176
177
178 assetEntryLocalService.deleteEntry(
179 BookmarksEntry.class.getName(), entry.getEntryId());
180
181
182
183 expandoRowLocalService.deleteRows(entry.getEntryId());
184
185
186
187 subscriptionLocalService.deleteSubscriptions(
188 entry.getCompanyId(), BookmarksEntry.class.getName(),
189 entry.getEntryId());
190
191
192
193 trashEntryLocalService.deleteEntry(
194 BookmarksEntry.class.getName(), entry.getEntryId());
195
196 return entry;
197 }
198
199 @Indexable(type = IndexableType.DELETE)
200 @Override
201 public BookmarksEntry deleteEntry(long entryId)
202 throws PortalException, SystemException {
203
204 BookmarksEntry entry = bookmarksEntryPersistence.findByPrimaryKey(
205 entryId);
206
207 return deleteEntry(entry);
208 }
209
210 @Override
211 public List<BookmarksEntry> getEntries(
212 long groupId, long folderId, int start, int end)
213 throws SystemException {
214
215 return bookmarksEntryPersistence.findByG_F_S(
216 groupId, folderId, WorkflowConstants.STATUS_APPROVED, start, end);
217 }
218
219 @Override
220 public List<BookmarksEntry> getEntries(
221 long groupId, long folderId, int start, int end,
222 OrderByComparator orderByComparator)
223 throws SystemException {
224
225 return bookmarksEntryPersistence.findByG_F_S(
226 groupId, folderId, WorkflowConstants.STATUS_APPROVED, start, end,
227 orderByComparator);
228 }
229
230 @Override
231 public int getEntriesCount(long groupId, long folderId)
232 throws SystemException {
233
234 return bookmarksEntryPersistence.countByG_F_S(
235 groupId, folderId, WorkflowConstants.STATUS_APPROVED);
236 }
237
238 @Override
239 public BookmarksEntry getEntry(long entryId)
240 throws PortalException, SystemException {
241
242 return bookmarksEntryPersistence.findByPrimaryKey(entryId);
243 }
244
245 @Override
246 public int getFoldersEntriesCount(long groupId, List<Long> folderIds)
247 throws SystemException {
248
249 return bookmarksEntryPersistence.countByG_F_S(
250 groupId,
251 ArrayUtil.toArray(folderIds.toArray(new Long[folderIds.size()])),
252 WorkflowConstants.STATUS_APPROVED);
253 }
254
255 @Override
256 public List<BookmarksEntry> getGroupEntries(
257 long groupId, int start, int end)
258 throws SystemException {
259
260 return bookmarksEntryPersistence.findByG_S(
261 groupId, WorkflowConstants.STATUS_APPROVED, start, end,
262 new EntryModifiedDateComparator());
263 }
264
265 @Override
266 public List<BookmarksEntry> getGroupEntries(
267 long groupId, long userId, int start, int end)
268 throws SystemException {
269
270 OrderByComparator orderByComparator = new EntryModifiedDateComparator();
271
272 if (userId <= 0) {
273 return bookmarksEntryPersistence.findByG_S(
274 groupId, WorkflowConstants.STATUS_APPROVED, start, end,
275 orderByComparator);
276 }
277 else {
278 return bookmarksEntryPersistence.findByG_U_S(
279 groupId, userId, WorkflowConstants.STATUS_APPROVED, start, end,
280 orderByComparator);
281 }
282 }
283
284 @Override
285 public int getGroupEntriesCount(long groupId) throws SystemException {
286 return bookmarksEntryPersistence.countByG_S(
287 groupId, WorkflowConstants.STATUS_APPROVED);
288 }
289
290 @Override
291 public int getGroupEntriesCount(long groupId, long userId)
292 throws SystemException {
293
294 if (userId <= 0) {
295 return getGroupEntriesCount(groupId);
296 }
297 else {
298 return bookmarksEntryPersistence.countByG_U_S(
299 groupId, userId, WorkflowConstants.STATUS_APPROVED);
300 }
301 }
302
303 @Override
304 public List<BookmarksEntry> getNoAssetEntries() throws SystemException {
305 return bookmarksEntryFinder.findByNoAssets();
306 }
307
308 @Indexable(type = IndexableType.REINDEX)
309 @Override
310 public BookmarksEntry moveEntry(long entryId, long parentFolderId)
311 throws PortalException, SystemException {
312
313 BookmarksEntry entry = getBookmarksEntry(entryId);
314
315 entry.setFolderId(parentFolderId);
316
317 bookmarksEntryPersistence.update(entry);
318
319 return entry;
320 }
321
322 @Override
323 public BookmarksEntry moveEntryFromTrash(
324 long userId, long entryId, long parentFolderId)
325 throws PortalException, SystemException {
326
327 BookmarksEntry entry = getBookmarksEntry(entryId);
328
329 if (entry.isInTrash()) {
330 restoreEntryFromTrash(userId, entryId);
331 }
332 else {
333 updateStatus(userId, entry, entry.getStatus());
334 }
335
336 return bookmarksEntryLocalService.moveEntry(entryId, parentFolderId);
337 }
338
339 @Indexable(type = IndexableType.REINDEX)
340 @Override
341 public BookmarksEntry moveEntryToTrash(long userId, BookmarksEntry entry)
342 throws PortalException, SystemException {
343
344 return updateStatus(userId, entry, WorkflowConstants.STATUS_IN_TRASH);
345 }
346
347 @Indexable(type = IndexableType.REINDEX)
348 @Override
349 public BookmarksEntry moveEntryToTrash(long userId, long entryId)
350 throws PortalException, SystemException {
351
352 BookmarksEntry entry = getEntry(entryId);
353
354 return moveEntryToTrash(userId, entry);
355 }
356
357 @Override
358 public BookmarksEntry openEntry(long userId, BookmarksEntry entry)
359 throws SystemException {
360
361 entry.setVisits(entry.getVisits() + 1);
362
363 bookmarksEntryPersistence.update(entry);
364
365 assetEntryLocalService.incrementViewCounter(
366 userId, BookmarksEntry.class.getName(), entry.getEntryId(), 1);
367
368 return entry;
369 }
370
371 @Override
372 public BookmarksEntry openEntry(long userId, long entryId)
373 throws PortalException, SystemException {
374
375 BookmarksEntry entry = bookmarksEntryPersistence.findByPrimaryKey(
376 entryId);
377
378 return openEntry(userId, entry);
379 }
380
381 @Indexable(type = IndexableType.REINDEX)
382 @Override
383 public BookmarksEntry restoreEntryFromTrash(long userId, long entryId)
384 throws PortalException, SystemException {
385
386 BookmarksEntry entry = bookmarksEntryPersistence.findByPrimaryKey(
387 entryId);
388
389 TrashEntry trashEntry = trashEntryLocalService.getEntry(
390 BookmarksEntry.class.getName(), entryId);
391
392 return updateStatus(userId, entry, trashEntry.getStatus());
393 }
394
395 @Override
396 public Hits search(
397 long groupId, long userId, long creatorUserId, int status,
398 int start, int end)
399 throws PortalException, SystemException {
400
401 Indexer indexer = IndexerRegistryUtil.getIndexer(
402 BookmarksEntry.class.getName());
403
404 SearchContext searchContext = new SearchContext();
405
406 searchContext.setAttribute(Field.STATUS, status);
407
408 if (creatorUserId > 0) {
409 searchContext.setAttribute(
410 Field.USER_ID, String.valueOf(creatorUserId));
411 }
412
413 searchContext.setAttribute("paginationType", "none");
414
415 Group group = groupLocalService.getGroup(groupId);
416
417 searchContext.setCompanyId(group.getCompanyId());
418
419 searchContext.setEnd(end);
420 searchContext.setGroupIds(new long[] {groupId});
421 searchContext.setSorts(new Sort(Field.MODIFIED_DATE, true));
422 searchContext.setStart(start);
423 searchContext.setUserId(userId);
424
425 return indexer.search(searchContext);
426 }
427
428 @Override
429 public void subscribeEntry(long userId, long entryId)
430 throws PortalException, SystemException {
431
432 BookmarksEntry entry = bookmarksEntryPersistence.findByPrimaryKey(
433 entryId);
434
435 subscriptionLocalService.addSubscription(
436 userId, entry.getGroupId(), BookmarksEntry.class.getName(),
437 entryId);
438 }
439
440 @Override
441 public void unsubscribeEntry(long userId, long entryId)
442 throws PortalException, SystemException {
443
444 subscriptionLocalService.deleteSubscription(
445 userId, BookmarksEntry.class.getName(), entryId);
446 }
447
448 @Override
449 public void updateAsset(
450 long userId, BookmarksEntry entry, long[] assetCategoryIds,
451 String[] assetTagNames, long[] assetLinkEntryIds)
452 throws PortalException, SystemException {
453
454 AssetEntry assetEntry = assetEntryLocalService.updateEntry(
455 userId, entry.getGroupId(), entry.getCreateDate(),
456 entry.getModifiedDate(), BookmarksEntry.class.getName(),
457 entry.getEntryId(), entry.getUuid(), 0, assetCategoryIds,
458 assetTagNames, true, null, null, null, ContentTypes.TEXT_PLAIN,
459 entry.getName(), entry.getDescription(), null, entry.getUrl(), null,
460 0, 0, null, false);
461
462 assetLinkLocalService.updateLinks(
463 userId, assetEntry.getEntryId(), assetLinkEntryIds,
464 AssetLinkConstants.TYPE_RELATED);
465 }
466
467 @Indexable(type = IndexableType.REINDEX)
468 @Override
469 public BookmarksEntry updateEntry(
470 long userId, long entryId, long groupId, long folderId, String name,
471 String url, String description, ServiceContext serviceContext)
472 throws PortalException, SystemException {
473
474
475
476 BookmarksEntry entry = bookmarksEntryPersistence.findByPrimaryKey(
477 entryId);
478
479 if (Validator.isNull(name)) {
480 name = url;
481 }
482
483 validate(url);
484
485 entry.setModifiedDate(serviceContext.getModifiedDate(null));
486 entry.setFolderId(folderId);
487 entry.setName(name);
488 entry.setUrl(url);
489 entry.setDescription(description);
490 entry.setExpandoBridgeAttributes(serviceContext);
491
492 bookmarksEntryPersistence.update(entry);
493
494
495
496 updateAsset(
497 userId, entry, serviceContext.getAssetCategoryIds(),
498 serviceContext.getAssetTagNames(),
499 serviceContext.getAssetLinkEntryIds());
500
501
502
503 JSONObject extraDataJSONObject = JSONFactoryUtil.createJSONObject();
504
505 extraDataJSONObject.put("title", entry.getName());
506
507 socialActivityLocalService.addActivity(
508 userId, entry.getGroupId(), BookmarksEntry.class.getName(), entryId,
509 BookmarksActivityKeys.UPDATE_ENTRY, extraDataJSONObject.toString(),
510 0);
511
512
513
514 notifySubscribers(entry, serviceContext);
515
516 return entry;
517 }
518
519 @Override
520 public BookmarksEntry updateStatus(
521 long userId, BookmarksEntry entry, int status)
522 throws PortalException, SystemException {
523
524
525
526 User user = userPersistence.findByPrimaryKey(userId);
527
528 int oldStatus = entry.getStatus();
529
530 entry.setStatus(status);
531 entry.setStatusByUserId(userId);
532 entry.setStatusByUserName(user.getScreenName());
533 entry.setStatusDate(new Date());
534
535 bookmarksEntryPersistence.update(entry);
536
537 JSONObject extraDataJSONObject = JSONFactoryUtil.createJSONObject();
538
539 extraDataJSONObject.put("title", entry.getName());
540
541 if (status == WorkflowConstants.STATUS_APPROVED) {
542
543
544
545 assetEntryLocalService.updateVisible(
546 BookmarksEntry.class.getName(), entry.getEntryId(), true);
547
548
549
550 socialActivityLocalService.addActivity(
551 userId, entry.getGroupId(), BookmarksEntry.class.getName(),
552 entry.getEntryId(),
553 SocialActivityConstants.TYPE_RESTORE_FROM_TRASH,
554 extraDataJSONObject.toString(), 0);
555 }
556 else if (status == WorkflowConstants.STATUS_IN_TRASH) {
557
558
559
560 assetEntryLocalService.updateVisible(
561 BookmarksEntry.class.getName(), entry.getEntryId(), false);
562
563
564
565 socialActivityLocalService.addActivity(
566 userId, entry.getGroupId(), BookmarksEntry.class.getName(),
567 entry.getEntryId(), SocialActivityConstants.TYPE_MOVE_TO_TRASH,
568 extraDataJSONObject.toString(), 0);
569 }
570
571
572
573 if (oldStatus == WorkflowConstants.STATUS_IN_TRASH) {
574 trashEntryLocalService.deleteEntry(
575 BookmarksEntry.class.getName(), entry.getEntryId());
576 }
577 else if (status == WorkflowConstants.STATUS_IN_TRASH) {
578 trashEntryLocalService.addTrashEntry(
579 userId, entry.getGroupId(), BookmarksEntry.class.getName(),
580 entry.getEntryId(), oldStatus, null, null);
581 }
582
583 return entry;
584 }
585
586 protected long getFolder(BookmarksEntry entry, long folderId)
587 throws SystemException {
588
589 if ((entry.getFolderId() != folderId) &&
590 (folderId != BookmarksFolderConstants.DEFAULT_PARENT_FOLDER_ID)) {
591
592 BookmarksFolder newFolder =
593 bookmarksFolderPersistence.fetchByPrimaryKey(folderId);
594
595 if ((newFolder == null) ||
596 (entry.getGroupId() != newFolder.getGroupId())) {
597
598 folderId = entry.getFolderId();
599 }
600 }
601
602 return folderId;
603 }
604
605 protected void notifySubscribers(
606 BookmarksEntry entry, ServiceContext serviceContext)
607 throws PortalException, SystemException {
608
609 String layoutFullURL = serviceContext.getLayoutFullURL();
610
611 if (Validator.isNull(layoutFullURL)) {
612 return;
613 }
614
615 PortletPreferences preferences =
616 ServiceContextUtil.getPortletPreferences(serviceContext);
617
618 if (preferences == null) {
619 long ownerId = entry.getGroupId();
620 int ownerType = PortletKeys.PREFS_OWNER_TYPE_GROUP;
621 long plid = PortletKeys.PREFS_PLID_SHARED;
622 String portletId = PortletKeys.BOOKMARKS;
623 String defaultPreferences = null;
624
625 preferences = portletPreferencesLocalService.getPreferences(
626 entry.getCompanyId(), ownerId, ownerType, plid, portletId,
627 defaultPreferences);
628 }
629
630 if ((serviceContext.isCommandAdd() &&
631 !BookmarksUtil.getEmailEntryAddedEnabled(preferences)) ||
632 (serviceContext.isCommandUpdate() &&
633 !BookmarksUtil.getEmailEntryUpdatedEnabled(preferences))) {
634
635 return;
636 }
637
638 String statusByUserName = StringPool.BLANK;
639
640 try {
641 User user = userLocalService.getUserById(
642 serviceContext.getGuestOrUserId());
643
644 statusByUserName = user.getFullName();
645 }
646 catch (Exception e) {
647 _log.error(e, e);
648 }
649
650 String entryURL =
651 layoutFullURL + Portal.FRIENDLY_URL_SEPARATOR + "bookmarks" +
652 StringPool.SLASH + entry.getEntryId();
653
654 String fromAddress = BookmarksUtil.getEmailFromAddress(
655 preferences, entry.getCompanyId());
656 String fromName = BookmarksUtil.getEmailFromName(
657 preferences, entry.getCompanyId());
658
659 Map<Locale, String> localizedSubjectMap = null;
660 Map<Locale, String> localizedBodyMap = null;
661
662 if (serviceContext.isCommandUpdate()) {
663 localizedSubjectMap = BookmarksUtil.getEmailEntryUpdatedSubjectMap(
664 preferences);
665 localizedBodyMap = BookmarksUtil.getEmailEntryUpdatedBodyMap(
666 preferences);
667 }
668 else {
669 localizedSubjectMap = BookmarksUtil.getEmailEntryAddedSubjectMap(
670 preferences);
671 localizedBodyMap = BookmarksUtil.getEmailEntryAddedBodyMap(
672 preferences);
673 }
674
675 SubscriptionSender subscriptionSender = new SubscriptionSender();
676
677 subscriptionSender.setCompanyId(entry.getCompanyId());
678 subscriptionSender.setContextAttributes(
679 "[$BOOKMARKS_ENTRY_STATUS_BY_USER_NAME$]", statusByUserName,
680 "[$BOOKMARKS_ENTRY_URL$]", entryURL);
681 subscriptionSender.setContextUserPrefix("BOOKMARKS_ENTRY");
682 subscriptionSender.setFrom(fromAddress, fromName);
683 subscriptionSender.setHtmlFormat(true);
684 subscriptionSender.setLocalizedBodyMap(localizedBodyMap);
685 subscriptionSender.setLocalizedSubjectMap(localizedSubjectMap);
686 subscriptionSender.setMailId("bookmarks_entry", entry.getEntryId());
687 subscriptionSender.setPortletId(PortletKeys.BOOKMARKS);
688 subscriptionSender.setReplyToAddress(fromAddress);
689 subscriptionSender.setScopeGroupId(entry.getGroupId());
690 subscriptionSender.setServiceContext(serviceContext);
691 subscriptionSender.setUserId(entry.getUserId());
692
693 subscriptionSender.addPersistedSubscribers(
694 BookmarksEntry.class.getName(), entry.getEntryId());
695
696 BookmarksFolder folder = entry.getFolder();
697
698 List<Long> folderIds = new ArrayList<Long>();
699
700 if (folder != null) {
701 folderIds.add(folder.getFolderId());
702
703 folderIds.addAll(folder.getAncestorFolderIds());
704 }
705
706 for (long curFolderId : folderIds) {
707 subscriptionSender.addPersistedSubscribers(
708 BookmarksFolder.class.getName(), curFolderId);
709 }
710
711 subscriptionSender.addPersistedSubscribers(
712 BookmarksFolder.class.getName(), entry.getGroupId());
713
714 subscriptionSender.flushNotificationsAsync();
715 }
716
717 protected void validate(String url) throws PortalException {
718 if (!Validator.isUrl(url)) {
719 throw new EntryURLException();
720 }
721 }
722
723 private static Log _log = LogFactoryUtil.getLog(
724 BookmarksEntryLocalServiceImpl.class);
725
726 }