1   /**
2    * Copyright (c) 2000-2010 Liferay, Inc. All rights reserved.
3    *
4    * The contents of this file are subject to the terms of the Liferay Enterprise
5    * Subscription License ("License"). You may not use this file except in
6    * compliance with the License. You can obtain a copy of the License by
7    * contacting Liferay, Inc. See the License for the specific language governing
8    * permissions and limitations under the License, including but not limited to
9    * distribution rights of the Software.
10   *
11   *
12   *
13   */
14  
15  package com.liferay.portlet.imagegallery.service.impl;
16  
17  import com.liferay.portal.PortalException;
18  import com.liferay.portal.SystemException;
19  import com.liferay.portal.kernel.search.BooleanClauseOccur;
20  import com.liferay.portal.kernel.search.BooleanQuery;
21  import com.liferay.portal.kernel.search.BooleanQueryFactoryUtil;
22  import com.liferay.portal.kernel.search.Field;
23  import com.liferay.portal.kernel.search.Hits;
24  import com.liferay.portal.kernel.search.SearchEngineUtil;
25  import com.liferay.portal.kernel.search.TermQuery;
26  import com.liferay.portal.kernel.search.TermQueryFactoryUtil;
27  import com.liferay.portal.kernel.util.FileUtil;
28  import com.liferay.portal.kernel.util.GetterUtil;
29  import com.liferay.portal.kernel.util.StringPool;
30  import com.liferay.portal.model.Group;
31  import com.liferay.portal.model.ResourceConstants;
32  import com.liferay.portal.model.User;
33  import com.liferay.portal.service.ServiceContext;
34  import com.liferay.portlet.imagegallery.DuplicateFolderNameException;
35  import com.liferay.portlet.imagegallery.FolderNameException;
36  import com.liferay.portlet.imagegallery.model.IGFolder;
37  import com.liferay.portlet.imagegallery.model.IGImage;
38  import com.liferay.portlet.imagegallery.model.impl.IGFolderImpl;
39  import com.liferay.portlet.imagegallery.service.base.IGFolderLocalServiceBaseImpl;
40  import com.liferay.portlet.imagegallery.util.Indexer;
41  import com.liferay.portlet.tags.util.TagsUtil;
42  
43  import java.util.ArrayList;
44  import java.util.Date;
45  import java.util.List;
46  
47  /**
48   * <a href="IGFolderLocalServiceImpl.java.html"><b><i>View Source</i></b></a>
49   *
50   * @author Brian Wing Shun Chan
51   */
52  public class IGFolderLocalServiceImpl extends IGFolderLocalServiceBaseImpl {
53  
54      public IGFolder addFolder(
55              long userId, long parentFolderId, String name, String description,
56              ServiceContext serviceContext)
57          throws PortalException, SystemException {
58  
59          return addFolder(
60              null, userId, parentFolderId, name, description, serviceContext);
61      }
62  
63      public IGFolder addFolder(
64              String uuid, long userId, long parentFolderId, String name,
65              String description, ServiceContext serviceContext)
66          throws PortalException, SystemException {
67  
68          User user = userPersistence.findByPrimaryKey(userId);
69          long groupId = serviceContext.getScopeGroupId();
70          parentFolderId = getParentFolderId(groupId, parentFolderId);
71          Date now = new Date();
72  
73          validate(groupId, parentFolderId, name);
74  
75          long folderId = counterLocalService.increment();
76  
77          IGFolder folder = igFolderPersistence.create(folderId);
78  
79          folder.setUuid(uuid);
80          folder.setGroupId(groupId);
81          folder.setCompanyId(user.getCompanyId());
82          folder.setUserId(user.getUserId());
83          folder.setCreateDate(serviceContext.getCreateDate(now));
84          folder.setModifiedDate(serviceContext.getModifiedDate(now));
85          folder.setParentFolderId(parentFolderId);
86          folder.setName(name);
87          folder.setDescription(description);
88          folder.setExpandoBridgeAttributes(serviceContext);
89  
90          igFolderPersistence.update(folder, false);
91  
92          // Resources
93  
94          if (serviceContext.getAddCommunityPermissions() ||
95              serviceContext.getAddGuestPermissions()) {
96  
97              addFolderResources(
98                  folder, serviceContext.getAddCommunityPermissions(),
99                  serviceContext.getAddGuestPermissions());
100         }
101         else {
102             addFolderResources(
103                 folder, serviceContext.getCommunityPermissions(),
104                 serviceContext.getGuestPermissions());
105         }
106 
107         return folder;
108     }
109 
110     public void addFolderResources(
111             IGFolder folder, boolean addCommunityPermissions,
112             boolean addGuestPermissions)
113         throws PortalException, SystemException {
114 
115         resourceLocalService.addResources(
116             folder.getCompanyId(), folder.getGroupId(), folder.getUserId(),
117             IGFolder.class.getName(), folder.getFolderId(), false,
118             addCommunityPermissions, addGuestPermissions);
119     }
120 
121     public void addFolderResources(
122             IGFolder folder, String[] communityPermissions,
123             String[] guestPermissions)
124         throws PortalException, SystemException {
125 
126         resourceLocalService.addModelResources(
127             folder.getCompanyId(), folder.getGroupId(), folder.getUserId(),
128             IGFolder.class.getName(), folder.getFolderId(),
129             communityPermissions, guestPermissions);
130     }
131 
132     public void addFolderResources(
133             long folderId, boolean addCommunityPermissions,
134             boolean addGuestPermissions)
135         throws PortalException, SystemException {
136 
137         IGFolder folder = igFolderPersistence.findByPrimaryKey(folderId);
138 
139         addFolderResources(
140             folder, addCommunityPermissions, addGuestPermissions);
141     }
142 
143     public void addFolderResources(
144             long folderId, String[] communityPermissions,
145             String[] guestPermissions)
146         throws PortalException, SystemException {
147 
148         IGFolder folder = igFolderPersistence.findByPrimaryKey(folderId);
149 
150         addFolderResources(folder, communityPermissions, guestPermissions);
151     }
152 
153     public void deleteFolder(IGFolder folder)
154         throws PortalException, SystemException {
155 
156         // Folders
157 
158         List<IGFolder> folders = igFolderPersistence.findByG_P(
159             folder.getGroupId(), folder.getFolderId());
160 
161         for (IGFolder curFolder : folders) {
162             deleteFolder(curFolder);
163         }
164 
165         // Folder
166 
167         igFolderPersistence.remove(folder);
168 
169         // Resources
170 
171         resourceLocalService.deleteResource(
172             folder.getCompanyId(), IGFolder.class.getName(),
173             ResourceConstants.SCOPE_INDIVIDUAL, folder.getFolderId());
174 
175         // Images
176 
177         igImageLocalService.deleteImages(folder.getFolderId());
178 
179         // Expando
180 
181         expandoValueLocalService.deleteValues(
182             IGFolder.class.getName(), folder.getFolderId());
183     }
184 
185     public void deleteFolder(long folderId)
186         throws PortalException, SystemException {
187 
188         IGFolder folder = igFolderPersistence.findByPrimaryKey(folderId);
189 
190         deleteFolder(folder);
191     }
192 
193     public void deleteFolders(long groupId)
194         throws PortalException, SystemException {
195 
196         List<IGFolder> folders = igFolderPersistence.findByG_P(
197             groupId, IGFolderImpl.DEFAULT_PARENT_FOLDER_ID);
198 
199         for (IGFolder folder : folders) {
200             deleteFolder(folder);
201         }
202     }
203 
204     public IGFolder getFolder(long folderId)
205         throws PortalException, SystemException {
206 
207         return igFolderPersistence.findByPrimaryKey(folderId);
208     }
209 
210     public IGFolder getFolder(long groupId, long parentFolderId, String name)
211         throws PortalException, SystemException {
212 
213         return igFolderPersistence.findByG_P_N(groupId, parentFolderId, name);
214     }
215 
216     public List<IGFolder> getFolders(long groupId) throws SystemException {
217         return igFolderPersistence.findByGroupId(groupId);
218     }
219 
220     public List<IGFolder> getFolders(long groupId, long parentFolderId)
221         throws SystemException {
222 
223         return igFolderPersistence.findByG_P(groupId, parentFolderId);
224     }
225 
226     public List<IGFolder> getFolders(
227             long groupId, long parentFolderId, int start, int end)
228         throws SystemException {
229 
230         return igFolderPersistence.findByG_P(
231             groupId, parentFolderId, start, end);
232     }
233 
234     public int getFoldersCount(long groupId, long parentFolderId)
235         throws SystemException {
236 
237         return igFolderPersistence.countByG_P(groupId, parentFolderId);
238     }
239 
240     public void getSubfolderIds(
241             List<Long> folderIds, long groupId, long folderId)
242         throws SystemException {
243 
244         List<IGFolder> folders = igFolderPersistence.findByG_P(
245             groupId, folderId);
246 
247         for (IGFolder folder : folders) {
248             folderIds.add(folder.getFolderId());
249 
250             getSubfolderIds(
251                 folderIds, folder.getGroupId(), folder.getFolderId());
252         }
253     }
254 
255     public void reIndex(String[] ids) throws SystemException {
256         if (SearchEngineUtil.isIndexReadOnly()) {
257             return;
258         }
259 
260         long companyId = GetterUtil.getLong(ids[0]);
261 
262         try {
263             reIndexFolders(companyId);
264         }
265         catch (SystemException se) {
266             throw se;
267         }
268         catch (Exception e) {
269             throw new SystemException(e);
270         }
271     }
272 
273     public Hits search(
274             long companyId, long groupId, long userId, long[] folderIds,
275             String keywords, int start, int end)
276         throws SystemException {
277 
278         try {
279             BooleanQuery contextQuery = BooleanQueryFactoryUtil.create();
280 
281             contextQuery.addRequiredTerm(Field.PORTLET_ID, Indexer.PORTLET_ID);
282 
283             if (groupId > 0) {
284                 Group group = groupLocalService.getGroup(groupId);
285 
286                 if (group.isLayout()) {
287                     contextQuery.addRequiredTerm(Field.SCOPE_GROUP_ID, groupId);
288 
289                     groupId = group.getParentGroupId();
290                 }
291 
292                 contextQuery.addRequiredTerm(Field.GROUP_ID, groupId);
293             }
294 
295             if ((folderIds != null) && (folderIds.length > 0)) {
296                 BooleanQuery folderIdsQuery = BooleanQueryFactoryUtil.create();
297 
298                 for (long folderId : folderIds) {
299                     if (userId > 0) {
300                         try {
301                             igFolderService.getFolder(folderId);
302                         }
303                         catch (Exception e) {
304                             continue;
305                         }
306                     }
307 
308                     TermQuery termQuery = TermQueryFactoryUtil.create(
309                         "folderId", folderId);
310 
311                     folderIdsQuery.add(termQuery, BooleanClauseOccur.SHOULD);
312                 }
313 
314                 contextQuery.add(folderIdsQuery, BooleanClauseOccur.MUST);
315             }
316 
317             BooleanQuery searchQuery = BooleanQueryFactoryUtil.create();
318 
319             searchQuery.addTerms(_KEYWORDS_FIELDS, keywords);
320 
321             searchQuery.addExactTerm(Field.TAGS_ENTRIES, keywords);
322 
323             BooleanQuery fullQuery = BooleanQueryFactoryUtil.create();
324 
325             fullQuery.add(contextQuery, BooleanClauseOccur.MUST);
326 
327             if (searchQuery.clauses().size() > 0) {
328                 fullQuery.add(searchQuery, BooleanClauseOccur.MUST);
329             }
330 
331             return SearchEngineUtil.search(
332                 companyId, groupId, userId, IGImage.class.getName(), fullQuery,
333                 start, end);
334         }
335         catch (Exception e) {
336             throw new SystemException(e);
337         }
338     }
339 
340     public IGFolder updateFolder(
341             long folderId, long parentFolderId, String name, String description,
342             boolean mergeWithParentFolder, ServiceContext serviceContext)
343         throws PortalException, SystemException {
344 
345         // Merge folders
346 
347         IGFolder folder = igFolderPersistence.findByPrimaryKey(folderId);
348 
349         parentFolderId = getParentFolderId(folder, parentFolderId);
350 
351         if (mergeWithParentFolder && (folderId != parentFolderId) &&
352             (parentFolderId != IGFolderImpl.DEFAULT_PARENT_FOLDER_ID)) {
353 
354             mergeFolders(folder, parentFolderId);
355 
356             return folder;
357         }
358 
359         // Folder
360 
361         validate(
362             folder.getFolderId(), folder.getGroupId(), parentFolderId, name);
363 
364         folder.setModifiedDate(serviceContext.getModifiedDate(null));
365         folder.setParentFolderId(parentFolderId);
366         folder.setName(name);
367         folder.setDescription(description);
368         folder.setExpandoBridgeAttributes(serviceContext);
369 
370         igFolderPersistence.update(folder, false);
371 
372         return folder;
373     }
374 
375     protected long getParentFolderId(IGFolder folder, long parentFolderId)
376         throws SystemException {
377 
378         if (parentFolderId == IGFolderImpl.DEFAULT_PARENT_FOLDER_ID) {
379             return parentFolderId;
380         }
381 
382         if (folder.getFolderId() == parentFolderId) {
383             return folder.getParentFolderId();
384         }
385         else {
386             IGFolder parentFolder = igFolderPersistence.fetchByPrimaryKey(
387                 parentFolderId);
388 
389             if ((parentFolder == null) ||
390                 (folder.getGroupId() != parentFolder.getGroupId())) {
391 
392                 return folder.getParentFolderId();
393             }
394 
395             List<Long> subfolderIds = new ArrayList<Long>();
396 
397             getSubfolderIds(
398                 subfolderIds, folder.getGroupId(), folder.getFolderId());
399 
400             if (subfolderIds.contains(parentFolderId)) {
401                 return folder.getParentFolderId();
402             }
403 
404             return parentFolderId;
405         }
406     }
407 
408     protected long getParentFolderId(long groupId, long parentFolderId)
409         throws SystemException {
410 
411         if (parentFolderId != IGFolderImpl.DEFAULT_PARENT_FOLDER_ID) {
412             IGFolder parentFolder = igFolderPersistence.fetchByPrimaryKey(
413                 parentFolderId);
414 
415             if ((parentFolder == null) ||
416                 (groupId != parentFolder.getGroupId())) {
417 
418                 parentFolderId = IGFolderImpl.DEFAULT_PARENT_FOLDER_ID;
419             }
420         }
421 
422         return parentFolderId;
423     }
424 
425     protected void mergeFolders(IGFolder fromFolder, long toFolderId)
426         throws PortalException, SystemException {
427 
428         List<IGFolder> folders = igFolderPersistence.findByG_P(
429             fromFolder.getGroupId(), fromFolder.getFolderId());
430 
431         for (IGFolder folder : folders) {
432             mergeFolders(folder, toFolderId);
433         }
434 
435         List<IGImage> images = igImagePersistence.findByFolderId(
436             fromFolder.getFolderId());
437 
438         for (IGImage image : images) {
439             image.setFolderId(toFolderId);
440 
441             igImagePersistence.update(image, false);
442 
443             igImageLocalService.reIndex(image);
444         }
445 
446         deleteFolder(fromFolder);
447     }
448 
449     protected void reIndexFolders(long companyId) throws SystemException {
450         int folderCount = igFolderPersistence.countByCompanyId(companyId);
451 
452         int folderPages = folderCount / Indexer.DEFAULT_INTERVAL;
453 
454         for (int i = 0; i <= folderPages; i++) {
455             int folderStart = (i * Indexer.DEFAULT_INTERVAL);
456             int folderEnd = folderStart + Indexer.DEFAULT_INTERVAL;
457 
458             reIndexFolders(companyId, folderStart, folderEnd);
459         }
460     }
461 
462     protected void reIndexFolders(
463             long companyId, int folderStart, int folderEnd)
464         throws SystemException {
465 
466         List<IGFolder> folders = igFolderPersistence.findByCompanyId(
467             companyId, folderStart, folderEnd);
468 
469         for (IGFolder folder : folders) {
470             long folderId = folder.getFolderId();
471 
472             int entryCount = igImagePersistence.countByFolderId(folderId);
473 
474             int entryPages = entryCount / Indexer.DEFAULT_INTERVAL;
475 
476             for (int i = 0; i <= entryPages; i++) {
477                 int entryStart = (i * Indexer.DEFAULT_INTERVAL);
478                 int entryEnd = entryStart + Indexer.DEFAULT_INTERVAL;
479 
480                 reIndexImages(folderId, entryStart, entryEnd);
481             }
482         }
483     }
484 
485     protected void reIndexImages(long folderId, int entryStart, int entryEnd)
486         throws SystemException {
487 
488         List<IGImage> images = igImagePersistence.findByFolderId(
489             folderId, entryStart, entryEnd);
490 
491         for (IGImage image : images) {
492             igImageLocalService.reIndex(image);
493         }
494     }
495 
496     protected void validate(
497             long folderId, long groupId, long parentFolderId, String name)
498         throws PortalException, SystemException {
499 
500         if (!TagsUtil.isValidWord(name)) {
501             throw new FolderNameException();
502         }
503 
504         IGFolder folder = igFolderPersistence.fetchByG_P_N(
505             groupId, parentFolderId, name);
506 
507         if ((folder != null) && (folder.getFolderId() != folderId)) {
508             throw new DuplicateFolderNameException();
509         }
510 
511         if (name.indexOf(StringPool.PERIOD) != -1) {
512             String nameWithExtension = name;
513 
514             name = FileUtil.stripExtension(nameWithExtension);
515 
516             List<IGImage> images = igImagePersistence.findByF_N(
517                 parentFolderId, name);
518 
519             for (IGImage image : images) {
520                 if (nameWithExtension.equals(image.getNameWithExtension())) {
521                     throw new DuplicateFolderNameException();
522                 }
523             }
524         }
525     }
526 
527     protected void validate(long groupId, long parentFolderId, String name)
528         throws PortalException, SystemException {
529 
530         long folderId = 0;
531 
532         validate(folderId, groupId, parentFolderId, name);
533     }
534 
535     private static final String[] _KEYWORDS_FIELDS = {
536         Field.DESCRIPTION, Field.TITLE
537     };
538 
539 }