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.kernel.dao.orm.QueryUtil;
018    import com.liferay.portal.kernel.exception.PortalException;
019    import com.liferay.portal.kernel.exception.SystemException;
020    import com.liferay.portal.kernel.io.unsync.UnsyncByteArrayInputStream;
021    import com.liferay.portal.kernel.log.Log;
022    import com.liferay.portal.kernel.log.LogFactoryUtil;
023    import com.liferay.portal.kernel.repository.Repository;
024    import com.liferay.portal.kernel.repository.RepositoryException;
025    import com.liferay.portal.kernel.repository.model.FileEntry;
026    import com.liferay.portal.kernel.repository.model.FileVersion;
027    import com.liferay.portal.kernel.repository.model.Folder;
028    import com.liferay.portal.kernel.search.Hits;
029    import com.liferay.portal.kernel.search.Query;
030    import com.liferay.portal.kernel.search.SearchContext;
031    import com.liferay.portal.kernel.search.SearchException;
032    import com.liferay.portal.kernel.transaction.TransactionCommitCallbackRegistryUtil;
033    import com.liferay.portal.kernel.util.FileUtil;
034    import com.liferay.portal.kernel.util.GetterUtil;
035    import com.liferay.portal.kernel.util.OrderByComparator;
036    import com.liferay.portal.kernel.util.StringBundler;
037    import com.liferay.portal.kernel.util.StringPool;
038    import com.liferay.portal.kernel.util.TempFileUtil;
039    import com.liferay.portal.kernel.workflow.WorkflowConstants;
040    import com.liferay.portal.model.Lock;
041    import com.liferay.portal.security.permission.ActionKeys;
042    import com.liferay.portal.service.ServiceContext;
043    import com.liferay.portlet.documentlibrary.NoSuchFileEntryException;
044    import com.liferay.portlet.documentlibrary.model.DLFileShortcut;
045    import com.liferay.portlet.documentlibrary.model.DLFolderConstants;
046    import com.liferay.portlet.documentlibrary.service.base.DLAppServiceBaseImpl;
047    import com.liferay.portlet.documentlibrary.service.permission.DLFolderPermission;
048    import com.liferay.portlet.documentlibrary.util.DLAppUtil;
049    import com.liferay.portlet.documentlibrary.util.DLProcessorRegistryUtil;
050    import com.liferay.portlet.documentlibrary.util.comparator.RepositoryModelModifiedDateComparator;
051    
052    import java.io.File;
053    import java.io.IOException;
054    import java.io.InputStream;
055    
056    import java.util.ArrayList;
057    import java.util.LinkedList;
058    import java.util.List;
059    import java.util.Queue;
060    import java.util.concurrent.Callable;
061    
062    /**
063     * The document library remote service. All portlets should interact with the
064     * document library through this class or through {@link DLAppLocalServiceImpl},
065     * rather than through the individual document library service classes.
066     *
067     * <p>
068     * This class provides a unified interface to all Liferay and third party
069     * repositories. While the method signatures are universal for all repositories.
070     * Additional implementation-specific parameters may be specified in the
071     * serviceContext.
072     * </p>
073     *
074     * <p>
075     * The <code>repositoryId</code> parameter used by most of the methods is the
076     * primary key of the specific repository. If the repository is a default
077     * Liferay repository, the <code>repositoryId</code> is the <code>groupId</code>
078     * or <code>scopeGroupId</code>. Otherwise, the <code>repositoryId</code> will
079     * correspond to values obtained from {@link RepositoryServiceUtil}.
080     * </p>
081     *
082     * @author Alexander Chow
083     * @author Mika Koivisto
084     * @author Shuyang Zhou
085     * @see    DLAppLocalServiceImpl
086     */
087    public class DLAppServiceImpl extends DLAppServiceBaseImpl {
088    
089            /**
090             * Adds a file entry and associated metadata. It is created based on a byte
091             * array.
092             *
093             * <p>
094             * This method takes two file names, the <code>sourceFileName</code> and the
095             * <code>title</code>. The <code>sourceFileName</code> corresponds to the
096             * name of the actual file being uploaded. The <code>title</code>
097             * corresponds to a name the client wishes to assign this file after it has
098             * been uploaded to the portal. If it is <code>null</code>, the <code>
099             * sourceFileName</code> will be used.
100             * </p>
101             *
102             * @param  repositoryId the primary key of the repository
103             * @param  folderId the primary key of the file entry's parent folder
104             * @param  sourceFileName the original file's name
105             * @param  mimeType the file's MIME type
106             * @param  title the name to be assigned to the file (optionally <code>null
107             *         </code>)
108             * @param  description the file's description
109             * @param  changeLog the file's version change log
110             * @param  bytes the file's data (optionally <code>null</code>)
111             * @param  serviceContext the service context to be applied. Can set the
112             *         asset category IDs, asset tag names, and expando bridge
113             *         attributes for the file entry. In a Liferay repository, it may
114             *         include:  <ul> <li> fileEntryTypeId - ID for a custom file entry
115             *         type </li> <li> fieldsMap - mapping for fields associated with a
116             *         custom file entry type </li> </ul>
117             * @return the file entry
118             * @throws PortalException if the parent folder could not be found or if the
119             *         file entry's information was invalid
120             * @throws SystemException if a system exception occurred
121             */
122            @Override
123            public FileEntry addFileEntry(
124                            long repositoryId, long folderId, String sourceFileName,
125                            String mimeType, String title, String description, String changeLog,
126                            byte[] bytes, ServiceContext serviceContext)
127                    throws PortalException, SystemException {
128    
129                    File file = null;
130    
131                    try {
132                            if ((bytes != null) && (bytes.length > 0)) {
133                                    file = FileUtil.createTempFile(bytes);
134                            }
135    
136                            return addFileEntry(
137                                    repositoryId, folderId, sourceFileName, mimeType, title,
138                                    description, changeLog, file, serviceContext);
139                    }
140                    catch (IOException ioe) {
141                            throw new SystemException("Unable to write temporary file", ioe);
142                    }
143                    finally {
144                            FileUtil.delete(file);
145                    }
146            }
147    
148            /**
149             * Adds a file entry and associated metadata. It is created based on a
150             * {@link File} object.
151             *
152             * <p>
153             * This method takes two file names, the <code>sourceFileName</code> and the
154             * <code>title</code>. The <code>sourceFileName</code> corresponds to the
155             * name of the actual file being uploaded. The <code>title</code>
156             * corresponds to a name the client wishes to assign this file after it has
157             * been uploaded to the portal. If it is <code>null</code>, the <code>
158             * sourceFileName</code> will be used.
159             * </p>
160             *
161             * @param  repositoryId the primary key of the repository
162             * @param  folderId the primary key of the file entry's parent folder
163             * @param  sourceFileName the original file's name
164             * @param  mimeType the file's MIME type
165             * @param  title the name to be assigned to the file (optionally <code>null
166             *         </code>)
167             * @param  description the file's description
168             * @param  changeLog the file's version change log
169             * @param  file the file's data (optionally <code>null</code>)
170             * @param  serviceContext the service context to be applied. Can set the
171             *         asset category IDs, asset tag names, and expando bridge
172             *         attributes for the file entry. In a Liferay repository, it may
173             *         include:  <ul> <li> fileEntryTypeId - ID for a custom file entry
174             *         type </li> <li> fieldsMap - mapping for fields associated with a
175             *         custom file entry type </li> </ul>
176             * @return the file entry
177             * @throws PortalException if the parent folder could not be found or if the
178             *         file entry's information was invalid
179             * @throws SystemException if a system exception occurred
180             */
181            @Override
182            public FileEntry addFileEntry(
183                            long repositoryId, long folderId, String sourceFileName,
184                            String mimeType, String title, String description, String changeLog,
185                            File file, ServiceContext serviceContext)
186                    throws PortalException, SystemException {
187    
188                    if ((file == null) || !file.exists() || (file.length() == 0)) {
189                            return addFileEntry(
190                                    repositoryId, folderId, sourceFileName, mimeType, title,
191                                    description, changeLog, null, 0, serviceContext);
192                    }
193    
194                    mimeType = DLAppUtil.getMimeType(
195                            sourceFileName, mimeType, title, file, null);
196    
197                    Repository repository = getRepository(repositoryId);
198    
199                    FileEntry fileEntry = repository.addFileEntry(
200                            folderId, sourceFileName, mimeType, title, description, changeLog,
201                            file, serviceContext);
202    
203                    dlAppHelperLocalService.addFileEntry(
204                            getUserId(), fileEntry, fileEntry.getFileVersion(), serviceContext);
205    
206                    return fileEntry;
207            }
208    
209            /**
210             * Adds a file entry and associated metadata. It is created based on a
211             * {@link InputStream} object.
212             *
213             * <p>
214             * This method takes two file names, the <code>sourceFileName</code> and the
215             * <code>title</code>. The <code>sourceFileName</code> corresponds to the
216             * name of the actual file being uploaded. The <code>title</code>
217             * corresponds to a name the client wishes to assign this file after it has
218             * been uploaded to the portal. If it is <code>null</code>, the <code>
219             * sourceFileName</code> will be used.
220             * </p>
221             *
222             * @param  repositoryId the primary key of the repository
223             * @param  folderId the primary key of the file entry's parent folder
224             * @param  sourceFileName the original file's name
225             * @param  mimeType the file's MIME type
226             * @param  title the name to be assigned to the file (optionally <code>null
227             *         </code>)
228             * @param  description the file's description
229             * @param  changeLog the file's version change log
230             * @param  is the file's data (optionally <code>null</code>)
231             * @param  size the file's size (optionally <code>0</code>)
232             * @param  serviceContext the service context to be applied. Can set the
233             *         asset category IDs, asset tag names, and expando bridge
234             *         attributes for the file entry. In a Liferay repository, it may
235             *         include:  <ul> <li> fileEntryTypeId - ID for a custom file entry
236             *         type </li> <li> fieldsMap - mapping for fields associated with a
237             *         custom file entry type </li> </ul>
238             * @return the file entry
239             * @throws PortalException if the parent folder could not be found or if the
240             *         file entry's information was invalid
241             * @throws SystemException if a system exception occurred
242             */
243            @Override
244            public FileEntry addFileEntry(
245                            long repositoryId, long folderId, String sourceFileName,
246                            String mimeType, String title, String description, String changeLog,
247                            InputStream is, long size, ServiceContext serviceContext)
248                    throws PortalException, SystemException {
249    
250                    if (is == null) {
251                            is = new UnsyncByteArrayInputStream(new byte[0]);
252                            size = 0;
253                    }
254    
255                    mimeType = DLAppUtil.getMimeType(
256                            sourceFileName, mimeType, title, null, is);
257    
258                    Repository repository = getRepository(repositoryId);
259    
260                    FileEntry fileEntry = repository.addFileEntry(
261                            folderId, sourceFileName, mimeType, title, description, changeLog,
262                            is, size, serviceContext);
263    
264                    dlAppHelperLocalService.addFileEntry(
265                            getUserId(), fileEntry, fileEntry.getFileVersion(), serviceContext);
266    
267                    return fileEntry;
268            }
269    
270            /**
271             * Adds a file shortcut to the existing file entry. This method is only
272             * supported by the Liferay repository.
273             *
274             * @param  repositoryId the primary key of the repository
275             * @param  folderId the primary key of the file shortcut's parent folder
276             * @param  toFileEntryId the primary key of the file shortcut's file entry
277             * @param  serviceContext the service context to be applied. Can set the
278             *         asset category IDs, asset tag names, and expando bridge
279             *         attributes for the file entry.
280             * @return the file shortcut
281             * @throws PortalException if the parent folder or file entry could not be
282             *         found, or if the file shortcut's information was invalid
283             * @throws SystemException if a system exception occurred
284             */
285            @Override
286            public DLFileShortcut addFileShortcut(
287                            long repositoryId, long folderId, long toFileEntryId,
288                            ServiceContext serviceContext)
289                    throws PortalException, SystemException {
290    
291                    return dlFileShortcutService.addFileShortcut(
292                            repositoryId, folderId, toFileEntryId, serviceContext);
293            }
294    
295            /**
296             * Adds a folder.
297             *
298             * @param  repositoryId the primary key of the repository
299             * @param  parentFolderId the primary key of the folder's parent folder
300             * @param  name the folder's name
301             * @param  description the folder's description
302             * @param  serviceContext the service context to be applied. In a Liferay
303             *         repository, it may include boolean mountPoint specifying whether
304             *         folder is a facade for mounting a third-party repository
305             * @return the folder
306             * @throws PortalException if the parent folder could not be found or if the
307             *         new folder's information was invalid
308             * @throws SystemException if a system exception occurred
309             */
310            @Override
311            public Folder addFolder(
312                            long repositoryId, long parentFolderId, String name,
313                            String description, ServiceContext serviceContext)
314                    throws PortalException, SystemException {
315    
316                    Repository repository = getRepository(repositoryId);
317    
318                    return repository.addFolder(
319                            parentFolderId, name, description, serviceContext);
320            }
321    
322            /**
323             * Adds a temporary file entry.
324             *
325             * <p>
326             * This allows a client to upload a file into a temporary location and
327             * manipulate its metadata prior to making it available for public usage.
328             * This is different from checking in and checking out a file entry.
329             * </p>
330             *
331             * @param  groupId the primary key of the group
332             * @param  folderId the primary key of the folder where the file entry will
333             *         eventually reside
334             * @param  fileName the file's original name
335             * @param  tempFolderName the temporary folder's name
336             * @param  file Name the file's original name
337             * @return the file's name
338             * @throws IOException if a problem occurred in the access or storage of the
339             *         file
340             * @throws PortalException if the file name was invalid
341             * @throws SystemException if a system exception occurred
342             * @see    com.liferay.portal.kernel.util.TempFileUtil
343             */
344            @Override
345            public String addTempFileEntry(
346                            long groupId, long folderId, String fileName, String tempFolderName,
347                            File file)
348                    throws IOException, PortalException, SystemException {
349    
350                    DLFolderPermission.check(
351                            getPermissionChecker(), groupId, folderId, ActionKeys.ADD_DOCUMENT);
352    
353                    return TempFileUtil.addTempFile(
354                            getUserId(), fileName, tempFolderName, file);
355            }
356    
357            @Override
358            public String addTempFileEntry(
359                            long groupId, long folderId, String fileName, String tempFolderName,
360                            InputStream inputStream)
361                    throws PortalException, SystemException {
362    
363                    DLFolderPermission.check(
364                            getPermissionChecker(), groupId, folderId, ActionKeys.ADD_DOCUMENT);
365    
366                    return TempFileUtil.addTempFile(
367                            getUserId(), fileName, tempFolderName, inputStream);
368            }
369    
370            /**
371             * Cancels the check out of the file entry. If a user has not checked out
372             * the specified file entry, invoking this method will result in no changes.
373             *
374             * <p>
375             * When a file entry is checked out, a PWC (private working copy) is created
376             * and the original file entry is locked. A client can make as many changes
377             * to the PWC as he desires without those changes being visible to other
378             * users. If the user is satisfied with the changes, he may elect to check
379             * in his changes, resulting in a new file version based on the PWC; the PWC
380             * will be removed and the file entry will be unlocked. If the user is not
381             * satisfied with the changes, he may elect to cancel his check out; this
382             * results in the deletion of the PWC and unlocking of the file entry.
383             * </p>
384             *
385             * @param  fileEntryId the primary key of the file entry to cancel the
386             *         checkout
387             * @throws PortalException if the file entry could not be found
388             * @throws SystemException if a system exception occurred
389             * @see    #checkInFileEntry(long, boolean, String, ServiceContext)
390             * @see    #checkOutFileEntry(long)
391             */
392            @Override
393            public void cancelCheckOut(long fileEntryId)
394                    throws PortalException, SystemException {
395    
396                    Repository repository = getRepository(0, fileEntryId, 0);
397    
398                    FileEntry fileEntry = repository.getFileEntry(fileEntryId);
399    
400                    DLProcessorRegistryUtil.cleanUp(fileEntry.getLatestFileVersion());
401    
402                    FileVersion draftFileVersion = repository.cancelCheckOut(fileEntryId);
403    
404                    ServiceContext serviceContext = new ServiceContext();
405    
406                    serviceContext.setWorkflowAction(WorkflowConstants.ACTION_PUBLISH);
407    
408                    dlAppHelperLocalService.cancelCheckOut(
409                            getUserId(), fileEntry, fileEntry.getFileVersion(),
410                            draftFileVersion, serviceContext);
411            }
412    
413            /**
414             * Checks in the file entry. If a user has not checked out the specified
415             * file entry, invoking this method will result in no changes.
416             *
417             * <p>
418             * When a file entry is checked out, a PWC (private working copy) is created
419             * and the original file entry is locked. A client can make as many changes
420             * to the PWC as he desires without those changes being visible to other
421             * users. If the user is satisfied with the changes, he may elect to check
422             * in his changes, resulting in a new file version based on the PWC; the PWC
423             * will be removed and the file entry will be unlocked. If the user is not
424             * satisfied with the changes, he may elect to cancel his check out; this
425             * results in the deletion of the PWC and unlocking of the file entry.
426             * </p>
427             *
428             * @param  fileEntryId the primary key of the file entry to check in
429             * @param  majorVersion whether the new file version is a major version
430             * @param  changeLog the file's version change log
431             * @param  serviceContext the service context to be applied
432             * @throws PortalException if the file entry could not be found
433             * @throws SystemException if a system exception occurred
434             * @see    #cancelCheckOut(long)
435             * @see    #checkOutFileEntry(long)
436             */
437            @Override
438            public void checkInFileEntry(
439                            long fileEntryId, boolean majorVersion, String changeLog,
440                            ServiceContext serviceContext)
441                    throws PortalException, SystemException {
442    
443                    Repository repository = getRepository(0, fileEntryId, 0);
444    
445                    repository.checkInFileEntry(
446                            fileEntryId, majorVersion, changeLog, serviceContext);
447    
448                    FileEntry fileEntry = getFileEntry(fileEntryId);
449    
450                    FileVersion fileVersion = fileEntry.getLatestFileVersion();
451    
452                    dlAppHelperLocalService.updateFileEntry(
453                            getUserId(), fileEntry, fileVersion,
454                            fileVersion.getFileVersionId());
455            }
456    
457            /**
458             * Checks in the file entry using the lock's UUID. If a user has not checked
459             * out the specified file entry, invoking this method will result in no
460             * changes. This method is primarily used by WebDAV.
461             *
462             * <p>
463             * When a file entry is checked out, a PWC (private working copy) is created
464             * and the original file entry is locked. A client can make as many changes
465             * to the PWC as he desires without those changes being visible to other
466             * users. If the user is satisfied with the changes, he may elect to check
467             * in his changes, resulting in a new file version based on the PWC; the PWC
468             * will be removed and the file entry will be unlocked. If the user is not
469             * satisfied with the changes, he may elect to cancel his check out; this
470             * results in the deletion of the PWC and unlocking of the file entry.
471             * </p>
472             *
473             * @param  fileEntryId the primary key of the file entry to check in
474             * @param  lockUuid the lock's universally unique identifier
475             * @throws PortalException if the file entry could not be found
476             * @throws SystemException if a system exception occurred
477             * @see    #cancelCheckOut(long)
478             * @see    #checkOutFileEntry(long, String, long)
479             */
480            @Override
481            public void checkInFileEntry(long fileEntryId, String lockUuid)
482                    throws PortalException, SystemException {
483    
484                    Repository repository = getRepository(0, fileEntryId, 0);
485    
486                    repository.checkInFileEntry(fileEntryId, lockUuid);
487    
488                    FileEntry fileEntry = getFileEntry(fileEntryId);
489    
490                    FileVersion fileVersion = fileEntry.getLatestFileVersion();
491    
492                    dlAppHelperLocalService.updateFileEntry(
493                            getUserId(), fileEntry, fileVersion,
494                            fileVersion.getFileVersionId());
495            }
496    
497            /**
498             * Check out a file entry.
499             *
500             * <p>
501             * When a file entry is checked out, a PWC (private working copy) is created
502             * and the original file entry is locked. A client can make as many changes
503             * to the PWC as he desires without those changes being visible to other
504             * users. If the user is satisfied with the changes, he may elect to check
505             * in his changes, resulting in a new file version based on the PWC; the PWC
506             * will be removed and the file entry will be unlocked. If the user is not
507             * satisfied with the changes, he may elect to cancel his check out; this
508             * results in the deletion of the PWC and unlocking of the file entry.
509             * </p>
510             *
511             * @param  fileEntryId the file entry to check out
512             * @param  serviceContext the service context to be applied
513             * @throws PortalException if the file entry could not be found
514             * @throws SystemException if a system exception occurred
515             * @see    #cancelCheckOut(long)
516             * @see    #checkInFileEntry(long, boolean, String, ServiceContext)
517             */
518            @Override
519            public void checkOutFileEntry(
520                            long fileEntryId, ServiceContext serviceContext)
521                    throws PortalException, SystemException {
522    
523                    Repository repository = getRepository(0, fileEntryId, 0);
524    
525                    FileEntry fileEntry = repository.checkOutFileEntry(
526                            fileEntryId, serviceContext);
527    
528                    FileVersion fileVersion = fileEntry.getLatestFileVersion();
529    
530                    dlAppHelperLocalService.updateFileEntry(
531                            getUserId(), fileEntry, fileVersion, fileEntryId);
532            }
533    
534            /**
535             * Checks out the file entry. This method is primarily used by WebDAV.
536             *
537             * <p>
538             * When a file entry is checked out, a PWC (private working copy) is created
539             * and the original file entry is locked. A client can make as many changes
540             * to the PWC as he desires without those changes being visible to other
541             * users. If the user is satisfied with the changes, he may elect to check
542             * in his changes, resulting in a new file version based on the PWC; the PWC
543             * will be removed and the file entry will be unlocked. If the user is not
544             * satisfied with the changes, he may elect to cancel his check out; this
545             * results in the deletion of the PWC and unlocking of the file entry.
546             * </p>
547             *
548             * @param  fileEntryId the file entry to check out
549             * @param  owner the owner string for the checkout (optionally
550             *         <code>null</code>)
551             * @param  expirationTime the time in milliseconds before the lock expires.
552             *         If the value is <code>0</code>, the default expiration time will
553             *         be used from <code>portal.properties>.
554             * @param  serviceContext the service context to be applied
555             * @return the file entry
556             * @throws PortalException if the file entry could not be found
557             * @throws SystemException if a system exception occurred
558             * @see    #cancelCheckOut(long)
559             * @see    #checkInFileEntry(long, String)
560             */
561            @Override
562            public FileEntry checkOutFileEntry(
563                            long fileEntryId, String owner, long expirationTime,
564                            ServiceContext serviceContext)
565                    throws PortalException, SystemException {
566    
567                    Repository repository = getRepository(0, fileEntryId, 0);
568    
569                    FileEntry fileEntry = repository.checkOutFileEntry(
570                            fileEntryId, owner, expirationTime, serviceContext);
571    
572                    FileVersion fileVersion = fileEntry.getLatestFileVersion();
573    
574                    dlAppHelperLocalService.updateFileEntry(
575                            getUserId(), fileEntry, fileVersion, fileEntryId);
576    
577                    return fileEntry;
578            }
579    
580            /**
581             * Performs a deep copy of the folder.
582             *
583             * @param  repositoryId the primary key of the repository
584             * @param  sourceFolderId the primary key of the folder to copy
585             * @param  parentFolderId the primary key of the new folder's parent folder
586             * @param  name the new folder's name
587             * @param  description the new folder's description
588             * @param  serviceContext the service context to be applied
589             * @return the folder
590             * @throws PortalException if the source folder or the new parent folder
591             *         could not be found or if the new folder's information was invalid
592             * @throws SystemException if a system exception occurred
593             */
594            @Override
595            public Folder copyFolder(
596                            long repositoryId, long sourceFolderId, long parentFolderId,
597                            String name, String description, ServiceContext serviceContext)
598                    throws PortalException, SystemException {
599    
600                    Repository repository = getRepository(repositoryId);
601    
602                    Folder srcFolder = repository.getFolder(sourceFolderId);
603    
604                    Folder destFolder = repository.addFolder(
605                            parentFolderId, name, description, serviceContext);
606    
607                    copyFolder(repository, srcFolder, destFolder, serviceContext);
608    
609                    return destFolder;
610            }
611    
612            /**
613             * Deletes the file entry with the primary key.
614             *
615             * @param  fileEntryId the primary key of the file entry
616             * @throws PortalException if the file entry could not be found
617             * @throws SystemException if a system exception occurred
618             */
619            @Override
620            public void deleteFileEntry(long fileEntryId)
621                    throws PortalException, SystemException {
622    
623                    Repository repository = getRepository(0, fileEntryId, 0);
624    
625                    FileEntry fileEntry = repository.getFileEntry(fileEntryId);
626    
627                    dlAppHelperLocalService.deleteFileEntry(fileEntry);
628    
629                    repository.deleteFileEntry(fileEntryId);
630            }
631    
632            /**
633             * Deletes the file entry with the title in the folder.
634             *
635             * @param  repositoryId the primary key of the repository
636             * @param  folderId the primary key of the file entry's parent folder
637             * @param  title the file entry's title
638             * @throws PortalException if the file entry could not be found
639             * @throws SystemException if a system exception occurred
640             */
641            @Override
642            public void deleteFileEntryByTitle(
643                            long repositoryId, long folderId, String title)
644                    throws PortalException, SystemException {
645    
646                    Repository repository = getRepository(repositoryId);
647    
648                    FileEntry fileEntry = repository.getFileEntry(folderId, title);
649    
650                    dlAppHelperLocalService.deleteFileEntry(fileEntry);
651    
652                    repository.deleteFileEntry(folderId, title);
653            }
654    
655            /**
656             * Deletes the file shortcut with the primary key. This method is only
657             * supported by the Liferay repository.
658             *
659             * @param  fileShortcutId the primary key of the file shortcut
660             * @throws PortalException if the file shortcut could not be found
661             * @throws SystemException if a system exception occurred
662             */
663            @Override
664            public void deleteFileShortcut(long fileShortcutId)
665                    throws PortalException, SystemException {
666    
667                    dlFileShortcutService.deleteFileShortcut(fileShortcutId);
668            }
669    
670            /**
671             * Deletes the file version. File versions can only be deleted if it is
672             * approved and there are other approved file versions available. This
673             * method is only supported by the Liferay repository.
674             *
675             * @param  fileEntryId the primary key of the file entry
676             * @param  version the version label of the file version
677             * @throws PortalException if the file version could not be found or invalid
678             * @throws SystemException if a system exception occurred
679             */
680            @Override
681            public void deleteFileVersion(long fileEntryId, String version)
682                    throws PortalException, SystemException {
683    
684                    Repository repository = getRepository(0, fileEntryId, 0);
685    
686                    repository.deleteFileVersion(fileEntryId, version);
687            }
688    
689            /**
690             * Deletes the folder with the primary key and all of its subfolders and
691             * file entries.
692             *
693             * @param  folderId the primary key of the folder
694             * @throws PortalException if the folder could not be found
695             * @throws SystemException if a system exception occurred
696             */
697            @Override
698            public void deleteFolder(long folderId)
699                    throws PortalException, SystemException {
700    
701                    Repository repository = getRepository(folderId, 0, 0);
702    
703                    repository.deleteFolder(folderId);
704            }
705    
706            /**
707             * Deletes the folder with the name in the parent folder and all of its
708             * subfolders and file entries.
709             *
710             * @param  repositoryId the primary key of the repository
711             * @param  parentFolderId the primary key of the folder's parent folder
712             * @param  name the folder's name
713             * @throws PortalException if the folder could not be found
714             * @throws SystemException if a system exception occurred
715             */
716            @Override
717            public void deleteFolder(
718                            long repositoryId, long parentFolderId, String name)
719                    throws PortalException, SystemException {
720    
721                    Repository repository = getRepository(repositoryId);
722    
723                    repository.deleteFolder(parentFolderId, name);
724            }
725    
726            /**
727             * Deletes the temporary file entry.
728             *
729             * @param  groupId the primary key of the group
730             * @param  folderId the primary key of the folder where the file entry was
731             *         eventually to reside
732             * @param  fileName the file's original name
733             * @param  tempFolderName the temporary folder's name
734             * @throws PortalException if the file name was invalid
735             * @throws SystemException if a system exception occurred
736             * @see    com.liferay.portal.kernel.util.TempFileUtil
737             */
738            @Override
739            public void deleteTempFileEntry(
740                            long groupId, long folderId, String fileName, String tempFolderName)
741                    throws PortalException, SystemException {
742    
743                    DLFolderPermission.check(
744                            getPermissionChecker(), groupId, folderId, ActionKeys.ADD_DOCUMENT);
745    
746                    TempFileUtil.deleteTempFile(getUserId(), fileName, tempFolderName);
747            }
748    
749            /**
750             * Returns all the file entries in the folder.
751             *
752             * @param  repositoryId the primary key of the file entry's repository
753             * @param  folderId the primary key of the file entry's folder
754             * @return the file entries in the folder
755             * @throws PortalException if the folder could not be found
756             * @throws SystemException if a system exception occurred
757             */
758            @Override
759            public List<FileEntry> getFileEntries(long repositoryId, long folderId)
760                    throws PortalException, SystemException {
761    
762                    return getFileEntries(
763                            repositoryId, folderId, QueryUtil.ALL_POS, QueryUtil.ALL_POS);
764            }
765    
766            /**
767             * Returns a range of all the file entries in the folder.
768             *
769             * <p>
770             * Useful when paginating results. Returns a maximum of <code>end -
771             * start</code> instances. <code>start</code> and <code>end</code> are not
772             * primary keys, they are indexes in the result set. Thus, <code>0</code>
773             * refers to the first result in the set. Setting both <code>start</code>
774             * and <code>end</code> to {@link
775             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
776             * result set.
777             * </p>
778             *
779             * @param  repositoryId the primary key of the file entry's repository
780             * @param  folderId the primary key of the file entry's folder
781             * @param  start the lower bound of the range of results
782             * @param  end the upper bound of the range of results (not inclusive)
783             * @return the range of file entries in the folder
784             * @throws PortalException if the folder could not be found
785             * @throws SystemException if a system exception occurred
786             */
787            @Override
788            public List<FileEntry> getFileEntries(
789                            long repositoryId, long folderId, int start, int end)
790                    throws PortalException, SystemException {
791    
792                    return getFileEntries(repositoryId, folderId, start, end, null);
793            }
794    
795            /**
796             * Returns an ordered range of all the file entries in the folder.
797             *
798             * <p>
799             * Useful when paginating results. Returns a maximum of <code>end -
800             * start</code> instances. <code>start</code> and <code>end</code> are not
801             * primary keys, they are indexes in the result set. Thus, <code>0</code>
802             * refers to the first result in the set. Setting both <code>start</code>
803             * and <code>end</code> to {@link
804             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
805             * result set.
806             * </p>
807             *
808             * @param  repositoryId the primary key of the file entry's repository
809             * @param  folderId the primary key of the file entry's folder
810             * @param  start the lower bound of the range of results
811             * @param  end the upper bound of the range of results (not inclusive)
812             * @param  obc the comparator to order the file entries (optionally
813             *         <code>null</code>)
814             * @return the range of file entries in the folder ordered by comparator
815             *         <code>obc</code>
816             * @throws PortalException if the folder could not be found
817             * @throws SystemException if a system exception occurred
818             */
819            @Override
820            public List<FileEntry> getFileEntries(
821                            long repositoryId, long folderId, int start, int end,
822                            OrderByComparator obc)
823                    throws PortalException, SystemException {
824    
825                    Repository repository = getRepository(repositoryId);
826    
827                    return repository.getFileEntries(folderId, start, end, obc);
828            }
829    
830            /**
831             * Returns the file entries with the file entry type in the folder.
832             *
833             * @param  repositoryId the primary key of the file entry's repository
834             * @param  folderId the primary key of the file entry's folder
835             * @param  fileEntryTypeId the primary key of the file entry type
836             * @return the file entries with the file entry type in the folder
837             * @throws PortalException if the folder could not be found
838             * @throws SystemException if a system exception occurred
839             */
840            @Override
841            public List<FileEntry> getFileEntries(
842                            long repositoryId, long folderId, long fileEntryTypeId)
843                    throws PortalException, SystemException {
844    
845                    return getFileEntries(
846                            repositoryId, folderId, fileEntryTypeId, QueryUtil.ALL_POS,
847                            QueryUtil.ALL_POS);
848            }
849    
850            /**
851             * Returns a range of all the file entries with the file entry type in the
852             * folder.
853             *
854             * @param  repositoryId the primary key of the file entry's repository
855             * @param  folderId the primary key of the file entry's folder
856             * @param  fileEntryTypeId the primary key of the file entry type
857             * @param  start the lower bound of the range of results
858             * @param  end the upper bound of the range of results (not inclusive)
859             * @return the file entries in the folder
860             * @throws PortalException if the folder could not be found
861             * @throws SystemException if a system exception occurred
862             */
863            @Override
864            public List<FileEntry> getFileEntries(
865                            long repositoryId, long folderId, long fileEntryTypeId, int start,
866                            int end)
867                    throws PortalException, SystemException {
868    
869                    return getFileEntries(
870                            repositoryId, folderId, fileEntryTypeId, start, end, null);
871            }
872    
873            /**
874             * Returns an ordered range of all the file entries with the file entry type
875             * in the folder.
876             *
877             * @param  repositoryId the primary key of the repository
878             * @param  folderId the primary key of the folder
879             * @param  fileEntryTypeId the primary key of the file entry type
880             * @param  start the lower bound of the range of results
881             * @param  end the upper bound of the range of results (not inclusive)
882             * @param  obc the comparator to order the results by (optionally
883             *         <code>null</code>)
884             * @return the range of file entries with the file entry type in the folder
885             *         ordered by <code>null</code>
886             * @throws PortalException if the folder could not be found
887             * @throws SystemException if a system exception occurred
888             */
889            @Override
890            public List<FileEntry> getFileEntries(
891                            long repositoryId, long folderId, long fileEntryTypeId, int start,
892                            int end, OrderByComparator obc)
893                    throws PortalException, SystemException {
894    
895                    Repository repository = getRepository(repositoryId);
896    
897                    return repository.getFileEntries(
898                            folderId, fileEntryTypeId, start, end, obc);
899            }
900    
901            /**
902             * Returns a range of all the file entries and shortcuts in the folder.
903             *
904             * <p>
905             * Useful when paginating results. Returns a maximum of <code>end -
906             * start</code> instances. <code>start</code> and <code>end</code> are not
907             * primary keys, they are indexes in the result set. Thus, <code>0</code>
908             * refers to the first result in the set. Setting both <code>start</code>
909             * and <code>end</code> to {@link
910             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
911             * result set.
912             * </p>
913             *
914             * @param  repositoryId the primary key of the repository
915             * @param  folderId the primary key of the folder
916             * @param  status the workflow status
917             * @param  start the lower bound of the range of results
918             * @param  end the upper bound of the range of results (not inclusive)
919             * @return the range of file entries and shortcuts in the folder
920             * @throws PortalException if the folder could not be found
921             * @throws SystemException if a system exception occurred
922             */
923            @Override
924            public List<Object> getFileEntriesAndFileShortcuts(
925                            long repositoryId, long folderId, int status, int start, int end)
926                    throws PortalException, SystemException {
927    
928                    Repository repository = getRepository(repositoryId);
929    
930                    return repository.getFileEntriesAndFileShortcuts(
931                            folderId, status, start, end);
932            }
933    
934            /**
935             * Returns the number of file entries and shortcuts in the folder.
936             *
937             * @param  repositoryId the primary key of the repository
938             * @param  folderId the primary key of the folder
939             * @param  status the workflow status
940             * @return the number of file entries and shortcuts in the folder
941             * @throws PortalException if the folder ould not be found
942             * @throws SystemException if a system exception occurred
943             */
944            @Override
945            public int getFileEntriesAndFileShortcutsCount(
946                            long repositoryId, long folderId, int status)
947                    throws PortalException, SystemException {
948    
949                    Repository repository = getRepository(repositoryId);
950    
951                    return repository.getFileEntriesAndFileShortcutsCount(folderId, status);
952            }
953    
954            /**
955             * Returns the number of file entries and shortcuts in the folder.
956             *
957             * @param  repositoryId the primary key of the repository
958             * @param  folderId the primary key of the folder
959             * @param  status the workflow status
960             * @param  mimeTypes allowed media types
961             * @return the number of file entries and shortcuts in the folder
962             * @throws PortalException if the folder ould not be found
963             * @throws SystemException if a system exception occurred
964             */
965            @Override
966            public int getFileEntriesAndFileShortcutsCount(
967                            long repositoryId, long folderId, int status, String[] mimeTypes)
968                    throws PortalException, SystemException {
969    
970                    Repository repository = getRepository(repositoryId);
971    
972                    return repository.getFileEntriesAndFileShortcutsCount(
973                            folderId, status, mimeTypes);
974            }
975    
976            /**
977             * Returns the number of file entries in the folder.
978             *
979             * @param  repositoryId the primary key of the file entry's repository
980             * @param  folderId the primary key of the file entry's folder
981             * @return the number of file entries in the folder
982             * @throws PortalException if the folder could not be found
983             * @throws SystemException if a system exception occurred
984             */
985            @Override
986            public int getFileEntriesCount(long repositoryId, long folderId)
987                    throws PortalException, SystemException {
988    
989                    Repository repository = getRepository(repositoryId);
990    
991                    return repository.getFileEntriesCount(folderId);
992            }
993    
994            /**
995             * Returns the number of file entries with the file entry type in the
996             * folder.
997             *
998             * @param  repositoryId the primary key of the file entry's repository
999             * @param  folderId the primary key of the file entry's folder
1000             * @param  fileEntryTypeId the primary key of the file entry type
1001             * @return the number of file entries with the file entry type in the folder
1002             * @throws PortalException if the folder could not be found
1003             * @throws SystemException if a system exception occurred
1004             */
1005            @Override
1006            public int getFileEntriesCount(
1007                            long repositoryId, long folderId, long fileEntryTypeId)
1008                    throws PortalException, SystemException {
1009    
1010                    Repository repository = getRepository(repositoryId);
1011    
1012                    return repository.getFileEntriesCount(folderId, fileEntryTypeId);
1013            }
1014    
1015            /**
1016             * Returns the file entry with the primary key.
1017             *
1018             * @param  fileEntryId the primary key of the file entry
1019             * @return the file entry with the primary key
1020             * @throws PortalException if the file entry could not be found
1021             * @throws SystemException if a system exception occurred
1022             */
1023            @Override
1024            public FileEntry getFileEntry(long fileEntryId)
1025                    throws PortalException, SystemException {
1026    
1027                    Repository repository = getRepository(0, fileEntryId, 0);
1028    
1029                    return repository.getFileEntry(fileEntryId);
1030            }
1031    
1032            /**
1033             * Returns the file entry with the title in the folder.
1034             *
1035             * @param  groupId the primary key of the file entry's group
1036             * @param  folderId the primary key of the file entry's folder
1037             * @param  title the file entry's title
1038             * @return the file entry with the title in the folder
1039             * @throws PortalException if the file entry could not be found
1040             * @throws SystemException if a system exception occurred
1041             */
1042            @Override
1043            public FileEntry getFileEntry(long groupId, long folderId, String title)
1044                    throws PortalException, SystemException {
1045    
1046                    try {
1047                            Repository repository = getRepository(groupId);
1048    
1049                            return repository.getFileEntry(folderId, title);
1050                    }
1051                    catch (NoSuchFileEntryException nsfee) {
1052                            if (folderId != DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
1053                                    Repository repository = getRepository(folderId, 0, 0);
1054    
1055                                    return repository.getFileEntry(folderId, title);
1056                            }
1057                            else {
1058                                    throw nsfee;
1059                            }
1060                    }
1061            }
1062    
1063            /**
1064             * Returns the file entry with the UUID and group.
1065             *
1066             * @param  uuid the file entry's universally unique identifier
1067             * @param  groupId the primary key of the file entry's group
1068             * @return the file entry with the UUID and group
1069             * @throws PortalException if the file entry could not be found
1070             * @throws SystemException if a system exception occurred
1071             */
1072            @Override
1073            public FileEntry getFileEntryByUuidAndGroupId(String uuid, long groupId)
1074                    throws PortalException, SystemException {
1075    
1076                    try {
1077                            Repository repository = getRepository(groupId);
1078    
1079                            return repository.getFileEntryByUuid(uuid);
1080                    }
1081                    catch (NoSuchFileEntryException nsfee) {
1082                    }
1083                    catch (RepositoryException re) {
1084                            throw new NoSuchFileEntryException(re);
1085                    }
1086    
1087                    List<com.liferay.portal.model.Repository> repositories =
1088                            repositoryPersistence.findByGroupId(groupId);
1089    
1090                    for (int i = 0; i < repositories.size(); i++) {
1091                            try {
1092                                    long repositoryId = repositories.get(i).getRepositoryId();
1093    
1094                                    Repository repository = getRepository(repositoryId);
1095    
1096                                    return repository.getFileEntryByUuid(uuid);
1097                            }
1098                            catch (NoSuchFileEntryException nsfee) {
1099                            }
1100                    }
1101    
1102                    StringBundler msg = new StringBundler(6);
1103    
1104                    msg.append("No DLFileEntry exists with the key {");
1105                    msg.append("uuid=");
1106                    msg.append(uuid);
1107                    msg.append(", groupId=");
1108                    msg.append(groupId);
1109                    msg.append(StringPool.CLOSE_CURLY_BRACE);
1110    
1111                    throw new NoSuchFileEntryException(msg.toString());
1112            }
1113    
1114            /**
1115             * Returns the file shortcut with the primary key. This method is only
1116             * supported by the Liferay repository.
1117             *
1118             * @param  fileShortcutId the primary key of the file shortcut
1119             * @return the file shortcut with the primary key
1120             * @throws PortalException if the file shortcut could not be found
1121             * @throws SystemException if a system exception occurred
1122             */
1123            @Override
1124            public DLFileShortcut getFileShortcut(long fileShortcutId)
1125                    throws PortalException, SystemException {
1126    
1127                    return dlFileShortcutService.getFileShortcut(fileShortcutId);
1128            }
1129    
1130            /**
1131             * Returns the folder with the primary key.
1132             *
1133             * @param  folderId the primary key of the folder
1134             * @return the folder with the primary key
1135             * @throws PortalException if the folder could not be found
1136             * @throws SystemException if a system exception occurred
1137             */
1138            @Override
1139            public Folder getFolder(long folderId)
1140                    throws PortalException, SystemException {
1141    
1142                    Repository repository = getRepository(folderId, 0, 0);
1143    
1144                    return repository.getFolder(folderId);
1145            }
1146    
1147            /**
1148             * Returns the folder with the name in the parent folder.
1149             *
1150             * @param  repositoryId the primary key of the folder's repository
1151             * @param  parentFolderId the primary key of the folder's parent folder
1152             * @param  name the folder's name
1153             * @return the folder with the name in the parent folder
1154             * @throws PortalException if the folder could not be found
1155             * @throws SystemException if a system exception occurred
1156             */
1157            @Override
1158            public Folder getFolder(long repositoryId, long parentFolderId, String name)
1159                    throws PortalException, SystemException {
1160    
1161                    Repository repository = getRepository(repositoryId);
1162    
1163                    return repository.getFolder(parentFolderId, name);
1164            }
1165    
1166            /**
1167             * Returns all immediate subfolders of the parent folder.
1168             *
1169             * @param  repositoryId the primary key of the folder's repository
1170             * @param  parentFolderId the primary key of the folder's parent folder
1171             * @return the immediate subfolders of the parent folder
1172             * @throws PortalException if the parent folder could not be found
1173             * @throws SystemException if a system exception occurred
1174             */
1175            @Override
1176            public List<Folder> getFolders(long repositoryId, long parentFolderId)
1177                    throws PortalException, SystemException {
1178    
1179                    return getFolders(
1180                            repositoryId, parentFolderId, QueryUtil.ALL_POS, QueryUtil.ALL_POS);
1181            }
1182    
1183            /**
1184             * Returns all immediate subfolders of the parent folder, optionally
1185             * including mount folders for third-party repositories.
1186             *
1187             * @param  repositoryId the primary key of the folder's repository
1188             * @param  parentFolderId the primary key of the folder's parent folder
1189             * @param  includeMountFolders whether to include mount folders for
1190             *         third-party repositories
1191             * @return the immediate subfolders of the parent folder
1192             * @throws PortalException if the parent folder could not be found
1193             * @throws SystemException if a system exception occurred
1194             */
1195            @Override
1196            public List<Folder> getFolders(
1197                            long repositoryId, long parentFolderId, boolean includeMountFolders)
1198                    throws PortalException, SystemException {
1199    
1200                    return getFolders(
1201                            repositoryId, parentFolderId, includeMountFolders,
1202                            QueryUtil.ALL_POS, QueryUtil.ALL_POS);
1203            }
1204    
1205            /**
1206             * Returns a range of all the immediate subfolders of the parent folder,
1207             * optionally including mount folders for third-party repositories.
1208             *
1209             * <p>
1210             * Useful when paginating results. Returns a maximum of <code>end -
1211             * start</code> instances. <code>start</code> and <code>end</code> are not
1212             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1213             * refers to the first result in the set. Setting both <code>start</code>
1214             * and <code>end</code> to {@link
1215             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1216             * result set.
1217             * </p>
1218             *
1219             * @param  repositoryId the primary key of the folder's repository
1220             * @param  parentFolderId the primary key of the folder's parent folder
1221             * @param  includeMountFolders whether to include mount folders for
1222             *         third-party repositories
1223             * @param  start the lower bound of the range of results
1224             * @param  end the upper bound of the range of results (not inclusive)
1225             * @return the range of immediate subfolders of the parent folder
1226             * @throws PortalException if the parent folder could not be found
1227             * @throws SystemException if a system exception occurred
1228             */
1229            @Override
1230            public List<Folder> getFolders(
1231                            long repositoryId, long parentFolderId, boolean includeMountFolders,
1232                            int start, int end)
1233                    throws PortalException, SystemException {
1234    
1235                    return getFolders(
1236                            repositoryId, parentFolderId, includeMountFolders, start, end,
1237                            null);
1238            }
1239    
1240            /**
1241             * Returns an ordered range of all the immediate subfolders of the parent
1242             * folder.
1243             *
1244             * <p>
1245             * Useful when paginating results. Returns a maximum of <code>end -
1246             * start</code> instances. <code>start</code> and <code>end</code> are not
1247             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1248             * refers to the first result in the set. Setting both <code>start</code>
1249             * and <code>end</code> to {@link
1250             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1251             * result set.
1252             * </p>
1253             *
1254             * @param  repositoryId the primary key of the folder's repository
1255             * @param  parentFolderId the primary key of the folder's parent folder
1256             * @param  includeMountFolders whether to include mount folders for
1257             *         third-party repositories
1258             * @param  start the lower bound of the range of results
1259             * @param  end the upper bound of the range of results (not inclusive)
1260             * @param  obc the comparator to order the folders (optionally
1261             *         <code>null</code>)
1262             * @return the range of immediate subfolders of the parent folder ordered by
1263             *         comparator <code>obc</code>
1264             * @throws PortalException if the parent folder could not be found
1265             * @throws SystemException if a system exception occurred
1266             */
1267            @Override
1268            public List<Folder> getFolders(
1269                            long repositoryId, long parentFolderId, boolean includeMountFolders,
1270                            int start, int end, OrderByComparator obc)
1271                    throws PortalException, SystemException {
1272    
1273                    Repository repository = getRepository(repositoryId);
1274    
1275                    return repository.getFolders(
1276                            parentFolderId, includeMountFolders, start, end, obc);
1277            }
1278    
1279            /**
1280             * Returns a range of all the immediate subfolders of the parent folder.
1281             *
1282             * <p>
1283             * Useful when paginating results. Returns a maximum of <code>end -
1284             * start</code> instances. <code>start</code> and <code>end</code> are not
1285             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1286             * refers to the first result in the set. Setting both <code>start</code>
1287             * and <code>end</code> to {@link
1288             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1289             * result set.
1290             * </p>
1291             *
1292             * @param  repositoryId the primary key of the folder's repository
1293             * @param  parentFolderId the primary key of the folder's parent folder
1294             * @param  start the lower bound of the range of results
1295             * @param  end the upper bound of the range of results (not inclusive)
1296             * @return the range of immediate subfolders of the parent folder
1297             * @throws PortalException if the parent folder could not be found
1298             * @throws SystemException if a system exception occurred
1299             */
1300            @Override
1301            public List<Folder> getFolders(
1302                            long repositoryId, long parentFolderId, int start, int end)
1303                    throws PortalException, SystemException {
1304    
1305                    return getFolders(repositoryId, parentFolderId, start, end, null);
1306            }
1307    
1308            /**
1309             * Returns an ordered range of all the immediate subfolders of the parent
1310             * folder.
1311             *
1312             * <p>
1313             * Useful when paginating results. Returns a maximum of <code>end -
1314             * start</code> instances. <code>start</code> and <code>end</code> are not
1315             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1316             * refers to the first result in the set. Setting both <code>start</code>
1317             * and <code>end</code> to {@link
1318             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1319             * result set.
1320             * </p>
1321             *
1322             * @param  repositoryId the primary key of the folder's repository
1323             * @param  parentFolderId the primary key of the folder's parent folder
1324             * @param  start the lower bound of the range of results
1325             * @param  end the upper bound of the range of results (not inclusive)
1326             * @param  obc the comparator to order the folders (optionally
1327             *         <code>null</code>)
1328             * @return the range of immediate subfolders of the parent folder ordered by
1329             *         comparator <code>obc</code>
1330             * @throws PortalException if the parent folder could not be found
1331             * @throws SystemException if a system exception occurred
1332             */
1333            @Override
1334            public List<Folder> getFolders(
1335                            long repositoryId, long parentFolderId, int start, int end,
1336                            OrderByComparator obc)
1337                    throws PortalException, SystemException {
1338    
1339                    Repository repository = getRepository(repositoryId);
1340    
1341                    return repository.getFolders(parentFolderId, true, start, end, obc);
1342            }
1343    
1344            /**
1345             * Returns a range of all the immediate subfolders, file entries, and file
1346             * shortcuts in the parent folder.
1347             *
1348             * <p>
1349             * Useful when paginating results. Returns a maximum of <code>end -
1350             * start</code> instances. <code>start</code> and <code>end</code> are not
1351             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1352             * refers to the first result in the set. Setting both <code>start</code>
1353             * and <code>end</code> to {@link
1354             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1355             * result set.
1356             * </p>
1357             *
1358             * @param  repositoryId the primary key of the repository
1359             * @param  folderId the primary key of the parent folder
1360             * @param  status the workflow status
1361             * @param  includeMountFolders whether to include mount folders for
1362             *         third-party repositories
1363             * @param  start the lower bound of the range of results
1364             * @param  end the upper bound of the range of results (not inclusive)
1365             * @return the range of immediate subfolders, file entries, and file
1366             *         shortcuts in the parent folder ordered by comparator
1367             *         <code>obc</code>
1368             * @throws PortalException if the parent folder could not be found
1369             * @throws SystemException if a system exception occurred
1370             */
1371            @Override
1372            public List<Object> getFoldersAndFileEntriesAndFileShortcuts(
1373                            long repositoryId, long folderId, int status,
1374                            boolean includeMountFolders, int start, int end)
1375                    throws PortalException, SystemException {
1376    
1377                    return getFoldersAndFileEntriesAndFileShortcuts(
1378                            repositoryId, folderId, status, includeMountFolders, start, end,
1379                            null);
1380            }
1381    
1382            /**
1383             * Returns an ordered range of all the immediate subfolders, file entries,
1384             * and file shortcuts in the parent folder.
1385             *
1386             * <p>
1387             * Useful when paginating results. Returns a maximum of <code>end -
1388             * start</code> instances. <code>start</code> and <code>end</code> are not
1389             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1390             * refers to the first result in the set. Setting both <code>start</code>
1391             * and <code>end</code> to {@link
1392             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1393             * result set.
1394             * </p>
1395             *
1396             * @param  repositoryId the primary key of the repository
1397             * @param  folderId the primary key of the parent folder
1398             * @param  status the workflow status
1399             * @param  includeMountFolders whether to include mount folders for
1400             *         third-party repositories
1401             * @param  start the lower bound of the range of results
1402             * @param  end the upper bound of the range of results (not inclusive)
1403             * @param  obc the comparator to order the results (optionally
1404             *         <code>null</code>)
1405             * @return the range of immediate subfolders, file entries, and file
1406             *         shortcuts in the parent folder ordered by comparator
1407             *         <code>obc</code>
1408             * @throws PortalException if the parent folder could not be found
1409             * @throws SystemException if a system exception occurred
1410             */
1411            @Override
1412            public List<Object> getFoldersAndFileEntriesAndFileShortcuts(
1413                            long repositoryId, long folderId, int status,
1414                            boolean includeMountFolders, int start, int end,
1415                            OrderByComparator obc)
1416                    throws PortalException, SystemException {
1417    
1418                    return getFoldersAndFileEntriesAndFileShortcuts(
1419                            repositoryId, folderId, status, null, includeMountFolders, start,
1420                            end, obc);
1421            }
1422    
1423            @Override
1424            public List<Object> getFoldersAndFileEntriesAndFileShortcuts(
1425                            long repositoryId, long folderId, int status, String[] mimeTypes,
1426                            boolean includeMountFolders, int start, int end,
1427                            OrderByComparator obc)
1428                    throws PortalException, SystemException {
1429    
1430                    Repository repository = getRepository(repositoryId);
1431    
1432                    return repository.getFoldersAndFileEntriesAndFileShortcuts(
1433                            folderId, status, mimeTypes, includeMountFolders, start, end, obc);
1434            }
1435    
1436            /**
1437             * Returns the number of immediate subfolders, file entries, and file
1438             * shortcuts in the parent folder.
1439             *
1440             * @param  repositoryId the primary key of the repository
1441             * @param  folderId the primary key of the parent folder
1442             * @param  status the workflow status
1443             * @param  includeMountFolders whether to include mount folders for
1444             *         third-party repositories
1445             * @return the number of immediate subfolders, file entries, and file
1446             *         shortcuts in the parent folder
1447             * @throws PortalException if the folder could not be found
1448             * @throws SystemException if a system exception occurred
1449             */
1450            @Override
1451            public int getFoldersAndFileEntriesAndFileShortcutsCount(
1452                            long repositoryId, long folderId, int status,
1453                            boolean includeMountFolders)
1454                    throws PortalException, SystemException {
1455    
1456                    return getFoldersAndFileEntriesAndFileShortcutsCount(
1457                            repositoryId, folderId, status, null, includeMountFolders);
1458            }
1459    
1460            @Override
1461            public int getFoldersAndFileEntriesAndFileShortcutsCount(
1462                            long repositoryId, long folderId, int status, String[] mimeTypes,
1463                            boolean includeMountFolders)
1464                    throws PortalException, SystemException {
1465    
1466                    Repository repository = getRepository(repositoryId);
1467    
1468                    return repository.getFoldersAndFileEntriesAndFileShortcutsCount(
1469                            folderId, status, mimeTypes, includeMountFolders);
1470            }
1471    
1472            /**
1473             * Returns the number of immediate subfolders of the parent folder.
1474             *
1475             * @param  repositoryId the primary key of the folder's repository
1476             * @param  parentFolderId the primary key of the folder's parent folder
1477             * @return the number of immediate subfolders of the parent folder
1478             * @throws PortalException if the parent folder could not be found
1479             * @throws SystemException if a system exception occurred
1480             */
1481            @Override
1482            public int getFoldersCount(long repositoryId, long parentFolderId)
1483                    throws PortalException, SystemException {
1484    
1485                    return getFoldersCount(repositoryId, parentFolderId, true);
1486            }
1487    
1488            /**
1489             * Returns the number of immediate subfolders of the parent folder,
1490             * optionally including mount folders for third-party repositories.
1491             *
1492             * @param  repositoryId the primary key of the folder's repository
1493             * @param  parentFolderId the primary key of the folder's parent folder
1494             * @param  includeMountFolders whether to include mount folders for
1495             *         third-party repositories
1496             * @return the number of immediate subfolders of the parent folder
1497             * @throws PortalException if the parent folder could not be found
1498             * @throws SystemException if a system exception occurred
1499             */
1500            @Override
1501            public int getFoldersCount(
1502                            long repositoryId, long parentFolderId, boolean includeMountFolders)
1503                    throws PortalException, SystemException {
1504    
1505                    Repository repository = getRepository(repositoryId);
1506    
1507                    return repository.getFoldersCount(parentFolderId, includeMountFolders);
1508            }
1509    
1510            /**
1511             * Returns the number of immediate subfolders and file entries across the
1512             * folders.
1513             *
1514             * @param  repositoryId the primary key of the repository
1515             * @param  folderIds the primary keys of folders from which to count
1516             *         immediate subfolders and file entries
1517             * @param  status the workflow status
1518             * @return the number of immediate subfolders and file entries across the
1519             *         folders
1520             * @throws PortalException if the repository could not be found
1521             * @throws SystemException if a system exception occurred
1522             */
1523            @Override
1524            public int getFoldersFileEntriesCount(
1525                            long repositoryId, List<Long> folderIds, int status)
1526                    throws PortalException, SystemException {
1527    
1528                    Repository repository = getRepository(repositoryId);
1529    
1530                    return repository.getFoldersFileEntriesCount(folderIds, status);
1531            }
1532    
1533            /**
1534             * Returns an ordered range of all the file entries in the group starting at
1535             * the repository default parent folder that are stored within the Liferay
1536             * repository. This method is primarily used to search for recently modified
1537             * file entries. It can be limited to the file entries modified by a given
1538             * user.
1539             *
1540             * <p>
1541             * Useful when paginating results. Returns a maximum of <code>end -
1542             * start</code> instances. <code>start</code> and <code>end</code> are not
1543             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1544             * refers to the first result in the set. Setting both <code>start</code>
1545             * and <code>end</code> to {@link
1546             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1547             * result set.
1548             * </p>
1549             *
1550             * @param  groupId the primary key of the group
1551             * @param  userId the primary key of the user who created the file
1552             *         (optionally <code>0</code>)
1553             * @param  start the lower bound of the range of results
1554             * @param  end the upper bound of the range of results (not inclusive)
1555             * @return the range of matching file entries ordered by date modified
1556             * @throws PortalException if the group could not be found
1557             * @throws SystemException if a system exception occurred
1558             */
1559            @Override
1560            public List<FileEntry> getGroupFileEntries(
1561                            long groupId, long userId, int start, int end)
1562                    throws PortalException, SystemException {
1563    
1564                    return getGroupFileEntries(
1565                            groupId, userId, DLFolderConstants.DEFAULT_PARENT_FOLDER_ID, start,
1566                            end, new RepositoryModelModifiedDateComparator());
1567            }
1568    
1569            /**
1570             * Returns an ordered range of all the file entries in the group that are
1571             * stored within the Liferay repository. This method is primarily used to
1572             * search for recently modified file entries. It can be limited to the file
1573             * entries modified by a given user.
1574             *
1575             * <p>
1576             * Useful when paginating results. Returns a maximum of <code>end -
1577             * start</code> instances. <code>start</code> and <code>end</code> are not
1578             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1579             * refers to the first result in the set. Setting both <code>start</code>
1580             * and <code>end</code> to {@link
1581             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1582             * result set.
1583             * </p>
1584             *
1585             * @param  groupId the primary key of the group
1586             * @param  userId the primary key of the user who created the file
1587             *         (optionally <code>0</code>)
1588             * @param  start the lower bound of the range of results
1589             * @param  end the upper bound of the range of results (not inclusive)
1590             * @param  obc the comparator to order the file entries (optionally
1591             *         <code>null</code>)
1592             * @return the range of matching file entries ordered by comparator
1593             *         <code>obc</code>
1594             * @throws PortalException if the group could not be found
1595             * @throws SystemException if a system exception occurred
1596             */
1597            @Override
1598            public List<FileEntry> getGroupFileEntries(
1599                            long groupId, long userId, int start, int end,
1600                            OrderByComparator obc)
1601                    throws PortalException, SystemException {
1602    
1603                    return getGroupFileEntries(
1604                            groupId, userId, DLFolderConstants.DEFAULT_PARENT_FOLDER_ID, start,
1605                            end, obc);
1606            }
1607    
1608            /**
1609             * Returns an ordered range of all the file entries in the group starting at
1610             * the root folder that are stored within the Liferay repository. This
1611             * method is primarily used to search for recently modified file entries. It
1612             * can be limited to the file entries modified by a given user.
1613             *
1614             * <p>
1615             * Useful when paginating results. Returns a maximum of <code>end -
1616             * start</code> instances. <code>start</code> and <code>end</code> are not
1617             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1618             * refers to the first result in the set. Setting both <code>start</code>
1619             * and <code>end</code> to {@link
1620             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1621             * result set.
1622             * </p>
1623             *
1624             * @param  groupId the primary key of the group
1625             * @param  userId the primary key of the user who created the file
1626             *         (optionally <code>0</code>)
1627             * @param  rootFolderId the primary key of the root folder to begin the
1628             *         search
1629             * @param  start the lower bound of the range of results
1630             * @param  end the upper bound of the range of results (not inclusive)
1631             * @return the range of matching file entries ordered by date modified
1632             * @throws PortalException if the group could not be found
1633             * @throws SystemException if a system exception occurred
1634             */
1635            @Override
1636            public List<FileEntry> getGroupFileEntries(
1637                            long groupId, long userId, long rootFolderId, int start, int end)
1638                    throws PortalException, SystemException {
1639    
1640                    return getGroupFileEntries(
1641                            groupId, userId, rootFolderId, start, end,
1642                            new RepositoryModelModifiedDateComparator());
1643            }
1644    
1645            /**
1646             * Returns an ordered range of all the file entries in the group starting at
1647             * the root folder that are stored within the Liferay repository. This
1648             * method is primarily used to search for recently modified file entries. It
1649             * can be limited to the file entries modified by a given user.
1650             *
1651             * <p>
1652             * Useful when paginating results. Returns a maximum of <code>end -
1653             * start</code> instances. <code>start</code> and <code>end</code> are not
1654             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1655             * refers to the first result in the set. Setting both <code>start</code>
1656             * and <code>end</code> to {@link
1657             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1658             * result set.
1659             * </p>
1660             *
1661             * @param  groupId the primary key of the group
1662             * @param  userId the primary key of the user who created the file
1663             *         (optionally <code>0</code>)
1664             * @param  rootFolderId the primary key of the root folder to begin the
1665             *         search
1666             * @param  start the lower bound of the range of results
1667             * @param  end the upper bound of the range of results (not inclusive)
1668             * @param  obc the comparator to order the file entries (optionally
1669             *         <code>null</code>)
1670             * @return the range of matching file entries ordered by comparator
1671             *         <code>obc</code>
1672             * @throws PortalException if the group could not be found
1673             * @throws SystemException if a system exception occurred
1674             */
1675            @Override
1676            public List<FileEntry> getGroupFileEntries(
1677                            long groupId, long userId, long rootFolderId, int start, int end,
1678                            OrderByComparator obc)
1679                    throws PortalException, SystemException {
1680    
1681                    Repository repository = getRepository(groupId);
1682    
1683                    return repository.getRepositoryFileEntries(
1684                            userId, rootFolderId, start, end, obc);
1685            }
1686    
1687            @Override
1688            public List<FileEntry> getGroupFileEntries(
1689                            long groupId, long userId, long rootFolderId, String[] mimeTypes,
1690                            int status, int start, int end, OrderByComparator obc)
1691                    throws PortalException, SystemException {
1692    
1693                    Repository repository = getRepository(groupId);
1694    
1695                    return repository.getRepositoryFileEntries(
1696                            userId, rootFolderId, mimeTypes, status, start, end, obc);
1697            }
1698    
1699            /**
1700             * Returns the number of file entries in a group starting at the repository
1701             * default parent folder that are stored within the Liferay repository. This
1702             * method is primarily used to search for recently modified file entries. It
1703             * can be limited to the file entries modified by a given user.
1704             *
1705             * @param  groupId the primary key of the group
1706             * @param  userId the primary key of the user who created the file
1707             *         (optionally <code>0</code>)
1708             * @return the number of matching file entries
1709             * @throws PortalException if the group could not be found
1710             * @throws SystemException if a system exception occurred
1711             */
1712            @Override
1713            public int getGroupFileEntriesCount(long groupId, long userId)
1714                    throws PortalException, SystemException {
1715    
1716                    return getGroupFileEntriesCount(
1717                            groupId, userId, DLFolderConstants.DEFAULT_PARENT_FOLDER_ID);
1718            }
1719    
1720            /**
1721             * Returns the number of file entries in a group starting at the root folder
1722             * that are stored within the Liferay repository. This method is primarily
1723             * used to search for recently modified file entries. It can be limited to
1724             * the file entries modified by a given user.
1725             *
1726             * @param  groupId the primary key of the group
1727             * @param  userId the primary key of the user who created the file
1728             *         (optionally <code>0</code>)
1729             * @param  rootFolderId the primary key of the root folder to begin the
1730             *         search
1731             * @return the number of matching file entries
1732             * @throws PortalException if the group could not be found
1733             * @throws SystemException if a system exception occurred
1734             */
1735            @Override
1736            public int getGroupFileEntriesCount(
1737                            long groupId, long userId, long rootFolderId)
1738                    throws PortalException, SystemException {
1739    
1740                    Repository repository = getRepository(groupId);
1741    
1742                    return repository.getRepositoryFileEntriesCount(userId, rootFolderId);
1743            }
1744    
1745            @Override
1746            public int getGroupFileEntriesCount(
1747                            long groupId, long userId, long rootFolderId, String[] mimeTypes,
1748                            int status)
1749                    throws PortalException, SystemException {
1750    
1751                    Repository repository = getRepository(groupId);
1752    
1753                    return repository.getRepositoryFileEntriesCount(
1754                            userId, rootFolderId, mimeTypes, status);
1755            }
1756    
1757            /**
1758             * Returns all immediate subfolders of the parent folder that are used for
1759             * mounting third-party repositories. This method is only supported by the
1760             * Liferay repository.
1761             *
1762             * @param  repositoryId the primary key of the folder's repository
1763             * @param  parentFolderId the primary key of the folder's parent folder
1764             * @return the immediate subfolders of the parent folder that are used for
1765             *         mounting third-party repositories
1766             * @throws PortalException if the repository or parent folder could not be
1767             *         found
1768             * @throws SystemException if a system exception occurred
1769             */
1770            @Override
1771            public List<Folder> getMountFolders(long repositoryId, long parentFolderId)
1772                    throws PortalException, SystemException {
1773    
1774                    return getMountFolders(
1775                            repositoryId, parentFolderId, QueryUtil.ALL_POS, QueryUtil.ALL_POS);
1776            }
1777    
1778            /**
1779             * Returns a range of all the immediate subfolders of the parent folder that
1780             * are used for mounting third-party repositories. This method is only
1781             * supported by the Liferay repository.
1782             *
1783             * <p>
1784             * Useful when paginating results. Returns a maximum of <code>end -
1785             * start</code> instances. <code>start</code> and <code>end</code> are not
1786             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1787             * refers to the first result in the set. Setting both <code>start</code>
1788             * and <code>end</code> to {@link
1789             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1790             * result set.
1791             * </p>
1792             *
1793             * @param  repositoryId the primary key of the repository
1794             * @param  parentFolderId the primary key of the parent folder
1795             * @param  start the lower bound of the range of results
1796             * @param  end the upper bound of the range of results (not inclusive)
1797             * @return the range of immediate subfolders of the parent folder that are
1798             *         used for mounting third-party repositories
1799             * @throws PortalException if the repository or parent folder could not be
1800             *         found
1801             * @throws SystemException if a system exception occurred
1802             */
1803            @Override
1804            public List<Folder> getMountFolders(
1805                            long repositoryId, long parentFolderId, int start, int end)
1806                    throws PortalException, SystemException {
1807    
1808                    return getMountFolders(repositoryId, parentFolderId, start, end, null);
1809            }
1810    
1811            /**
1812             * Returns an ordered range of all the immediate subfolders of the parent
1813             * folder that are used for mounting third-party repositories. This method
1814             * is only supported by the Liferay repository.
1815             *
1816             * <p>
1817             * Useful when paginating results. Returns a maximum of <code>end -
1818             * start</code> instances. <code>start</code> and <code>end</code> are not
1819             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1820             * refers to the first result in the set. Setting both <code>start</code>
1821             * and <code>end</code> to {@link
1822             * com.liferay.portal.kernel.dao.orm.QueryUtil#ALL_POS} will return the full
1823             * result set.
1824             * </p>
1825             *
1826             * @param  repositoryId the primary key of the folder's repository
1827             * @param  parentFolderId the primary key of the folder's parent folder
1828             * @param  start the lower bound of the range of results
1829             * @param  end the upper bound of the range of results (not inclusive)
1830             * @param  obc the comparator to order the folders (optionally
1831             *         <code>null</code>)
1832             * @return the range of immediate subfolders of the parent folder that are
1833             *         used for mounting third-party repositories ordered by comparator
1834             *         <code>obc</code>
1835             * @throws PortalException if the repository or parent folder could not be
1836             *         found
1837             * @throws SystemException if a system exception occurred
1838             */
1839            @Override
1840            public List<Folder> getMountFolders(
1841                            long repositoryId, long parentFolderId, int start, int end,
1842                            OrderByComparator obc)
1843                    throws PortalException, SystemException {
1844    
1845                    Repository repository = getRepository(repositoryId);
1846    
1847                    return repository.getMountFolders(parentFolderId, start, end, obc);
1848            }
1849    
1850            /**
1851             * Returns the number of immediate subfolders of the parent folder that are
1852             * used for mounting third-party repositories. This method is only supported
1853             * by the Liferay repository.
1854             *
1855             * @param  repositoryId the primary key of the repository
1856             * @param  parentFolderId the primary key of the parent folder
1857             * @return the number of folders of the parent folder that are used for
1858             *         mounting third-party repositories
1859             * @throws PortalException if the repository or parent folder could not be
1860             *         found
1861             * @throws SystemException if a system exception occurred
1862             */
1863            @Override
1864            public int getMountFoldersCount(long repositoryId, long parentFolderId)
1865                    throws PortalException, SystemException {
1866    
1867                    Repository repository = getRepository(repositoryId);
1868    
1869                    return repository.getMountFoldersCount(parentFolderId);
1870            }
1871    
1872            @Override
1873            public void getSubfolderIds(
1874                            long repositoryId, List<Long> folderIds, long folderId)
1875                    throws PortalException, SystemException {
1876    
1877                    Repository repository = getRepository(repositoryId);
1878    
1879                    repository.getSubfolderIds(folderIds, folderId);
1880            }
1881    
1882            /**
1883             * Returns all the descendant folders of the folder with the primary key.
1884             *
1885             * @param  repositoryId the primary key of the repository
1886             * @param  folderId the primary key of the folder
1887             * @return the descendant folders of the folder with the primary key
1888             * @throws PortalException if the repository or parent folder could not be
1889             *         found
1890             * @throws SystemException if a system exception occurred
1891             */
1892            @Override
1893            public List<Long> getSubfolderIds(long repositoryId, long folderId)
1894                    throws PortalException, SystemException {
1895    
1896                    return getSubfolderIds(repositoryId, folderId, true);
1897            }
1898    
1899            /**
1900             * Returns descendant folders of the folder with the primary key, optionally
1901             * limiting to one level deep.
1902             *
1903             * @param  repositoryId the primary key of the repository
1904             * @param  folderId the primary key of the folder
1905             * @param  recurse whether to recurse through each subfolder
1906             * @return the descendant folders of the folder with the primary key
1907             * @throws PortalException if the repository or parent folder could not be
1908             *         found
1909             * @throws SystemException if a system exception occurred
1910             */
1911            @Override
1912            public List<Long> getSubfolderIds(
1913                            long repositoryId, long folderId, boolean recurse)
1914                    throws PortalException, SystemException {
1915    
1916                    Repository repository = getRepository(repositoryId);
1917    
1918                    return repository.getSubfolderIds(folderId, recurse);
1919            }
1920    
1921            /**
1922             * Returns all the temporary file entry names.
1923             *
1924             * @param  groupId the primary key of the group
1925             * @param  folderId the primary key of the folder where the file entry will
1926             *         eventually reside
1927             * @param  tempFolderName the temporary folder's name
1928             * @return the temporary file entry names
1929             * @throws PortalException if the folder was invalid
1930             * @throws SystemException if a system exception occurred
1931             * @see    #addTempFileEntry(long, long, String, String, File)
1932             * @see    com.liferay.portal.kernel.util.TempFileUtil
1933             */
1934            @Override
1935            public String[] getTempFileEntryNames(
1936                            long groupId, long folderId, String tempFolderName)
1937                    throws PortalException, SystemException {
1938    
1939                    DLFolderPermission.check(
1940                            getPermissionChecker(), groupId, folderId, ActionKeys.ADD_DOCUMENT);
1941    
1942                    return TempFileUtil.getTempFileEntryNames(getUserId(), tempFolderName);
1943            }
1944    
1945            /**
1946             * @deprecated {@link #checkOutFileEntry(long, ServiceContext)}
1947             */
1948            @Override
1949            public Lock lockFileEntry(long fileEntryId)
1950                    throws PortalException, SystemException {
1951    
1952                    checkOutFileEntry(fileEntryId, new ServiceContext());
1953    
1954                    FileEntry fileEntry = getFileEntry(fileEntryId);
1955    
1956                    return fileEntry.getLock();
1957            }
1958    
1959            /**
1960             * @deprecated {@link #checkOutFileEntry(long, String, long,
1961             *             ServiceContext)}
1962             */
1963            @Override
1964            public Lock lockFileEntry(
1965                            long fileEntryId, String owner, long expirationTime)
1966                    throws PortalException, SystemException {
1967    
1968                    FileEntry fileEntry = checkOutFileEntry(
1969                            fileEntryId, owner, expirationTime, new ServiceContext());
1970    
1971                    return fileEntry.getLock();
1972            }
1973    
1974            /**
1975             * Locks the folder. This method is primarily used by WebDAV.
1976             *
1977             * @param  repositoryId the primary key of the repository
1978             * @param  folderId the primary key of the folder
1979             * @return the lock object
1980             * @throws PortalException if the repository or folder could not be found
1981             * @throws SystemException if a system exception occurred
1982             */
1983            @Override
1984            public Lock lockFolder(long repositoryId, long folderId)
1985                    throws PortalException, SystemException {
1986    
1987                    Repository repository = getRepository(repositoryId);
1988    
1989                    return repository.lockFolder(folderId);
1990            }
1991    
1992            /**
1993             * Locks the folder. This method is primarily used by WebDAV.
1994             *
1995             * @param  repositoryId the primary key of the repository
1996             * @param  folderId the primary key of the folder
1997             * @param  owner the owner string for the checkout (optionally
1998             *         <code>null</code>)
1999             * @param  inheritable whether the lock must propagate to descendants
2000             * @param  expirationTime the time in milliseconds before the lock expires.
2001             *         If the value is <code>0</code>, the default expiration time will
2002             *         be used from <code>portal.properties>.
2003             * @return the lock object
2004             * @throws PortalException if the repository or folder could not be found
2005             * @throws SystemException if a system exception occurred
2006             */
2007            @Override
2008            public Lock lockFolder(
2009                            long repositoryId, long folderId, String owner, boolean inheritable,
2010                            long expirationTime)
2011                    throws PortalException, SystemException {
2012    
2013                    Repository repository = getRepository(repositoryId);
2014    
2015                    return repository.lockFolder(
2016                            folderId, owner, inheritable, expirationTime);
2017            }
2018    
2019            /**
2020             * Moves the file entry to the new folder.
2021             *
2022             * @param  fileEntryId the primary key of the file entry
2023             * @param  newFolderId the primary key of the new folder
2024             * @param  serviceContext the service context to be applied
2025             * @return the file entry
2026             * @throws PortalException if the file entry or the new folder could not be
2027             *         found
2028             * @throws SystemException if a system exception occurred
2029             */
2030            @Override
2031            public FileEntry moveFileEntry(
2032                            long fileEntryId, long newFolderId, ServiceContext serviceContext)
2033                    throws PortalException, SystemException {
2034    
2035                    Repository fromRepository = getRepository(0, fileEntryId, 0);
2036                    Repository toRepository = getRepository(newFolderId, serviceContext);
2037    
2038                    if (newFolderId != DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
2039                            Folder toFolder = toRepository.getFolder(newFolderId);
2040    
2041                            if (toFolder.isMountPoint()) {
2042                                    toRepository = getRepository(toFolder.getRepositoryId());
2043                            }
2044                    }
2045    
2046                    if (fromRepository.getRepositoryId() ==
2047                                    toRepository.getRepositoryId()) {
2048    
2049                            // Move file entries within repository
2050    
2051                            FileEntry fileEntry = fromRepository.moveFileEntry(
2052                                    fileEntryId, newFolderId, serviceContext);
2053    
2054                            return fileEntry;
2055                    }
2056    
2057                    // Move file entries between repositories
2058    
2059                    return moveFileEntries(
2060                            fileEntryId, newFolderId, fromRepository, toRepository,
2061                            serviceContext);
2062            }
2063    
2064            /**
2065             * Moves the folder to the new parent folder with the primary key.
2066             *
2067             * @param  folderId the primary key of the folder
2068             * @param  parentFolderId the primary key of the new parent folder
2069             * @param  serviceContext the service context to be applied
2070             * @return the file entry
2071             * @throws PortalException if the folder could not be found
2072             * @throws SystemException if a system exception occurred
2073             */
2074            @Override
2075            public Folder moveFolder(
2076                            long folderId, long parentFolderId, ServiceContext serviceContext)
2077                    throws PortalException, SystemException {
2078    
2079                    Repository fromRepository = getRepository(folderId, 0, 0);
2080                    Repository toRepository = getRepository(parentFolderId, serviceContext);
2081    
2082                    if (parentFolderId != DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
2083                            Folder toFolder = toRepository.getFolder(parentFolderId);
2084    
2085                            if (toFolder.isMountPoint()) {
2086                                    toRepository = getRepository(toFolder.getRepositoryId());
2087                            }
2088                    }
2089    
2090                    if (fromRepository.getRepositoryId() ==
2091                                    toRepository.getRepositoryId()) {
2092    
2093                            // Move file entries within repository
2094    
2095                            Folder folder = fromRepository.moveFolder(
2096                                    folderId, parentFolderId, serviceContext);
2097    
2098                            return folder;
2099                    }
2100    
2101                    // Move file entries between repositories
2102    
2103                    return moveFolders(
2104                            folderId, parentFolderId, fromRepository, toRepository,
2105                            serviceContext);
2106            }
2107    
2108            /**
2109             * Refreshes the lock for the file entry. This method is primarily used by
2110             * WebDAV.
2111             *
2112             * @param  lockUuid the lock's universally unique identifier
2113             * @param  expirationTime the time in milliseconds before the lock expires.
2114             *         If the value is <code>0</code>, the default expiration time will
2115             *         be used from <code>portal.properties>.
2116             * @return the lock object
2117             * @throws PortalException if the file entry or lock could not be found
2118             * @throws SystemException if a system exception occurred
2119             */
2120            @Override
2121            public Lock refreshFileEntryLock(String lockUuid, long expirationTime)
2122                    throws PortalException, SystemException {
2123    
2124                    Lock lock = lockLocalService.getLockByUuid(lockUuid);
2125    
2126                    long fileEntryId = GetterUtil.getLong(lock.getKey());
2127    
2128                    Repository repository = getRepository(0, fileEntryId, 0);
2129    
2130                    return repository.refreshFileEntryLock(lockUuid, expirationTime);
2131            }
2132    
2133            /**
2134             * Refreshes the lock for the folder. This method is primarily used by
2135             * WebDAV.
2136             *
2137             * @param  lockUuid the lock's universally unique identifier
2138             * @param  expirationTime the time in milliseconds before the lock expires.
2139             *         If the value is <code>0</code>, the default expiration time will
2140             *         be used from <code>portal.properties>.
2141             * @return the lock object
2142             * @throws PortalException if the folder or lock could not be found
2143             * @throws SystemException if a system exception occurred
2144             */
2145            @Override
2146            public Lock refreshFolderLock(String lockUuid, long expirationTime)
2147                    throws PortalException, SystemException {
2148    
2149                    Lock lock = lockLocalService.getLockByUuid(lockUuid);
2150    
2151                    long folderId = GetterUtil.getLong(lock.getKey());
2152    
2153                    Repository repository = getRepository(0, folderId, 0);
2154    
2155                    return repository.refreshFolderLock(lockUuid, expirationTime);
2156            }
2157    
2158            /**
2159             * Reverts the file entry to a previous version. A new version will be
2160             * created based on the previous version and metadata.
2161             *
2162             * @param  fileEntryId the primary key of the file entry
2163             * @param  version the version to revert back to
2164             * @param  serviceContext the service context to be applied
2165             * @throws PortalException if the file entry or version could not be found
2166             * @throws SystemException if a system exception occurred
2167             */
2168            @Override
2169            public void revertFileEntry(
2170                            long fileEntryId, String version, ServiceContext serviceContext)
2171                    throws PortalException, SystemException {
2172    
2173                    Repository repository = getRepository(0, fileEntryId, 0);
2174    
2175                    repository.revertFileEntry(fileEntryId, version, serviceContext);
2176    
2177                    FileEntry fileEntry = getFileEntry(fileEntryId);
2178    
2179                    dlAppHelperLocalService.updateFileEntry(
2180                            getUserId(), fileEntry, fileEntry.getFileVersion(), serviceContext);
2181            }
2182    
2183            @Override
2184            public Hits search(long repositoryId, SearchContext searchContext)
2185                    throws SearchException {
2186    
2187                    try {
2188                            Repository repository = getRepository(repositoryId);
2189    
2190                            return repository.search(searchContext);
2191                    }
2192                    catch (Exception e) {
2193                            throw new SearchException(e);
2194                    }
2195            }
2196    
2197            @Override
2198            public Hits search(
2199                            long repositoryId, SearchContext searchContext, Query query)
2200                    throws SearchException {
2201    
2202                    try {
2203                            Repository repository = getRepository(repositoryId);
2204    
2205                            return repository.search(searchContext, query);
2206                    }
2207                    catch (Exception e) {
2208                            throw new SearchException(e);
2209                    }
2210            }
2211    
2212            /**
2213             * @deprecated Use {@link #checkInFileEntry(long, boolean, String,
2214             *             ServiceContext)}.
2215             */
2216            @Override
2217            public void unlockFileEntry(long fileEntryId)
2218                    throws PortalException, SystemException {
2219    
2220                    checkInFileEntry(
2221                            fileEntryId, false, StringPool.BLANK, new ServiceContext());
2222            }
2223    
2224            /**
2225             * @deprecated Use {@link #checkInFileEntry(long, String)}.
2226             */
2227            @Override
2228            public void unlockFileEntry(long fileEntryId, String lockUuid)
2229                    throws PortalException, SystemException {
2230    
2231                    checkInFileEntry(fileEntryId, lockUuid);
2232            }
2233    
2234            /**
2235             * Unlocks the folder. This method is primarily used by WebDAV.
2236             *
2237             * @param  repositoryId the primary key of the repository
2238             * @param  folderId the primary key of the folder
2239             * @param  lockUuid the lock's universally unique identifier
2240             * @throws PortalException if the repository or folder could not be found
2241             * @throws SystemException if a system exception occurred
2242             */
2243            @Override
2244            public void unlockFolder(long repositoryId, long folderId, String lockUuid)
2245                    throws PortalException, SystemException {
2246    
2247                    Repository repository = getRepository(repositoryId);
2248    
2249                    repository.unlockFolder(folderId, lockUuid);
2250            }
2251    
2252            /**
2253             * Unlocks the folder. This method is primarily used by WebDAV.
2254             *
2255             * @param  repositoryId the primary key of the repository
2256             * @param  parentFolderId the primary key of the parent folder
2257             * @param  name the folder's name
2258             * @param  lockUuid the lock's universally unique identifier
2259             * @throws PortalException if the repository or folder could not be found
2260             * @throws SystemException if a system exception occurred
2261             */
2262            @Override
2263            public void unlockFolder(
2264                            long repositoryId, long parentFolderId, String name,
2265                            String lockUuid)
2266                    throws PortalException, SystemException {
2267    
2268                    Repository repository = getRepository(repositoryId);
2269    
2270                    repository.unlockFolder(parentFolderId, name, lockUuid);
2271            }
2272    
2273            /**
2274             * Updates a file entry and associated metadata based on a byte array
2275             * object. If the file data is <code>null</code>, then only the associated
2276             * metadata (i.e., <code>title</code>, <code>description</code>, and
2277             * parameters in the <code>serviceContext</code>) will be updated.
2278             *
2279             * <p>
2280             * This method takes two file names, the <code>sourceFileName</code> and the
2281             * <code>title</code>. The <code>sourceFileName</code> corresponds to the
2282             * name of the actual file being uploaded. The <code>title</code>
2283             * corresponds to a name the client wishes to assign this file after it has
2284             * been uploaded to the portal.
2285             * </p>
2286             *
2287             * @param  fileEntryId the primary key of the file entry
2288             * @param  sourceFileName the original file's name (optionally
2289             *         <code>null</code>)
2290             * @param  mimeType the file's MIME type (optionally <code>null</code>)
2291             * @param  title the new name to be assigned to the file (optionally <code>
2292             *         <code>null</code></code>)
2293             * @param  description the file's new description
2294             * @param  changeLog the file's version change log (optionally
2295             *         <code>null</code>)
2296             * @param  majorVersion whether the new file version is a major version
2297             * @param  bytes the file's data (optionally <code>null</code>)
2298             * @param  serviceContext the service context to be applied. Can set the
2299             *         asset category IDs, asset tag names, and expando bridge
2300             *         attributes for the file entry. In a Liferay repository, it may
2301             *         include:  <ul> <li> fileEntryTypeId - ID for a custom file entry
2302             *         type </li> <li> fieldsMap - mapping for fields associated with a
2303             *         custom file entry type </li> </ul>
2304             * @return the file entry
2305             * @throws PortalException if the file entry could not be found
2306             * @throws SystemException if a system exception occurred
2307             */
2308            @Override
2309            public FileEntry updateFileEntry(
2310                            long fileEntryId, String sourceFileName, String mimeType,
2311                            String title, String description, String changeLog,
2312                            boolean majorVersion, byte[] bytes, ServiceContext serviceContext)
2313                    throws PortalException, SystemException {
2314    
2315                    File file = null;
2316    
2317                    try {
2318                            if ((bytes != null) && (bytes.length > 0)) {
2319                                    file = FileUtil.createTempFile(bytes);
2320                            }
2321    
2322                            return updateFileEntry(
2323                                    fileEntryId, sourceFileName, mimeType, title, description,
2324                                    changeLog, majorVersion, file, serviceContext);
2325                    }
2326                    catch (IOException ioe) {
2327                            throw new SystemException("Unable to write temporary file", ioe);
2328                    }
2329                    finally {
2330                            FileUtil.delete(file);
2331                    }
2332            }
2333    
2334            /**
2335             * Updates a file entry and associated metadata based on a {@link File}
2336             * object. If the file data is <code>null</code>, then only the associated
2337             * metadata (i.e., <code>title</code>, <code>description</code>, and
2338             * parameters in the <code>serviceContext</code>) will be updated.
2339             *
2340             * <p>
2341             * This method takes two file names, the <code>sourceFileName</code> and the
2342             * <code>title</code>. The <code>sourceFileName</code> corresponds to the
2343             * name of the actual file being uploaded. The <code>title</code>
2344             * corresponds to a name the client wishes to assign this file after it has
2345             * been uploaded to the portal.
2346             * </p>
2347             *
2348             * @param  fileEntryId the primary key of the file entry
2349             * @param  sourceFileName the original file's name (optionally
2350             *         <code>null</code>)
2351             * @param  mimeType the file's MIME type (optionally <code>null</code>)
2352             * @param  title the new name to be assigned to the file (optionally <code>
2353             *         <code>null</code></code>)
2354             * @param  description the file's new description
2355             * @param  changeLog the file's version change log (optionally
2356             *         <code>null</code>)
2357             * @param  majorVersion whether the new file version is a major version
2358             * @param  file EntryId the primary key of the file entry
2359             * @param  serviceContext the service context to be applied. Can set the
2360             *         asset category IDs, asset tag names, and expando bridge
2361             *         attributes for the file entry. In a Liferay repository, it may
2362             *         include:  <ul> <li> fileEntryTypeId - ID for a custom file entry
2363             *         type </li> <li> fieldsMap - mapping for fields associated with a
2364             *         custom file entry type </li> </ul>
2365             * @return the file entry
2366             * @throws PortalException if the file entry could not be found
2367             * @throws SystemException if a system exception occurred
2368             */
2369            @Override
2370            public FileEntry updateFileEntry(
2371                            long fileEntryId, String sourceFileName, String mimeType,
2372                            String title, String description, String changeLog,
2373                            boolean majorVersion, File file, ServiceContext serviceContext)
2374                    throws PortalException, SystemException {
2375    
2376                    if ((file == null) || !file.exists() || (file.length() == 0)) {
2377                            return updateFileEntry(
2378                                    fileEntryId, sourceFileName, mimeType, title, description,
2379                                    changeLog, majorVersion, null, 0, serviceContext);
2380                    }
2381    
2382                    mimeType = DLAppUtil.getMimeType(
2383                            sourceFileName, mimeType, title, file, null);
2384    
2385                    Repository repository = getRepository(0, fileEntryId, 0);
2386    
2387                    FileEntry fileEntry = repository.updateFileEntry(
2388                            fileEntryId, sourceFileName, mimeType, title, description,
2389                            changeLog, majorVersion, file, serviceContext);
2390    
2391                    DLProcessorRegistryUtil.cleanUp(fileEntry.getLatestFileVersion());
2392    
2393                    dlAppHelperLocalService.updateFileEntry(
2394                            getUserId(), fileEntry, fileEntry.getFileVersion(), serviceContext);
2395    
2396                    return fileEntry;
2397            }
2398    
2399            /**
2400             * Updates a file entry and associated metadata based on an {@link
2401             * InputStream} object. If the file data is <code>null</code>, then only the
2402             * associated metadata (i.e., <code>title</code>, <code>description</code>,
2403             * and parameters in the <code>serviceContext</code>) will be updated.
2404             *
2405             * <p>
2406             * This method takes two file names, the <code>sourceFileName</code> and the
2407             * <code>title</code>. The <code>sourceFileName</code> corresponds to the
2408             * name of the actual file being uploaded. The <code>title</code>
2409             * corresponds to a name the client wishes to assign this file after it has
2410             * been uploaded to the portal.
2411             * </p>
2412             *
2413             * @param  fileEntryId the primary key of the file entry
2414             * @param  sourceFileName the original file's name (optionally
2415             *         <code>null</code>)
2416             * @param  mimeType the file's MIME type (optionally <code>null</code>)
2417             * @param  title the new name to be assigned to the file (optionally <code>
2418             *         <code>null</code></code>)
2419             * @param  description the file's new description
2420             * @param  changeLog the file's version change log (optionally
2421             *         <code>null</code>)
2422             * @param  majorVersion whether the new file version is a major version
2423             * @param  is the file's data (optionally <code>null</code>)
2424             * @param  size the file's size (optionally <code>0</code>)
2425             * @param  serviceContext the service context to be applied. Can set the
2426             *         asset category IDs, asset tag names, and expando bridge
2427             *         attributes for the file entry. In a Liferay repository, it may
2428             *         include:  <ul> <li> fileEntryTypeId - ID for a custom file entry
2429             *         type </li> <li> fieldsMap - mapping for fields associated with a
2430             *         custom file entry type </li> </ul>
2431             * @return the file entry
2432             * @throws PortalException if the file entry could not be found
2433             * @throws SystemException if a system exception occurred
2434             */
2435            @Override
2436            public FileEntry updateFileEntry(
2437                            long fileEntryId, String sourceFileName, String mimeType,
2438                            String title, String description, String changeLog,
2439                            boolean majorVersion, InputStream is, long size,
2440                            ServiceContext serviceContext)
2441                    throws PortalException, SystemException {
2442    
2443                    mimeType = DLAppUtil.getMimeType(
2444                            sourceFileName, mimeType, title, null, is);
2445    
2446                    Repository repository = getRepository(0, fileEntryId, 0);
2447    
2448                    FileEntry fileEntry = repository.updateFileEntry(
2449                            fileEntryId, sourceFileName, mimeType, title, description,
2450                            changeLog, majorVersion, is, size, serviceContext);
2451    
2452                    if (is != null) {
2453                            DLProcessorRegistryUtil.cleanUp(fileEntry.getLatestFileVersion());
2454                    }
2455    
2456                    dlAppHelperLocalService.updateFileEntry(
2457                            getUserId(), fileEntry, fileEntry.getFileVersion(), serviceContext);
2458    
2459                    return fileEntry;
2460            }
2461    
2462            @Override
2463            public FileEntry updateFileEntryAndCheckIn(
2464                            long fileEntryId, String sourceFileName, String mimeType,
2465                            String title, String description, String changeLog,
2466                            boolean majorVersion, File file, ServiceContext serviceContext)
2467                    throws PortalException, SystemException {
2468    
2469                    if ((file == null) || !file.exists() || (file.length() == 0)) {
2470                            return updateFileEntryAndCheckIn(
2471                                    fileEntryId, sourceFileName, mimeType, title, description,
2472                                    changeLog, majorVersion, null, 0, serviceContext);
2473                    }
2474    
2475                    Repository repository = getRepository(0, fileEntryId, 0);
2476    
2477                    FileEntry fileEntry = repository.updateFileEntry(
2478                            fileEntryId, sourceFileName, mimeType, title, description,
2479                            changeLog, majorVersion, file, serviceContext);
2480    
2481                    DLProcessorRegistryUtil.cleanUp(fileEntry.getLatestFileVersion());
2482    
2483                    repository.checkInFileEntry(
2484                            fileEntryId, majorVersion, changeLog, serviceContext);
2485    
2486                    dlAppHelperLocalService.updateFileEntry(
2487                            getUserId(), fileEntry, fileEntry.getFileVersion(), serviceContext);
2488    
2489                    return fileEntry;
2490            }
2491    
2492            @Override
2493            public FileEntry updateFileEntryAndCheckIn(
2494                            long fileEntryId, String sourceFileName, String mimeType,
2495                            String title, String description, String changeLog,
2496                            boolean majorVersion, InputStream is, long size,
2497                            ServiceContext serviceContext)
2498                    throws PortalException, SystemException {
2499    
2500                    Repository repository = getRepository(0, fileEntryId, 0);
2501    
2502                    FileEntry fileEntry = repository.updateFileEntry(
2503                            fileEntryId, sourceFileName, mimeType, title, description,
2504                            changeLog, majorVersion, is, size, serviceContext);
2505    
2506                    if (is != null) {
2507                            DLProcessorRegistryUtil.cleanUp(fileEntry.getLatestFileVersion());
2508                    }
2509    
2510                    repository.checkInFileEntry(
2511                            fileEntryId, majorVersion, changeLog, serviceContext);
2512    
2513                    dlAppHelperLocalService.updateFileEntry(
2514                            getUserId(), fileEntry, fileEntry.getFileVersion(), serviceContext);
2515    
2516                    return fileEntry;
2517            }
2518    
2519            /**
2520             * Updates a file shortcut to the existing file entry. This method is only
2521             * supported by the Liferay repository.
2522             *
2523             * @param  fileShortcutId the primary key of the file shortcut
2524             * @param  folderId the primary key of the file shortcut's parent folder
2525             * @param  toFileEntryId the primary key of the file shortcut's file entry
2526             * @param  serviceContext the service context to be applied. Can set the
2527             *         asset category IDs, asset tag names, and expando bridge
2528             *         attributes for the file entry.
2529             * @return the file shortcut
2530             * @throws PortalException if the file shortcut, folder, or file entry could
2531             *         not be found
2532             * @throws SystemException if a system exception occurred
2533             */
2534            @Override
2535            public DLFileShortcut updateFileShortcut(
2536                            long fileShortcutId, long folderId, long toFileEntryId,
2537                            ServiceContext serviceContext)
2538                    throws PortalException, SystemException {
2539    
2540                    return dlFileShortcutService.updateFileShortcut(
2541                            fileShortcutId, folderId, toFileEntryId, serviceContext);
2542            }
2543    
2544            /**
2545             * Updates the folder.
2546             *
2547             * @param  folderId the primary key of the folder
2548             * @param  name the folder's new name
2549             * @param  description the folder's new description
2550             * @param  serviceContext the service context to be applied. In a Liferay
2551             *         repository, it may include:  <ul> <li> defaultFileEntryTypeId -
2552             *         the file entry type to default all Liferay file entries to </li>
2553             *         <li> dlFileEntryTypesSearchContainerPrimaryKeys - a
2554             *         comma-delimited list of file entry type primary keys allowed in
2555             *         the given folder and all descendants </li> <li>
2556             *         overrideFileEntryTypes - boolean specifying whether to override
2557             *         ancestral folder's restriction of file entry types allowed </li>
2558             *         <li> workflowDefinitionXYZ - the workflow definition name
2559             *         specified per file entry type. The parameter name must be the
2560             *         string <code>workflowDefinition</code> appended by the <code>
2561             *         fileEntryTypeId</code> (optionally <code>0</code>). </li> </ul>
2562             * @return the folder
2563             * @throws PortalException if the current or new parent folder could not be
2564             *         found or if the new parent folder's information was invalid
2565             * @throws SystemException if a system exception occurred
2566             */
2567            @Override
2568            public Folder updateFolder(
2569                            long folderId, String name, String description,
2570                            ServiceContext serviceContext)
2571                    throws PortalException, SystemException {
2572    
2573                    Repository repository = null;
2574    
2575                    if (folderId == DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
2576                            repository = getRepository(serviceContext.getScopeGroupId());
2577                    }
2578                    else {
2579                            repository = getRepository(folderId, 0, 0);
2580                    }
2581    
2582                    return repository.updateFolder(
2583                            folderId, name, description, serviceContext);
2584            }
2585    
2586            /**
2587             * Returns <code>true</code> if the file entry is checked out. This method
2588             * is primarily used by WebDAV.
2589             *
2590             * @param  repositoryId the primary key for the repository
2591             * @param  fileEntryId the primary key for the file entry
2592             * @param  lockUuid the lock's universally unique identifier
2593             * @return <code>true</code> if the file entry is checked out;
2594             *         <code>false</code> otherwise
2595             * @throws PortalException if the file entry could not be found
2596             * @throws SystemException if a system exception occurred
2597             */
2598            @Override
2599            public boolean verifyFileEntryCheckOut(
2600                            long repositoryId, long fileEntryId, String lockUuid)
2601                    throws PortalException, SystemException {
2602    
2603                    Repository repository = getRepository(repositoryId);
2604    
2605                    return repository.verifyFileEntryCheckOut(fileEntryId, lockUuid);
2606            }
2607    
2608            @Override
2609            public boolean verifyFileEntryLock(
2610                            long repositoryId, long fileEntryId, String lockUuid)
2611                    throws PortalException, SystemException {
2612    
2613                    Repository repository = getRepository(repositoryId);
2614    
2615                    return repository.verifyFileEntryLock(fileEntryId, lockUuid);
2616            }
2617    
2618            /**
2619             * Returns <code>true</code> if the inheritable lock exists. This method is
2620             * primarily used by WebDAV.
2621             *
2622             * @param  repositoryId the primary key for the repository
2623             * @param  folderId the primary key for the folder
2624             * @param  lockUuid the lock's universally unique identifier
2625             * @return <code>true</code> if the inheritable lock exists;
2626             *         <code>false</code> otherwise
2627             * @throws PortalException if the folder could not be found
2628             * @throws SystemException if a system exception occurred
2629             */
2630            @Override
2631            public boolean verifyInheritableLock(
2632                            long repositoryId, long folderId, String lockUuid)
2633                    throws PortalException, SystemException {
2634    
2635                    Repository repository = getRepository(repositoryId);
2636    
2637                    return repository.verifyInheritableLock(folderId, lockUuid);
2638            }
2639    
2640            protected FileEntry copyFileEntry(
2641                            Repository toRepository, FileEntry fileEntry, long newFolderId,
2642                            ServiceContext serviceContext)
2643                    throws PortalException, SystemException {
2644    
2645                    List<FileVersion> fileVersions = fileEntry.getFileVersions(
2646                            WorkflowConstants.STATUS_ANY);
2647    
2648                    FileVersion latestFileVersion = fileVersions.get(
2649                            fileVersions.size() - 1);
2650    
2651                    FileEntry destinationFileEntry = toRepository.addFileEntry(
2652                            newFolderId, fileEntry.getTitle(), latestFileVersion.getMimeType(),
2653                            latestFileVersion.getTitle(), latestFileVersion.getDescription(),
2654                            StringPool.BLANK, latestFileVersion.getContentStream(false),
2655                            latestFileVersion.getSize(), serviceContext);
2656    
2657                    for (int i = fileVersions.size() - 2; i >= 0; i--) {
2658                            FileVersion fileVersion = fileVersions.get(i);
2659    
2660                            FileVersion previousFileVersion = fileVersions.get(i + 1);
2661    
2662                            try {
2663                                    destinationFileEntry = toRepository.updateFileEntry(
2664                                            destinationFileEntry.getFileEntryId(), fileEntry.getTitle(),
2665                                            destinationFileEntry.getMimeType(),
2666                                            destinationFileEntry.getTitle(),
2667                                            destinationFileEntry.getDescription(), StringPool.BLANK,
2668                                            DLAppUtil.isMajorVersion(previousFileVersion, fileVersion),
2669                                            fileVersion.getContentStream(false), fileVersion.getSize(),
2670                                            serviceContext);
2671                            }
2672                            catch (PortalException pe) {
2673                                    toRepository.deleteFileEntry(
2674                                            destinationFileEntry.getFileEntryId());
2675    
2676                                    throw pe;
2677                            }
2678                    }
2679    
2680                    dlAppHelperLocalService.addFileEntry(
2681                            getUserId(), destinationFileEntry,
2682                            destinationFileEntry.getFileVersion(), serviceContext);
2683    
2684                    return destinationFileEntry;
2685            }
2686    
2687            protected void copyFolder(
2688                            Repository repository, Folder srcFolder, Folder destFolder,
2689                            ServiceContext serviceContext)
2690                    throws PortalException, SystemException {
2691    
2692                    Queue<Folder[]> folders = new LinkedList<Folder[]>();
2693                    final List<FileEntry> fileEntries = new ArrayList<FileEntry>();
2694    
2695                    Folder curSrcFolder = srcFolder;
2696                    Folder curDestFolder = destFolder;
2697    
2698                    while (true) {
2699                            List<FileEntry> srcFileEntries = repository.getFileEntries(
2700                                    curSrcFolder.getFolderId(), QueryUtil.ALL_POS,
2701                                    QueryUtil.ALL_POS, null);
2702    
2703                            for (FileEntry srcFileEntry : srcFileEntries) {
2704                                    try {
2705                                            FileEntry fileEntry = repository.copyFileEntry(
2706                                                    curDestFolder.getGroupId(),
2707                                                    srcFileEntry.getFileEntryId(),
2708                                                    curDestFolder.getFolderId(), serviceContext);
2709    
2710                                            dlAppHelperLocalService.addFileEntry(
2711                                                    getUserId(), fileEntry, fileEntry.getFileVersion(),
2712                                                    serviceContext);
2713    
2714                                            fileEntries.add(fileEntry);
2715                                    }
2716                                    catch (Exception e) {
2717                                            _log.error(e, e);
2718    
2719                                            continue;
2720                                    }
2721                            }
2722    
2723                            List<Folder> srcSubfolders = repository.getFolders(
2724                                    curSrcFolder.getFolderId(), false, QueryUtil.ALL_POS,
2725                                    QueryUtil.ALL_POS, null);
2726    
2727                            for (Folder srcSubfolder : srcSubfolders) {
2728                                    Folder destSubfolder = repository.addFolder(
2729                                            curDestFolder.getFolderId(), srcSubfolder.getName(),
2730                                            srcSubfolder.getDescription(), serviceContext);
2731    
2732                                    folders.offer(new Folder[] {srcSubfolder, destSubfolder});
2733                            }
2734    
2735                            Folder[] next = folders.poll();
2736    
2737                            if (next == null) {
2738                                    break;
2739                            }
2740                            else {
2741                                    curSrcFolder = next[0];
2742                                    curDestFolder = next[1];
2743                            }
2744                    }
2745    
2746                    TransactionCommitCallbackRegistryUtil.registerCallback(
2747                            new Callable<Void>() {
2748    
2749                                    @Override
2750                                    public Void call() throws Exception {
2751                                            for (FileEntry fileEntry : fileEntries) {
2752                                                    DLProcessorRegistryUtil.trigger(fileEntry);
2753                                            }
2754    
2755                                            return null;
2756                                    }
2757    
2758                            });
2759            }
2760    
2761            protected void deleteFileEntry(
2762                            long oldFileEntryId, long newFileEntryId, Repository fromRepository,
2763                            Repository toRepository)
2764                    throws PortalException, SystemException {
2765    
2766                    try {
2767                            FileEntry fileEntry = fromRepository.getFileEntry(oldFileEntryId);
2768    
2769                            dlAppHelperLocalService.deleteFileEntry(fileEntry);
2770    
2771                            fromRepository.deleteFileEntry(oldFileEntryId);
2772                    }
2773                    catch (PortalException pe) {
2774                            FileEntry fileEntry = toRepository.getFileEntry(newFileEntryId);
2775    
2776                            toRepository.deleteFileEntry(newFileEntryId);
2777    
2778                            dlAppHelperLocalService.deleteFileEntry(fileEntry);
2779    
2780                            throw pe;
2781                    }
2782            }
2783    
2784            protected Repository getRepository(long repositoryId)
2785                    throws PortalException, SystemException {
2786    
2787                    return repositoryService.getRepositoryImpl(repositoryId);
2788            }
2789    
2790            protected Repository getRepository(
2791                            long folderId, long fileEntryId, long fileVersionId)
2792                    throws PortalException, SystemException {
2793    
2794                    return repositoryService.getRepositoryImpl(
2795                            folderId, fileEntryId, fileVersionId);
2796            }
2797    
2798            protected Repository getRepository(
2799                            long folderId, ServiceContext serviceContext)
2800                    throws PortalException, SystemException {
2801    
2802                    Repository repository = null;
2803    
2804                    if (folderId == DLFolderConstants.DEFAULT_PARENT_FOLDER_ID) {
2805                            repository = getRepository(serviceContext.getScopeGroupId());
2806                    }
2807                    else {
2808                            repository = getRepository(folderId, 0, 0);
2809                    }
2810    
2811                    return repository;
2812            }
2813    
2814            protected FileEntry moveFileEntries(
2815                            long fileEntryId, long newFolderId, Repository fromRepository,
2816                            Repository toRepository, ServiceContext serviceContext)
2817                    throws PortalException, SystemException {
2818    
2819                    FileEntry sourceFileEntry = fromRepository.getFileEntry(fileEntryId);
2820    
2821                    FileEntry destinationFileEntry = copyFileEntry(
2822                            toRepository, sourceFileEntry, newFolderId, serviceContext);
2823    
2824                    deleteFileEntry(
2825                            fileEntryId, destinationFileEntry.getFileEntryId(), fromRepository,
2826                            toRepository);
2827    
2828                    return destinationFileEntry;
2829            }
2830    
2831            protected Folder moveFolders(
2832                            long folderId, long parentFolderId, Repository fromRepository,
2833                            Repository toRepository, ServiceContext serviceContext)
2834                    throws PortalException, SystemException {
2835    
2836                    Folder folder = fromRepository.getFolder(folderId);
2837    
2838                    Folder newFolder = toRepository.addFolder(
2839                            parentFolderId, folder.getName(), folder.getDescription(),
2840                            serviceContext);
2841    
2842                    List<Object> foldersAndFileEntriesAndFileShortcuts =
2843                            getFoldersAndFileEntriesAndFileShortcuts(
2844                                    fromRepository.getRepositoryId(), folderId,
2845                                    WorkflowConstants.STATUS_ANY, true, QueryUtil.ALL_POS,
2846                                    QueryUtil.ALL_POS);
2847    
2848                    try {
2849                            for (Object folderAndFileEntryAndFileShortcut :
2850                                            foldersAndFileEntriesAndFileShortcuts) {
2851    
2852                                    if (folderAndFileEntryAndFileShortcut instanceof FileEntry) {
2853                                            FileEntry fileEntry =
2854                                                    (FileEntry)folderAndFileEntryAndFileShortcut;
2855    
2856                                            copyFileEntry(
2857                                                    toRepository, fileEntry, newFolder.getFolderId(),
2858                                                    serviceContext);
2859                                    }
2860                                    else if (folderAndFileEntryAndFileShortcut instanceof Folder) {
2861                                            Folder currentFolder =
2862                                                    (Folder)folderAndFileEntryAndFileShortcut;
2863    
2864                                            moveFolders(
2865                                                    currentFolder.getFolderId(), newFolder.getFolderId(),
2866                                                    fromRepository, toRepository, serviceContext);
2867    
2868                                    }
2869                                    else if (folderAndFileEntryAndFileShortcut
2870                                                            instanceof DLFileShortcut) {
2871    
2872                                            if (newFolder.isSupportsShortcuts()) {
2873                                                    DLFileShortcut dlFileShorcut =
2874                                                            (DLFileShortcut)folderAndFileEntryAndFileShortcut;
2875    
2876                                                    dlFileShortcutService.addFileShortcut(
2877                                                            dlFileShorcut.getGroupId(), newFolder.getFolderId(),
2878                                                            dlFileShorcut.getToFileEntryId(), serviceContext);
2879                                            }
2880                                    }
2881                            }
2882                    }
2883                    catch (PortalException pe) {
2884                            toRepository.deleteFolder(newFolder.getFolderId());
2885    
2886                            throw pe;
2887                    }
2888    
2889                    try {
2890                            fromRepository.deleteFolder(folderId);
2891                    }
2892                    catch (PortalException pe) {
2893                            toRepository.deleteFolder(newFolder.getFolderId());
2894    
2895                            throw pe;
2896                    }
2897    
2898                    return newFolder;
2899            }
2900    
2901            private static Log _log = LogFactoryUtil.getLog(DLAppServiceImpl.class);
2902    
2903    }