001    /**
002     * Copyright (c) 2000-2013 Liferay, Inc. All rights reserved.
003     *
004     * This library is free software; you can redistribute it and/or modify it under
005     * the terms of the GNU Lesser General Public License as published by the Free
006     * Software Foundation; either version 2.1 of the License, or (at your option)
007     * any later version.
008     *
009     * This library is distributed in the hope that it will be useful, but WITHOUT
010     * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
011     * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
012     * details.
013     */
014    
015    package com.liferay.portlet.documentlibrary.service.impl;
016    
017    import com.liferay.portal.ExpiredLockException;
018    import com.liferay.portal.InvalidLockException;
019    import com.liferay.portal.NoSuchLockException;
020    import com.liferay.portal.kernel.dao.orm.QueryDefinition;
021    import com.liferay.portal.kernel.exception.PortalException;
022    import com.liferay.portal.kernel.exception.SystemException;
023    import com.liferay.portal.kernel.log.Log;
024    import com.liferay.portal.kernel.log.LogFactoryUtil;
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.systemevent.SystemEvent;
030    import com.liferay.portal.kernel.util.ObjectValuePair;
031    import com.liferay.portal.kernel.util.OrderByComparator;
032    import com.liferay.portal.kernel.util.ParamUtil;
033    import com.liferay.portal.kernel.util.StringPool;
034    import com.liferay.portal.kernel.util.UnicodeProperties;
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.Lock;
039    import com.liferay.portal.model.ResourceConstants;
040    import com.liferay.portal.model.SystemEventConstants;
041    import com.liferay.portal.model.User;
042    import com.liferay.portal.repository.liferayrepository.model.LiferayFolder;
043    import com.liferay.portal.service.ServiceContext;
044    import com.liferay.portlet.asset.util.AssetUtil;
045    import com.liferay.portlet.documentlibrary.DuplicateFileException;
046    import com.liferay.portlet.documentlibrary.DuplicateFolderNameException;
047    import com.liferay.portlet.documentlibrary.FolderNameException;
048    import com.liferay.portlet.documentlibrary.NoSuchDirectoryException;
049    import com.liferay.portlet.documentlibrary.NoSuchFileEntryException;
050    import com.liferay.portlet.documentlibrary.model.DLFileEntryTypeConstants;
051    import com.liferay.portlet.documentlibrary.model.DLFolder;
052    import com.liferay.portlet.documentlibrary.model.DLFolderConstants;
053    import com.liferay.portlet.documentlibrary.model.impl.DLFolderImpl;
054    import com.liferay.portlet.documentlibrary.service.base.DLFolderLocalServiceBaseImpl;
055    import com.liferay.portlet.documentlibrary.store.DLStoreUtil;
056    
057    import java.io.Serializable;
058    
059    import java.util.ArrayList;
060    import java.util.Collections;
061    import java.util.Date;
062    import java.util.List;
063    import java.util.Map;
064    
065    /**
066     * @author Brian Wing Shun Chan
067     * @author Alexander Chow
068     */
069    public class DLFolderLocalServiceImpl extends DLFolderLocalServiceBaseImpl {
070    
071            @Override
072            public DLFolder addFolder(
073                            long userId, long groupId, long repositoryId, boolean mountPoint,
074                            long parentFolderId, String name, String description,
075                            boolean hidden, ServiceContext serviceContext)
076                    throws PortalException, SystemException {
077    
078                    // Folder
079    
080                    User user = userPersistence.findByPrimaryKey(userId);
081                    parentFolderId = getParentFolderId(groupId, parentFolderId);
082                    Date now = new Date();
083    
084                    validateFolder(groupId, parentFolderId, name);
085    
086                    long folderId = counterLocalService.increment();
087    
088                    DLFolder dlFolder = dlFolderPersistence.create(folderId);
089    
090                    dlFolder.setUuid(serviceContext.getUuid());
091                    dlFolder.setGroupId(groupId);
092                    dlFolder.setCompanyId(user.getCompanyId());
093                    dlFolder.setUserId(user.getUserId());
094                    dlFolder.setUserName(user.getFullName());
095                    dlFolder.setCreateDate(serviceContext.getCreateDate(now));
096                    dlFolder.setModifiedDate(serviceContext.getModifiedDate(now));
097                    dlFolder.setRepositoryId(repositoryId);
098                    dlFolder.setMountPoint(mountPoint);
099                    dlFolder.setParentFolderId(parentFolderId);
100                    dlFolder.setName(name);
101                    dlFolder.setDescription(description);
102                    dlFolder.setLastPostDate(now);
103                    dlFolder.setHidden(hidden);
104                    dlFolder.setOverrideFileEntryTypes(false);
105                    dlFolder.setExpandoBridgeAttributes(serviceContext);
106    
107                    dlFolderPersistence.update(dlFolder);
108    
109                    // Resources
110    
111                    if (serviceContext.isAddGroupPermissions() ||
112                            serviceContext.isAddGuestPermissions()) {
113    
114                            addFolderResources(
115                                    dlFolder, serviceContext.isAddGroupPermissions(),
116                                    serviceContext.isAddGuestPermissions());
117                    }
118                    else {
119                            if (serviceContext.isDeriveDefaultPermissions()) {
120                                    serviceContext.deriveDefaultPermissions(
121                                            repositoryId, DLFolderConstants.getClassName());
122                            }
123    
124                            addFolderResources(
125                                    dlFolder, serviceContext.getGroupPermissions(),
126                                    serviceContext.getGuestPermissions());
127                    }
128    
129                    // Parent folder
130    
131                    if (parentFolderId != DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
132                            DLFolder parentDLFolder = dlFolderPersistence.findByPrimaryKey(
133                                    parentFolderId);
134    
135                            parentDLFolder.setLastPostDate(now);
136    
137                            dlFolderPersistence.update(parentDLFolder);
138                    }
139    
140                    // App helper
141    
142                    dlAppHelperLocalService.addFolder(
143                            userId, new LiferayFolder(dlFolder), serviceContext);
144    
145                    return dlFolder;
146            }
147    
148            /**
149             * @deprecated As of 6.2.0, replaced by more general {@link #addFolder(long,
150             *             long, long, boolean, long, String, String, boolean,
151             *             ServiceContext)}
152             */
153            @Override
154            public DLFolder addFolder(
155                            long userId, long groupId, long repositoryId, boolean mountPoint,
156                            long parentFolderId, String name, String description,
157                            ServiceContext serviceContext)
158                    throws PortalException, SystemException {
159    
160                    return addFolder(
161                            userId, groupId, repositoryId, mountPoint, parentFolderId, name,
162                            description, false, serviceContext);
163            }
164    
165            @Override
166            public void deleteAll(long groupId)
167                    throws PortalException, SystemException {
168    
169                    Group group = groupLocalService.getGroup(groupId);
170    
171                    List<DLFolder> dlFolders = dlFolderPersistence.findByG_P(
172                            groupId, DLFolderConstants.DEFAULT_PARENT_FOLDER_ID);
173    
174                    for (DLFolder dlFolder : dlFolders) {
175                            dlFolderLocalService.deleteFolder(dlFolder);
176                    }
177    
178                    dlFileEntryLocalService.deleteFileEntries(
179                            groupId, DLFolderConstants.DEFAULT_PARENT_FOLDER_ID);
180    
181                    dlFileShortcutLocalService.deleteFileShortcuts(
182                            groupId, DLFolderConstants.DEFAULT_PARENT_FOLDER_ID);
183    
184                    try {
185                            DLStoreUtil.deleteDirectory(
186                                    group.getCompanyId(), groupId, StringPool.BLANK);
187                    }
188                    catch (NoSuchDirectoryException nsde) {
189                            if (_log.isDebugEnabled()) {
190                                    _log.debug(nsde.getMessage());
191                            }
192                    }
193            }
194    
195            @Indexable(type = IndexableType.DELETE)
196            @Override
197            @SystemEvent(
198                    action = SystemEventConstants.ACTION_SKIP,
199                    type = SystemEventConstants.TYPE_DELETE)
200            public DLFolder deleteFolder(DLFolder dlFolder)
201                    throws PortalException, SystemException {
202    
203                    return deleteFolder(dlFolder, true);
204            }
205    
206            @Indexable(type = IndexableType.DELETE)
207            @Override
208            @SystemEvent(
209                    action = SystemEventConstants.ACTION_SKIP,
210                    type = SystemEventConstants.TYPE_DELETE)
211            public DLFolder deleteFolder(
212                            DLFolder dlFolder, boolean includeTrashedEntries)
213                    throws PortalException, SystemException {
214    
215                    // Folders
216    
217                    List<DLFolder> dlFolders = dlFolderPersistence.findByG_P(
218                            dlFolder.getGroupId(), dlFolder.getFolderId());
219    
220                    for (DLFolder curDLFolder : dlFolders) {
221                            if (includeTrashedEntries || !curDLFolder.isInTrash()) {
222                                    dlFolderLocalService.deleteFolder(
223                                            curDLFolder, includeTrashedEntries);
224                            }
225                    }
226    
227                    // Resources
228    
229                    resourceLocalService.deleteResource(
230                            dlFolder.getCompanyId(), DLFolder.class.getName(),
231                            ResourceConstants.SCOPE_INDIVIDUAL, dlFolder.getFolderId());
232    
233                    // WebDAVProps
234    
235                    webDAVPropsLocalService.deleteWebDAVProps(
236                            DLFolder.class.getName(), dlFolder.getFolderId());
237    
238                    // File entries
239    
240                    dlFileEntryLocalService.deleteFileEntries(
241                            dlFolder.getGroupId(), dlFolder.getFolderId(),
242                            includeTrashedEntries);
243    
244                    // File entry types
245    
246                    dlFileEntryTypeLocalService.unsetFolderFileEntryTypes(
247                            dlFolder.getFolderId());
248    
249                    // File shortcuts
250    
251                    dlFileShortcutLocalService.deleteFileShortcuts(
252                            dlFolder.getGroupId(), dlFolder.getFolderId(),
253                            includeTrashedEntries);
254    
255                    // Expando
256    
257                    expandoRowLocalService.deleteRows(dlFolder.getFolderId());
258    
259                    // App helper
260    
261                    dlAppHelperLocalService.deleteFolder(new LiferayFolder(dlFolder));
262    
263                    // Folder
264    
265                    dlFolderPersistence.remove(dlFolder);
266    
267                    // Directory
268    
269                    try {
270                            if (includeTrashedEntries) {
271                                    DLStoreUtil.deleteDirectory(
272                                            dlFolder.getCompanyId(), dlFolder.getFolderId(),
273                                            StringPool.BLANK);
274                            }
275                    }
276                    catch (NoSuchDirectoryException nsde) {
277                            if (_log.isDebugEnabled()) {
278                                    _log.debug(nsde.getMessage());
279                            }
280                    }
281    
282                    return dlFolder;
283            }
284    
285            @Indexable(type = IndexableType.DELETE)
286            @Override
287            public DLFolder deleteFolder(long folderId)
288                    throws PortalException, SystemException {
289    
290                    return dlFolderLocalService.deleteFolder(folderId, true);
291            }
292    
293            @Indexable(type = IndexableType.DELETE)
294            @Override
295            public DLFolder deleteFolder(long folderId, boolean includeTrashedEntries)
296                    throws PortalException, SystemException {
297    
298                    DLFolder dlFolder = dlFolderPersistence.findByPrimaryKey(folderId);
299    
300                    return dlFolderLocalService.deleteFolder(
301                            dlFolder, includeTrashedEntries);
302            }
303    
304            @Indexable(type = IndexableType.DELETE)
305            @Override
306            public DLFolder deleteFolder(
307                            long userId, long folderId, boolean includeTrashedEntries)
308                    throws PortalException, SystemException {
309    
310                    boolean hasLock = hasFolderLock(userId, folderId);
311    
312                    Lock lock = null;
313    
314                    if (!hasLock) {
315    
316                            // Lock
317    
318                            lock = lockFolder(
319                                    userId, folderId, null, false,
320                                    DLFolderImpl.LOCK_EXPIRATION_TIME);
321                    }
322    
323                    try {
324                            return deleteFolder(folderId, includeTrashedEntries);
325                    }
326                    finally {
327                            if (!hasLock) {
328    
329                                    // Unlock
330    
331                                    unlockFolder(folderId, lock.getUuid());
332                            }
333                    }
334    
335            }
336    
337            @Override
338            public DLFolder fetchFolder(long folderId) throws SystemException {
339                    return dlFolderPersistence.fetchByPrimaryKey(folderId);
340            }
341    
342            @Override
343            public DLFolder fetchFolder(long groupId, long parentFolderId, String name)
344                    throws SystemException {
345    
346                    return dlFolderPersistence.fetchByG_P_N(groupId, parentFolderId, name);
347            }
348    
349            @Override
350            public List<DLFolder> getCompanyFolders(long companyId, int start, int end)
351                    throws SystemException {
352    
353                    return dlFolderPersistence.findByCompanyId(companyId, start, end);
354            }
355    
356            @Override
357            public int getCompanyFoldersCount(long companyId) throws SystemException {
358                    return dlFolderPersistence.countByCompanyId(companyId);
359            }
360    
361            /**
362             * @deprecated As of 6.2.0, replaced by {@link
363             *             #getFileEntriesAndFileShortcuts(long, long, QueryDefinition)}
364             */
365            @Override
366            public List<Object> getFileEntriesAndFileShortcuts(
367                            long groupId, long folderId, int status, int start, int end)
368                    throws SystemException {
369    
370                    QueryDefinition queryDefinition = new QueryDefinition(
371                            status, start, end, null);
372    
373                    return getFileEntriesAndFileShortcuts(
374                            groupId, folderId, queryDefinition);
375            }
376    
377            @Override
378            public List<Object> getFileEntriesAndFileShortcuts(
379                            long groupId, long folderId, QueryDefinition queryDefinition)
380                    throws SystemException {
381    
382                    return dlFolderFinder.findFE_FS_ByG_F(
383                            groupId, folderId, queryDefinition);
384            }
385    
386            /**
387             * @deprecated As of 6.2.0, replaced by {@link
388             *             #getFileEntriesAndFileShortcutsCount(long, long,
389             *             QueryDefinition)}
390             */
391            @Override
392            public int getFileEntriesAndFileShortcutsCount(
393                            long groupId, long folderId, int status)
394                    throws SystemException {
395    
396                    QueryDefinition queryDefinition = new QueryDefinition(status);
397    
398                    return getFileEntriesAndFileShortcutsCount(
399                            groupId, folderId, queryDefinition);
400            }
401    
402            @Override
403            public int getFileEntriesAndFileShortcutsCount(
404                            long groupId, long folderId, QueryDefinition queryDefinition)
405                    throws SystemException {
406    
407                    return dlFolderFinder.countFE_FS_ByG_F(
408                            groupId, folderId, queryDefinition);
409            }
410    
411            @Override
412            public DLFolder getFolder(long folderId)
413                    throws PortalException, SystemException {
414    
415                    return dlFolderPersistence.findByPrimaryKey(folderId);
416            }
417    
418            @Override
419            public DLFolder getFolder(long groupId, long parentFolderId, String name)
420                    throws PortalException, SystemException {
421    
422                    return dlFolderPersistence.findByG_P_N(groupId, parentFolderId, name);
423            }
424    
425            @Override
426            public long getFolderId(long companyId, long folderId)
427                    throws SystemException {
428    
429                    if (folderId != DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
430    
431                            // Ensure folder exists and belongs to the proper company
432    
433                            DLFolder dlFolder = dlFolderPersistence.fetchByPrimaryKey(folderId);
434    
435                            if ((dlFolder == null) || (companyId != dlFolder.getCompanyId())) {
436                                    folderId = DLFolderConstants.DEFAULT_PARENT_FOLDER_ID;
437                            }
438                    }
439    
440                    return folderId;
441            }
442    
443            @Override
444            public List<DLFolder> getFolders(long groupId, long parentFolderId)
445                    throws SystemException {
446    
447                    return getFolders(groupId, parentFolderId, true);
448            }
449    
450            @Override
451            public List<DLFolder> getFolders(
452                            long groupId, long parentFolderId, boolean includeMountfolders)
453                    throws SystemException {
454    
455                    if (includeMountfolders) {
456                            return dlFolderPersistence.findByG_P(groupId, parentFolderId);
457                    }
458                    else {
459                            return dlFolderPersistence.findByG_M_P_H(
460                                    groupId, false, parentFolderId, false);
461                    }
462            }
463    
464            @Override
465            public List<DLFolder> getFolders(
466                            long groupId, long parentFolderId, boolean includeMountfolders,
467                            int start, int end, OrderByComparator obc)
468                    throws SystemException {
469    
470                    if (includeMountfolders) {
471                            return dlFolderPersistence.findByG_P(
472                                    groupId, parentFolderId, start, end, obc);
473                    }
474                    else {
475                            return dlFolderPersistence.findByG_M_P_H(
476                                    groupId, false, parentFolderId, false, start, end, obc);
477                    }
478            }
479    
480            @Override
481            public List<DLFolder> getFolders(
482                            long groupId, long parentFolderId, int start, int end,
483                            OrderByComparator obc)
484                    throws SystemException {
485    
486                    return getFolders(groupId, parentFolderId, true, start, end, obc);
487            }
488    
489            /**
490             * @deprecated As of 6.2.0, replaced by {@link
491             *             #getFoldersAndFileEntriesAndFileShortcuts(long, long,
492             *             String[], boolean, QueryDefinition)}
493             */
494            @Override
495            public List<Object> getFoldersAndFileEntriesAndFileShortcuts(
496                            long groupId, long folderId, int status,
497                            boolean includeMountFolders, int start, int end,
498                            OrderByComparator obc)
499                    throws SystemException {
500    
501                    QueryDefinition queryDefinition = new QueryDefinition(
502                            status, start, end, obc);
503    
504                    return getFoldersAndFileEntriesAndFileShortcuts(
505                            groupId, folderId, null, includeMountFolders, queryDefinition);
506            }
507    
508            /**
509             * @deprecated As of 6.2.0, replaced by {@link
510             *             #getFoldersAndFileEntriesAndFileShortcutsCount(long, long,
511             *             String[], boolean, QueryDefinition)}
512             */
513            @Override
514            public List<Object> getFoldersAndFileEntriesAndFileShortcuts(
515                            long groupId, long folderId, int status, String[] mimeTypes,
516                            boolean includeMountFolders, int start, int end,
517                            OrderByComparator obc)
518                    throws SystemException {
519    
520                    QueryDefinition queryDefinition = new QueryDefinition(
521                            status, start, end, obc);
522    
523                    return getFoldersAndFileEntriesAndFileShortcuts(
524                            groupId, folderId, mimeTypes, includeMountFolders, queryDefinition);
525            }
526    
527            @Override
528            public List<Object> getFoldersAndFileEntriesAndFileShortcuts(
529                            long groupId, long folderId, String[] mimeTypes,
530                            boolean includeMountFolders, QueryDefinition queryDefinition)
531                    throws SystemException {
532    
533                    return dlFolderFinder.findF_FE_FS_ByG_F_M_M(
534                            groupId, folderId, mimeTypes, includeMountFolders, queryDefinition);
535            }
536    
537            /**
538             * @deprecated As of 6.2.0, replaced by {@link
539             *             #getFoldersAndFileEntriesAndFileShortcutsCount(long, long,
540             *             String[], boolean, QueryDefinition)}
541             */
542            @Override
543            public int getFoldersAndFileEntriesAndFileShortcutsCount(
544                            long groupId, long folderId, int status,
545                            boolean includeMountFolders)
546                    throws SystemException {
547    
548                    QueryDefinition queryDefinition = new QueryDefinition(status);
549    
550                    return getFoldersAndFileEntriesAndFileShortcutsCount(
551                            groupId, folderId, null, includeMountFolders, queryDefinition);
552            }
553    
554            /**
555             * @deprecated As of 6.2.0, replaced by {@link
556             *             #getFoldersAndFileEntriesAndFileShortcutsCount(long, long,
557             *             String[], boolean, QueryDefinition)}
558             */
559            @Override
560            public int getFoldersAndFileEntriesAndFileShortcutsCount(
561                            long groupId, long folderId, int status, String[] mimeTypes,
562                            boolean includeMountFolders)
563                    throws SystemException {
564    
565                    QueryDefinition queryDefinition = new QueryDefinition(status);
566    
567                    return getFoldersAndFileEntriesAndFileShortcutsCount(
568                            groupId, folderId, mimeTypes, includeMountFolders, queryDefinition);
569            }
570    
571            @Override
572            public int getFoldersAndFileEntriesAndFileShortcutsCount(
573                            long groupId, long folderId, String[] mimeTypes,
574                            boolean includeMountFolders, QueryDefinition queryDefinition)
575                    throws SystemException {
576    
577                    return dlFolderFinder.countF_FE_FS_ByG_F_M_M(
578                            groupId, folderId, mimeTypes, includeMountFolders, queryDefinition);
579            }
580    
581            @Override
582            public int getFoldersCount(long groupId, long parentFolderId)
583                    throws SystemException {
584    
585                    return getFoldersCount(groupId, parentFolderId, true);
586            }
587    
588            @Override
589            public int getFoldersCount(
590                            long groupId, long parentFolderId, boolean includeMountfolders)
591                    throws SystemException {
592    
593                    if (includeMountfolders) {
594                            return dlFolderPersistence.countByG_P(groupId, parentFolderId);
595                    }
596                    else {
597                            return dlFolderPersistence.countByG_M_P_H(
598                                    groupId, false, parentFolderId, false);
599                    }
600            }
601    
602            @Override
603            public DLFolder getMountFolder(long repositoryId)
604                    throws PortalException, SystemException {
605    
606                    return dlFolderPersistence.findByRepositoryId(repositoryId);
607            }
608    
609            @Override
610            public List<DLFolder> getMountFolders(
611                            long groupId, long parentFolderId, int start, int end,
612                            OrderByComparator obc)
613                    throws SystemException {
614    
615                    return dlFolderPersistence.findByG_M_P_H(
616                            groupId, true, parentFolderId, false, start, end, obc);
617            }
618    
619            @Override
620            public int getMountFoldersCount(long groupId, long parentFolderId)
621                    throws SystemException {
622    
623                    return dlFolderPersistence.countByG_M_P_H(
624                            groupId, true, parentFolderId, false);
625            }
626    
627            @Override
628            public List<DLFolder> getNoAssetFolders() throws SystemException {
629                    return dlFolderFinder.findF_ByNoAssets();
630            }
631    
632            @Override
633            public void getSubfolderIds(
634                            List<Long> folderIds, long groupId, long folderId)
635                    throws SystemException {
636    
637                    List<DLFolder> dlFolders = dlFolderPersistence.findByG_P(
638                            groupId, folderId);
639    
640                    for (DLFolder dlFolder : dlFolders) {
641                            folderIds.add(dlFolder.getFolderId());
642    
643                            getSubfolderIds(
644                                    folderIds, dlFolder.getGroupId(), dlFolder.getFolderId());
645                    }
646            }
647    
648            @Override
649            public boolean hasFolderLock(long userId, long folderId)
650                    throws SystemException {
651    
652                    return lockLocalService.hasLock(
653                            userId, DLFolder.class.getName(), folderId);
654            }
655    
656            @Override
657            public Lock lockFolder(long userId, long folderId)
658                    throws PortalException, SystemException {
659    
660                    return lockFolder(
661                            userId, folderId, null, false, DLFolderImpl.LOCK_EXPIRATION_TIME);
662            }
663    
664            @Override
665            public Lock lockFolder(
666                            long userId, long folderId, String owner, boolean inheritable,
667                            long expirationTime)
668                    throws PortalException, SystemException {
669    
670                    if ((expirationTime <= 0) ||
671                            (expirationTime > DLFolderImpl.LOCK_EXPIRATION_TIME)) {
672    
673                            expirationTime = DLFolderImpl.LOCK_EXPIRATION_TIME;
674                    }
675    
676                    return lockLocalService.lock(
677                            userId, DLFolder.class.getName(), folderId, owner, inheritable,
678                            expirationTime);
679            }
680    
681            @Indexable(type = IndexableType.REINDEX)
682            @Override
683            public DLFolder moveFolder(
684                            long userId, long folderId, long parentFolderId,
685                            ServiceContext serviceContext)
686                    throws PortalException, SystemException {
687    
688                    boolean hasLock = hasFolderLock(userId, folderId);
689    
690                    Lock lock = null;
691    
692                    if (!hasLock) {
693    
694                            // Lock
695    
696                            lock = lockFolder(userId, folderId);
697                    }
698    
699                    try {
700                            DLFolder dlFolder = dlFolderPersistence.findByPrimaryKey(folderId);
701    
702                            parentFolderId = getParentFolderId(dlFolder, parentFolderId);
703    
704                            validateFolder(
705                                    dlFolder.getFolderId(), dlFolder.getGroupId(), parentFolderId,
706                                    dlFolder.getName());
707    
708                            dlFolder.setModifiedDate(serviceContext.getModifiedDate(null));
709                            dlFolder.setParentFolderId(parentFolderId);
710                            dlFolder.setExpandoBridgeAttributes(serviceContext);
711    
712                            dlFolderPersistence.update(dlFolder);
713    
714                            dlAppHelperLocalService.moveFolder(new LiferayFolder(dlFolder));
715    
716                            return dlFolder;
717                    }
718                    finally {
719                            if (!hasLock) {
720    
721                                    // Unlock
722    
723                                    unlockFolder(folderId, lock.getUuid());
724                            }
725                    }
726            }
727    
728            @Override
729            public void unlockFolder(
730                            long groupId, long parentFolderId, String name, String lockUuid)
731                    throws PortalException, SystemException {
732    
733                    DLFolder dlFolder = getFolder(groupId, parentFolderId, name);
734    
735                    unlockFolder(dlFolder.getFolderId(), lockUuid);
736            }
737    
738            @Override
739            public void unlockFolder(long folderId, String lockUuid)
740                    throws PortalException, SystemException {
741    
742                    if (Validator.isNotNull(lockUuid)) {
743                            try {
744                                    Lock lock = lockLocalService.getLock(
745                                            DLFolder.class.getName(), folderId);
746    
747                                    if (!lockUuid.equals(lock.getUuid())) {
748                                            throw new InvalidLockException("UUIDs do not match");
749                                    }
750                            }
751                            catch (PortalException pe) {
752                                    if (pe instanceof ExpiredLockException ||
753                                            pe instanceof NoSuchLockException) {
754                                    }
755                                    else {
756                                            throw pe;
757                                    }
758                            }
759                    }
760    
761                    lockLocalService.unlock(DLFolder.class.getName(), folderId);
762            }
763    
764            @Indexable(type = IndexableType.REINDEX)
765            @Override
766            public DLFolder updateFolder(
767                            long folderId, long parentFolderId, String name, String description,
768                            long defaultFileEntryTypeId, List<Long> fileEntryTypeIds,
769                            boolean overrideFileEntryTypes, ServiceContext serviceContext)
770                    throws PortalException, SystemException {
771    
772                    boolean hasLock = hasFolderLock(serviceContext.getUserId(), folderId);
773    
774                    Lock lock = null;
775    
776                    if (!hasLock) {
777    
778                            // Lock
779    
780                            lock = lockFolder(
781                                    serviceContext.getUserId(), folderId, null, false,
782                                    DLFolderImpl.LOCK_EXPIRATION_TIME);
783                    }
784    
785                    try {
786    
787                            // File entry types
788    
789                            DLFolder dlFolder = null;
790    
791                            if (folderId > DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
792                                    dlFolder = dlFolderLocalService.updateFolderAndFileEntryTypes(
793                                            serviceContext.getUserId(), folderId, parentFolderId, name,
794                                            description, defaultFileEntryTypeId, fileEntryTypeIds,
795                                            overrideFileEntryTypes, serviceContext);
796    
797                                    dlFileEntryTypeLocalService.cascadeFileEntryTypes(
798                                            serviceContext.getUserId(), dlFolder);
799                            }
800    
801                            // Workflow definitions
802    
803                            List<ObjectValuePair<Long, String>> workflowDefinitionOVPs =
804                                    new ArrayList<ObjectValuePair<Long, String>>();
805    
806                            if (fileEntryTypeIds.isEmpty()) {
807                                    fileEntryTypeIds.add(
808                                            DLFileEntryTypeConstants.FILE_ENTRY_TYPE_ID_ALL);
809                            }
810                            else {
811                                    workflowDefinitionOVPs.add(
812                                            new ObjectValuePair<Long, String>(
813                                                    DLFileEntryTypeConstants.FILE_ENTRY_TYPE_ID_ALL,
814                                                    StringPool.BLANK));
815                            }
816    
817                            for (long fileEntryTypeId : fileEntryTypeIds) {
818                                    String workflowDefinition = ParamUtil.getString(
819                                            serviceContext, "workflowDefinition" + fileEntryTypeId);
820    
821                                    workflowDefinitionOVPs.add(
822                                            new ObjectValuePair<Long, String>(
823                                                    fileEntryTypeId, workflowDefinition));
824                            }
825    
826                            workflowDefinitionLinkLocalService.updateWorkflowDefinitionLinks(
827                                    serviceContext.getUserId(), serviceContext.getCompanyId(),
828                                    serviceContext.getScopeGroupId(), DLFolder.class.getName(),
829                                    folderId, workflowDefinitionOVPs);
830    
831                            return dlFolder;
832                    }
833                    finally {
834                            if (!hasLock) {
835    
836                                    // Unlock
837    
838                                    unlockFolder(folderId, lock.getUuid());
839                            }
840                    }
841            }
842    
843            @Indexable(type = IndexableType.REINDEX)
844            @Override
845            public DLFolder updateFolder(
846                            long folderId, String name, String description,
847                            long defaultFileEntryTypeId, List<Long> fileEntryTypeIds,
848                            boolean overrideFileEntryTypes, ServiceContext serviceContext)
849                    throws PortalException, SystemException {
850    
851                    return updateFolder(
852                            folderId, folderId, name, description, defaultFileEntryTypeId,
853                            fileEntryTypeIds, overrideFileEntryTypes, serviceContext);
854            }
855    
856            @Override
857            public DLFolder updateFolderAndFileEntryTypes(
858                            long userId, long folderId, long parentFolderId, String name,
859                            String description, long defaultFileEntryTypeId,
860                            List<Long> fileEntryTypeIds, boolean overrideFileEntryTypes,
861                            ServiceContext serviceContext)
862                    throws PortalException, SystemException {
863    
864                    boolean hasLock = hasFolderLock(userId, folderId);
865    
866                    Lock lock = null;
867    
868                    if (!hasLock) {
869    
870                            // Lock
871    
872                            lock = lockFolder(
873                                    userId, folderId, null, false,
874                                    DLFolderImpl.LOCK_EXPIRATION_TIME);
875                    }
876    
877                    try {
878    
879                            // Folder
880    
881                            if (!overrideFileEntryTypes) {
882                                    fileEntryTypeIds = Collections.emptyList();
883                            }
884    
885                            DLFolder dlFolder = dlFolderPersistence.findByPrimaryKey(folderId);
886    
887                            parentFolderId = getParentFolderId(dlFolder, parentFolderId);
888    
889                            validateFolder(
890                                    folderId, dlFolder.getGroupId(), parentFolderId, name);
891    
892                            dlFolder.setModifiedDate(serviceContext.getModifiedDate(null));
893                            dlFolder.setParentFolderId(parentFolderId);
894                            dlFolder.setName(name);
895                            dlFolder.setDescription(description);
896                            dlFolder.setExpandoBridgeAttributes(serviceContext);
897                            dlFolder.setOverrideFileEntryTypes(overrideFileEntryTypes);
898                            dlFolder.setDefaultFileEntryTypeId(defaultFileEntryTypeId);
899    
900                            dlFolderPersistence.update(dlFolder);
901    
902                            // File entry types
903    
904                            if (fileEntryTypeIds != null) {
905                                    dlFileEntryTypeLocalService.updateFolderFileEntryTypes(
906                                            dlFolder, fileEntryTypeIds, defaultFileEntryTypeId,
907                                            serviceContext);
908                            }
909    
910                            // App helper
911    
912                            dlAppHelperLocalService.updateFolder(
913                                    userId, new LiferayFolder(dlFolder), serviceContext);
914    
915                            return dlFolder;
916                    }
917                    finally {
918                            if (!hasLock) {
919    
920                                    // Unlock
921    
922                                    unlockFolder(folderId, lock.getUuid());
923                            }
924                    }
925            }
926    
927            /**
928             * @deprecated As of 6.2.0
929             */
930            @Override
931            public void updateLastPostDate(long folderId, Date lastPostDate)
932                    throws PortalException, SystemException {
933    
934                    DLFolder dlFolder = dlFolderPersistence.findByPrimaryKey(folderId);
935    
936                    dlFolder.setLastPostDate(lastPostDate);
937    
938                    dlFolderPersistence.update(dlFolder);
939            }
940    
941            @Override
942            public DLFolder updateStatus(
943                            long userId, long folderId, int status,
944                            Map<String, Serializable> workflowContext,
945                            ServiceContext serviceContext)
946                    throws PortalException, SystemException {
947    
948                    // Folder
949    
950                    User user = userPersistence.findByPrimaryKey(userId);
951    
952                    DLFolder dlFolder = dlFolderPersistence.findByPrimaryKey(folderId);
953    
954                    int oldStatus = dlFolder.getStatus();
955    
956                    dlFolder.setStatus(status);
957                    dlFolder.setStatusByUserId(user.getUserId());
958                    dlFolder.setStatusByUserName(user.getFullName());
959                    dlFolder.setStatusDate(new Date());
960    
961                    dlFolderPersistence.update(dlFolder);
962    
963                    // Folders, file entries, and file shortcuts
964    
965                    QueryDefinition queryDefinition = new QueryDefinition(
966                            WorkflowConstants.STATUS_ANY);
967    
968                    List<Object> foldersAndFileEntriesAndFileShortcuts =
969                            getFoldersAndFileEntriesAndFileShortcuts(
970                                    dlFolder.getGroupId(), folderId, null, false, queryDefinition);
971    
972                    dlAppHelperLocalService.updateDependentStatus(
973                            user, foldersAndFileEntriesAndFileShortcuts, status);
974    
975                    // Asset
976    
977                    if (status == WorkflowConstants.STATUS_APPROVED) {
978                            assetEntryLocalService.updateVisible(
979                                    DLFolder.class.getName(), dlFolder.getFolderId(), true);
980                    }
981                    else if (status == WorkflowConstants.STATUS_IN_TRASH) {
982                            assetEntryLocalService.updateVisible(
983                                    DLFolder.class.getName(), dlFolder.getFolderId(), false);
984                    }
985    
986                    // Trash
987    
988                    if (status == WorkflowConstants.STATUS_IN_TRASH) {
989                            UnicodeProperties typeSettingsProperties = new UnicodeProperties();
990    
991                            typeSettingsProperties.put("title", dlFolder.getName());
992    
993                            trashEntryLocalService.addTrashEntry(
994                                    userId, dlFolder.getGroupId(), DLFolderConstants.getClassName(),
995                                    dlFolder.getFolderId(), WorkflowConstants.STATUS_APPROVED, null,
996                                    typeSettingsProperties);
997                    }
998                    else {
999                            trashEntryLocalService.deleteEntry(
1000                                    DLFolderConstants.getClassName(), dlFolder.getFolderId());
1001                    }
1002    
1003                    // Indexer
1004    
1005                    if (((status == WorkflowConstants.STATUS_APPROVED) ||
1006                             (status == WorkflowConstants.STATUS_IN_TRASH) ||
1007                             (oldStatus == WorkflowConstants.STATUS_IN_TRASH)) &&
1008                            ((serviceContext == null) || serviceContext.isIndexingEnabled())) {
1009    
1010                            Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
1011                                    DLFolderConstants.getClassName());
1012    
1013                            indexer.reindex(dlFolder);
1014                    }
1015    
1016                    return dlFolder;
1017            }
1018    
1019            protected void addFolderResources(
1020                            DLFolder dlFolder, boolean addGroupPermissions,
1021                            boolean addGuestPermissions)
1022                    throws PortalException, SystemException {
1023    
1024                    resourceLocalService.addResources(
1025                            dlFolder.getCompanyId(), dlFolder.getGroupId(),
1026                            dlFolder.getUserId(), DLFolder.class.getName(),
1027                            dlFolder.getFolderId(), false, addGroupPermissions,
1028                            addGuestPermissions);
1029            }
1030    
1031            protected void addFolderResources(
1032                            DLFolder dlFolder, String[] groupPermissions,
1033                            String[] guestPermissions)
1034                    throws PortalException, SystemException {
1035    
1036                    resourceLocalService.addModelResources(
1037                            dlFolder.getCompanyId(), dlFolder.getGroupId(),
1038                            dlFolder.getUserId(), DLFolder.class.getName(),
1039                            dlFolder.getFolderId(), groupPermissions, guestPermissions);
1040            }
1041    
1042            protected void addFolderResources(
1043                            long folderId, boolean addGroupPermissions,
1044                            boolean addGuestPermissions)
1045                    throws PortalException, SystemException {
1046    
1047                    DLFolder dlFolder = dlFolderPersistence.findByPrimaryKey(folderId);
1048    
1049                    addFolderResources(dlFolder, addGroupPermissions, addGuestPermissions);
1050            }
1051    
1052            protected void addFolderResources(
1053                            long folderId, String[] groupPermissions, String[] guestPermissions)
1054                    throws PortalException, SystemException {
1055    
1056                    DLFolder dlFolder = dlFolderPersistence.findByPrimaryKey(folderId);
1057    
1058                    addFolderResources(dlFolder, groupPermissions, guestPermissions);
1059            }
1060    
1061            protected long getParentFolderId(DLFolder dlFolder, long parentFolderId)
1062                    throws SystemException {
1063    
1064                    if (parentFolderId == DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
1065                            return parentFolderId;
1066                    }
1067    
1068                    if (dlFolder.getFolderId() == parentFolderId) {
1069                            return dlFolder.getParentFolderId();
1070                    }
1071                    else {
1072                            DLFolder parentDLFolder = dlFolderPersistence.fetchByPrimaryKey(
1073                                    parentFolderId);
1074    
1075                            if ((parentDLFolder == null) ||
1076                                    (dlFolder.getGroupId() != parentDLFolder.getGroupId())) {
1077    
1078                                    return dlFolder.getParentFolderId();
1079                            }
1080    
1081                            List<Long> subfolderIds = new ArrayList<Long>();
1082    
1083                            getSubfolderIds(
1084                                    subfolderIds, dlFolder.getGroupId(), dlFolder.getFolderId());
1085    
1086                            if (subfolderIds.contains(parentFolderId)) {
1087                                    return dlFolder.getParentFolderId();
1088                            }
1089    
1090                            return parentFolderId;
1091                    }
1092            }
1093    
1094            protected long getParentFolderId(long groupId, long parentFolderId)
1095                    throws SystemException {
1096    
1097                    if (parentFolderId != DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
1098                            DLFolder parentDLFolder = dlFolderPersistence.fetchByPrimaryKey(
1099                                    parentFolderId);
1100    
1101                            if ((parentDLFolder == null) ||
1102                                    (groupId != parentDLFolder.getGroupId())) {
1103    
1104                                    parentFolderId = DLFolderConstants.DEFAULT_PARENT_FOLDER_ID;
1105                            }
1106                    }
1107    
1108                    return parentFolderId;
1109            }
1110    
1111            protected void validateFolder(
1112                            long folderId, long groupId, long parentFolderId, String name)
1113                    throws PortalException, SystemException {
1114    
1115                    validateFolderName(name);
1116    
1117                    try {
1118                            dlFileEntryLocalService.getFileEntry(groupId, parentFolderId, name);
1119    
1120                            throw new DuplicateFileException(name);
1121                    }
1122                    catch (NoSuchFileEntryException nsfee) {
1123                    }
1124    
1125                    DLFolder dlFolder = dlFolderPersistence.fetchByG_P_N(
1126                            groupId, parentFolderId, name);
1127    
1128                    if ((dlFolder != null) && (dlFolder.getFolderId() != folderId)) {
1129                            throw new DuplicateFolderNameException(name);
1130                    }
1131            }
1132    
1133            protected void validateFolder(
1134                            long groupId, long parentFolderId, String name)
1135                    throws PortalException, SystemException {
1136    
1137                    long folderId = 0;
1138    
1139                    validateFolder(folderId, groupId, parentFolderId, name);
1140            }
1141    
1142            protected void validateFolderName(String name) throws PortalException {
1143                    if (!AssetUtil.isValidWord(name)) {
1144                            throw new FolderNameException();
1145                    }
1146            }
1147    
1148            private static Log _log = LogFactoryUtil.getLog(
1149                    DLFolderLocalServiceImpl.class);
1150    
1151    }