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