mirror of
https://github.com/Alfresco/alfresco-community-repo.git
synced 2025-07-31 17:39:05 +00:00
MNT-21671 : Download as zip REST api does not include custom folders (#1090)
Add dictionaryService to CreateDwonloadArchiveAction ZipDownloadExporter constructor now required dictionaryService ZipDownloadExporter#startNode will include into archive all subclasses of node type cm:folder. Add a custom model and create a custom node in DownloadServiceIntegrationTest, this use case will be tested in DownloadServiceIntegrationTest#createDownload()
This commit is contained in:
committed by
GitHub
parent
ba76d3c0d9
commit
3a31ac3634
@@ -43,6 +43,7 @@ import org.alfresco.repo.transaction.RetryingTransactionHelper.RetryingTransacti
|
|||||||
import org.alfresco.service.cmr.action.Action;
|
import org.alfresco.service.cmr.action.Action;
|
||||||
import org.alfresco.service.cmr.action.ParameterDefinition;
|
import org.alfresco.service.cmr.action.ParameterDefinition;
|
||||||
import org.alfresco.service.cmr.coci.CheckOutCheckInService;
|
import org.alfresco.service.cmr.coci.CheckOutCheckInService;
|
||||||
|
import org.alfresco.service.cmr.dictionary.DictionaryService;
|
||||||
import org.alfresco.service.cmr.download.DownloadRequest;
|
import org.alfresco.service.cmr.download.DownloadRequest;
|
||||||
import org.alfresco.service.cmr.download.DownloadStatus;
|
import org.alfresco.service.cmr.download.DownloadStatus;
|
||||||
import org.alfresco.service.cmr.download.DownloadStatus.Status;
|
import org.alfresco.service.cmr.download.DownloadStatus.Status;
|
||||||
@@ -84,6 +85,7 @@ public class CreateDownloadArchiveAction extends ActionExecuterAbstractBase
|
|||||||
private NodeService nodeService;
|
private NodeService nodeService;
|
||||||
private RetryingTransactionHelper transactionHelper;
|
private RetryingTransactionHelper transactionHelper;
|
||||||
private DownloadStatusUpdateService updateService;
|
private DownloadStatusUpdateService updateService;
|
||||||
|
private DictionaryService dictionaryService;
|
||||||
|
|
||||||
private long maximumContentSize = -1l;
|
private long maximumContentSize = -1l;
|
||||||
|
|
||||||
@@ -167,6 +169,11 @@ public class CreateDownloadArchiveAction extends ActionExecuterAbstractBase
|
|||||||
this.updateService = updateService;
|
this.updateService = updateService;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void setDictionaryService(DictionaryService dictionaryService)
|
||||||
|
{
|
||||||
|
this.dictionaryService = dictionaryService;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create an archive file containing content from the repository.
|
* Create an archive file containing content from the repository.
|
||||||
*
|
*
|
||||||
@@ -246,7 +253,7 @@ public class CreateDownloadArchiveAction extends ActionExecuterAbstractBase
|
|||||||
{
|
{
|
||||||
// perform the actual export
|
// perform the actual export
|
||||||
final File tempFile = TempFileProvider.createTempFile(TEMP_FILE_PREFIX, TEMP_FILE_SUFFIX);
|
final File tempFile = TempFileProvider.createTempFile(TEMP_FILE_PREFIX, TEMP_FILE_SUFFIX);
|
||||||
final ZipDownloadExporter handler = new ZipDownloadExporter(tempFile, checkOutCheckInService, nodeService, transactionHelper, updateService, downloadStorage, actionedUponNodeRef, estimator.getSize(), estimator.getFileCount());
|
final ZipDownloadExporter handler = new ZipDownloadExporter(tempFile, checkOutCheckInService, nodeService, transactionHelper, updateService, downloadStorage, dictionaryService, actionedUponNodeRef, estimator.getSize(), estimator.getFileCount());
|
||||||
|
|
||||||
try {
|
try {
|
||||||
exporterService.exportView(handler, crawlerParameters, null);
|
exporterService.exportView(handler, crawlerParameters, null);
|
||||||
|
@@ -39,6 +39,7 @@ import org.alfresco.model.ContentModel;
|
|||||||
import org.alfresco.repo.transaction.RetryingTransactionHelper;
|
import org.alfresco.repo.transaction.RetryingTransactionHelper;
|
||||||
import org.alfresco.repo.transaction.RetryingTransactionHelper.RetryingTransactionCallback;
|
import org.alfresco.repo.transaction.RetryingTransactionHelper.RetryingTransactionCallback;
|
||||||
import org.alfresco.service.cmr.coci.CheckOutCheckInService;
|
import org.alfresco.service.cmr.coci.CheckOutCheckInService;
|
||||||
|
import org.alfresco.service.cmr.dictionary.DictionaryService;
|
||||||
import org.alfresco.service.cmr.download.DownloadStatus;
|
import org.alfresco.service.cmr.download.DownloadStatus;
|
||||||
import org.alfresco.service.cmr.download.DownloadStatus.Status;
|
import org.alfresco.service.cmr.download.DownloadStatus.Status;
|
||||||
import org.alfresco.service.cmr.repository.ContentData;
|
import org.alfresco.service.cmr.repository.ContentData;
|
||||||
@@ -77,6 +78,7 @@ public class ZipDownloadExporter extends BaseExporter
|
|||||||
|
|
||||||
private RetryingTransactionHelper transactionHelper;
|
private RetryingTransactionHelper transactionHelper;
|
||||||
private DownloadStorage downloadStorage;
|
private DownloadStorage downloadStorage;
|
||||||
|
private DictionaryService dictionaryService;
|
||||||
private DownloadStatusUpdateService updateService;
|
private DownloadStatusUpdateService updateService;
|
||||||
|
|
||||||
private Deque<Pair<String, NodeRef>> path = new LinkedList<Pair<String, NodeRef>>();
|
private Deque<Pair<String, NodeRef>> path = new LinkedList<Pair<String, NodeRef>>();
|
||||||
@@ -93,11 +95,12 @@ public class ZipDownloadExporter extends BaseExporter
|
|||||||
* @param transactionHelper RetryingTransactionHelper
|
* @param transactionHelper RetryingTransactionHelper
|
||||||
* @param updateService DownloadStatusUpdateService
|
* @param updateService DownloadStatusUpdateService
|
||||||
* @param downloadStorage DownloadStorage
|
* @param downloadStorage DownloadStorage
|
||||||
|
* @param dictionaryService DictionaryService
|
||||||
* @param downloadNodeRef NodeRef
|
* @param downloadNodeRef NodeRef
|
||||||
* @param total long
|
* @param total long
|
||||||
* @param totalFileCount long
|
* @param totalFileCount long
|
||||||
*/
|
*/
|
||||||
public ZipDownloadExporter(File zipFile, CheckOutCheckInService checkOutCheckInService, NodeService nodeService, RetryingTransactionHelper transactionHelper, DownloadStatusUpdateService updateService, DownloadStorage downloadStorage, NodeRef downloadNodeRef, long total, long totalFileCount)
|
public ZipDownloadExporter(File zipFile, CheckOutCheckInService checkOutCheckInService, NodeService nodeService, RetryingTransactionHelper transactionHelper, DownloadStatusUpdateService updateService, DownloadStorage downloadStorage, DictionaryService dictionaryService, NodeRef downloadNodeRef, long total, long totalFileCount)
|
||||||
{
|
{
|
||||||
super(checkOutCheckInService, nodeService);
|
super(checkOutCheckInService, nodeService);
|
||||||
try
|
try
|
||||||
@@ -106,6 +109,7 @@ public class ZipDownloadExporter extends BaseExporter
|
|||||||
this.updateService = updateService;
|
this.updateService = updateService;
|
||||||
this.transactionHelper = transactionHelper;
|
this.transactionHelper = transactionHelper;
|
||||||
this.downloadStorage = downloadStorage;
|
this.downloadStorage = downloadStorage;
|
||||||
|
this.dictionaryService = dictionaryService;
|
||||||
|
|
||||||
this.downloadNodeRef = downloadNodeRef;
|
this.downloadNodeRef = downloadNodeRef;
|
||||||
this.total = total;
|
this.total = total;
|
||||||
@@ -134,7 +138,7 @@ public class ZipDownloadExporter extends BaseExporter
|
|||||||
{
|
{
|
||||||
this.currentName = (String)nodeService.getProperty(nodeRef, ContentModel.PROP_NAME);
|
this.currentName = (String)nodeService.getProperty(nodeRef, ContentModel.PROP_NAME);
|
||||||
path.push(new Pair<String, NodeRef>(currentName, nodeRef));
|
path.push(new Pair<String, NodeRef>(currentName, nodeRef));
|
||||||
if (ContentModel.TYPE_FOLDER.equals(nodeService.getType(nodeRef)))
|
if (dictionaryService.isSubClass(nodeService.getType(nodeRef), ContentModel.TYPE_FOLDER))
|
||||||
{
|
{
|
||||||
String path = getPath() + PATH_SEPARATOR;
|
String path = getPath() + PATH_SEPARATOR;
|
||||||
ZipArchiveEntry archiveEntry = new ZipArchiveEntry(path);
|
ZipArchiveEntry archiveEntry = new ZipArchiveEntry(path);
|
||||||
|
@@ -100,6 +100,7 @@
|
|||||||
<property name="publicAction" value="false"/>
|
<property name="publicAction" value="false"/>
|
||||||
<property name="transactionHelper" ref="retryingTransactionHelper"/>
|
<property name="transactionHelper" ref="retryingTransactionHelper"/>
|
||||||
<property name="updateService" ref="downloadStatusUpdateService"/>
|
<property name="updateService" ref="downloadStatusUpdateService"/>
|
||||||
|
<property name="dictionaryService" ref="dictionaryService"/>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<bean id="downloadExporterComponent" parent="exporterComponent">
|
<bean id="downloadExporterComponent" parent="exporterComponent">
|
||||||
|
@@ -34,6 +34,7 @@ import org.alfresco.repo.security.authentication.AuthenticationUtil;
|
|||||||
import org.alfresco.repo.security.permissions.AccessDeniedException;
|
import org.alfresco.repo.security.permissions.AccessDeniedException;
|
||||||
import org.alfresco.repo.transaction.RetryingTransactionHelper;
|
import org.alfresco.repo.transaction.RetryingTransactionHelper;
|
||||||
import org.alfresco.repo.transaction.RetryingTransactionHelper.RetryingTransactionCallback;
|
import org.alfresco.repo.transaction.RetryingTransactionHelper.RetryingTransactionCallback;
|
||||||
|
import org.alfresco.service.cmr.admin.RepoAdminService;
|
||||||
import org.alfresco.service.cmr.coci.CheckOutCheckInService;
|
import org.alfresco.service.cmr.coci.CheckOutCheckInService;
|
||||||
import org.alfresco.service.cmr.download.DownloadService;
|
import org.alfresco.service.cmr.download.DownloadService;
|
||||||
import org.alfresco.service.cmr.download.DownloadStatus;
|
import org.alfresco.service.cmr.download.DownloadStatus;
|
||||||
@@ -69,8 +70,11 @@ import org.junit.Test;
|
|||||||
import org.junit.experimental.categories.Category;
|
import org.junit.experimental.categories.Category;
|
||||||
import org.junit.rules.RuleChain;
|
import org.junit.rules.RuleChain;
|
||||||
|
|
||||||
|
import java.io.ByteArrayInputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
import java.io.Serializable;
|
import java.io.Serializable;
|
||||||
|
import java.io.UnsupportedEncodingException;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
@@ -123,6 +127,7 @@ public class DownloadServiceIntegrationTest
|
|||||||
private static PermissionService PERMISSION_SERVICE;
|
private static PermissionService PERMISSION_SERVICE;
|
||||||
private static RetryingTransactionHelper TRANSACTION_HELPER;
|
private static RetryingTransactionHelper TRANSACTION_HELPER;
|
||||||
private static IntegrityChecker INTEGRITY_CHECKER;
|
private static IntegrityChecker INTEGRITY_CHECKER;
|
||||||
|
private static RepoAdminService REPO_ADMIN_SERVICE;
|
||||||
|
|
||||||
// Test Content
|
// Test Content
|
||||||
private NodeRef rootFolder;
|
private NodeRef rootFolder;
|
||||||
@@ -137,6 +142,41 @@ public class DownloadServiceIntegrationTest
|
|||||||
|
|
||||||
private NodeRef fileToCheckout;
|
private NodeRef fileToCheckout;
|
||||||
|
|
||||||
|
// MNT-21671 Download as zip does not include custom folders.
|
||||||
|
// Define a custom model that is child of cm:folder
|
||||||
|
private static final String CUSTOM_FOLDER_MODEL_XML =
|
||||||
|
"<model name=\"custom:customModel\" xmlns=\"http://www.alfresco.org/model/dictionary/1.0\">" +
|
||||||
|
" <description>Custom Model</description>" +
|
||||||
|
" <author></author>" +
|
||||||
|
" <version>1.0</version>" +
|
||||||
|
|
||||||
|
" <imports>" +
|
||||||
|
" <import uri=\"http://www.alfresco.org/model/dictionary/1.0\" prefix=\"d\"/>" +
|
||||||
|
" <import uri=\"http://www.alfresco.org/model/content/1.0\" prefix=\"cm\"/>" +
|
||||||
|
" </imports>" +
|
||||||
|
|
||||||
|
" <namespaces>" +
|
||||||
|
" <namespace uri=\"custom.model\" prefix=\"custom\"/>" +
|
||||||
|
" </namespaces>" +
|
||||||
|
|
||||||
|
" <types>" +
|
||||||
|
" <type name=\"custom:folderx\">" +
|
||||||
|
" <title>Custom FolderX</title>" +
|
||||||
|
" <parent>cm:folder</parent>" +
|
||||||
|
" <properties>" +
|
||||||
|
" <property name=\"custom:invoice\">" +
|
||||||
|
" <type>d:text</type>" +
|
||||||
|
" </property>" +
|
||||||
|
" </properties>" +
|
||||||
|
" <associations>" +
|
||||||
|
" </associations>" +
|
||||||
|
" </type>" +
|
||||||
|
" </types>" +
|
||||||
|
|
||||||
|
" <aspects>" +
|
||||||
|
" </aspects>" +
|
||||||
|
"</model>";
|
||||||
|
|
||||||
@BeforeClass public static void init()
|
@BeforeClass public static void init()
|
||||||
{
|
{
|
||||||
// Resolve required services
|
// Resolve required services
|
||||||
@@ -151,6 +191,7 @@ public class DownloadServiceIntegrationTest
|
|||||||
INTEGRITY_CHECKER.setEnabled(true);
|
INTEGRITY_CHECKER.setEnabled(true);
|
||||||
INTEGRITY_CHECKER.setFailOnViolation(true);
|
INTEGRITY_CHECKER.setFailOnViolation(true);
|
||||||
INTEGRITY_CHECKER.setTraceOn(true);
|
INTEGRITY_CHECKER.setTraceOn(true);
|
||||||
|
REPO_ADMIN_SERVICE = APP_CONTEXT_INIT.getApplicationContext().getBean("RepoAdminService", RepoAdminService.class);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -203,6 +244,24 @@ public class DownloadServiceIntegrationTest
|
|||||||
allEntries.add("rootFolder/level1Folder2/fileToCheckout.txt");
|
allEntries.add("rootFolder/level1Folder2/fileToCheckout.txt");
|
||||||
PERMISSION_SERVICE.setPermission(level1Folder2, TEST_USER.getUsername(), PermissionService.ALL_PERMISSIONS, true);
|
PERMISSION_SERVICE.setPermission(level1Folder2, TEST_USER.getUsername(), PermissionService.ALL_PERMISSIONS, true);
|
||||||
PERMISSION_SERVICE.setPermission(fileToCheckout, TEST_USER.getUsername(), PermissionService.ALL_PERMISSIONS, true);
|
PERMISSION_SERVICE.setPermission(fileToCheckout, TEST_USER.getUsername(), PermissionService.ALL_PERMISSIONS, true);
|
||||||
|
|
||||||
|
// MNT-21671 Download as zip does not include custom folders.
|
||||||
|
// deploy custom model
|
||||||
|
final String modelFileName1 = "model-MNT-21671.xml";
|
||||||
|
InputStream modelStream = null;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
modelStream = new ByteArrayInputStream(CUSTOM_FOLDER_MODEL_XML.getBytes("UTF-8"));
|
||||||
|
}
|
||||||
|
catch (UnsupportedEncodingException e)
|
||||||
|
{
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
REPO_ADMIN_SERVICE.deployModel(modelStream, modelFileName1);
|
||||||
|
final QName customFolderType = QName.createQName("{custom.model}folderx");
|
||||||
|
|
||||||
|
testNodes.createNode(rootFolder, "level1CustomFolder", customFolderType, AuthenticationUtil.getAdminUserName());
|
||||||
|
allEntries.add("rootFolder/level1CustomFolder/");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test public void createDownload() throws IOException, InterruptedException
|
@Test public void createDownload() throws IOException, InterruptedException
|
||||||
|
Reference in New Issue
Block a user