mirror of
https://github.com/Alfresco/alfresco-community-repo.git
synced 2025-07-24 17:32:48 +00:00
Heinous merge from HEAD. Seems to basically work. Be on guard however.
git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/BRANCHES/WCM-DEV2/root@4137 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
@@ -109,7 +109,7 @@ public abstract class AbstractContentStore implements ContentStore
|
||||
// extract the relative part of the URL
|
||||
String path = contentUrl.substring(index);
|
||||
// more extensive checks can be added in, but it seems overkill
|
||||
if (path.length() < 10)
|
||||
if (path.length() < 8)
|
||||
{
|
||||
throw new AlfrescoRuntimeException(
|
||||
"The content URL is invalid: \n" +
|
||||
|
@@ -56,6 +56,7 @@ public class MimetypeMap implements MimetypeService
|
||||
public static final String MIMETYPE_IMAGE_GIF = "image/gif";
|
||||
public static final String MIMETYPE_IMAGE_JPEG = "image/jpeg";
|
||||
public static final String MIMETYPE_IMAGE_RGB = "image/x-rgb";
|
||||
public static final String MIMETYPE_IMAGE_SVG = "image/svg";
|
||||
public static final String MIMETYPE_JAVASCRIPT = "application/x-javascript";
|
||||
public static final String MIMETYPE_ZIP = "application/zip";
|
||||
// Open Document
|
||||
|
@@ -323,7 +323,6 @@ public class RoutingContentService implements ContentService
|
||||
|
||||
public ContentWriter getWriter(NodeRef nodeRef, QName propertyQName, boolean update)
|
||||
{
|
||||
|
||||
// check for an existing URL - the get of the reader will perform type checking
|
||||
ContentReader existingContentReader = getReader(nodeRef, propertyQName, false);
|
||||
|
||||
|
@@ -1,262 +1,249 @@
|
||||
/*
|
||||
* Copyright (C) 2005 Alfresco, Inc.
|
||||
*
|
||||
* Licensed under the Mozilla Public License version 1.1
|
||||
* with a permitted attribution clause. You may obtain a
|
||||
* copy of the License at
|
||||
*
|
||||
* http://www.alfresco.org/legal/license.txt
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
|
||||
* either express or implied. See the License for the specific
|
||||
* language governing permissions and limitations under the
|
||||
* License.
|
||||
*/
|
||||
package org.alfresco.repo.content.cleanup;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Date;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import org.alfresco.error.AlfrescoRuntimeException;
|
||||
import org.alfresco.repo.avm.AVMNodeDAO;
|
||||
import org.alfresco.repo.content.ContentStore;
|
||||
import org.alfresco.repo.node.db.NodeDaoService;
|
||||
import org.alfresco.repo.transaction.TransactionUtil;
|
||||
import org.alfresco.repo.transaction.TransactionUtil.TransactionWork;
|
||||
import org.alfresco.service.cmr.dictionary.DictionaryService;
|
||||
import org.alfresco.service.cmr.repository.ContentData;
|
||||
import org.alfresco.service.cmr.repository.ContentReader;
|
||||
import org.alfresco.service.transaction.TransactionService;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
/**
|
||||
* This component is responsible for finding orphaned content in a given
|
||||
* content store or stores. Deletion handlers can be provided to ensure
|
||||
* that the content is moved to another location prior to being removed
|
||||
* from the store(s) being cleaned.
|
||||
*
|
||||
* @author Derek Hulley
|
||||
*/
|
||||
public class ContentStoreCleaner
|
||||
{
|
||||
private static Log logger = LogFactory.getLog(ContentStoreCleaner.class);
|
||||
|
||||
private DictionaryService dictionaryService;
|
||||
private NodeDaoService nodeDaoService;
|
||||
private TransactionService transactionService;
|
||||
private AVMNodeDAO avmNodeDAO;
|
||||
private List<ContentStore> stores;
|
||||
private List<ContentStoreCleanerListener> listeners;
|
||||
private int protectDays;
|
||||
|
||||
public ContentStoreCleaner()
|
||||
{
|
||||
this.stores = new ArrayList<ContentStore>(0);
|
||||
this.listeners = new ArrayList<ContentStoreCleanerListener>(0);
|
||||
this.protectDays = 7;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param dictionaryService used to determine which properties are content properties
|
||||
*/
|
||||
public void setDictionaryService(DictionaryService dictionaryService)
|
||||
{
|
||||
this.dictionaryService = dictionaryService;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param nodeDaoService used to get the property values
|
||||
*/
|
||||
public void setNodeDaoService(NodeDaoService nodeDaoService)
|
||||
{
|
||||
this.nodeDaoService = nodeDaoService;
|
||||
}
|
||||
|
||||
/**
|
||||
* Setter for Spring.
|
||||
* @param avmNodeDAO The AVM Node DAO to get urls with.
|
||||
*/
|
||||
public void setAvmNodeDAO(AVMNodeDAO avmNodeDAO)
|
||||
{
|
||||
this.avmNodeDAO = avmNodeDAO;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param transactionService the component to ensure proper transactional wrapping
|
||||
*/
|
||||
public void setTransactionService(TransactionService transactionService)
|
||||
{
|
||||
this.transactionService = transactionService;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param stores the content stores to clean
|
||||
*/
|
||||
public void setStores(List<ContentStore> stores)
|
||||
{
|
||||
this.stores = stores;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param listeners the listeners that can react to deletions
|
||||
*/
|
||||
public void setListeners(List<ContentStoreCleanerListener> listeners)
|
||||
{
|
||||
this.listeners = listeners;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the minimum number of days old that orphaned content must be
|
||||
* before deletion is possible. The default is 7 days.
|
||||
*
|
||||
* @param protectDays minimum age (in days) of deleted content
|
||||
*/
|
||||
public void setProtectDays(int protectDays)
|
||||
{
|
||||
this.protectDays = protectDays;
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform basic checks to ensure that the necessary dependencies were injected.
|
||||
*/
|
||||
private void checkProperties()
|
||||
{
|
||||
if (dictionaryService == null)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Property 'dictionaryService' not set");
|
||||
}
|
||||
if (nodeDaoService == null)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Property 'nodeDaoService' not set");
|
||||
}
|
||||
if (transactionService == null)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Property 'transactionService' not set");
|
||||
}
|
||||
if (stores == null || stores.size() == 0)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Property 'stores' not set");
|
||||
}
|
||||
if (listeners == null)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Property 'listeners' not set");
|
||||
}
|
||||
|
||||
// check the protect days
|
||||
if (protectDays < 0)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Property 'protectDays' must be 0 or greater (0 is not recommended)");
|
||||
}
|
||||
else if (protectDays == 0)
|
||||
{
|
||||
logger.warn(
|
||||
"Property 'protectDays' is set to 0. " +
|
||||
"It is possible that in-transaction content will be deleted.");
|
||||
}
|
||||
}
|
||||
|
||||
private Set<String> getValidUrls()
|
||||
{
|
||||
// This does the work for the regular Alfresco repository.
|
||||
// wrap to make the request in a transaction
|
||||
TransactionWork<List<String>> getUrlsWork = new TransactionWork<List<String>>()
|
||||
{
|
||||
public List<String> doWork() throws Exception
|
||||
{
|
||||
return nodeDaoService.getContentDataStrings();
|
||||
};
|
||||
};
|
||||
// execute in READ-ONLY txn
|
||||
List<String> contentDataStrings = TransactionUtil.executeInUserTransaction(
|
||||
transactionService,
|
||||
getUrlsWork,
|
||||
true);
|
||||
|
||||
// Do the same for the AVM repository.
|
||||
TransactionWork<List<String>> getAVMUrlsWork = new TransactionWork<List<String>>()
|
||||
{
|
||||
public List<String> doWork() throws Exception
|
||||
{
|
||||
return avmNodeDAO.getContentUrls();
|
||||
}
|
||||
};
|
||||
|
||||
List<String> avmContentUrls = TransactionUtil.executeInUserTransaction(
|
||||
transactionService,
|
||||
getAVMUrlsWork,
|
||||
true);
|
||||
|
||||
// get all valid URLs
|
||||
Set<String> validUrls = new HashSet<String>(contentDataStrings.size());
|
||||
// convert the strings to objects and extract the URL
|
||||
for (String contentDataString : contentDataStrings)
|
||||
{
|
||||
ContentData contentData = ContentData.createContentProperty(contentDataString);
|
||||
if (contentData.getContentUrl() != null)
|
||||
{
|
||||
// a URL was present
|
||||
validUrls.add(contentData.getContentUrl());
|
||||
}
|
||||
}
|
||||
// put all the avm urls into validUrls.
|
||||
for (String url : avmContentUrls)
|
||||
{
|
||||
validUrls.add(url);
|
||||
}
|
||||
|
||||
// done
|
||||
if (logger.isDebugEnabled())
|
||||
{
|
||||
logger.debug("Found " + validUrls.size() + " valid URLs in metadata");
|
||||
}
|
||||
return validUrls;
|
||||
}
|
||||
|
||||
public void execute()
|
||||
{
|
||||
checkProperties();
|
||||
Set<String> validUrls = getValidUrls();
|
||||
// now clean each store in turn
|
||||
for (ContentStore store : stores)
|
||||
{
|
||||
clean(validUrls, store);
|
||||
}
|
||||
}
|
||||
|
||||
private void clean(Set<String> validUrls, ContentStore store)
|
||||
{
|
||||
Date checkAllBeforeDate = new Date(System.currentTimeMillis() - (long) protectDays * 3600L * 1000L * 24L);
|
||||
// get the store's URLs
|
||||
Set<String> storeUrls = store.getUrls(null, checkAllBeforeDate);
|
||||
// remove all URLs that occur in the validUrls
|
||||
storeUrls.removeAll(validUrls);
|
||||
// now clean the store
|
||||
for (String url : storeUrls)
|
||||
{
|
||||
ContentReader sourceReader = store.getReader(url);
|
||||
// announce this to the listeners
|
||||
for (ContentStoreCleanerListener listener : listeners)
|
||||
{
|
||||
// get a fresh reader
|
||||
ContentReader listenerReader = sourceReader.getReader();
|
||||
// call it
|
||||
listener.beforeDelete(listenerReader);
|
||||
}
|
||||
// delete it
|
||||
store.delete(url);
|
||||
|
||||
if (logger.isDebugEnabled())
|
||||
{
|
||||
logger.debug("Removed URL from store: \n" +
|
||||
" Store: " + store + "\n" +
|
||||
" URL: " + url);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
/*
|
||||
* Copyright (C) 2005 Alfresco, Inc.
|
||||
*
|
||||
* Licensed under the Mozilla Public License version 1.1
|
||||
* with a permitted attribution clause. You may obtain a
|
||||
* copy of the License at
|
||||
*
|
||||
* http://www.alfresco.org/legal/license.txt
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
|
||||
* either express or implied. See the License for the specific
|
||||
* language governing permissions and limitations under the
|
||||
* License.
|
||||
*/
|
||||
package org.alfresco.repo.content.cleanup;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Date;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import org.alfresco.error.AlfrescoRuntimeException;
|
||||
import org.alfresco.repo.avm.AVMNodeDAO;
|
||||
import org.alfresco.repo.content.ContentStore;
|
||||
import org.alfresco.repo.node.db.NodeDaoService;
|
||||
import org.alfresco.repo.transaction.TransactionUtil;
|
||||
import org.alfresco.repo.transaction.TransactionUtil.TransactionWork;
|
||||
import org.alfresco.service.cmr.dictionary.DataTypeDefinition;
|
||||
import org.alfresco.service.cmr.dictionary.DictionaryService;
|
||||
import org.alfresco.service.cmr.repository.ContentData;
|
||||
import org.alfresco.service.cmr.repository.ContentReader;
|
||||
import org.alfresco.service.transaction.TransactionService;
|
||||
import org.alfresco.util.PropertyCheck;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
/**
|
||||
* This component is responsible for finding orphaned content in a given
|
||||
* content store or stores. Deletion handlers can be provided to ensure
|
||||
* that the content is moved to another location prior to being removed
|
||||
* from the store(s) being cleaned.
|
||||
*
|
||||
* @author Derek Hulley
|
||||
*/
|
||||
public class ContentStoreCleaner
|
||||
{
|
||||
private static Log logger = LogFactory.getLog(ContentStoreCleaner.class);
|
||||
|
||||
private DictionaryService dictionaryService;
|
||||
private NodeDaoService nodeDaoService;
|
||||
private TransactionService transactionService;
|
||||
private AVMNodeDAO avmNodeDAO;
|
||||
private List<ContentStore> stores;
|
||||
private List<ContentStoreCleanerListener> listeners;
|
||||
private int protectDays;
|
||||
|
||||
public ContentStoreCleaner()
|
||||
{
|
||||
this.stores = new ArrayList<ContentStore>(0);
|
||||
this.listeners = new ArrayList<ContentStoreCleanerListener>(0);
|
||||
this.protectDays = 7;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param dictionaryService used to determine which properties are content properties
|
||||
*/
|
||||
public void setDictionaryService(DictionaryService dictionaryService)
|
||||
{
|
||||
this.dictionaryService = dictionaryService;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param nodeDaoService used to get the property values
|
||||
*/
|
||||
public void setNodeDaoService(NodeDaoService nodeDaoService)
|
||||
{
|
||||
this.nodeDaoService = nodeDaoService;
|
||||
}
|
||||
|
||||
/**
|
||||
* Setter for Spring.
|
||||
* @param avmNodeDAO The AVM Node DAO to get urls with.
|
||||
*/
|
||||
public void setAvmNodeDAO(AVMNodeDAO avmNodeDAO)
|
||||
{
|
||||
this.avmNodeDAO = avmNodeDAO;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param transactionService the component to ensure proper transactional wrapping
|
||||
*/
|
||||
public void setTransactionService(TransactionService transactionService)
|
||||
{
|
||||
this.transactionService = transactionService;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param stores the content stores to clean
|
||||
*/
|
||||
public void setStores(List<ContentStore> stores)
|
||||
{
|
||||
this.stores = stores;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param listeners the listeners that can react to deletions
|
||||
*/
|
||||
public void setListeners(List<ContentStoreCleanerListener> listeners)
|
||||
{
|
||||
this.listeners = listeners;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the minimum number of days old that orphaned content must be
|
||||
* before deletion is possible. The default is 7 days.
|
||||
*
|
||||
* @param protectDays minimum age (in days) of deleted content
|
||||
*/
|
||||
public void setProtectDays(int protectDays)
|
||||
{
|
||||
this.protectDays = protectDays;
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform basic checks to ensure that the necessary dependencies were injected.
|
||||
*/
|
||||
private void checkProperties()
|
||||
{
|
||||
PropertyCheck.mandatory(this, "dictionaryService", dictionaryService);
|
||||
PropertyCheck.mandatory(this, "nodeDaoService", nodeDaoService);
|
||||
PropertyCheck.mandatory(this, "transactionService", transactionService);
|
||||
PropertyCheck.mandatory(this, "listeners", listeners);
|
||||
|
||||
// check the protect days
|
||||
if (protectDays < 0)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Property 'protectDays' must be 0 or greater (0 is not recommended)");
|
||||
}
|
||||
else if (protectDays == 0)
|
||||
{
|
||||
logger.warn(
|
||||
"Property 'protectDays' is set to 0. " +
|
||||
"It is possible that in-transaction content will be deleted.");
|
||||
}
|
||||
}
|
||||
|
||||
private Set<String> getValidUrls()
|
||||
{
|
||||
final DataTypeDefinition contentDataType = dictionaryService.getDataType(DataTypeDefinition.CONTENT);
|
||||
// wrap to make the request in a transaction
|
||||
TransactionWork<List<Serializable>> getUrlsWork = new TransactionWork<List<Serializable>>()
|
||||
{
|
||||
public List<Serializable> doWork() throws Exception
|
||||
{
|
||||
return nodeDaoService.getPropertyValuesByActualType(contentDataType);
|
||||
};
|
||||
};
|
||||
// execute in READ-ONLY txn
|
||||
List<Serializable> values = TransactionUtil.executeInUserTransaction(
|
||||
transactionService,
|
||||
getUrlsWork,
|
||||
true);
|
||||
|
||||
// Do the same for the AVM repository.
|
||||
TransactionWork<List<String>> getAVMUrlsWork = new TransactionWork<List<String>>()
|
||||
{
|
||||
public List<String> doWork() throws Exception
|
||||
{
|
||||
return avmNodeDAO.getContentUrls();
|
||||
}
|
||||
};
|
||||
|
||||
List<String> avmContentUrls = TransactionUtil.executeInUserTransaction(
|
||||
transactionService,
|
||||
getAVMUrlsWork,
|
||||
true);
|
||||
|
||||
// get all valid URLs
|
||||
Set<String> validUrls = new HashSet<String>(values.size());
|
||||
// convert the strings to objects and extract the URL
|
||||
for (Serializable value : values)
|
||||
{
|
||||
ContentData contentData = (ContentData) value;
|
||||
if (contentData.getContentUrl() != null)
|
||||
{
|
||||
// a URL was present
|
||||
validUrls.add(contentData.getContentUrl());
|
||||
}
|
||||
}
|
||||
// put all the avm urls into validUrls.
|
||||
for (String url : avmContentUrls)
|
||||
{
|
||||
validUrls.add(url);
|
||||
}
|
||||
|
||||
// done
|
||||
if (logger.isDebugEnabled())
|
||||
{
|
||||
logger.debug("Found " + validUrls.size() + " valid URLs in metadata");
|
||||
}
|
||||
return validUrls;
|
||||
}
|
||||
|
||||
public void execute()
|
||||
{
|
||||
checkProperties();
|
||||
Set<String> validUrls = getValidUrls();
|
||||
// now clean each store in turn
|
||||
for (ContentStore store : stores)
|
||||
{
|
||||
clean(validUrls, store);
|
||||
}
|
||||
}
|
||||
|
||||
private void clean(Set<String> validUrls, ContentStore store)
|
||||
{
|
||||
Date checkAllBeforeDate = new Date(System.currentTimeMillis() - (long) protectDays * 3600L * 1000L * 24L);
|
||||
// get the store's URLs
|
||||
Set<String> storeUrls = store.getUrls(null, checkAllBeforeDate);
|
||||
// remove all URLs that occur in the validUrls
|
||||
storeUrls.removeAll(validUrls);
|
||||
// now clean the store
|
||||
for (String url : storeUrls)
|
||||
{
|
||||
ContentReader sourceReader = store.getReader(url);
|
||||
// announce this to the listeners
|
||||
for (ContentStoreCleanerListener listener : listeners)
|
||||
{
|
||||
// get a fresh reader
|
||||
ContentReader listenerReader = sourceReader.getReader();
|
||||
// call it
|
||||
listener.beforeDelete(listenerReader);
|
||||
}
|
||||
// delete it
|
||||
store.delete(url);
|
||||
|
||||
if (logger.isDebugEnabled())
|
||||
{
|
||||
logger.debug("Removed URL from store: \n" +
|
||||
" Store: " + store + "\n" +
|
||||
" URL: " + url);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -19,7 +19,10 @@ package org.alfresco.repo.content.transform;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.net.URL;
|
||||
import java.util.List;
|
||||
import java.util.Date;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.TreeSet;
|
||||
|
||||
import org.alfresco.repo.content.MimetypeMap;
|
||||
import org.alfresco.repo.content.filestore.FileContentReader;
|
||||
@@ -120,45 +123,71 @@ public abstract class AbstractContentTransformerTest extends BaseSpringTest
|
||||
* case where optimizations are being done around the selection of the most
|
||||
* appropriate transformer, different transformers could be used during the iteration
|
||||
* process.
|
||||
* <p>
|
||||
* Results for the transformations are dumped to a temporary file named
|
||||
* <b>AbstractContentTransformerTest-results-1234.txt</b>.
|
||||
*/
|
||||
public void testAllConversions() throws Exception
|
||||
{
|
||||
StringBuilder sb = new StringBuilder(2048);
|
||||
sb.append("Mimetype Conversion Tests \n")
|
||||
.append("========================= \n")
|
||||
.append(" Date: ").append(new Date()).append("\n")
|
||||
.append("\n");
|
||||
|
||||
// get all mimetypes
|
||||
List<String> mimetypes = mimetypeMap.getMimetypes();
|
||||
Set<String> mimetypes = new TreeSet<String>(mimetypeMap.getMimetypes());
|
||||
for (String sourceMimetype : mimetypes)
|
||||
{
|
||||
// attempt to get a source file for each mimetype
|
||||
String sourceExtension = mimetypeMap.getExtension(sourceMimetype);
|
||||
File sourceFile = AbstractContentTransformerTest.loadQuickTestFile(sourceExtension);
|
||||
if (sourceFile == null)
|
||||
{
|
||||
continue; // no test file available for that extension
|
||||
}
|
||||
|
||||
sb.append(" Source Extension: ").append(sourceExtension).append("\n");
|
||||
|
||||
// attempt to convert to every other mimetype
|
||||
for (String targetMimetype : mimetypes)
|
||||
{
|
||||
ContentWriter targetWriter = null;
|
||||
// construct a reader onto the source file
|
||||
String targetExtension = mimetypeMap.getExtension(targetMimetype);
|
||||
|
||||
// must we test the transformation?
|
||||
ContentTransformer transformer = getTransformer(sourceMimetype, targetMimetype);
|
||||
if (transformer == null || transformer.getReliability(sourceMimetype, targetMimetype) <= 0.0)
|
||||
{
|
||||
// no transformer
|
||||
continue;
|
||||
}
|
||||
|
||||
// dump
|
||||
sb.append(" Target Extension: ").append(targetExtension);
|
||||
sb.append(" <").append(transformer.getClass().getSimpleName()).append(">");
|
||||
|
||||
// is there a test file for this conversion?
|
||||
File sourceFile = AbstractContentTransformerTest.loadQuickTestFile(sourceExtension);
|
||||
if (sourceFile == null)
|
||||
{
|
||||
sb.append(" <no source test file>\n");
|
||||
continue; // no test file available for that extension
|
||||
}
|
||||
ContentReader sourceReader = new FileContentReader(sourceFile);
|
||||
|
||||
// perform the transformation several times so that we get a good idea of performance
|
||||
int count = 0;
|
||||
long before = System.currentTimeMillis();
|
||||
Set<String> transformerClasses = new HashSet<String>(2);
|
||||
for (int i = 0; i < 5; i++)
|
||||
{
|
||||
// must we test the transformation?
|
||||
ContentTransformer transformer = getTransformer(sourceMimetype, targetMimetype);
|
||||
if (transformer == null)
|
||||
// get the transformer repeatedly as it might be different each time around
|
||||
transformer = getTransformer(sourceMimetype, targetMimetype);
|
||||
// must we report on this class?
|
||||
if (!transformerClasses.contains(transformer.getClass().getName()))
|
||||
{
|
||||
break; // test is not required
|
||||
transformerClasses.add(transformer.getClass().getName());
|
||||
sb.append(" <").append(transformer.getClass().getSimpleName()).append(">");
|
||||
}
|
||||
else if (transformer.getReliability(sourceMimetype, targetMimetype) <= 0.0)
|
||||
{
|
||||
break; // not reliable for this transformation
|
||||
}
|
||||
|
||||
|
||||
// make a writer for the target file
|
||||
String targetExtension = mimetypeMap.getExtension(targetMimetype);
|
||||
File targetFile = TempFileProvider.createTempFile(
|
||||
getClass().getSimpleName() + "_" + getName() + "_" + sourceExtension + "_",
|
||||
"." + targetExtension);
|
||||
@@ -198,6 +227,11 @@ public abstract class AbstractContentTransformerTest extends BaseSpringTest
|
||||
// increment count
|
||||
count++;
|
||||
}
|
||||
long after = System.currentTimeMillis();
|
||||
double average = (double) (after - before) / (double) count;
|
||||
|
||||
// dump
|
||||
sb.append(String.format(" average %10.0f ms", average)).append("\n");
|
||||
|
||||
if (logger.isDebugEnabled())
|
||||
{
|
||||
@@ -209,5 +243,11 @@ public abstract class AbstractContentTransformerTest extends BaseSpringTest
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// dump to file
|
||||
File outputFile = TempFileProvider.createTempFile("AbstractContentTransformerTest-results-", ".txt");
|
||||
ContentWriter outputWriter = new FileContentWriter(outputFile);
|
||||
outputWriter.setEncoding("UTF8");
|
||||
outputWriter.putContent(sb.toString());
|
||||
}
|
||||
}
|
||||
|
@@ -16,9 +16,16 @@
|
||||
*/
|
||||
package org.alfresco.repo.content.transform;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
import net.sf.jooreports.openoffice.connection.OpenOfficeConnection;
|
||||
|
||||
import org.alfresco.repo.content.MimetypeMap;
|
||||
import org.alfresco.repo.content.filestore.FileContentReader;
|
||||
import org.alfresco.repo.content.filestore.FileContentWriter;
|
||||
import org.alfresco.service.cmr.repository.ContentReader;
|
||||
import org.alfresco.service.cmr.repository.ContentWriter;
|
||||
import org.alfresco.util.TempFileProvider;
|
||||
|
||||
/**
|
||||
* @see org.alfresco.repo.content.transform.OpenOfficeContentTransformer
|
||||
@@ -75,4 +82,24 @@ public class OpenOfficeContentTransformerTest extends AbstractContentTransformer
|
||||
reliability = transformer.getReliability(MimetypeMap.MIMETYPE_WORD, MimetypeMap.MIMETYPE_TEXT_PLAIN);
|
||||
assertEquals("Mimetype should be supported", 1.0, reliability);
|
||||
}
|
||||
|
||||
/**
|
||||
* Test what is up with HTML to PDF
|
||||
*/
|
||||
public void testHtmlToPdf() throws Exception
|
||||
{
|
||||
if (!transformer.isConnected())
|
||||
{
|
||||
// no connection
|
||||
return;
|
||||
}
|
||||
File htmlSourceFile = loadQuickTestFile("html");
|
||||
File pdfTargetFile = TempFileProvider.createTempFile(getName() + "-target-", ".pdf");
|
||||
ContentReader reader = new FileContentReader(htmlSourceFile);
|
||||
reader.setMimetype(MimetypeMap.MIMETYPE_HTML);
|
||||
ContentWriter writer = new FileContentWriter(pdfTargetFile);
|
||||
writer.setMimetype(MimetypeMap.MIMETYPE_PDF);
|
||||
|
||||
transformer.transform(reader, writer);
|
||||
}
|
||||
}
|
||||
|
@@ -145,6 +145,10 @@ public abstract class AbstractImageMagickContentTransformer extends AbstractCont
|
||||
{
|
||||
return false; // rgb extension doesn't work
|
||||
}
|
||||
else if (mimetype.equals(MimetypeMap.MIMETYPE_IMAGE_SVG))
|
||||
{
|
||||
return false; // svg extension doesn't work
|
||||
}
|
||||
else
|
||||
{
|
||||
return true;
|
||||
|
Reference in New Issue
Block a user