mirror of
https://github.com/Alfresco/alfresco-community-repo.git
synced 2025-07-31 17:39:05 +00:00
REPO-4639 Content conversion failed using Tika (#587)
The Tika T-Engine was not being called by the Transform Service or Local transforms, because the sub-transform name was required. Moved common classes (with repo) to alfresco-transform-model so that it can be used by the T-Engines to work out which sub transformer to use. InT also performed a refactor on these classes (alfresco-transform-model 1.0.2.7). Also includes changes to legacy transformers so that they don't pass the sub transformer name any more.
This commit is contained in:
20
.travis.yml
20
.travis.yml
@@ -64,11 +64,11 @@ jobs:
|
||||
before_install:
|
||||
- docker run -d -p 5433:5432 -e POSTGRES_PASSWORD=alfresco -e POSTGRES_USER=alfresco -e POSTGRES_DB=alfresco postgres:11.4 postgres -c 'max_connections=300'
|
||||
- docker run -d -p 61616:61616 -p 5672:5672 alfresco/alfresco-activemq:5.15.8
|
||||
- docker run -d -p 8090:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-pdf-renderer:2.1.0-EA4
|
||||
- docker run -d -p 8091:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-imagemagick:2.1.0-EA4
|
||||
- docker run -d -p 8092:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-libreoffice:2.1.0-EA4
|
||||
- docker run -d -p 8093:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-tika:2.1.0-EA4
|
||||
- docker run -d -p 8094:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-transform-misc:2.1.0-EA4
|
||||
- docker run -d -p 8090:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-pdf-renderer:2.1.0-DEV1
|
||||
- docker run -d -p 8091:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-imagemagick:2.1.0-DEV1
|
||||
- docker run -d -p 8092:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-libreoffice:2.1.0-DEV1
|
||||
- docker run -d -p 8093:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-tika:2.1.0-DEV1
|
||||
- docker run -d -p 8094:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-transform-misc:2.1.0-DEV1
|
||||
script: travis_wait 20 mvn test -B -Dtest=AppContext06TestSuite -Ddb.driver=org.postgresql.Driver -Ddb.name=alfresco -Ddb.url=jdbc:postgresql://localhost:5433/alfresco -Ddb.username=alfresco -Ddb.password=alfresco -Dalfresco-pdf-renderer.url=http://localhost:8090/ -Djodconverter.url=http://localhost:8092/ -Dimg.url=http://localhost:8091/ -Dtika.url=http://localhost:8093/ -Dtransform.misc.url=http://localhost:8094/
|
||||
- name: "AppContextExtraTestSuite"
|
||||
before_install:
|
||||
@@ -79,11 +79,11 @@ jobs:
|
||||
before_install:
|
||||
- docker run -d -p 5433:5432 -e POSTGRES_PASSWORD=alfresco -e POSTGRES_USER=alfresco -e POSTGRES_DB=alfresco postgres:11.4 postgres -c 'max_connections=300'
|
||||
- docker run -d -p 61616:61616 -p 5672:5672 alfresco/alfresco-activemq:5.15.8
|
||||
- docker run -d -p 8090:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-pdf-renderer:2.1.0-EA4
|
||||
- docker run -d -p 8091:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-imagemagick:2.1.0-EA4
|
||||
- docker run -d -p 8092:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-libreoffice:2.1.0-EA4
|
||||
- docker run -d -p 8093:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-tika:2.1.0-EA4
|
||||
- docker run -d -p 8094:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-transform-misc:2.1.0-EA4
|
||||
- docker run -d -p 8090:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-pdf-renderer:2.1.0-DEV1
|
||||
- docker run -d -p 8091:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-imagemagick:2.1.0-DEV1
|
||||
- docker run -d -p 8092:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-libreoffice:2.1.0-DEV1
|
||||
- docker run -d -p 8093:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-tika:2.1.0-DEV1
|
||||
- docker run -d -p 8094:8090 -e JAVA_OPTS=" -Xms256m -Xmx256m" alfresco/alfresco-transform-misc:2.1.0-DEV1
|
||||
script: travis_wait 20 mvn test -B -Dtest=MiscContextTestSuite -Ddb.driver=org.postgresql.Driver -Ddb.name=alfresco -Ddb.url=jdbc:postgresql://localhost:5433/alfresco -Ddb.username=alfresco -Ddb.password=alfresco -Dalfresco-pdf-renderer.url=http://localhost:8090/ -Djodconverter.url=http://localhost:8092/ -Dimg.url=http://localhost:8091/ -Dtika.url=http://localhost:8093/ -Dtransform.misc.url=http://localhost:8094/
|
||||
- name: "MySQL tests"
|
||||
before_install:
|
||||
|
14
pom.xml
14
pom.xml
@@ -40,11 +40,11 @@
|
||||
<dependency.alfresco-legacy-lucene.version>6.2</dependency.alfresco-legacy-lucene.version>
|
||||
<dependency.alfresco-core.version>7.21</dependency.alfresco-core.version>
|
||||
<dependency.alfresco-greenmail.version>6.1</dependency.alfresco-greenmail.version>
|
||||
<dependency.alfresco-data-model.version>8.48</dependency.alfresco-data-model.version>
|
||||
<dependency.alfresco-data-model.version>8.49</dependency.alfresco-data-model.version>
|
||||
<dependency.alfresco-jlan.version>7.1</dependency.alfresco-jlan.version>
|
||||
<dependency.alfresco-pdf-renderer.version>1.1</dependency.alfresco-pdf-renderer.version>
|
||||
<dependency.alfresco-hb-data-sender.version>1.0.11</dependency.alfresco-hb-data-sender.version>
|
||||
|
||||
<dependency.transform.model.version>1.0.2.7</dependency.transform.model.version>
|
||||
|
||||
<dependency.spring.version>5.1.8.RELEASE</dependency.spring.version>
|
||||
<dependency.httpcomponents.version>4.5.9</dependency.httpcomponents.version>
|
||||
@@ -66,7 +66,6 @@
|
||||
<dependency.cxf.version>3.3.2</dependency.cxf.version>
|
||||
<dependency.jackson.version>2.9.9</dependency.jackson.version>
|
||||
<dependency.jackson-databind.version>2.9.9.3</dependency.jackson-databind.version>
|
||||
<dependency.transform.model.version>1.0.2.5</dependency.transform.model.version>
|
||||
</properties>
|
||||
|
||||
<dependencyManagement>
|
||||
@@ -194,7 +193,7 @@
|
||||
<dependency>
|
||||
<groupId>org.apache.commons</groupId>
|
||||
<artifactId>commons-compress</artifactId>
|
||||
<version>1.18</version>
|
||||
<version>1.19</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.commons</groupId>
|
||||
@@ -1052,6 +1051,13 @@
|
||||
<version>4.12</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.alfresco</groupId>
|
||||
<artifactId>alfresco-transform-model</artifactId>
|
||||
<version>${dependency.transform.model.version}</version>
|
||||
<classifier>tests</classifier>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.alfresco</groupId>
|
||||
<artifactId>alfresco-core</artifactId>
|
||||
|
@@ -141,12 +141,6 @@ public class ArchiveContentTransformer extends TikaPoweredContentTransformer
|
||||
return context;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "Archive";
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void transformRemote(RemoteTransformerClient remoteTransformerClient, ContentReader reader,
|
||||
ContentWriter writer, TransformationOptions options,
|
||||
@@ -154,7 +148,6 @@ public class ArchiveContentTransformer extends TikaPoweredContentTransformer
|
||||
String sourceExtension, String targetExtension,
|
||||
String targetEncoding) throws Exception
|
||||
{
|
||||
String transform = getTransform();
|
||||
long timeoutMs = options.getTimeoutMs();
|
||||
boolean recurse = includeContents;
|
||||
if(options.getIncludeEmbedded() != null)
|
||||
@@ -162,7 +155,10 @@ public class ArchiveContentTransformer extends TikaPoweredContentTransformer
|
||||
recurse = options.getIncludeEmbedded();
|
||||
}
|
||||
remoteTransformerClient.request(reader, writer, sourceMimetype, sourceExtension, targetExtension,
|
||||
timeoutMs, logger, "transform", transform, "includeContents", Boolean.toString(recurse),
|
||||
"targetMimetype", targetMimetype, "targetEncoding", targetEncoding);
|
||||
timeoutMs, logger,
|
||||
"includeContents", Boolean.toString(recurse),
|
||||
"sourceMimetype", sourceMimetype,
|
||||
"targetMimetype", targetMimetype,
|
||||
"targetEncoding", targetEncoding);
|
||||
}
|
||||
}
|
||||
|
@@ -143,11 +143,11 @@ public class LocalTransformImpl extends AbstractLocalTransform
|
||||
String sourceExtension, String targetExtension,
|
||||
String renditionName, NodeRef sourceNodeRef) throws Exception
|
||||
{
|
||||
// At some point in the future, we may decide to only pass the sourceEncoding and other dynamic values like
|
||||
// it if they were supplied in the rendition definition without a value. The sourceEncoding value is also
|
||||
// supplied in the TransformRequest (message to the T-Router).
|
||||
// Only pass the sourceEncoding and other dynamic values like it if they were supplied in the rendition
|
||||
// definition without a value. The sourceEncoding value is also supplied in the RenditionEventProducer in
|
||||
// the message to the T-Router.
|
||||
transformOptions = new HashMap<>(transformOptions);
|
||||
if (transformOptions.get(SOURCE_ENCODING) == null)
|
||||
if (transformOptions.containsKey(SOURCE_ENCODING) && transformOptions.get(SOURCE_ENCODING) == null)
|
||||
{
|
||||
String sourceEncoding = reader.getEncoding();
|
||||
transformOptions.put(SOURCE_ENCODING, sourceEncoding);
|
||||
|
@@ -25,20 +25,6 @@
|
||||
*/
|
||||
package org.alfresco.repo.content.transform;
|
||||
|
||||
import org.alfresco.service.cmr.repository.ContentReader;
|
||||
import org.alfresco.service.cmr.repository.ContentWriter;
|
||||
import org.alfresco.service.cmr.repository.MimetypeService;
|
||||
import org.alfresco.service.cmr.repository.NodeRef;
|
||||
import org.alfresco.transform.client.model.config.CombinedConfig;
|
||||
import org.alfresco.transform.client.model.config.InlineTransformer;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistry;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistryImpl;
|
||||
import org.alfresco.transform.client.model.config.TransformStep;
|
||||
import org.alfresco.util.PropertyCheck;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
@@ -48,6 +34,21 @@ import java.util.Map;
|
||||
import java.util.Properties;
|
||||
import java.util.Set;
|
||||
|
||||
import org.alfresco.service.cmr.repository.ContentReader;
|
||||
import org.alfresco.service.cmr.repository.ContentWriter;
|
||||
import org.alfresco.service.cmr.repository.MimetypeService;
|
||||
import org.alfresco.service.cmr.repository.NodeRef;
|
||||
import org.alfresco.transform.client.registry.CombinedConfig;
|
||||
import org.alfresco.transform.client.model.config.TransformOption;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistryImpl;
|
||||
import org.alfresco.transform.client.model.config.TransformStep;
|
||||
import org.alfresco.transform.client.model.config.Transformer;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistry;
|
||||
import org.alfresco.util.PropertyCheck;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
|
||||
/**
|
||||
* Implements {@link TransformServiceRegistry} providing a mechanism of validating if a local transformation
|
||||
* (based on {@link LocalTransform} request is supported. It also extends this interface to provide a
|
||||
@@ -156,7 +157,8 @@ public class LocalTransformServiceRegistry extends TransformServiceRegistryImpl
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void register(InlineTransformer transformer, String baseUrl, String readFrom)
|
||||
public void register(Transformer transformer, Map<String, Set<TransformOption>> transformOptions,
|
||||
String baseUrl, String readFrom)
|
||||
{
|
||||
try
|
||||
{
|
||||
@@ -242,7 +244,7 @@ public class LocalTransformServiceRegistry extends TransformServiceRegistryImpl
|
||||
}
|
||||
}
|
||||
localTransforms.put(name, localTransform);
|
||||
super.register(transformer, baseUrl, readFrom);
|
||||
super.register(transformer, transformOptions, baseUrl, readFrom);
|
||||
}
|
||||
catch (IllegalArgumentException e)
|
||||
{
|
||||
@@ -394,7 +396,7 @@ public class LocalTransformServiceRegistry extends TransformServiceRegistryImpl
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getMaxSize(String sourceMimetype, String targetMimetype, Map<String, String> options, String renditionName)
|
||||
public long findMaxSize(String sourceMimetype, String targetMimetype, Map<String, String> options, String renditionName)
|
||||
{
|
||||
// This message is not logged if placed in afterPropertiesSet
|
||||
if (getFirstTime())
|
||||
@@ -404,7 +406,7 @@ public class LocalTransformServiceRegistry extends TransformServiceRegistryImpl
|
||||
}
|
||||
|
||||
return enabled
|
||||
? super.getMaxSize(sourceMimetype, targetMimetype, options, renditionName)
|
||||
? super.findMaxSize(sourceMimetype, targetMimetype, options, renditionName)
|
||||
: 0;
|
||||
}
|
||||
|
||||
@@ -422,7 +424,7 @@ public class LocalTransformServiceRegistry extends TransformServiceRegistryImpl
|
||||
public LocalTransform getLocalTransform(Map<String, String> actualOptions, String renditionName,
|
||||
String sourceMimetype, String targetMimetype, long sourceSizeInBytes)
|
||||
{
|
||||
String name = getTransformerName(sourceMimetype, sourceSizeInBytes, targetMimetype, actualOptions, renditionName);
|
||||
String name = findTransformerName(sourceMimetype, sourceSizeInBytes, targetMimetype, actualOptions, renditionName);
|
||||
LocalData data = getData();
|
||||
Map<String, LocalTransform> localTransforms = data.localTransforms;
|
||||
return localTransforms.get(name);
|
||||
|
@@ -51,10 +51,4 @@ public class MailContentTransformer extends TikaPoweredContentTransformer
|
||||
protected Parser getParser() {
|
||||
return new OfficeParser();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "OutlookMsg";
|
||||
}
|
||||
}
|
||||
|
@@ -98,13 +98,6 @@ public class PdfBoxContentTransformer extends TikaPoweredContentTransformer
|
||||
return context;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "PdfBox";
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
protected void transformRemote(RemoteTransformerClient remoteTransformerClient, ContentReader reader,
|
||||
ContentWriter writer, TransformationOptions options,
|
||||
@@ -112,8 +105,6 @@ public class PdfBoxContentTransformer extends TikaPoweredContentTransformer
|
||||
String sourceExtension, String targetExtension,
|
||||
String targetEncoding) throws Exception
|
||||
{
|
||||
|
||||
String transform = getTransform();
|
||||
long timeoutMs = options.getTimeoutMs();
|
||||
String notExtractBookmarksText = null;
|
||||
|
||||
@@ -124,8 +115,8 @@ public class PdfBoxContentTransformer extends TikaPoweredContentTransformer
|
||||
|
||||
remoteTransformerClient.request(reader, writer, sourceMimetype, sourceExtension, targetExtension,
|
||||
timeoutMs, logger,
|
||||
"transform", transform,
|
||||
"notExtractBookmarksText", notExtractBookmarksText,
|
||||
"sourceMimetype", sourceMimetype,
|
||||
"targetMimetype", targetMimetype,
|
||||
"targetEncoding", targetEncoding);
|
||||
}
|
||||
|
@@ -76,10 +76,4 @@ public class PoiContentTransformer extends TikaPoweredContentTransformer
|
||||
protected Parser getParser() {
|
||||
return new OfficeParser();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "Office";
|
||||
}
|
||||
}
|
||||
|
@@ -211,10 +211,4 @@ public class PoiHssfContentTransformer extends TikaPoweredContentTransformer
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "Poi";
|
||||
}
|
||||
}
|
||||
|
@@ -65,10 +65,4 @@ public class PoiOOXMLContentTransformer extends TikaPoweredContentTransformer
|
||||
protected Parser getParser() {
|
||||
return new OOXMLParser();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "OOXML";
|
||||
}
|
||||
}
|
||||
|
@@ -51,10 +51,4 @@ public class TextMiningContentTransformer extends TikaPoweredContentTransformer
|
||||
protected Parser getParser() {
|
||||
return new OfficeParser();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "TextMining";
|
||||
}
|
||||
}
|
||||
|
@@ -131,10 +131,4 @@ public class TikaAutoContentTransformer extends TikaPoweredContentTransformer
|
||||
{
|
||||
return parser;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "TikaAuto";
|
||||
}
|
||||
}
|
||||
|
@@ -292,18 +292,15 @@ public abstract class TikaPoweredContentTransformer extends AbstractRemoteConten
|
||||
String sourceExtension, String targetExtension,
|
||||
String targetEncoding) throws Exception
|
||||
{
|
||||
String transform = getTransform();
|
||||
long timeoutMs = options.getTimeoutMs();
|
||||
|
||||
remoteTransformerClient.request(reader, writer, sourceMimetype, sourceExtension, targetExtension,
|
||||
timeoutMs, logger,
|
||||
"transform", transform,
|
||||
"sourceMimetype", sourceMimetype,
|
||||
"targetMimetype", targetMimetype,
|
||||
"targetEncoding", targetEncoding);
|
||||
}
|
||||
|
||||
protected abstract String getTransform();
|
||||
|
||||
private String calculateMemoryAndTimeUsage(ContentReader reader, long startTime)
|
||||
{
|
||||
long endTime = System.currentTimeMillis();
|
||||
|
@@ -107,10 +107,4 @@ public class TikaSpringConfiguredContentTransformer extends TikaPoweredContentTr
|
||||
throw new AlfrescoRuntimeException("Unable to create specified Parser", e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTransform()
|
||||
{
|
||||
return "tikaspring"; // This transformer is no longer created by Spring, so is not supported by the Tika transformer image
|
||||
}
|
||||
}
|
||||
|
@@ -25,10 +25,10 @@
|
||||
*/
|
||||
package org.alfresco.repo.rendition2;
|
||||
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistry;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistry;
|
||||
|
||||
/**
|
||||
* Contains common code used in TransformServiceRegistries.
|
||||
*
|
||||
@@ -37,9 +37,8 @@ import java.util.Map;
|
||||
public abstract class AbstractTransformServiceRegistry implements TransformServiceRegistry
|
||||
{
|
||||
@Override
|
||||
public boolean isSupported(String sourceMimetype, long size, String targetMimetype, Map<String, String> options, String renditionName)
|
||||
public String findTransformerName(String sourceMimetype, long sourceSizeInBytes, String targetMimetype, Map<String, String> actualOptions, String renditionName)
|
||||
{
|
||||
long maxSize = getMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
return maxSize != 0 && (maxSize == -1L || maxSize >= size);
|
||||
throw new UnsupportedOperationException("AbstractTransformServiceRegistry.findTransformerName(...) is not supported. Only supported in ");
|
||||
}
|
||||
}
|
||||
|
@@ -28,7 +28,7 @@ package org.alfresco.repo.rendition2;
|
||||
import org.alfresco.repo.content.transform.TransformerDebug;
|
||||
import org.alfresco.service.cmr.repository.ContentService;
|
||||
import org.alfresco.service.cmr.repository.TransformationOptions;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistry;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistry;
|
||||
import org.alfresco.util.PropertyCheck;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
|
||||
@@ -84,7 +84,7 @@ public class LegacyTransformServiceRegistry extends AbstractTransformServiceRegi
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getMaxSize(String sourceMimetype, String targetMimetype, Map<String, String> options, String renditionName)
|
||||
public long findMaxSize(String sourceMimetype, String targetMimetype, Map<String, String> options, String renditionName)
|
||||
{
|
||||
// This message is not logged if placed in afterPropertiesSet
|
||||
if (firstTime)
|
||||
|
@@ -27,7 +27,7 @@ package org.alfresco.repo.rendition2;
|
||||
|
||||
import com.fasterxml.jackson.databind.JsonNode;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistry;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistry;
|
||||
import org.alfresco.util.ConfigFileFinder;
|
||||
import org.alfresco.util.ConfigScheduler;
|
||||
import org.alfresco.util.Pair;
|
||||
@@ -343,7 +343,7 @@ public class RenditionDefinitionRegistry2Impl implements RenditionDefinitionRegi
|
||||
String targetMimetype = renditionDefinition2.getTargetMimetype();
|
||||
String renditionName = renditionDefinition2.getRenditionName();
|
||||
Map<String, String> options = renditionDefinition2.getTransformOptions();
|
||||
Long maxSize = transformServiceRegistry.getMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
Long maxSize = transformServiceRegistry.findMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
if (maxSize != null)
|
||||
{
|
||||
String renditionNameMaxSizePair = entry.getKey();
|
||||
|
@@ -25,7 +25,7 @@
|
||||
*/
|
||||
package org.alfresco.repo.rendition2;
|
||||
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistry;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistry;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
@@ -46,17 +46,17 @@ public class SwitchingTransformServiceRegistry extends AbstractTransformServiceR
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getMaxSize(String sourceMimetype, String targetMimetype, Map<String, String> options, String renditionName)
|
||||
public long findMaxSize(String sourceMimetype, String targetMimetype, Map<String, String> options, String renditionName)
|
||||
{
|
||||
long maxSize;
|
||||
long primaryMaxSize = primary.getMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
long primaryMaxSize = primary.findMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
if (primaryMaxSize == -1L)
|
||||
{
|
||||
maxSize = -1L;
|
||||
}
|
||||
else
|
||||
{
|
||||
long secondaryMaxSize = secondary.getMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
long secondaryMaxSize = secondary.findMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
maxSize = primaryMaxSize == 0
|
||||
? secondaryMaxSize
|
||||
: secondaryMaxSize == 0
|
||||
|
@@ -45,7 +45,7 @@ import org.alfresco.service.cmr.thumbnail.ThumbnailException;
|
||||
import org.alfresco.service.namespace.NamespaceService;
|
||||
import org.alfresco.service.namespace.QName;
|
||||
import org.alfresco.service.transaction.TransactionService;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistry;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistry;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.beans.BeansException;
|
||||
@@ -457,7 +457,7 @@ public class ThumbnailRegistry implements ApplicationContextAware, ApplicationLi
|
||||
{
|
||||
Map<String, String> options = renditionDefinition.getTransformOptions();
|
||||
String renditionName = renditionDefinition.getRenditionName();
|
||||
maxSize = transformServiceRegistry.getMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
maxSize = transformServiceRegistry.findMaxSize(sourceMimetype, targetMimetype, options, renditionName);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@@ -1,66 +0,0 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2005 - 2018 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.model.config;
|
||||
|
||||
/**
|
||||
* Represents a single transformer in a pipeline of multiple transformers. A transformer's options may be optional or
|
||||
* required in the containing transformer. Historically in ACS only options for the final transformer were provided.
|
||||
*/
|
||||
public class ChildTransformer
|
||||
{
|
||||
private boolean required;
|
||||
private InlineTransformer transformer;
|
||||
|
||||
public ChildTransformer()
|
||||
{
|
||||
}
|
||||
|
||||
public ChildTransformer(boolean required, InlineTransformer transformer)
|
||||
{
|
||||
this.required = required;
|
||||
this.transformer = transformer;
|
||||
}
|
||||
|
||||
public boolean isRequired()
|
||||
{
|
||||
return required;
|
||||
}
|
||||
|
||||
public void setRequired(boolean required)
|
||||
{
|
||||
this.required = required;
|
||||
}
|
||||
|
||||
public InlineTransformer getTransformer()
|
||||
{
|
||||
return transformer;
|
||||
}
|
||||
|
||||
public void setTransformer(InlineTransformer transformer)
|
||||
{
|
||||
this.transformer = transformer;
|
||||
}
|
||||
}
|
@@ -1,440 +0,0 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2019 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.model.config;
|
||||
|
||||
import com.fasterxml.jackson.databind.JsonNode;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.node.ArrayNode;
|
||||
import com.fasterxml.jackson.databind.node.ObjectNode;
|
||||
import org.alfresco.error.AlfrescoRuntimeException;
|
||||
import org.alfresco.util.ConfigFileFinder;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.http.HttpEntity;
|
||||
import org.apache.http.StatusLine;
|
||||
import org.apache.http.client.methods.CloseableHttpResponse;
|
||||
import org.apache.http.client.methods.HttpGet;
|
||||
import org.apache.http.impl.client.CloseableHttpClient;
|
||||
import org.apache.http.impl.client.HttpClients;
|
||||
import org.apache.http.util.EntityUtils;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.StringReader;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* This class recreates the json format used in ACS 6.1 where we just had an array of transformers and each
|
||||
* transformer has a list of node options. The idea of this code is that it replaces the references with the
|
||||
* actual node options that have been separated out into their own section.<p>
|
||||
*
|
||||
* The T-Router and T-Engines return the format with the node option separated into their own section. Pipeline
|
||||
* definitions used by the LocalTransformServiceRegistry may use node reference options defined in the json
|
||||
* returned by T-Engines. with the actual definitions from the node options
|
||||
* reference section. It also combines multiple json sources into a single jsonNode structure that can be parsed as
|
||||
* before.
|
||||
*/
|
||||
public class CombinedConfig
|
||||
{
|
||||
private static final String TRANSFORMER_NAME = "transformerName";
|
||||
private static final String TRANSFORM_CONFIG = "/transform/config";
|
||||
private static final String TRANSFORM_OPTIONS = "transformOptions";
|
||||
private static final String GROUP = "group";
|
||||
private static final String TRANSFORMERS = "transformers";
|
||||
|
||||
private final Log log;
|
||||
private Map<String, ArrayNode> allTransformOptions = new HashMap<>();
|
||||
private List<TransformNodeAndItsOrigin> allTransforms = new ArrayList<>();
|
||||
private ObjectMapper jsonObjectMapper = new ObjectMapper();
|
||||
private ConfigFileFinder configFileFinder;
|
||||
private int tEngineCount;
|
||||
|
||||
static class TransformNodeAndItsOrigin
|
||||
{
|
||||
final ObjectNode node;
|
||||
final String baseUrl;
|
||||
final String readFrom;
|
||||
|
||||
TransformNodeAndItsOrigin(ObjectNode node, String baseUrl, String readFrom)
|
||||
{
|
||||
this.node = node;
|
||||
this.baseUrl = baseUrl;
|
||||
this.readFrom = readFrom;
|
||||
}
|
||||
}
|
||||
|
||||
static class TransformAndItsOrigin
|
||||
{
|
||||
final InlineTransformer transform;
|
||||
final String baseUrl;
|
||||
final String readFrom;
|
||||
|
||||
TransformAndItsOrigin(InlineTransformer transform, String baseUrl, String readFrom)
|
||||
{
|
||||
this.transform = transform;
|
||||
this.baseUrl = baseUrl;
|
||||
this.readFrom = readFrom;
|
||||
}
|
||||
}
|
||||
|
||||
public CombinedConfig(Log log)
|
||||
{
|
||||
this.log = log;
|
||||
|
||||
configFileFinder = new ConfigFileFinder(jsonObjectMapper)
|
||||
{
|
||||
@Override
|
||||
protected void readJson(JsonNode jsonNode, String readFromMessage, String baseUrl) throws IOException
|
||||
{
|
||||
JsonNode transformOptions = jsonNode.get(TRANSFORM_OPTIONS);
|
||||
if (transformOptions != null && transformOptions.isObject())
|
||||
{
|
||||
Iterator<Map.Entry<String, JsonNode>> iterator = transformOptions.fields();
|
||||
while (iterator.hasNext())
|
||||
{
|
||||
Map.Entry<String, JsonNode> entry = iterator.next();
|
||||
|
||||
JsonNode options = entry.getValue();
|
||||
if (options.isArray())
|
||||
{
|
||||
String optionsName = entry.getKey();
|
||||
allTransformOptions.put(optionsName, (ArrayNode)options);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
JsonNode transformers = jsonNode.get(TRANSFORMERS);
|
||||
if (transformers != null && transformers.isArray())
|
||||
{
|
||||
for (JsonNode transformer : transformers)
|
||||
{
|
||||
if (transformer.isObject())
|
||||
{
|
||||
allTransforms.add(new TransformNodeAndItsOrigin((ObjectNode)transformer, baseUrl, readFromMessage));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
public boolean addRemoteConfig(List<String> urls, String remoteType)
|
||||
{
|
||||
boolean successReadingConfig = true;
|
||||
for (String url : urls)
|
||||
{
|
||||
if (addRemoteConfig(url, remoteType))
|
||||
{
|
||||
tEngineCount++ ;
|
||||
}
|
||||
else
|
||||
{
|
||||
successReadingConfig = false;
|
||||
}
|
||||
}
|
||||
return successReadingConfig;
|
||||
}
|
||||
|
||||
private boolean addRemoteConfig(String baseUrl, String remoteType)
|
||||
{
|
||||
String url = baseUrl + TRANSFORM_CONFIG;
|
||||
HttpGet httpGet = new HttpGet(url);
|
||||
boolean successReadingConfig = true;
|
||||
try
|
||||
{
|
||||
try (CloseableHttpClient httpclient = HttpClients.createDefault())
|
||||
{
|
||||
try (CloseableHttpResponse response = execute(httpclient, httpGet))
|
||||
{
|
||||
StatusLine statusLine = response.getStatusLine();
|
||||
if (statusLine == null)
|
||||
{
|
||||
throw new AlfrescoRuntimeException(remoteType+" on " + url+" returned no status ");
|
||||
}
|
||||
HttpEntity resEntity = response.getEntity();
|
||||
if (resEntity != null)
|
||||
{
|
||||
int statusCode = statusLine.getStatusCode();
|
||||
if (statusCode == 200)
|
||||
{
|
||||
try
|
||||
{
|
||||
String content = getContent(resEntity);
|
||||
|
||||
try (StringReader reader = new StringReader(content))
|
||||
{
|
||||
int transformCount = allTransforms.size();
|
||||
configFileFinder.readFile(reader, remoteType+" on "+baseUrl, "json", baseUrl, log);
|
||||
if (transformCount == allTransforms.size())
|
||||
{
|
||||
successReadingConfig = false;
|
||||
}
|
||||
}
|
||||
|
||||
EntityUtils.consume(resEntity);
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Failed to read the returned content from "+
|
||||
remoteType+" on " + url, e);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
String message = getErrorMessage(resEntity);
|
||||
throw new AlfrescoRuntimeException(remoteType+" on " + url+" returned a " + statusCode +
|
||||
" status " + message);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new AlfrescoRuntimeException(remoteType+" on " + url+" did not return an entity " + url);
|
||||
}
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Failed to connect or to read the response from "+remoteType+
|
||||
" on " + url, e);
|
||||
}
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new AlfrescoRuntimeException(remoteType+" on " + url+" failed to create an HttpClient", e);
|
||||
}
|
||||
}
|
||||
catch (AlfrescoRuntimeException e)
|
||||
{
|
||||
log.error(e.getMessage());
|
||||
successReadingConfig = false;
|
||||
}
|
||||
return successReadingConfig;
|
||||
}
|
||||
|
||||
// Tests mock the return values
|
||||
CloseableHttpResponse execute(CloseableHttpClient httpclient, HttpGet httpGet) throws IOException
|
||||
{
|
||||
return httpclient.execute(httpGet);
|
||||
}
|
||||
|
||||
// Tests mock the return values
|
||||
String getContent(HttpEntity resEntity) throws IOException
|
||||
{
|
||||
return EntityUtils.toString(resEntity);
|
||||
}
|
||||
|
||||
// Strip out just the error message in the response
|
||||
private String getErrorMessage(HttpEntity resEntity) throws IOException
|
||||
{
|
||||
String message = "";
|
||||
String content = getContent(resEntity);
|
||||
int i = content.indexOf("\"message\":\"");
|
||||
if (i != -1)
|
||||
{
|
||||
int j = content.indexOf("\",\"path\":", i);
|
||||
if (j != -1)
|
||||
{
|
||||
message = content.substring(i+11, j);
|
||||
}
|
||||
}
|
||||
return message;
|
||||
}
|
||||
|
||||
public boolean addLocalConfig(String path) throws IOException
|
||||
{
|
||||
return configFileFinder.readFiles(path, log);
|
||||
}
|
||||
|
||||
public void register(TransformServiceRegistryImpl registry) throws IOException
|
||||
{
|
||||
TransformServiceRegistryImpl.Data data = registry.getData();
|
||||
data.setTEngineCount(tEngineCount);
|
||||
data.setFileCount(configFileFinder.getFileCount());
|
||||
List<TransformAndItsOrigin> transformers = getTransforms();
|
||||
transformers.forEach(t->registry.register(t.transform, t.baseUrl, t.readFrom));
|
||||
}
|
||||
|
||||
public List<TransformAndItsOrigin> getTransforms() throws IOException
|
||||
{
|
||||
List<TransformAndItsOrigin> transforms = new ArrayList<>();
|
||||
|
||||
// After all json input has been loaded build the output with the options in place.
|
||||
ArrayNode transformersNode = jsonObjectMapper.createArrayNode();
|
||||
for (TransformNodeAndItsOrigin entity : allTransforms)
|
||||
{
|
||||
transformersNode.add(entity.node);
|
||||
|
||||
try
|
||||
{
|
||||
ArrayNode transformOptions = (ArrayNode) entity.node.get(TRANSFORM_OPTIONS);
|
||||
if (transformOptions != null)
|
||||
{
|
||||
|
||||
ArrayNode options;
|
||||
int size = transformOptions.size();
|
||||
if (size == 1)
|
||||
{
|
||||
// If there is a single node option reference, we can just use it.
|
||||
int i = 0;
|
||||
options = getTransformOptions(transformOptions, i, entity.node);
|
||||
}
|
||||
else
|
||||
{
|
||||
// If there are many node option references (typically in a pipeline), then each element
|
||||
// has a group for each set of node options.
|
||||
options = jsonObjectMapper.createArrayNode();
|
||||
for (int i = size - 1; i >= 0; i--)
|
||||
{
|
||||
JsonNode referencedTransformOptions = getTransformOptions(transformOptions, i, entity.node);
|
||||
if (referencedTransformOptions != null)
|
||||
{
|
||||
ObjectNode element = jsonObjectMapper.createObjectNode();
|
||||
options.add(element);
|
||||
|
||||
ObjectNode group = jsonObjectMapper.createObjectNode();
|
||||
group.set(TRANSFORM_OPTIONS, referencedTransformOptions);
|
||||
element.set(GROUP, group);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (options == null || options.size() == 0)
|
||||
{
|
||||
entity.node.remove(TRANSFORM_OPTIONS);
|
||||
}
|
||||
else
|
||||
{
|
||||
entity.node.set(TRANSFORM_OPTIONS, options);
|
||||
}
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
InlineTransformer transform = jsonObjectMapper.convertValue(entity.node, InlineTransformer.class);
|
||||
transforms.add(new TransformAndItsOrigin(transform, entity.baseUrl, entity.readFrom));
|
||||
}
|
||||
catch (IllegalArgumentException e)
|
||||
{
|
||||
log.error("Invalid transformer "+getTransformName(entity.node)+" "+e.getMessage()+" baseUrl="+entity.baseUrl);
|
||||
}
|
||||
}
|
||||
catch (IllegalArgumentException e)
|
||||
{
|
||||
String transformString = jsonObjectMapper.writerWithDefaultPrettyPrinter().writeValueAsString(entity.node);
|
||||
log.error(e.getMessage());
|
||||
log.debug(transformString);
|
||||
}
|
||||
}
|
||||
if (log.isTraceEnabled())
|
||||
{
|
||||
log.trace("Combined config:\n"+jsonObjectMapper.writerWithDefaultPrettyPrinter().writeValueAsString(transformersNode));
|
||||
}
|
||||
|
||||
transforms = sortTransformers(transforms);
|
||||
return transforms;
|
||||
}
|
||||
|
||||
// Sort transformers so there are no forward references, if that is possible.
|
||||
private List<TransformAndItsOrigin> sortTransformers(List<TransformAndItsOrigin> original)
|
||||
{
|
||||
List<TransformAndItsOrigin> transformers = new ArrayList<>(original.size());
|
||||
List<TransformAndItsOrigin> todo = new ArrayList<>(original.size());
|
||||
Set<String> transformerNames = new HashSet<>();
|
||||
boolean added;
|
||||
do
|
||||
{
|
||||
added = false;
|
||||
for (TransformAndItsOrigin entry : original)
|
||||
{
|
||||
String name = entry.transform.getTransformerName();
|
||||
List<TransformStep> pipeline = entry.transform.getTransformerPipeline();
|
||||
boolean addEntry = true;
|
||||
if (pipeline != null && !pipeline.isEmpty())
|
||||
{
|
||||
for (TransformStep step : pipeline)
|
||||
{
|
||||
String stepName = step.getTransformerName();
|
||||
if (!transformerNames.contains(stepName))
|
||||
{
|
||||
todo.add(entry);
|
||||
addEntry = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (addEntry)
|
||||
{
|
||||
transformers.add(entry);
|
||||
added = true;
|
||||
if (name != null)
|
||||
{
|
||||
transformerNames.add(name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
original.clear();
|
||||
original.addAll(todo);
|
||||
todo.clear();
|
||||
}
|
||||
while (added && !original.isEmpty());
|
||||
|
||||
transformers.addAll(todo);
|
||||
|
||||
return transformers;
|
||||
}
|
||||
|
||||
private ArrayNode getTransformOptions(ArrayNode transformOptions, int i, ObjectNode transform)
|
||||
{
|
||||
ArrayNode options = null;
|
||||
JsonNode optionName = transformOptions.get(i);
|
||||
if (optionName.isTextual())
|
||||
{
|
||||
String name = optionName.asText();
|
||||
options = allTransformOptions.get(name);
|
||||
if (options == null)
|
||||
{
|
||||
String message = "Reference to \"transformOptions\": \"" + name + "\" not found. Transformer " +
|
||||
getTransformName(transform) + " ignored.";
|
||||
throw new IllegalArgumentException(message);
|
||||
}
|
||||
}
|
||||
return options;
|
||||
}
|
||||
|
||||
private String getTransformName(ObjectNode transform)
|
||||
{
|
||||
String name = "Unknown";
|
||||
JsonNode nameNode = transform.get(TRANSFORMER_NAME);
|
||||
if (nameNode != null && nameNode.isTextual())
|
||||
{
|
||||
name = '"'+nameNode.asText()+'"';
|
||||
}
|
||||
return name;
|
||||
}
|
||||
}
|
@@ -1,67 +0,0 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2005 - 2018 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.model.config;
|
||||
|
||||
import org.quartz.CronExpression;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Used by clients work out if a transformation is supported by a Transform Service.
|
||||
*/
|
||||
public interface TransformServiceRegistry
|
||||
{
|
||||
/**
|
||||
* Works out if the Transform Server should be able to transform content of a given source mimetype and size into a
|
||||
* target mimetype given a list of actual transform option names and values (Strings) plus the data contained in the
|
||||
* {@Transform} objects registered with this class.
|
||||
* @param sourceMimetype the mimetype of the source content
|
||||
* @param sourceSizeInBytes the size in bytes of the source content. Ignored if negative.
|
||||
* @param targetMimetype the mimetype of the target
|
||||
* @param actualOptions the actual name value pairs available that could be passed to the Transform Service.
|
||||
* @param transformName (optional) name for the set of options and target mimetype. If supplied is used to cache
|
||||
* results to avoid having to work out if a given transformation is supported a second time.
|
||||
* The sourceMimetype and sourceSizeInBytes may still change. In the case of ACS this is the
|
||||
* rendition name.
|
||||
*/
|
||||
boolean isSupported(String sourceMimetype, long sourceSizeInBytes, String targetMimetype,
|
||||
Map<String, String> actualOptions, String transformName);
|
||||
|
||||
/**
|
||||
* Returns the maximun size (in bytes) of the source content that can be transformed.
|
||||
* @param sourceMimetype the mimetype of the source content
|
||||
* @param targetMimetype the mimetype of the target
|
||||
* @param actualOptions the actual name value pairs available that could be passed to the Transform Service.
|
||||
* @param transformName (optional) name for the set of options and target mimetype. If supplied is used to cache
|
||||
* results to avoid having to work out if a given transformation is supported a second time.
|
||||
* The sourceMimetype and sourceSizeInBytes may still change. In the case of ACS this is the
|
||||
* rendition name.
|
||||
* @return the maximum size (in bytes) of the source content that can be transformed. If {@code -1} there is no
|
||||
* limit, but if {@code 0} the transform is not supported.
|
||||
*/
|
||||
long getMaxSize(String sourceMimetype, String targetMimetype,
|
||||
Map<String, String> actualOptions, String transformName);
|
||||
}
|
@@ -1,459 +0,0 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2005 - 2018 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.model.config;
|
||||
|
||||
import com.fasterxml.jackson.core.type.TypeReference;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.alfresco.util.ConfigScheduler;
|
||||
import org.alfresco.util.PropertyCheck;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.quartz.CronExpression;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.Reader;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
import java.util.concurrent.ConcurrentMap;
|
||||
|
||||
import static org.alfresco.repo.rendition2.RenditionDefinition2.TIMEOUT;
|
||||
|
||||
/**
|
||||
* Used by clients to work out if a transformation is supported by the Transform Service.
|
||||
*/
|
||||
public abstract class TransformServiceRegistryImpl implements TransformServiceRegistry, InitializingBean
|
||||
{
|
||||
public static class Data
|
||||
{
|
||||
ConcurrentMap<String, ConcurrentMap<String, List<SupportedTransform>>> transformers = new ConcurrentHashMap<>();
|
||||
ConcurrentMap<String, ConcurrentMap<String, List<SupportedTransform>>> cachedSupportedTransformList = new ConcurrentHashMap<>();
|
||||
private int transformerCount = 0;
|
||||
private int transformCount = 0;
|
||||
private int tEngineCount = 0;
|
||||
private int fileCount;
|
||||
boolean firstTime = true;
|
||||
|
||||
@Override
|
||||
public String toString()
|
||||
{
|
||||
return transformerCount == 0 && transformCount == 0 && tEngineCount == 0 && fileCount == 0
|
||||
? ""
|
||||
: "(transformers: "+transformerCount+" transforms: "+transformCount+" t-engines: "+tEngineCount+" files: "+fileCount+")";
|
||||
}
|
||||
|
||||
public void setTEngineCount(int tEngineCount)
|
||||
{
|
||||
this.tEngineCount = tEngineCount;
|
||||
}
|
||||
|
||||
public void setFileCount(int fileCount)
|
||||
{
|
||||
this.fileCount = fileCount;
|
||||
}
|
||||
}
|
||||
|
||||
static class SupportedTransform
|
||||
{
|
||||
TransformOptionGroup transformOptions;
|
||||
long maxSourceSizeBytes;
|
||||
private String name;
|
||||
private int priority;
|
||||
|
||||
public SupportedTransform(Data data, String name, Set<TransformOption> transformOptions, long maxSourceSizeBytes, int priority)
|
||||
{
|
||||
// Logically the top level TransformOptionGroup is required, so that child options are optional or required
|
||||
// based on their own setting.
|
||||
this.transformOptions = new TransformOptionGroup(true, transformOptions);
|
||||
this.maxSourceSizeBytes = maxSourceSizeBytes;
|
||||
this.name = name;
|
||||
this.priority = priority;
|
||||
data.transformCount++;
|
||||
}
|
||||
}
|
||||
|
||||
protected boolean enabled = true;
|
||||
private ObjectMapper jsonObjectMapper;
|
||||
private CronExpression cronExpression;
|
||||
private CronExpression initialAndOnErrorCronExpression;
|
||||
|
||||
private ConfigScheduler<Data> configScheduler = new ConfigScheduler(this)
|
||||
{
|
||||
@Override
|
||||
public boolean readConfig() throws IOException
|
||||
{
|
||||
return TransformServiceRegistryImpl.this.readConfig();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object createData()
|
||||
{
|
||||
return TransformServiceRegistryImpl.this.createData();
|
||||
}
|
||||
};
|
||||
|
||||
public void setJsonObjectMapper(ObjectMapper jsonObjectMapper)
|
||||
{
|
||||
this.jsonObjectMapper = jsonObjectMapper;
|
||||
}
|
||||
|
||||
public CronExpression getCronExpression()
|
||||
{
|
||||
return cronExpression;
|
||||
}
|
||||
|
||||
public void setCronExpression(CronExpression cronExpression)
|
||||
{
|
||||
this.cronExpression = cronExpression;
|
||||
}
|
||||
|
||||
public CronExpression getInitialAndOnErrorCronExpression()
|
||||
{
|
||||
return initialAndOnErrorCronExpression;
|
||||
}
|
||||
|
||||
public void setInitialAndOnErrorCronExpression(CronExpression initialAndOnErrorCronExpression)
|
||||
{
|
||||
this.initialAndOnErrorCronExpression = initialAndOnErrorCronExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterPropertiesSet() throws Exception
|
||||
{
|
||||
PropertyCheck.mandatory(this, "jsonObjectMapper", jsonObjectMapper);
|
||||
// If we have a cronExpression it indicates that we will schedule reading.
|
||||
if (cronExpression != null)
|
||||
{
|
||||
PropertyCheck.mandatory(this, "initialAndOnErrorCronExpression", initialAndOnErrorCronExpression);
|
||||
}
|
||||
|
||||
Log log = getLog();
|
||||
configScheduler.run(enabled, log, cronExpression, initialAndOnErrorCronExpression);
|
||||
}
|
||||
|
||||
public Data createData()
|
||||
{
|
||||
return new Data();
|
||||
}
|
||||
|
||||
public Data getData()
|
||||
{
|
||||
return configScheduler.getData();
|
||||
}
|
||||
|
||||
public abstract boolean readConfig() throws IOException;
|
||||
|
||||
public boolean isEnabled()
|
||||
{
|
||||
return enabled;
|
||||
}
|
||||
|
||||
public void setEnabled(boolean enabled)
|
||||
{
|
||||
this.enabled = enabled;
|
||||
setFirstTime(true);
|
||||
}
|
||||
|
||||
protected void setFirstTime(boolean firstTime)
|
||||
{
|
||||
getData().firstTime = firstTime;
|
||||
}
|
||||
|
||||
protected boolean getFirstTime()
|
||||
{
|
||||
return getData().firstTime;
|
||||
}
|
||||
|
||||
protected abstract Log getLog();
|
||||
|
||||
public void register(Reader reader, String readFrom) throws IOException
|
||||
{
|
||||
List<InlineTransformer> transformers = jsonObjectMapper.readValue(reader, new TypeReference<List<InlineTransformer>>(){});
|
||||
transformers.forEach(t -> register(t, null, readFrom));
|
||||
}
|
||||
|
||||
protected void register(InlineTransformer transformer, String baseUrl, String readFrom)
|
||||
{
|
||||
Data data = getData();
|
||||
data.transformerCount++;
|
||||
transformer.getSupportedSourceAndTargetList().forEach(
|
||||
e -> data.transformers.computeIfAbsent(e.getSourceMediaType(),
|
||||
k -> new ConcurrentHashMap<>()).computeIfAbsent(e.getTargetMediaType(),
|
||||
k -> new ArrayList<>()).add(
|
||||
new SupportedTransform(data, transformer.getTransformerName(),
|
||||
transformer.getTransformOptions(), e.getMaxSourceSizeBytes(), e.getPriority())));
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSupported(String sourceMimetype, long sourceSizeInBytes, String targetMimetype,
|
||||
Map<String, String> actualOptions, String renditionName)
|
||||
{
|
||||
long maxSize = getMaxSize(sourceMimetype, targetMimetype, actualOptions, renditionName);
|
||||
return maxSize != 0 && (maxSize == -1L || maxSize >= sourceSizeInBytes);
|
||||
}
|
||||
|
||||
/**
|
||||
* Works out the name of the transformer (might not map to an actual transformer) that will be used to transform
|
||||
* content of a given source mimetype and size into a target mimetype given a list of actual transform option names
|
||||
* and values (Strings) plus the data contained in the {@Transform} objects registered with this class.
|
||||
* @param sourceMimetype the mimetype of the source content
|
||||
* @param sourceSizeInBytes the size in bytes of the source content. Ignored if negative.
|
||||
* @param targetMimetype the mimetype of the target
|
||||
* @param actualOptions the actual name value pairs available that could be passed to the Transform Service.
|
||||
* @param renditionName (optional) name for the set of options and target mimetype. If supplied is used to cache
|
||||
* results to avoid having to work out if a given transformation is supported a second time.
|
||||
* The sourceMimetype and sourceSizeInBytes may still change. In the case of ACS this is the
|
||||
* rendition name.
|
||||
*/
|
||||
protected String getTransformerName(String sourceMimetype, long sourceSizeInBytes, String targetMimetype, Map<String, String> actualOptions, String renditionName)
|
||||
{
|
||||
List<SupportedTransform> supportedTransforms = getTransformListBySize(sourceMimetype, targetMimetype, actualOptions, renditionName);
|
||||
for (SupportedTransform supportedTransform : supportedTransforms)
|
||||
{
|
||||
if (supportedTransform.maxSourceSizeBytes == -1 || supportedTransform.maxSourceSizeBytes >= sourceSizeInBytes)
|
||||
{
|
||||
return supportedTransform.name;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public long getMaxSize(String sourceMimetype, String targetMimetype,
|
||||
Map<String, String> actualOptions, String renditionName)
|
||||
{
|
||||
List<SupportedTransform> supportedTransforms = getTransformListBySize(sourceMimetype, targetMimetype, actualOptions, renditionName);
|
||||
return supportedTransforms.isEmpty() ? 0 : supportedTransforms.get(supportedTransforms.size()-1).maxSourceSizeBytes;
|
||||
}
|
||||
|
||||
// Returns transformers in increasing supported size order, where lower priority transformers for the same size have
|
||||
// been discarded.
|
||||
private List<SupportedTransform> getTransformListBySize(String sourceMimetype, String targetMimetype,
|
||||
Map<String, String> actualOptions, String renditionName)
|
||||
{
|
||||
if (actualOptions == null)
|
||||
{
|
||||
actualOptions = Collections.EMPTY_MAP;
|
||||
}
|
||||
if (renditionName != null && renditionName.trim().isEmpty())
|
||||
{
|
||||
renditionName = null;
|
||||
}
|
||||
|
||||
Data data = getData();
|
||||
List<SupportedTransform> transformListBySize = renditionName == null ? null
|
||||
: data.cachedSupportedTransformList.computeIfAbsent(renditionName, k -> new ConcurrentHashMap<>()).get(sourceMimetype);
|
||||
if (transformListBySize != null)
|
||||
{
|
||||
return transformListBySize;
|
||||
}
|
||||
|
||||
// Remove the "timeout" property from the actualOptions as it is not used to select a transformer.
|
||||
if (actualOptions.containsKey(TIMEOUT))
|
||||
{
|
||||
actualOptions = new HashMap(actualOptions);
|
||||
actualOptions.remove(TIMEOUT);
|
||||
}
|
||||
|
||||
transformListBySize = new ArrayList<>();
|
||||
ConcurrentMap<String, List<SupportedTransform>> targetMap = data.transformers.get(sourceMimetype);
|
||||
if (targetMap != null)
|
||||
{
|
||||
List<SupportedTransform> supportedTransformList = targetMap.get(targetMimetype);
|
||||
if (supportedTransformList != null)
|
||||
{
|
||||
for (SupportedTransform supportedTransform : supportedTransformList)
|
||||
{
|
||||
TransformOptionGroup transformOptions = supportedTransform.transformOptions;
|
||||
Map<String, Boolean> possibleTransformOptions = new HashMap<>();
|
||||
addToPossibleTransformOptions(possibleTransformOptions, transformOptions, true, actualOptions);
|
||||
if (isSupported(possibleTransformOptions, actualOptions))
|
||||
{
|
||||
addToSupportedTransformList(transformListBySize, supportedTransform);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (renditionName != null)
|
||||
{
|
||||
data.cachedSupportedTransformList.get(renditionName).put(sourceMimetype, transformListBySize);
|
||||
}
|
||||
|
||||
return transformListBySize;
|
||||
}
|
||||
|
||||
// Add newTransform to the transformListBySize in increasing size order and discards lower priority (numerically
|
||||
// higher) transforms with a smaller or equal size.
|
||||
private void addToSupportedTransformList(List<SupportedTransform> transformListBySize, SupportedTransform newTransform)
|
||||
{
|
||||
for (int i=0; i < transformListBySize.size(); i++)
|
||||
{
|
||||
SupportedTransform existingTransform = transformListBySize.get(i);
|
||||
int added = -1;
|
||||
int compare = compare(newTransform.maxSourceSizeBytes, existingTransform.maxSourceSizeBytes);
|
||||
if (compare < 0)
|
||||
{
|
||||
transformListBySize.add(i, newTransform);
|
||||
added = i;
|
||||
}
|
||||
else if (compare == 0)
|
||||
{
|
||||
if (newTransform.priority < existingTransform.priority)
|
||||
{
|
||||
transformListBySize.set(i, newTransform);
|
||||
added = i;
|
||||
}
|
||||
}
|
||||
if (added == i)
|
||||
{
|
||||
for (i--; i >= 0; i--)
|
||||
{
|
||||
existingTransform = transformListBySize.get(i);
|
||||
if (newTransform.priority <= existingTransform.priority)
|
||||
{
|
||||
transformListBySize.remove(i);
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
}
|
||||
transformListBySize.add(newTransform);
|
||||
}
|
||||
|
||||
// compare where -1 is unlimited.
|
||||
private int compare(long a, long b)
|
||||
{
|
||||
return a == -1
|
||||
? b == -1 ? 0 : 1
|
||||
: b == -1 ? -1
|
||||
: a == b ? 0
|
||||
: a > b ? 1 : -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Flatten out the transform options by adding them to the supplied possibleTransformOptions.</p>
|
||||
*
|
||||
* If possible discards options in the supplied transformOptionGroup if the group is optional and the actualOptions
|
||||
* don't provide any of the options in the group. Or to put it another way:<p/>
|
||||
*
|
||||
* It adds individual transform options from the transformOptionGroup to possibleTransformOptions if the group is
|
||||
* required or if the actualOptions include individual options from the group. As a result it is possible that none
|
||||
* of the group are added if it is optional. It is also possible to add individual transform options that are
|
||||
* themselves required but not in the actualOptions. In this the isSupported method will return false.
|
||||
* @return true if any options were added. Used by nested call parents to determine if an option was added from a
|
||||
* nested sub group.
|
||||
*/
|
||||
boolean addToPossibleTransformOptions(Map<String, Boolean> possibleTransformOptions,
|
||||
TransformOptionGroup transformOptionGroup,
|
||||
Boolean parentGroupRequired, Map<String, String> actualOptions)
|
||||
{
|
||||
boolean added = false;
|
||||
boolean required = false;
|
||||
|
||||
Set<TransformOption> optionList = transformOptionGroup.getTransformOptions();
|
||||
if (optionList != null && !optionList.isEmpty())
|
||||
{
|
||||
// We need to avoid adding options from a group that is required but its parents are not.
|
||||
boolean transformOptionGroupRequired = transformOptionGroup.isRequired() && parentGroupRequired;
|
||||
|
||||
// Check if the group contains options in actualOptions. This will add any options from sub groups.
|
||||
for (TransformOption transformOption : optionList)
|
||||
{
|
||||
if (transformOption instanceof TransformOptionGroup)
|
||||
{
|
||||
added = addToPossibleTransformOptions(possibleTransformOptions, (TransformOptionGroup) transformOption,
|
||||
transformOptionGroupRequired, actualOptions);
|
||||
required |= added;
|
||||
}
|
||||
else
|
||||
{
|
||||
String name = ((TransformOptionValue) transformOption).getName();
|
||||
if (actualOptions.containsKey(name))
|
||||
{
|
||||
required = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (required || transformOptionGroupRequired)
|
||||
{
|
||||
for (TransformOption transformOption : optionList)
|
||||
{
|
||||
if (transformOption instanceof TransformOptionValue)
|
||||
{
|
||||
added = true;
|
||||
TransformOptionValue transformOptionValue = (TransformOptionValue) transformOption;
|
||||
String name = transformOptionValue.getName();
|
||||
boolean optionValueRequired = transformOptionValue.isRequired();
|
||||
possibleTransformOptions.put(name, optionValueRequired);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return added;
|
||||
}
|
||||
|
||||
boolean isSupported(Map<String, Boolean> transformOptions, Map<String, String> actualOptions)
|
||||
{
|
||||
boolean supported = true;
|
||||
|
||||
// Check all required transformOptions are supplied
|
||||
for (Map.Entry<String, Boolean> transformOption : transformOptions.entrySet())
|
||||
{
|
||||
Boolean required = transformOption.getValue();
|
||||
if (required)
|
||||
{
|
||||
String name = transformOption.getKey();
|
||||
if (!actualOptions.containsKey(name))
|
||||
{
|
||||
supported = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (supported)
|
||||
{
|
||||
// Check there are no extra unused actualOptions
|
||||
for (String actualOption : actualOptions.keySet())
|
||||
{
|
||||
if (!transformOptions.containsKey(actualOption))
|
||||
{
|
||||
supported = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return supported;
|
||||
}
|
||||
}
|
@@ -0,0 +1,241 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2019 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.registry;
|
||||
|
||||
import com.fasterxml.jackson.databind.JsonNode;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.alfresco.error.AlfrescoRuntimeException;
|
||||
import org.alfresco.transform.client.model.config.TransformConfig;
|
||||
import org.alfresco.transform.client.model.config.TransformOption;
|
||||
import org.alfresco.transform.client.model.config.Transformer;
|
||||
import org.alfresco.util.ConfigFileFinder;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.http.HttpEntity;
|
||||
import org.apache.http.StatusLine;
|
||||
import org.apache.http.client.methods.CloseableHttpResponse;
|
||||
import org.apache.http.client.methods.HttpGet;
|
||||
import org.apache.http.impl.client.CloseableHttpClient;
|
||||
import org.apache.http.impl.client.HttpClients;
|
||||
import org.apache.http.util.EntityUtils;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.StringReader;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* This class reads multiple T-Engine config and local files and registers them all with a registry as if they were all
|
||||
* in one file. Transform options are shared between all sources.<p>
|
||||
*
|
||||
* The caller should make calls to {@link #addRemoteConfig(List, String)} and {@link #addLocalConfig(String)} followed
|
||||
* by a call to {@link #register(TransformServiceRegistryImpl)}.
|
||||
*
|
||||
* @author adavis
|
||||
*/
|
||||
public class CombinedConfig
|
||||
{
|
||||
private static final String TRANSFORM_CONFIG = "/transform/config";
|
||||
|
||||
private final Log log;
|
||||
|
||||
static class TransformAndItsOrigin
|
||||
{
|
||||
final Transformer transformer;
|
||||
final String baseUrl;
|
||||
final String readFrom;
|
||||
|
||||
TransformAndItsOrigin(Transformer transformer, String baseUrl, String readFrom)
|
||||
{
|
||||
this.transformer = transformer;
|
||||
this.baseUrl = baseUrl;
|
||||
this.readFrom = readFrom;
|
||||
}
|
||||
}
|
||||
|
||||
Map<String, Set<TransformOption>> combinedTransformOptions = new HashMap<>();
|
||||
List<TransformAndItsOrigin> combinedTransformers = new ArrayList<>();
|
||||
|
||||
private ObjectMapper jsonObjectMapper = new ObjectMapper();
|
||||
private ConfigFileFinder configFileFinder;
|
||||
private int tEngineCount;
|
||||
|
||||
public CombinedConfig(Log log)
|
||||
{
|
||||
this.log = log;
|
||||
|
||||
configFileFinder = new ConfigFileFinder(jsonObjectMapper)
|
||||
{
|
||||
@Override
|
||||
protected void readJson(JsonNode jsonNode, String readFrom, String baseUrl)
|
||||
{
|
||||
TransformConfig transformConfig = jsonObjectMapper.convertValue(jsonNode, TransformConfig.class);
|
||||
transformConfig.getTransformOptions().forEach((key, map) -> combinedTransformOptions.put(key, map));
|
||||
transformConfig.getTransformers().forEach(transformer -> combinedTransformers.add(
|
||||
new TransformAndItsOrigin(transformer, baseUrl, readFrom)));
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
public boolean addLocalConfig(String path)
|
||||
{
|
||||
return configFileFinder.readFiles(path, log);
|
||||
}
|
||||
|
||||
public boolean addRemoteConfig(List<String> urls, String remoteType)
|
||||
{
|
||||
boolean successReadingConfig = true;
|
||||
for (String url : urls)
|
||||
{
|
||||
if (addRemoteConfig(url, remoteType))
|
||||
{
|
||||
tEngineCount++ ;
|
||||
}
|
||||
else
|
||||
{
|
||||
successReadingConfig = false;
|
||||
}
|
||||
}
|
||||
return successReadingConfig;
|
||||
}
|
||||
|
||||
private boolean addRemoteConfig(String baseUrl, String remoteType)
|
||||
{
|
||||
String url = baseUrl + TRANSFORM_CONFIG;
|
||||
HttpGet httpGet = new HttpGet(url);
|
||||
boolean successReadingConfig = true;
|
||||
try
|
||||
{
|
||||
try (CloseableHttpClient httpclient = HttpClients.createDefault())
|
||||
{
|
||||
try (CloseableHttpResponse response = execute(httpclient, httpGet))
|
||||
{
|
||||
StatusLine statusLine = response.getStatusLine();
|
||||
if (statusLine == null)
|
||||
{
|
||||
throw new AlfrescoRuntimeException(remoteType+" on " + url+" returned no status ");
|
||||
}
|
||||
HttpEntity resEntity = response.getEntity();
|
||||
if (resEntity != null)
|
||||
{
|
||||
int statusCode = statusLine.getStatusCode();
|
||||
if (statusCode == 200)
|
||||
{
|
||||
try
|
||||
{
|
||||
String content = getContent(resEntity);
|
||||
|
||||
try (StringReader reader = new StringReader(content))
|
||||
{
|
||||
int transformCount = combinedTransformers.size();
|
||||
configFileFinder.readFile(reader, remoteType+" on "+baseUrl, "json", baseUrl, log);
|
||||
if (transformCount == combinedTransformers.size())
|
||||
{
|
||||
successReadingConfig = false;
|
||||
}
|
||||
}
|
||||
|
||||
EntityUtils.consume(resEntity);
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Failed to read the returned content from "+
|
||||
remoteType+" on " + url, e);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
String message = getErrorMessage(resEntity);
|
||||
throw new AlfrescoRuntimeException(remoteType+" on " + url+" returned a " + statusCode +
|
||||
" status " + message);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new AlfrescoRuntimeException(remoteType+" on " + url+" did not return an entity " + url);
|
||||
}
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new AlfrescoRuntimeException("Failed to connect or to read the response from "+remoteType+
|
||||
" on " + url, e);
|
||||
}
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new AlfrescoRuntimeException(remoteType+" on " + url+" failed to create an HttpClient", e);
|
||||
}
|
||||
}
|
||||
catch (AlfrescoRuntimeException e)
|
||||
{
|
||||
log.error(e.getMessage());
|
||||
successReadingConfig = false;
|
||||
}
|
||||
return successReadingConfig;
|
||||
}
|
||||
|
||||
// Tests mock the return values
|
||||
CloseableHttpResponse execute(CloseableHttpClient httpclient, HttpGet httpGet) throws IOException
|
||||
{
|
||||
return httpclient.execute(httpGet);
|
||||
}
|
||||
|
||||
// Tests mock the return values
|
||||
String getContent(HttpEntity resEntity) throws IOException
|
||||
{
|
||||
return EntityUtils.toString(resEntity);
|
||||
}
|
||||
|
||||
// Strip out just the error message in the response
|
||||
private String getErrorMessage(HttpEntity resEntity) throws IOException
|
||||
{
|
||||
String message = "";
|
||||
String content = getContent(resEntity);
|
||||
int i = content.indexOf("\"message\":\"");
|
||||
if (i != -1)
|
||||
{
|
||||
int j = content.indexOf("\",\"path\":", i);
|
||||
if (j != -1)
|
||||
{
|
||||
message = content.substring(i+11, j);
|
||||
}
|
||||
}
|
||||
return message;
|
||||
}
|
||||
|
||||
public void register(TransformServiceRegistryImpl registry)
|
||||
{
|
||||
TransformServiceRegistryImpl.Data data = registry.getData();
|
||||
data.setTEngineCount(tEngineCount);
|
||||
data.setFileCount(configFileFinder.getFileCount());
|
||||
|
||||
combinedTransformers.forEach(transformer ->
|
||||
registry.register(transformer.transformer, combinedTransformOptions,
|
||||
transformer.baseUrl, transformer.readFrom));
|
||||
}
|
||||
}
|
@@ -0,0 +1,169 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2005 - 2018 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.registry;
|
||||
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
|
||||
import org.alfresco.transform.client.registry.AbstractTransformRegistry;
|
||||
import org.alfresco.transform.client.registry.TransformCache;
|
||||
import org.alfresco.util.ConfigScheduler;
|
||||
import org.alfresco.util.PropertyCheck;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.quartz.CronExpression;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
/**
|
||||
* Used by clients to work out if a transformation is supported by the Transform Service.
|
||||
*/
|
||||
public abstract class TransformServiceRegistryImpl extends AbstractTransformRegistry implements InitializingBean
|
||||
{
|
||||
public static class Data extends TransformCache
|
||||
{
|
||||
private int tEngineCount = 0;
|
||||
private int fileCount;
|
||||
boolean firstTime = true;
|
||||
|
||||
@Override
|
||||
public String toString()
|
||||
{
|
||||
return transformerCount == 0 && transformCount == 0 && tEngineCount == 0 && fileCount == 0
|
||||
? ""
|
||||
: "(transformers: "+transformerCount+" transforms: "+transformCount+" t-engines: "+tEngineCount+" files: "+fileCount+")";
|
||||
}
|
||||
|
||||
public void setTEngineCount(int tEngineCount)
|
||||
{
|
||||
this.tEngineCount = tEngineCount;
|
||||
}
|
||||
|
||||
public void setFileCount(int fileCount)
|
||||
{
|
||||
this.fileCount = fileCount;
|
||||
}
|
||||
}
|
||||
|
||||
protected boolean enabled = true;
|
||||
private ObjectMapper jsonObjectMapper;
|
||||
private CronExpression cronExpression;
|
||||
private CronExpression initialAndOnErrorCronExpression;
|
||||
|
||||
private ConfigScheduler<Data> configScheduler = new ConfigScheduler<>(this)
|
||||
{
|
||||
@Override
|
||||
public boolean readConfig() throws IOException
|
||||
{
|
||||
return TransformServiceRegistryImpl.this.readConfig();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Data createData()
|
||||
{
|
||||
return TransformServiceRegistryImpl.this.createData();
|
||||
}
|
||||
};
|
||||
|
||||
public void setJsonObjectMapper(ObjectMapper jsonObjectMapper)
|
||||
{
|
||||
this.jsonObjectMapper = jsonObjectMapper;
|
||||
}
|
||||
|
||||
public CronExpression getCronExpression()
|
||||
{
|
||||
return cronExpression;
|
||||
}
|
||||
|
||||
public void setCronExpression(CronExpression cronExpression)
|
||||
{
|
||||
this.cronExpression = cronExpression;
|
||||
}
|
||||
|
||||
public CronExpression getInitialAndOnErrorCronExpression()
|
||||
{
|
||||
return initialAndOnErrorCronExpression;
|
||||
}
|
||||
|
||||
public void setInitialAndOnErrorCronExpression(CronExpression initialAndOnErrorCronExpression)
|
||||
{
|
||||
this.initialAndOnErrorCronExpression = initialAndOnErrorCronExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void afterPropertiesSet() throws Exception
|
||||
{
|
||||
PropertyCheck.mandatory(this, "jsonObjectMapper", jsonObjectMapper);
|
||||
// If we have a cronExpression it indicates that we will schedule reading.
|
||||
if (cronExpression != null)
|
||||
{
|
||||
PropertyCheck.mandatory(this, "initialAndOnErrorCronExpression", initialAndOnErrorCronExpression);
|
||||
}
|
||||
|
||||
Log log = getLog();
|
||||
configScheduler.run(enabled, log, cronExpression, initialAndOnErrorCronExpression);
|
||||
}
|
||||
|
||||
public Data createData()
|
||||
{
|
||||
return new Data();
|
||||
}
|
||||
|
||||
public Data getData()
|
||||
{
|
||||
return configScheduler.getData();
|
||||
}
|
||||
|
||||
public abstract boolean readConfig() throws IOException;
|
||||
|
||||
public boolean isEnabled()
|
||||
{
|
||||
return enabled;
|
||||
}
|
||||
|
||||
public void setEnabled(boolean enabled)
|
||||
{
|
||||
this.enabled = enabled;
|
||||
setFirstTime(true);
|
||||
}
|
||||
|
||||
protected void setFirstTime(boolean firstTime)
|
||||
{
|
||||
getData().firstTime = firstTime;
|
||||
}
|
||||
|
||||
protected boolean getFirstTime()
|
||||
{
|
||||
return getData().firstTime;
|
||||
}
|
||||
|
||||
protected abstract Log getLog();
|
||||
|
||||
@Override
|
||||
protected void logError(String msg)
|
||||
{
|
||||
getLog().error(msg);
|
||||
}
|
||||
}
|
@@ -201,7 +201,7 @@ import org.junit.runners.Suite;
|
||||
org.alfresco.util.resource.HierarchicalResourceLoaderTest.class,
|
||||
org.alfresco.repo.events.ClientUtilTest.class,
|
||||
org.alfresco.repo.rendition2.RenditionService2Test.class,
|
||||
org.alfresco.transform.client.model.config.TransformServiceRegistryConfigTest.class
|
||||
org.alfresco.transform.client.registry.TransformServiceRegistryConfigTest.class
|
||||
})
|
||||
public class AllUnitTestsSuite
|
||||
{
|
||||
|
@@ -49,7 +49,7 @@ import org.junit.runners.Suite;
|
||||
org.alfresco.repo.rawevents.TransactionAwareEventProducerTest.class,
|
||||
|
||||
// Requires running transformers
|
||||
org.alfresco.transform.client.model.config.LocalTransformServiceRegistryConfigTest.class,
|
||||
org.alfresco.transform.client.registry.LocalTransformServiceRegistryConfigTest.class,
|
||||
org.alfresco.repo.rendition2.RenditionService2IntegrationTest.class,
|
||||
org.alfresco.repo.rendition2.LocalTransformServiceRegistryIntegrationTest.class,
|
||||
org.alfresco.repo.rendition2.LocalTransformClientIntegrationTest.class,
|
||||
|
@@ -45,7 +45,7 @@ import org.alfresco.service.cmr.security.PermissionService;
|
||||
import org.alfresco.service.cmr.security.PersonService;
|
||||
import org.alfresco.service.namespace.QName;
|
||||
import org.alfresco.service.transaction.TransactionService;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistry;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistry;
|
||||
import org.alfresco.util.BaseSpringTest;
|
||||
import org.alfresco.util.GUID;
|
||||
import org.alfresco.util.PropertyMap;
|
||||
|
@@ -59,6 +59,6 @@ public class LocalRenditionTest extends AbstractRenditionTest
|
||||
@Test
|
||||
public void testAllSourceExtensions() throws Exception
|
||||
{
|
||||
internalTestAllSourceExtensions(57, 0);
|
||||
internalTestAllSourceExtensions(81, 0);
|
||||
}
|
||||
}
|
||||
|
@@ -26,8 +26,8 @@
|
||||
package org.alfresco.repo.rendition2;
|
||||
|
||||
import org.alfresco.repo.content.transform.LocalTransformServiceRegistry;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistry;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistryImpl;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistry;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistryImpl;
|
||||
import org.junit.After;
|
||||
import org.junit.AfterClass;
|
||||
import org.junit.Assert;
|
||||
|
@@ -39,7 +39,7 @@ import org.alfresco.service.cmr.repository.NodeService;
|
||||
import org.alfresco.service.cmr.rule.RuleService;
|
||||
import org.alfresco.service.namespace.QName;
|
||||
import org.alfresco.service.transaction.TransactionService;
|
||||
import org.alfresco.transform.client.model.config.TransformServiceRegistryImpl;
|
||||
import org.alfresco.transform.client.registry.TransformServiceRegistryImpl;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
|
@@ -1,54 +0,0 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2005 - 2018 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.model.config;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* Helper class that builds a {@link InlineTransformer} given the source and target types and a pipeline of Transformers
|
||||
* for creating intermediary content.
|
||||
*/
|
||||
public class TransformBuilder
|
||||
{
|
||||
public InlineTransformer buildPipeLine(String name, Set<SupportedSourceAndTarget> sourceAndTargetList,
|
||||
List<ChildTransformer> transformerList)
|
||||
{
|
||||
Set<TransformOption> options = new HashSet<>(transformerList.size());
|
||||
transformerList.forEach(t ->
|
||||
{
|
||||
// Avoid creating an enpty TransformOptionGroup if the transformer has no options.
|
||||
// Works with an empty TransformOptionGroup but adds to the complexity.
|
||||
if (t.getTransformer().getTransformOptions() != null)
|
||||
{
|
||||
options.add(new TransformOptionGroup(t.isRequired(), t.getTransformer().getTransformOptions()));
|
||||
}
|
||||
});
|
||||
return new InlineTransformer(name, options, sourceAndTargetList);
|
||||
}
|
||||
}
|
@@ -1,896 +0,0 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2005 - 2019 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.model.config;
|
||||
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.apache.log4j.Level;
|
||||
import org.apache.log4j.LogManager;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import org.quartz.CronExpression;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.File;
|
||||
import java.io.FileReader;
|
||||
import java.io.FileWriter;
|
||||
import java.io.IOException;
|
||||
import java.io.Reader;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.ConcurrentMap;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
/**
|
||||
* Test the config received from the Transform Service about what it supports.
|
||||
*/
|
||||
public class TransformServiceRegistryConfigTest
|
||||
{
|
||||
private static Log log = LogFactory.getLog(TransformServiceRegistryConfigTest.class);
|
||||
|
||||
public static final String GIF = "image/gif";
|
||||
public static final String JPEG = "image/jpeg";
|
||||
public static final String PNG = "image/png";
|
||||
public static final String TIFF = "image/tiff";
|
||||
public static final String PDF = "application/pdf";
|
||||
public static final String DOC = "application/msword";
|
||||
public static final String XLS = "application/vnd.ms-excel";
|
||||
public static final String PPT = "application/vnd.ms-powerpoint";
|
||||
public static final String MSG = "application/vnd.ms-outlook";
|
||||
public static final String TXT = "text/plain";
|
||||
|
||||
private static final String TRANSFORM_SERVICE_CONFIG = "alfresco/transform-service-config-test.json";
|
||||
private static final String TRANSFORM_SERVICE_CONFIG_PIPELINE = "alfresco/transform-service-config-pipeline-test.json";
|
||||
|
||||
public static final ObjectMapper JSON_OBJECT_MAPPER = new ObjectMapper();
|
||||
|
||||
private TransformServiceRegistryImpl registry;
|
||||
protected TransformBuilder builder;
|
||||
protected InlineTransformer transformer;
|
||||
|
||||
@Before
|
||||
public void setUp() throws Exception
|
||||
{
|
||||
registry = buildTransformServiceRegistryImpl();
|
||||
builder = new TransformBuilder();
|
||||
LogManager.getLogger(TransformServiceRegistryConfigTest.class).setLevel(Level.DEBUG);
|
||||
}
|
||||
|
||||
protected TransformServiceRegistryImpl buildTransformServiceRegistryImpl() throws Exception
|
||||
{
|
||||
TransformServiceRegistryImpl registry = new TransformServiceRegistryImpl()
|
||||
{
|
||||
@Override
|
||||
public boolean readConfig() throws IOException
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Log getLog()
|
||||
{
|
||||
return log;
|
||||
}
|
||||
};
|
||||
registry.setJsonObjectMapper(JSON_OBJECT_MAPPER);
|
||||
registry.setCronExpression(null); // just read once
|
||||
registry.afterPropertiesSet();
|
||||
return registry;
|
||||
}
|
||||
|
||||
@After
|
||||
public void tearDown()
|
||||
{
|
||||
// shut down
|
||||
}
|
||||
|
||||
protected String getTransformServiceConfig()
|
||||
{
|
||||
return TRANSFORM_SERVICE_CONFIG;
|
||||
}
|
||||
|
||||
protected String getTransformServiceConfigPipeline()
|
||||
{
|
||||
return TRANSFORM_SERVICE_CONFIG_PIPELINE;
|
||||
}
|
||||
|
||||
private void assertAddToPossibleOptions(TransformOptionGroup transformOptionGroup, String actualOptionNames, String expectedNames, String expectedRequired)
|
||||
{
|
||||
Map<String, String> actualOptions = buildActualOptions(actualOptionNames);
|
||||
Set<String> expectedNameSet = expectedNames == null || expectedNames.isEmpty() ? Collections.EMPTY_SET : new HashSet(Arrays.asList(expectedNames.split(", ")));
|
||||
Set<String> expectedRequiredSet = expectedRequired == null || expectedRequired.isEmpty() ? Collections.EMPTY_SET : new HashSet(Arrays.asList(expectedRequired.split(", ")));
|
||||
|
||||
Map<String, Boolean> possibleTransformOptions = new HashMap<>();
|
||||
|
||||
registry.addToPossibleTransformOptions(possibleTransformOptions, transformOptionGroup, true, actualOptions);
|
||||
|
||||
assertEquals("The expected options don't match", expectedNameSet, possibleTransformOptions.keySet());
|
||||
for (String name: possibleTransformOptions.keySet())
|
||||
{
|
||||
Boolean required = possibleTransformOptions.get(name);
|
||||
if (required)
|
||||
{
|
||||
assertTrue(name+" should be REQUIRED", expectedRequiredSet.contains(name));
|
||||
}
|
||||
else
|
||||
{
|
||||
assertFalse(name+" should be OPTIONAL", expectedRequiredSet.contains(name));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// transformOptionNames are upper case if required.
|
||||
private void assertIsSupported(String actualOptionNames, String transformOptionNames, String unsupportedMsg)
|
||||
{
|
||||
Map<String, String> actualOptions = buildActualOptions(actualOptionNames);
|
||||
|
||||
Map<String, Boolean> transformOptions = new HashMap<>();
|
||||
Set<String> transformOptionNameSet = transformOptionNames == null || transformOptionNames.isEmpty() ? Collections.EMPTY_SET : new HashSet(Arrays.asList(transformOptionNames.split(", ")));
|
||||
for (String name : transformOptionNameSet)
|
||||
{
|
||||
Boolean required = name.toUpperCase().equals(name);
|
||||
transformOptions.put(name, required);
|
||||
}
|
||||
|
||||
boolean supported = registry.isSupported(transformOptions, actualOptions);
|
||||
if (unsupportedMsg == null || unsupportedMsg.isEmpty())
|
||||
{
|
||||
assertTrue("Expected these options to be SUPPORTED", supported);
|
||||
}
|
||||
else
|
||||
{
|
||||
assertFalse("Expected these options NOT to be supported, because "+unsupportedMsg, supported);
|
||||
}
|
||||
}
|
||||
|
||||
private void assertTransformOptions(Set<TransformOption> transformOptions) throws Exception
|
||||
{
|
||||
transformer = new InlineTransformer("name",
|
||||
transformOptions,
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, TXT, -1),
|
||||
new SupportedSourceAndTarget(XLS, TXT, 1024000)));
|
||||
|
||||
registry = buildTransformServiceRegistryImpl();
|
||||
registry.register(transformer, getBaseUrl(transformer), getClass().getName());
|
||||
|
||||
assertTrue(registry.isSupported(XLS, 1024, TXT, Collections.emptyMap(), null));
|
||||
assertTrue(registry.isSupported(XLS, 1024000, TXT, null, null));
|
||||
assertFalse(registry.isSupported(XLS, 1024001, TXT, Collections.emptyMap(), null));
|
||||
assertTrue(registry.isSupported(DOC, 1024001, TXT, null, null));
|
||||
}
|
||||
|
||||
protected String getBaseUrl(InlineTransformer transformer)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
private void assertTransformerName(String sourceMimetype, long sourceSizeInBytes, String targetMimetype,
|
||||
Map<String, String> actualOptions, String expectedTransformerName,
|
||||
InlineTransformer... transformers) throws Exception
|
||||
{
|
||||
buildAndPopulateRegistry(transformers);
|
||||
String transformerName = registry.getTransformerName(sourceMimetype, sourceSizeInBytes, targetMimetype, actualOptions, null);
|
||||
assertEquals(sourceMimetype+" to "+targetMimetype+" should have returned "+expectedTransformerName, expectedTransformerName, transformerName);
|
||||
}
|
||||
|
||||
private void assertSupported(String sourceMimetype, long sourceSizeInBytes, String targetMimetype,
|
||||
Map<String, String> actualOptions, String unsupportedMsg) throws Exception
|
||||
{
|
||||
assertSupported(sourceMimetype, sourceSizeInBytes, targetMimetype, actualOptions, unsupportedMsg, transformer);
|
||||
}
|
||||
|
||||
private void assertSupported(String sourceMimetype, long sourceSizeInBytes, String targetMimetype,
|
||||
Map<String, String> actualOptions, String unsupportedMsg,
|
||||
InlineTransformer... transformers) throws Exception
|
||||
{
|
||||
buildAndPopulateRegistry(transformers);
|
||||
assertSupported(sourceMimetype, sourceSizeInBytes, targetMimetype, actualOptions, null, unsupportedMsg);
|
||||
}
|
||||
|
||||
private void buildAndPopulateRegistry(InlineTransformer[] transformers) throws Exception
|
||||
{
|
||||
registry = buildTransformServiceRegistryImpl();
|
||||
for (InlineTransformer transformer : transformers)
|
||||
{
|
||||
registry.register(transformer, getBaseUrl(transformer), getClass().getName());
|
||||
}
|
||||
}
|
||||
|
||||
private void assertSupported(String sourceMimetype, long sourceSizeInBytes, String targetMimetype,
|
||||
Map<String, String> actualOptions, String renditionName,
|
||||
String unsupportedMsg)
|
||||
{
|
||||
boolean supported = registry.isSupported(sourceMimetype, sourceSizeInBytes, targetMimetype, actualOptions, renditionName);
|
||||
if (unsupportedMsg == null || unsupportedMsg.isEmpty())
|
||||
{
|
||||
assertTrue(sourceMimetype+" to "+targetMimetype+" should be SUPPORTED", supported);
|
||||
}
|
||||
else
|
||||
{
|
||||
assertFalse(sourceMimetype+" to "+targetMimetype+" should NOT be supported", supported);
|
||||
}
|
||||
}
|
||||
|
||||
private Map<String, String> buildActualOptions(String actualOptionNames)
|
||||
{
|
||||
Map<String, String> actualOptions = new HashMap<>();
|
||||
Set<String> actualOptionNamesSet = actualOptionNames == null || actualOptionNames.isEmpty() ? Collections.EMPTY_SET : new HashSet(Arrays.asList(actualOptionNames.split(", ")));
|
||||
for (String name : actualOptionNamesSet)
|
||||
{
|
||||
actualOptions.put(name, "value for " + name);
|
||||
}
|
||||
return actualOptions;
|
||||
}
|
||||
|
||||
private void register(String path) throws IOException
|
||||
{
|
||||
CombinedConfig combinedConfig = new CombinedConfig(log);
|
||||
combinedConfig.addLocalConfig(path);
|
||||
combinedConfig.register(registry);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testReadWriteJson() throws IOException
|
||||
{
|
||||
InlineTransformer libreoffice = new InlineTransformer("libreoffice",
|
||||
null, // there are no options
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, PDF, -1),
|
||||
new SupportedSourceAndTarget(XLS, PDF, 1024000),
|
||||
new SupportedSourceAndTarget(PPT, PDF, -1),
|
||||
new SupportedSourceAndTarget(MSG, PDF, -1)));
|
||||
|
||||
InlineTransformer pdfrenderer = new InlineTransformer("pdfrenderer",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "page"),
|
||||
new TransformOptionValue(false, "width"),
|
||||
new TransformOptionValue(false, "height"),
|
||||
new TransformOptionValue(false, "allowPdfEnlargement"),
|
||||
new TransformOptionValue(false, "maintainPdfAspectRatio")),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(PDF, PNG, -1)));
|
||||
|
||||
InlineTransformer tika = new InlineTransformer("tika",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "transform"),
|
||||
new TransformOptionValue(false, "includeContents"),
|
||||
new TransformOptionValue(false, "notExtractBookmarksText"),
|
||||
new TransformOptionValue(false, "targetMimetype"),
|
||||
new TransformOptionValue(false, "targetEncoding")),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(PDF, TXT, -1),
|
||||
new SupportedSourceAndTarget(DOC, TXT, -1),
|
||||
new SupportedSourceAndTarget(XLS, TXT, 1024000),
|
||||
new SupportedSourceAndTarget(PPT, TXT, -1),
|
||||
new SupportedSourceAndTarget(MSG, TXT, -1)));
|
||||
|
||||
InlineTransformer imagemagick = new InlineTransformer("imagemagick",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "alphaRemove"),
|
||||
new TransformOptionValue(false, "autoOrient"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "cropGravity"),
|
||||
new TransformOptionValue(false, "cropWidth"),
|
||||
new TransformOptionValue(false, "cropHeight"),
|
||||
new TransformOptionValue(false, "cropPercentage"),
|
||||
new TransformOptionValue(false, "cropXOffset"),
|
||||
new TransformOptionValue(false, "cropYOffset"))),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "thumbnail"),
|
||||
new TransformOptionValue(false, "resizeHeight"),
|
||||
new TransformOptionValue(false, "resizeWidth"),
|
||||
new TransformOptionValue(false, "resizePercentage"),
|
||||
new TransformOptionValue(false, "maintainAspectRatio")))),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(GIF, GIF, -1),
|
||||
new SupportedSourceAndTarget(GIF, JPEG, -1),
|
||||
new SupportedSourceAndTarget(GIF, PNG, -1),
|
||||
new SupportedSourceAndTarget(GIF, TIFF, -1),
|
||||
|
||||
new SupportedSourceAndTarget(JPEG, GIF, -1),
|
||||
new SupportedSourceAndTarget(JPEG, JPEG, -1),
|
||||
new SupportedSourceAndTarget(JPEG, PNG, -1),
|
||||
new SupportedSourceAndTarget(JPEG, TIFF, -1),
|
||||
|
||||
new SupportedSourceAndTarget(PNG, GIF, -1),
|
||||
new SupportedSourceAndTarget(PNG, JPEG, -1),
|
||||
new SupportedSourceAndTarget(PNG, PNG, -1),
|
||||
new SupportedSourceAndTarget(PNG, TIFF, -1),
|
||||
|
||||
new SupportedSourceAndTarget(TIFF, GIF, -1),
|
||||
new SupportedSourceAndTarget(TIFF, JPEG, -1),
|
||||
new SupportedSourceAndTarget(TIFF, PNG, -1),
|
||||
new SupportedSourceAndTarget(TIFF, TIFF, -1)));
|
||||
|
||||
InlineTransformer officeToImage = builder.buildPipeLine("transformer1",
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, GIF, -1),
|
||||
new SupportedSourceAndTarget(DOC, JPEG, -1),
|
||||
new SupportedSourceAndTarget(DOC, PNG, -1),
|
||||
new SupportedSourceAndTarget(DOC, TIFF, -1),
|
||||
new SupportedSourceAndTarget(XLS, GIF, -1),
|
||||
new SupportedSourceAndTarget(XLS, JPEG, -1),
|
||||
new SupportedSourceAndTarget(XLS, PNG, -1),
|
||||
new SupportedSourceAndTarget(XLS, TIFF, -1),
|
||||
new SupportedSourceAndTarget(PPT, GIF, -1),
|
||||
new SupportedSourceAndTarget(PPT, JPEG, -1),
|
||||
new SupportedSourceAndTarget(PPT, PNG, -1),
|
||||
new SupportedSourceAndTarget(PPT, TIFF, -1),
|
||||
new SupportedSourceAndTarget(MSG, GIF, -1),
|
||||
new SupportedSourceAndTarget(MSG, JPEG, -1),
|
||||
new SupportedSourceAndTarget(MSG, PNG, -1),
|
||||
new SupportedSourceAndTarget(MSG, TIFF, -1)),
|
||||
Arrays.asList(
|
||||
new ChildTransformer(false, libreoffice), // to pdf
|
||||
new ChildTransformer(false, pdfrenderer), // to png
|
||||
new ChildTransformer(true, imagemagick))); // to other image formats
|
||||
|
||||
List<InlineTransformer> transformers1 = Arrays.asList(libreoffice, tika, pdfrenderer, imagemagick, officeToImage);
|
||||
|
||||
File tempFile = File.createTempFile("test", ".json");
|
||||
ObjectMapper objectMapper = new ObjectMapper();
|
||||
objectMapper.writerWithDefaultPrettyPrinter().writeValue(new FileWriter(tempFile), transformers1);
|
||||
|
||||
try (Reader reader = new BufferedReader(new FileReader(tempFile)))
|
||||
{
|
||||
registry.register(reader, getClass().getName());
|
||||
// Check the count of transforms supported
|
||||
assertEquals("The number of UNIQUE source to target mimetypes transforms has changed. Config change?",
|
||||
42, countSupportedTransforms(true));
|
||||
assertEquals("The number of source to target mimetypes transforms has changed. " +
|
||||
"There may be multiple transformers for the same combination. Config change?",
|
||||
42, countSupportedTransforms(false));
|
||||
|
||||
// Check a supported transform for each transformer.
|
||||
assertSupported(DOC, 1234, PDF, null, null, ""); // libreoffice
|
||||
assertSupported(DOC, 1234, PDF, null, null, ""); // libreoffice
|
||||
assertSupported(PDF, 1234, PNG, null, null, ""); // pdfrenderer
|
||||
assertSupported(JPEG,1234, GIF, null, null, ""); // imagemagick
|
||||
assertSupported(MSG, 1234, TXT, null, null, ""); // tika
|
||||
assertSupported(MSG, 1234, GIF, null, null, ""); // transformer1 (officeToImageViaPdf)
|
||||
assertSupported(DOC, 1234, PNG, null, null, ""); // transformer1 (officeToImageViaPdf)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testJsonConfig() throws IOException
|
||||
{
|
||||
register(getTransformServiceConfig());
|
||||
|
||||
// Check the count of transforms supported
|
||||
assertEquals("The number of UNIQUE source to target mimetypes transforms has changed. Config change?",
|
||||
60, countSupportedTransforms(true));
|
||||
assertEquals("The number of source to target mimetypes transforms has changed. " +
|
||||
"There may be multiple transformers for the same combination. Config change?",
|
||||
60, countSupportedTransforms(false));
|
||||
|
||||
// Check a supported transform for each transformer.
|
||||
assertSupported(DOC, 1234, PDF, null, null, ""); // libreoffice
|
||||
assertSupported(DOC, 1234, PDF, null, null, ""); // libreoffice
|
||||
assertSupported(PDF, 1234, PNG, null, null, ""); // pdfrenderer
|
||||
assertSupported(JPEG,1234, GIF, null, null, ""); // imagemagick
|
||||
assertSupported(MSG, 1234, TXT, null, null, ""); // tika
|
||||
assertSupported(MSG, 1234, GIF, null, null, ""); // officeToImageViaPdf
|
||||
|
||||
Map<String, String> invalidPdfOptions = new HashMap<>();
|
||||
invalidPdfOptions.put("allowEnlargement", "false");
|
||||
assertSupported(DOC, 1234, PDF, invalidPdfOptions, null, "Invalid as there is a extra option");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testJsonPipeline() throws IOException
|
||||
{
|
||||
register(getTransformServiceConfigPipeline());
|
||||
|
||||
// Check the count of transforms supported
|
||||
int expectedTransforms = getExpectedTransformsForTestJsonPipeline();
|
||||
assertEquals("The number of UNIQUE source to target mimetypes transforms has changed. Config change?",
|
||||
expectedTransforms, countSupportedTransforms(true));
|
||||
assertEquals("The number of source to target mimetypes transforms has changed. " +
|
||||
"There may be multiple transformers for the same combination. Config change?",
|
||||
expectedTransforms, countSupportedTransforms(false));
|
||||
|
||||
ConcurrentMap<String, List<TransformServiceRegistryImpl.SupportedTransform>> transformer =
|
||||
registry.getData().transformers.get("officeToImageViaPdf");
|
||||
|
||||
// Check required and optional default correctly
|
||||
ConcurrentMap<String, List<TransformServiceRegistryImpl.SupportedTransform>> transformsToWord =
|
||||
registry.getData().transformers.get(DOC);
|
||||
List<TransformServiceRegistryImpl.SupportedTransform> supportedTransforms = transformsToWord.get(GIF);
|
||||
TransformServiceRegistryImpl.SupportedTransform supportedTransform = supportedTransforms.get(0);
|
||||
|
||||
Set<TransformOption> transformOptionsSet = supportedTransform.transformOptions.getTransformOptions();
|
||||
System.out.println("Nothing");
|
||||
|
||||
Iterator<TransformOption> iterator = transformOptionsSet.iterator();
|
||||
assertTrue("Expected transform values", iterator.hasNext());
|
||||
// Because Set is unordered we don't know which TransformOptionGroup we retrieve
|
||||
TransformOptionGroup transformOptions1 = (TransformOptionGroup)iterator.next();
|
||||
|
||||
assertTrue("Expected transform values", iterator.hasNext());
|
||||
TransformOptionGroup transformOptions2 = (TransformOptionGroup)iterator.next();
|
||||
|
||||
TransformOptionGroup imagemagick;
|
||||
TransformOptionGroup pdf;
|
||||
|
||||
if(containsTransformOptionValueName(transformOptions1, "alphaRemove"))
|
||||
{
|
||||
imagemagick = transformOptions1;
|
||||
pdf = transformOptions2;
|
||||
}
|
||||
else
|
||||
{
|
||||
imagemagick = transformOptions2;
|
||||
pdf = transformOptions1;
|
||||
}
|
||||
|
||||
TransformOptionValue alphaRemove = (TransformOptionValue)retrieveTransformOptionByPropertyName(imagemagick, "alphaRemove", "TransformOptionValue");
|
||||
TransformOptionGroup crop = (TransformOptionGroup)retrieveTransformOptionByPropertyName(imagemagick, "crop", "TransformOptionGroup");
|
||||
TransformOptionValue cropGravity = (TransformOptionValue)retrieveTransformOptionByPropertyName(crop, "cropGravity", "TransformOptionValue");
|
||||
TransformOptionValue cropWidth = (TransformOptionValue)retrieveTransformOptionByPropertyName(crop, "cropWidth", "TransformOptionValue");
|
||||
|
||||
assertTrue("The holding group should be required", supportedTransform.transformOptions.isRequired());
|
||||
assertFalse("imagemagick should be optional as it is not set", imagemagick.isRequired());
|
||||
assertFalse("pdf should be optional as required is not set", pdf.isRequired());
|
||||
assertEquals("alphaRemove", alphaRemove.getName());
|
||||
assertEquals("cropGravity", cropGravity.getName());
|
||||
assertEquals("cropWidth", cropWidth.getName());
|
||||
assertFalse("alphaRemove should be optional as required is not set", alphaRemove.isRequired());
|
||||
assertFalse("crop should be optional as required is not set", crop.isRequired());
|
||||
assertTrue("cropGravity should be required as it is set", cropGravity.isRequired());
|
||||
assertFalse("cropWidth should be optional as required is not set", cropWidth.isRequired());
|
||||
|
||||
// Check a supported transform for each transformer.
|
||||
assertSupported(DOC,1234, GIF, null, null, "");
|
||||
assertSupported(DOC,1234, PNG, null, null, "");
|
||||
assertSupported(DOC,1234, JPEG, null, null, "");
|
||||
assertSupported(DOC,1234, TIFF, null, null, "");
|
||||
|
||||
Map<String, String> actualOptions = new HashMap<>();
|
||||
actualOptions.put("thumbnail", "true");
|
||||
actualOptions.put("resizeWidth", "100");
|
||||
actualOptions.put("resizeHeight", "100");
|
||||
actualOptions.put("allowEnlargement", "false");
|
||||
actualOptions.put("maintainAspectRatio", "true");
|
||||
assertSupported(DOC,1234, PNG, actualOptions, null, "");
|
||||
}
|
||||
|
||||
private TransformOption retrieveTransformOptionByPropertyName (TransformOptionGroup transformOptionGroup, String propertyName, String propertyType)
|
||||
{
|
||||
Iterator<TransformOption> iterator = transformOptionGroup.getTransformOptions().iterator();
|
||||
|
||||
List<TransformOption> transformOptionsList = new ArrayList<>();
|
||||
while(iterator.hasNext())
|
||||
{
|
||||
transformOptionsList.add(iterator.next());
|
||||
}
|
||||
|
||||
for (TransformOption t : transformOptionsList)
|
||||
{
|
||||
if (t instanceof TransformOptionValue)
|
||||
{
|
||||
TransformOptionValue value = (TransformOptionValue) t;
|
||||
if (propertyType.equalsIgnoreCase("TransformOptionValue"))
|
||||
{
|
||||
if (value.getName().equalsIgnoreCase(propertyName))
|
||||
return value;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (value.getName().contains(propertyName))
|
||||
return transformOptionGroup;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
TransformOption result = retrieveTransformOptionByPropertyName((TransformOptionGroup)t, propertyName, propertyType);
|
||||
if (result != null)
|
||||
return result;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private boolean containsTransformOptionValueName (TransformOptionGroup transformOptionGroup, String propertyName)
|
||||
{
|
||||
if (retrieveTransformOptionByPropertyName(transformOptionGroup, propertyName, "TransformOptionValue") != null)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
private boolean containsTransformOptionGroupeName (TransformOptionGroup transformOptionGroup, String propertyName)
|
||||
{
|
||||
if (retrieveTransformOptionByPropertyName(transformOptionGroup, propertyName, "TransformOptionGroup") != null)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
protected int getExpectedTransformsForTestJsonPipeline()
|
||||
{
|
||||
return 4;
|
||||
}
|
||||
|
||||
private int countSupportedTransforms(boolean unique)
|
||||
{
|
||||
int count = 0;
|
||||
int uniqueCount = 0;
|
||||
for (ConcurrentMap<String, List<TransformServiceRegistryImpl.SupportedTransform>> targetMap : registry.getData().transformers.values())
|
||||
{
|
||||
for (List<TransformServiceRegistryImpl.SupportedTransform> supportedTransforms : targetMap.values())
|
||||
{
|
||||
uniqueCount++;
|
||||
count += supportedTransforms.size();
|
||||
}
|
||||
}
|
||||
return unique ? uniqueCount : count;
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testOptionalGroups()
|
||||
{
|
||||
TransformOptionGroup transformOptionGroup =
|
||||
new TransformOptionGroup(true, Set.of(
|
||||
new TransformOptionValue(false, "1"),
|
||||
new TransformOptionValue(true, "2"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "3.1"),
|
||||
new TransformOptionValue(false, "3.2"),
|
||||
new TransformOptionValue(false, "3.3"))),
|
||||
new TransformOptionGroup(false, Set.of( // OPTIONAL
|
||||
new TransformOptionValue(false, "4.1"),
|
||||
new TransformOptionValue(true, "4.2"),
|
||||
new TransformOptionValue(false, "4.3")))));
|
||||
|
||||
assertAddToPossibleOptions(transformOptionGroup, "", "1, 2", "2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1", "1, 2", "2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2", "1, 2", "2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2, 3.2", "1, 2, 3.1, 3.2, 3.3", "2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2, 4.1", "1, 2, 4.1, 4.2, 4.3", "2, 4.2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2, 4.2", "1, 2, 4.1, 4.2, 4.3", "2, 4.2");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testRequiredGroup()
|
||||
{
|
||||
TransformOptionGroup transformOptionGroup =
|
||||
new TransformOptionGroup(true, Set.of(
|
||||
new TransformOptionValue(false, "1"),
|
||||
new TransformOptionValue(true, "2"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "3.1"),
|
||||
new TransformOptionValue(false, "3.2"),
|
||||
new TransformOptionValue(false, "3.3"))),
|
||||
new TransformOptionGroup(true, Set.of( // REQUIRED
|
||||
new TransformOptionValue(false, "4.1"),
|
||||
new TransformOptionValue(true, "4.2"),
|
||||
new TransformOptionValue(false, "4.3")))));
|
||||
|
||||
assertAddToPossibleOptions(transformOptionGroup, "", "1, 2, 4.1, 4.2, 4.3", "2, 4.2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1", "1, 2, 4.1, 4.2, 4.3", "2, 4.2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2, 3.2", "1, 2, 3.1, 3.2, 3.3, 4.1, 4.2, 4.3", "2, 4.2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2, 4.1", "1, 2, 4.1, 4.2, 4.3", "2, 4.2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2, 4.2", "1, 2, 4.1, 4.2, 4.3", "2, 4.2");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNesstedGrpups()
|
||||
{
|
||||
TransformOptionGroup transformOptionGroup =
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "1"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "1.2"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "1.2.3"))))))),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "2"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "2.2"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "2.2.1.2"))))))))),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(true, "3"), // REQUIRED
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "3.1.1.2"))))))))),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "4"),
|
||||
new TransformOptionGroup(true, Set.of( // REQUIRED
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "4.1.1.2"))))))))),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "5"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(true, Set.of( // REQUIRED
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "5.1.1.2"))))))))),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "6"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(true, Set.of( // REQUIRED
|
||||
new TransformOptionValue(false, "6.1.1.2"))))))))),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(false, "7"),
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionGroup(false, Set.of(
|
||||
new TransformOptionValue(true, "7.1.1.2"))))))))) // REQUIRED
|
||||
));
|
||||
|
||||
assertAddToPossibleOptions(transformOptionGroup, "", "", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1", "1", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 7", "1, 7", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 7.1.1.2", "1, 7, 7.1.1.2", "7.1.1.2");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 6", "1, 6", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 6.1.1.2", "1, 6, 6.1.1.2", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 5", "1, 5", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 5.1.1.2", "1, 5, 5.1.1.2", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 4", "1, 4", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 4.1.1.2", "1, 4, 4.1.1.2", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 3", "1, 3", "3");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "1, 3.1.1.2", "1, 3, 3.1.1.2", "3");
|
||||
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2", "2", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "2, 2.2", "2, 2.2", "");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "3", "3", "3");
|
||||
assertAddToPossibleOptions(transformOptionGroup, "3.1.1.2", "3, 3.1.1.2", "3");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSupportedOptions()
|
||||
{
|
||||
assertIsSupported("a", "a, B, c", "required option B is missing");
|
||||
assertIsSupported("", "a, B, c", "required option B is missing");
|
||||
assertIsSupported("B", "a, B, c", null);
|
||||
assertIsSupported("B, c", "a, B, c", null);
|
||||
assertIsSupported("B, a, c", "a, B, c", null);
|
||||
|
||||
assertIsSupported("B, d", "a, B, c", "there is an extra option d");
|
||||
assertIsSupported("B, c, d", "a, B, c", "there is an extra option d");
|
||||
assertIsSupported("d", "a, B, c", "required option B is missing and there is an extra option d");
|
||||
|
||||
assertIsSupported("a", "a, b, c", null);
|
||||
assertIsSupported("", "a, b, c", null);
|
||||
assertIsSupported("a, b, c", "a, b, c", null);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNoActualOptions() throws Exception
|
||||
{
|
||||
assertTransformOptions(Set.of(
|
||||
new TransformOptionValue(false, "option1"),
|
||||
new TransformOptionValue(false, "option2")));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNoTrasformOptions() throws Exception
|
||||
{
|
||||
assertTransformOptions(Collections.emptySet());
|
||||
assertTransformOptions(null);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSupported() throws Exception
|
||||
{
|
||||
transformer = new InlineTransformer("name",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "page"),
|
||||
new TransformOptionValue(false, "width"),
|
||||
new TransformOptionValue(false, "height")),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, GIF, 102400),
|
||||
new SupportedSourceAndTarget(DOC, JPEG, -1),
|
||||
new SupportedSourceAndTarget(MSG, GIF, -1)));
|
||||
|
||||
assertSupported(DOC, 1024, GIF, null, null);
|
||||
assertSupported(DOC, 102400, GIF, null, null);
|
||||
assertSupported(DOC, 102401, GIF, null, "source is too large");
|
||||
assertSupported(DOC, 1024, JPEG, null, null);
|
||||
assertSupported(GIF, 1024, DOC, null, GIF+" is not a source of this transformer");
|
||||
assertSupported(MSG, 1024, GIF, null, null);
|
||||
assertSupported(MSG, 1024, JPEG, null, MSG+" to "+JPEG+" is not supported by this transformer");
|
||||
|
||||
assertSupported(DOC, 1024, GIF, buildActualOptions("page, width"), null);
|
||||
assertSupported(DOC, 1024, GIF, buildActualOptions("page, width, startPage"), "startPage is not an option");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCache()
|
||||
{
|
||||
// Note: transformNames are an alias for a set of actualOptions and the target mimetpe. The source mimetype may change.
|
||||
transformer = new InlineTransformer("name",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "page"),
|
||||
new TransformOptionValue(false, "width"),
|
||||
new TransformOptionValue(false, "height")),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, GIF, 102400),
|
||||
new SupportedSourceAndTarget(MSG, GIF, -1)));
|
||||
|
||||
registry.register(transformer, getBaseUrl(transformer), getClass().getName());
|
||||
|
||||
assertSupported(DOC, 1024, GIF, null, "doclib", "");
|
||||
assertSupported(MSG, 1024, GIF, null, "doclib", "");
|
||||
|
||||
assertEquals(102400L, registry.getMaxSize(DOC, GIF, null, "doclib"));
|
||||
assertEquals(-1L, registry.getMaxSize(MSG, GIF, null, "doclib"));
|
||||
|
||||
// Change the cached value and try and check we are now using the cached value.
|
||||
List<TransformServiceRegistryImpl.SupportedTransform> supportedTransforms = registry.getData().cachedSupportedTransformList.get("doclib").get(DOC);
|
||||
supportedTransforms.get(0).maxSourceSizeBytes = 1234L;
|
||||
assertEquals(1234L, registry.getMaxSize(DOC, GIF, null, "doclib"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testGetTransformerName() throws Exception
|
||||
{
|
||||
InlineTransformer t1 = new InlineTransformer("transformer1", null,
|
||||
Set.of(new SupportedSourceAndTarget(MSG, GIF, 100, 50)));
|
||||
InlineTransformer t2 = new InlineTransformer("transformer2", null,
|
||||
Set.of(new SupportedSourceAndTarget(MSG, GIF, 200, 60)));
|
||||
InlineTransformer t3 = new InlineTransformer("transformer3", null,
|
||||
Set.of(new SupportedSourceAndTarget(MSG, GIF, 200, 40)));
|
||||
InlineTransformer t4 = new InlineTransformer("transformer4", null,
|
||||
Set.of(new SupportedSourceAndTarget(MSG, GIF, -1, 100)));
|
||||
InlineTransformer t5 = new InlineTransformer("transformer5", null,
|
||||
Set.of(new SupportedSourceAndTarget(MSG, GIF, -1, 80)));
|
||||
|
||||
Map<String, String> actualOptions = null;
|
||||
|
||||
// Select on size - priority is ignored
|
||||
assertTransformerName(MSG, 100, GIF, actualOptions, "transformer1", t1, t2);
|
||||
assertTransformerName(MSG, 150, GIF, actualOptions, "transformer2", t1, t2);
|
||||
assertTransformerName(MSG, 250, GIF, actualOptions, null, t1, t2);
|
||||
// Select on priority - t1, t2 and t4 are discarded.
|
||||
// t3 is a higher priority and has a larger size than t1 and t2.
|
||||
// Similar story fo t4 with t5.
|
||||
assertTransformerName(MSG, 100, GIF, actualOptions, "transformer3", t1, t2, t3, t4, t5);
|
||||
assertTransformerName(MSG, 200, GIF, actualOptions, "transformer3", t1, t2, t3, t4, t5);
|
||||
// Select on size and priority, t1 and t2 discarded
|
||||
assertTransformerName(MSG, 200, GIF, actualOptions, "transformer3", t1, t2, t3, t4);
|
||||
assertTransformerName(MSG, 300, GIF, actualOptions, "transformer4", t1, t2, t3, t4);
|
||||
assertTransformerName(MSG, 300, GIF, actualOptions, "transformer5", t1, t2, t3, t4, t5);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMultipleTransformers() throws Exception
|
||||
{
|
||||
InlineTransformer transformer1 = new InlineTransformer("transformer1",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "page"),
|
||||
new TransformOptionValue(false, "width"),
|
||||
new TransformOptionValue(false, "height")),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, GIF, 102400),
|
||||
new SupportedSourceAndTarget(DOC, JPEG, -1),
|
||||
new SupportedSourceAndTarget(MSG, GIF, -1)));
|
||||
|
||||
InlineTransformer transformer2 = new InlineTransformer("transformer2",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "opt1"),
|
||||
new TransformOptionValue(false, "opt2")),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(PDF, GIF, -1),
|
||||
new SupportedSourceAndTarget(PPT, JPEG, -1)));
|
||||
|
||||
InlineTransformer transformer3 = new InlineTransformer("transformer3",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "opt1")),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, GIF, -1)));
|
||||
|
||||
Map<String, String> actualOptions = null;
|
||||
|
||||
assertSupported(DOC, 1024, GIF, actualOptions, null, transformer1);
|
||||
assertSupported(DOC, 1024, GIF, actualOptions, null, transformer1, transformer2);
|
||||
assertSupported(DOC, 1024, GIF, actualOptions, null, transformer1, transformer2, transformer3);
|
||||
|
||||
assertSupported(DOC, 102401, GIF, null, "source is too large", transformer1);
|
||||
assertSupported(DOC, 102401, GIF, null, null, transformer1, transformer3);
|
||||
|
||||
assertSupported(PDF, 1024, GIF, actualOptions, "Only transformer2 supports these mimetypes", transformer1);
|
||||
assertSupported(PDF, 1024, GIF, actualOptions, null, transformer1, transformer2);
|
||||
assertSupported(PDF, 1024, GIF, actualOptions, null, transformer1, transformer2, transformer3);
|
||||
|
||||
actualOptions = buildActualOptions("opt1");
|
||||
assertSupported(PDF, 1024, GIF, actualOptions, "Only transformer2/4 supports these options", transformer1);
|
||||
assertSupported(PDF, 1024, GIF, actualOptions, null, transformer1, transformer2);
|
||||
assertSupported(PDF, 1024, GIF, actualOptions, null, transformer1, transformer2, transformer3);
|
||||
assertSupported(PDF, 1024, GIF, actualOptions, "transformer4 supports opt1 but not the source mimetype ", transformer1, transformer3);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testPipeline() throws Exception
|
||||
{
|
||||
InlineTransformer transformer1 = new InlineTransformer("transformer1",
|
||||
null, // there are no options
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, PDF, -1),
|
||||
new SupportedSourceAndTarget(MSG, PDF, -1)));
|
||||
|
||||
InlineTransformer transformer2 = new InlineTransformer("transformer2",
|
||||
Set.of(
|
||||
new TransformOptionValue(false, "page"),
|
||||
new TransformOptionValue(false, "width"),
|
||||
new TransformOptionValue(false, "height")),
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(PDF, GIF, -1),
|
||||
new SupportedSourceAndTarget(PDF, JPEG, -1)));
|
||||
|
||||
buildPipelineTransformer(transformer1, transformer2);
|
||||
|
||||
assertSupported(DOC, 1024, GIF, null, null);
|
||||
assertSupported(DOC, 1024, JPEG, null, null);
|
||||
assertSupported(GIF, 1024, DOC, null, GIF+" is not a source of this transformer");
|
||||
assertSupported(MSG, 1024, GIF, null, null);
|
||||
assertSupported(MSG, 1024, JPEG, null, MSG+" to "+JPEG+" is not supported by this transformer");
|
||||
|
||||
// Now try the options
|
||||
assertSupported(DOC, 1024, GIF, buildActualOptions("page, width"), null);
|
||||
assertSupported(DOC, 1024, GIF, buildActualOptions("page, width, startPage"), "startPage is not an option");
|
||||
|
||||
// Add options to the first transformer
|
||||
transformer1.setTransformOptions(Set.of(
|
||||
new TransformOptionValue(false, "startPage"),
|
||||
new TransformOptionValue(false, "endPage")));
|
||||
buildPipelineTransformer(transformer1, transformer2);
|
||||
|
||||
assertSupported(DOC, 1024, GIF, buildActualOptions("page, width"), null);
|
||||
assertSupported(DOC, 1024, GIF, buildActualOptions("page, width, startPage"), null);
|
||||
}
|
||||
|
||||
private void buildPipelineTransformer(InlineTransformer transformer1, InlineTransformer transformer2)
|
||||
{
|
||||
transformer = builder.buildPipeLine("transformer1",
|
||||
Set.of(
|
||||
new SupportedSourceAndTarget(DOC, GIF, -1),
|
||||
new SupportedSourceAndTarget(DOC, JPEG, -1),
|
||||
new SupportedSourceAndTarget(MSG, GIF, -1)),
|
||||
Arrays.asList(
|
||||
new ChildTransformer(false, transformer1),
|
||||
new ChildTransformer(true, transformer2)));
|
||||
}
|
||||
}
|
@@ -23,12 +23,15 @@
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.model.config;
|
||||
package org.alfresco.transform.client.registry;
|
||||
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.alfresco.repo.content.MimetypeMap;
|
||||
import org.alfresco.repo.content.transform.LocalTransformServiceRegistry;
|
||||
import org.alfresco.repo.content.transform.TransformerDebug;
|
||||
import org.alfresco.transform.client.model.config.SupportedSourceAndTarget;
|
||||
import org.alfresco.transform.client.model.config.TransformOption;
|
||||
import org.alfresco.transform.client.model.config.Transformer;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.junit.Before;
|
||||
@@ -43,12 +46,12 @@ import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Properties;
|
||||
import java.util.Set;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertNotEquals;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
import static org.junit.Assert.fail;
|
||||
|
||||
/**
|
||||
* Extends the {@link TransformServiceRegistryConfigTest} (used to test the config received from the Transform Service)
|
||||
@@ -115,12 +118,7 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
}
|
||||
}
|
||||
|
||||
protected TestLocalTransformServiceRegistry registry;
|
||||
|
||||
private Properties properties = new Properties();
|
||||
|
||||
@Mock private TransformerDebug transformerDebug;
|
||||
@Mock private MimetypeMap mimetypeMap;
|
||||
private static Log log = LogFactory.getLog(LocalTransformServiceRegistry.class);
|
||||
|
||||
private static final String LOCAL_TRANSFORM_SERVICE_CONFIG = "alfresco/local-transform-service-config-test.json";
|
||||
private static final String LOCAL_TRANSFORM_SERVICE_CONFIG_PIPELINE = "alfresco/local-transform-service-config-pipeline-test.json";
|
||||
@@ -129,7 +127,15 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
private static final String LOCAL_TRANSFORM = "localTransform.";
|
||||
private static final String URL = ".url";
|
||||
|
||||
private static Log log = LogFactory.getLog(LocalTransformServiceRegistry.class);
|
||||
private Map<String, Set<TransformOption>> mapOfTransformOptions;
|
||||
private List<CombinedConfig.TransformAndItsOrigin> transformerList;
|
||||
|
||||
protected TestLocalTransformServiceRegistry registry;
|
||||
|
||||
private Properties properties = new Properties();
|
||||
|
||||
@Mock private TransformerDebug transformerDebug;
|
||||
@Mock private MimetypeMap mimetypeMap;
|
||||
|
||||
private Map<String, List<String>> imagemagickSupportedTransformation;
|
||||
private Map<String, List<String>> tikaSupportedTransformation;
|
||||
@@ -187,20 +193,14 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads and loads localTransforms from LOCAL_TRANSFORM_SERVICE_CONFIG config file.
|
||||
* @return List<Transformer> list of local transformers.
|
||||
* Loads localTransforms from the LOCAL_TRANSFORM_SERVICE_CONFIG config file.
|
||||
*/
|
||||
private List<CombinedConfig.TransformAndItsOrigin> retrieveLocalTransformList()
|
||||
private void retrieveLocalTransformList()
|
||||
{
|
||||
try {
|
||||
CombinedConfig combinedConfig = new CombinedConfig(log);
|
||||
combinedConfig.addLocalConfig(LOCAL_TRANSFORM_SERVICE_CONFIG);
|
||||
return combinedConfig.getTransforms();
|
||||
} catch (IOException e) {
|
||||
log.error("Could not read LocalTransform config file");
|
||||
fail();
|
||||
}
|
||||
return null;
|
||||
mapOfTransformOptions = combinedConfig.combinedTransformOptions;
|
||||
transformerList = combinedConfig.combinedTransformers;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -280,11 +280,24 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
officeToImageViaPdfSupportedTransformation.put("application/vnd.ms-outlook", targetMimetype);
|
||||
}
|
||||
|
||||
protected String getBaseUrl(InlineTransformer transformer)
|
||||
@Override
|
||||
protected String getBaseUrl(Transformer transformer)
|
||||
{
|
||||
return LOCAL_TRANSFORM+transformer.getTransformerName()+".url";
|
||||
}
|
||||
|
||||
|
||||
private int countTopLevelOptions(Set<String> transformOptionNames)
|
||||
{
|
||||
int i = 0;
|
||||
for (String name: transformOptionNames)
|
||||
{
|
||||
Set<TransformOption> transformOptions = mapOfTransformOptions.get(name);
|
||||
i += transformOptions.size();
|
||||
}
|
||||
return i;
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testReadWriteJson() throws IOException
|
||||
{
|
||||
@@ -294,7 +307,8 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
@Test
|
||||
public void testReadJsonConfig()
|
||||
{
|
||||
List<CombinedConfig.TransformAndItsOrigin> transformerList = retrieveLocalTransformList();
|
||||
retrieveLocalTransformList();
|
||||
|
||||
// Assert expected size of the transformers.
|
||||
assertNotNull("Transformer list is null.", transformerList);
|
||||
assertEquals("Unexpected number of transformers retrieved", 5, transformerList.size());
|
||||
@@ -309,18 +323,20 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
|
||||
for (CombinedConfig.TransformAndItsOrigin t : transformerList)
|
||||
{
|
||||
assertTrue(t.transform.getTransformerName() + " should be an expected local transformer.", listOfExpectedTransformersName.contains(t.transform.getTransformerName()));
|
||||
listOfExpectedTransformersName.remove(t.transform.getTransformerName());
|
||||
assertTrue(t.transformer.getTransformerName() + " should be an expected local transformer.", listOfExpectedTransformersName.contains(t.transformer.getTransformerName()));
|
||||
listOfExpectedTransformersName.remove(t.transformer.getTransformerName());
|
||||
|
||||
switch (t.transform.getTransformerName())
|
||||
switch (t.transformer.getTransformerName())
|
||||
{
|
||||
case "imagemagick":
|
||||
assertEquals(t.transform.getTransformerName() + " incorrect number of supported transform", 14, t.transform.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transform.getTransformerName() + "incorrect number of transform options", 6, t.transform.getTransformOptions().size());
|
||||
assertEquals(t.transform.getTransformerName() + " expected to not be a transformer pipeline", t.transform.getTransformerPipeline().size(), 0);
|
||||
assertEquals(t.transformer.getTransformerName() + " incorrect number of supported transform", 14, t.transformer.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform option names", 1, t.transformer.getTransformOptions().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform options", 6, countTopLevelOptions(t.transformer.getTransformOptions()));
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to not be a transformer pipeline", t.transformer.getTransformerPipeline().size(), 0);
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to not be a failover pipeline", t.transformer.getTransformerFailover().size(), 0);
|
||||
|
||||
//Test supportedSourceAndTargetList
|
||||
for ( SupportedSourceAndTarget ssat: t.transform.getSupportedSourceAndTargetList())
|
||||
for ( SupportedSourceAndTarget ssat: t.transformer.getSupportedSourceAndTargetList())
|
||||
{
|
||||
assertTrue(ssat.getSourceMediaType() + " not expected to be a supported transform source.", imagemagickSupportedTransformation.containsKey(ssat.getSourceMediaType()));
|
||||
assertTrue(ssat.getTargetMediaType() + " not expected to be a supported transform target for " + ssat.getSourceMediaType(), imagemagickSupportedTransformation.get(ssat.getSourceMediaType()).contains(ssat.getTargetMediaType()));
|
||||
@@ -328,12 +344,14 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
break;
|
||||
|
||||
case "tika":
|
||||
assertEquals(t.transform.getTransformerName() + " incorrect number of supported transform", 8, t.transform.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transform.getTransformerName() + "incorrect number of transform options", 5, t.transform.getTransformOptions().size());
|
||||
assertEquals(t.transform.getTransformerName() + " expected to not be a transformer pipeline", t.transform.getTransformerPipeline().size(), 0);
|
||||
assertEquals(t.transformer.getTransformerName() + " incorrect number of supported transform", 8, t.transformer.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform option names", 1, t.transformer.getTransformOptions().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform options", 5, countTopLevelOptions(t.transformer.getTransformOptions()));
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to not be a transformer pipeline", t.transformer.getTransformerPipeline().size(), 0);
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to not be a failover pipeline", t.transformer.getTransformerFailover().size(), 0);
|
||||
|
||||
//Test supportedSourceAndTargetList
|
||||
for ( SupportedSourceAndTarget ssat: t.transform.getSupportedSourceAndTargetList())
|
||||
for ( SupportedSourceAndTarget ssat: t.transformer.getSupportedSourceAndTargetList())
|
||||
{
|
||||
assertTrue(ssat.getSourceMediaType() + " not expected to be a supported transform source.", tikaSupportedTransformation.containsKey(ssat.getSourceMediaType()));
|
||||
assertTrue(ssat.getTargetMediaType() + " not expected to be a supported transform target for " + ssat.getSourceMediaType(), tikaSupportedTransformation.get(ssat.getSourceMediaType()).contains(ssat.getTargetMediaType()));
|
||||
@@ -341,12 +359,14 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
break;
|
||||
|
||||
case "pdfrenderer":
|
||||
assertEquals(t.transform.getTransformerName() + " incorrect number of supported transform", 1, t.transform.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transform.getTransformerName() + "incorrect number of transform options", 5, t.transform.getTransformOptions().size());
|
||||
assertEquals(t.transform.getTransformerName() + " expected to not be a transformer pipeline", t.transform.getTransformerPipeline().size(), 0);
|
||||
assertEquals(t.transformer.getTransformerName() + " incorrect number of supported transform", 1, t.transformer.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform option names", 1, t.transformer.getTransformOptions().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform options", 5, countTopLevelOptions(t.transformer.getTransformOptions()));
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to not be a transformer pipeline", t.transformer.getTransformerPipeline().size(), 0);
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to not be a failover pipeline", t.transformer.getTransformerFailover().size(), 0);
|
||||
|
||||
//Test supportedSourceAndTargetList
|
||||
for ( SupportedSourceAndTarget ssat: t.transform.getSupportedSourceAndTargetList())
|
||||
for ( SupportedSourceAndTarget ssat: t.transformer.getSupportedSourceAndTargetList())
|
||||
{
|
||||
assertTrue(ssat.getSourceMediaType() + " not expected to be a supported transform source.", pdfRendererSupportedTransformation.containsKey(ssat.getSourceMediaType()));
|
||||
assertTrue(ssat.getTargetMediaType() + " not expected to be a supported transform target for " + ssat.getSourceMediaType(), pdfRendererSupportedTransformation.get(ssat.getSourceMediaType()).contains(ssat.getTargetMediaType()));
|
||||
@@ -354,12 +374,14 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
break;
|
||||
|
||||
case "libreoffice":
|
||||
assertEquals(t.transform.getTransformerName() + " incorrect number of supported transform", 9, t.transform.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transform.getTransformerName() + "incorrect number of transform options", t.transform.getTransformOptions().size(), 0);
|
||||
assertEquals(t.transform.getTransformerName() + " expected to not be a transformer pipeline", t.transform.getTransformerPipeline().size(), 0);
|
||||
assertEquals(t.transformer.getTransformerName() + " incorrect number of supported transform", 9, t.transformer.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform option names", 0, t.transformer.getTransformOptions().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform options", 0, countTopLevelOptions(t.transformer.getTransformOptions()));
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to not be a transformer pipeline", t.transformer.getTransformerPipeline().size(), 0);
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to not be a failover pipeline", t.transformer.getTransformerFailover().size(), 0);
|
||||
|
||||
//Test supportedSourceAndTargetList
|
||||
for ( SupportedSourceAndTarget ssat: t.transform.getSupportedSourceAndTargetList())
|
||||
for ( SupportedSourceAndTarget ssat: t.transformer.getSupportedSourceAndTargetList())
|
||||
{
|
||||
assertTrue(ssat.getSourceMediaType() + " not expected to be a supported transform source.", libreofficeSupportedTransformation.containsKey(ssat.getSourceMediaType()));
|
||||
assertTrue(ssat.getTargetMediaType() + " not expected to be a supported transform target for " + ssat.getSourceMediaType(), libreofficeSupportedTransformation.get(ssat.getSourceMediaType()).contains(ssat.getTargetMediaType()));
|
||||
@@ -367,12 +389,13 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
break;
|
||||
|
||||
case "officeToImageViaPdf":
|
||||
assertEquals(t.transform.getTransformerName() + " incorrect number of supported transform", 28, t.transform.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transform.getTransformerName() + "incorrect number of transform options", 2, t.transform.getTransformOptions().size());
|
||||
assertEquals(t.transform.getTransformerName() + " expected to be a transformer pipeline", t.transform.getTransformerPipeline().size(), 3);
|
||||
assertEquals(t.transformer.getTransformerName() + " incorrect number of supported transform", 28, t.transformer.getSupportedSourceAndTargetList().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform option names", 2, t.transformer.getTransformOptions().size());
|
||||
assertEquals( t.transformer.getTransformerName() + "incorrect number of transform options", 11, countTopLevelOptions(t.transformer.getTransformOptions()));
|
||||
assertEquals(t.transformer.getTransformerName() + " expected to be a transformer pipeline", t.transformer.getTransformerPipeline().size(), 3);
|
||||
|
||||
//Test supportedSourceAndTargetList
|
||||
for ( SupportedSourceAndTarget ssat: t.transform.getSupportedSourceAndTargetList())
|
||||
for ( SupportedSourceAndTarget ssat: t.transformer.getSupportedSourceAndTargetList())
|
||||
{
|
||||
assertTrue(ssat.getSourceMediaType() + " not expected to be a supported transform source.", officeToImageViaPdfSupportedTransformation.containsKey(ssat.getSourceMediaType()));
|
||||
assertTrue(ssat.getTargetMediaType() + " not expected to be a supported transform target for " + ssat.getSourceMediaType(), officeToImageViaPdfSupportedTransformation.get(ssat.getSourceMediaType()).contains(ssat.getTargetMediaType()));
|
||||
@@ -386,13 +409,14 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
@Test
|
||||
public void testReadTransformProperties()
|
||||
{
|
||||
List<CombinedConfig.TransformAndItsOrigin> transformerList = retrieveLocalTransformList();
|
||||
retrieveLocalTransformList();
|
||||
|
||||
assertNotNull("Transformer list is null.", transformerList);
|
||||
for (CombinedConfig.TransformAndItsOrigin t : transformerList)
|
||||
{
|
||||
if(t.transform.getTransformerPipeline() == null)
|
||||
if(t.transformer.getTransformerPipeline() == null)
|
||||
{
|
||||
assertNotNull(t.transform.getTransformerName()+ " JVM property not set.", System.getProperty(LOCAL_TRANSFORM + t.transform.getTransformerName() + URL));
|
||||
assertNotNull(t.transformer.getTransformerName()+ " JVM property not set.", System.getProperty(LOCAL_TRANSFORM + t.transformer.getTransformerName() + URL));
|
||||
}
|
||||
}
|
||||
assertEquals("Unexpected pdfrenderer JVM property value", "http://localhost:8090/", System.getProperty(LOCAL_TRANSFORM + "pdfrenderer" + URL));
|
||||
@@ -402,9 +426,9 @@ public class LocalTransformServiceRegistryConfigTest extends TransformServiceReg
|
||||
|
||||
for (CombinedConfig.TransformAndItsOrigin t : transformerList)
|
||||
{
|
||||
if(t.transform.getTransformerPipeline() == null)
|
||||
if(t.transformer.getTransformerPipeline() == null)
|
||||
{
|
||||
assertNotNull(t.transform.getTransformerName()+ " alfresco-global property not set.", properties.getProperty(LOCAL_TRANSFORM + t.transform.getTransformerName() + URL));
|
||||
assertNotNull(t.transformer.getTransformerName()+ " alfresco-global property not set.", properties.getProperty(LOCAL_TRANSFORM + t.transformer.getTransformerName() + URL));
|
||||
}
|
||||
}
|
||||
assertEquals("Unexpected pdfrenderer alfresco-global property value", "http://localhost:8090/", properties.getProperty(LOCAL_TRANSFORM + "pdfrenderer" + URL));
|
@@ -0,0 +1,287 @@
|
||||
/*
|
||||
* #%L
|
||||
* Alfresco Repository
|
||||
* %%
|
||||
* Copyright (C) 2005 - 2019 Alfresco Software Limited
|
||||
* %%
|
||||
* This file is part of the Alfresco software.
|
||||
* If the software was purchased under a paid Alfresco license, the terms of
|
||||
* the paid license agreement will prevail. Otherwise, the software is
|
||||
* provided under the following open source license terms:
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
* #L%
|
||||
*/
|
||||
package org.alfresco.transform.client.registry;
|
||||
|
||||
import static java.util.Collections.emptyMap;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import org.alfresco.transform.client.model.config.TransformOption;
|
||||
import org.alfresco.transform.client.model.config.TransformOptionGroup;
|
||||
import org.alfresco.transform.client.model.config.TransformOptionValue;
|
||||
import org.alfresco.transform.client.registry.SupportedTransform;
|
||||
import org.alfresco.transform.client.registry.TransformRegistryTest;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.apache.log4j.Level;
|
||||
import org.apache.log4j.LogManager;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
|
||||
/**
|
||||
* Test the config received from the Transform Service about what it supports.
|
||||
*
|
||||
* @author adavis
|
||||
*/
|
||||
public class TransformServiceRegistryConfigTest extends TransformRegistryTest
|
||||
{
|
||||
private static Log log = LogFactory.getLog(TransformServiceRegistryConfigTest.class);
|
||||
|
||||
public static final String PNG = "image/png";
|
||||
public static final String TIFF = "image/tiff";
|
||||
|
||||
private static final String TRANSFORM_SERVICE_CONFIG = "alfresco/transform-service-config-test.json";
|
||||
private static final String TRANSFORM_SERVICE_CONFIG_PIPELINE = "alfresco/transform-service-config-pipeline-test.json";
|
||||
|
||||
public static final ObjectMapper JSON_OBJECT_MAPPER = new ObjectMapper();
|
||||
|
||||
@Before
|
||||
@Override
|
||||
public void setUp() throws Exception
|
||||
{
|
||||
super.setUp();
|
||||
LogManager.getLogger(TransformServiceRegistryConfigTest.class).setLevel(Level.DEBUG);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected TransformServiceRegistryImpl buildTransformServiceRegistryImpl() throws Exception
|
||||
{
|
||||
TransformServiceRegistryImpl registry = new TransformServiceRegistryImpl()
|
||||
{
|
||||
@Override
|
||||
public boolean readConfig() throws IOException
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Log getLog()
|
||||
{
|
||||
return log;
|
||||
}
|
||||
};
|
||||
registry.setJsonObjectMapper(JSON_OBJECT_MAPPER);
|
||||
registry.setCronExpression(null); // just read once
|
||||
registry.afterPropertiesSet();
|
||||
return registry;
|
||||
}
|
||||
|
||||
@After
|
||||
public void tearDown()
|
||||
{
|
||||
// shut down
|
||||
}
|
||||
|
||||
protected String getTransformServiceConfig()
|
||||
{
|
||||
return TRANSFORM_SERVICE_CONFIG;
|
||||
}
|
||||
|
||||
protected String getTransformServiceConfigPipeline()
|
||||
{
|
||||
return TRANSFORM_SERVICE_CONFIG_PIPELINE;
|
||||
}
|
||||
|
||||
private void register(String path) throws IOException
|
||||
{
|
||||
CombinedConfig combinedConfig = new CombinedConfig(log);
|
||||
combinedConfig.addLocalConfig(path);
|
||||
combinedConfig.register((TransformServiceRegistryImpl)registry);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testJsonConfig() throws IOException
|
||||
{
|
||||
register(getTransformServiceConfig());
|
||||
|
||||
// Check the count of transforms supported
|
||||
assertEquals("The number of UNIQUE source to target mimetypes transforms has changed. Config change?",
|
||||
60, countSupportedTransforms(true));
|
||||
assertEquals("The number of source to target mimetypes transforms has changed. " +
|
||||
"There may be multiple transformers for the same combination. Config change?",
|
||||
60, countSupportedTransforms(false));
|
||||
|
||||
// Check a supported transform for each transformer.
|
||||
assertSupported(DOC, 1234, PDF, emptyMap(), null, ""); // libreoffice
|
||||
assertSupported(DOC, 1234, PDF, emptyMap(), null, ""); // libreoffice
|
||||
assertSupported(PDF, 1234, PNG, emptyMap(), null, ""); // pdfrenderer
|
||||
assertSupported(JPEG,1234, GIF, emptyMap(), null, ""); // imagemagick
|
||||
assertSupported(MSG, 1234, TXT, emptyMap(), null, ""); // tika
|
||||
assertSupported(MSG, 1234, GIF, emptyMap(), null, ""); // officeToImageViaPdf
|
||||
|
||||
Map<String, String> invalidPdfOptions = new HashMap<>();
|
||||
invalidPdfOptions.put("allowEnlargement", "false");
|
||||
assertSupported(DOC, 1234, PDF, invalidPdfOptions, null, "Invalid as there is a extra option");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testJsonPipeline() throws IOException
|
||||
{
|
||||
register(getTransformServiceConfigPipeline());
|
||||
|
||||
// Check the count of transforms supported
|
||||
int expectedTransforms = getExpectedTransformsForTestJsonPipeline();
|
||||
assertEquals("The number of UNIQUE source to target mimetypes transforms has changed. Config change?",
|
||||
expectedTransforms, countSupportedTransforms(true));
|
||||
assertEquals("The number of source to target mimetypes transforms has changed. " +
|
||||
"There may be multiple transformers for the same combination. Config change?",
|
||||
expectedTransforms, countSupportedTransforms(false));
|
||||
|
||||
// Check required and optional default correctly
|
||||
Map<String, List<SupportedTransform>> transformsToWord =
|
||||
registry.getData().getTransforms().get(DOC);
|
||||
List<SupportedTransform> supportedTransforms = transformsToWord.get(GIF);
|
||||
SupportedTransform supportedTransform = supportedTransforms.get(0);
|
||||
|
||||
Set<TransformOption> transformOptionsSet = supportedTransform.getTransformOptions().getTransformOptions();
|
||||
System.out.println("Nothing");
|
||||
|
||||
Iterator<TransformOption> iterator = transformOptionsSet.iterator();
|
||||
assertTrue("Expected transform values", iterator.hasNext());
|
||||
// Because Set is unordered we don't know which TransformOptionGroup we retrieve
|
||||
TransformOptionGroup transformOptions1 = (TransformOptionGroup)iterator.next();
|
||||
|
||||
assertTrue("Expected transform values", iterator.hasNext());
|
||||
TransformOptionGroup transformOptions2 = (TransformOptionGroup)iterator.next();
|
||||
|
||||
TransformOptionGroup imagemagick;
|
||||
TransformOptionGroup pdf;
|
||||
|
||||
if(containsTransformOptionValueName(transformOptions1, "alphaRemove"))
|
||||
{
|
||||
imagemagick = transformOptions1;
|
||||
pdf = transformOptions2;
|
||||
}
|
||||
else
|
||||
{
|
||||
imagemagick = transformOptions2;
|
||||
pdf = transformOptions1;
|
||||
}
|
||||
|
||||
TransformOptionValue alphaRemove = (TransformOptionValue)retrieveTransformOptionByPropertyName(imagemagick, "alphaRemove", "TransformOptionValue");
|
||||
TransformOptionGroup crop = (TransformOptionGroup)retrieveTransformOptionByPropertyName(imagemagick, "crop", "TransformOptionGroup");
|
||||
TransformOptionValue cropGravity = (TransformOptionValue)retrieveTransformOptionByPropertyName(crop, "cropGravity", "TransformOptionValue");
|
||||
TransformOptionValue cropWidth = (TransformOptionValue)retrieveTransformOptionByPropertyName(crop, "cropWidth", "TransformOptionValue");
|
||||
|
||||
assertTrue("The holding group should be required", supportedTransform.getTransformOptions().isRequired());
|
||||
assertFalse("imagemagick should be optional as it is not set", imagemagick.isRequired());
|
||||
assertFalse("pdf should be optional as required is not set", pdf.isRequired());
|
||||
assertEquals("alphaRemove", alphaRemove.getName());
|
||||
assertEquals("cropGravity", cropGravity.getName());
|
||||
assertEquals("cropWidth", cropWidth.getName());
|
||||
assertFalse("alphaRemove should be optional as required is not set", alphaRemove.isRequired());
|
||||
assertFalse("crop should be optional as required is not set", crop.isRequired());
|
||||
assertTrue("cropGravity should be required as it is set", cropGravity.isRequired());
|
||||
assertFalse("cropWidth should be optional as required is not set", cropWidth.isRequired());
|
||||
|
||||
// Check a supported transform for each transformer.
|
||||
assertSupported(DOC,1234, GIF, emptyMap(), null, "");
|
||||
assertSupported(DOC,1234, PNG, emptyMap(), null, "");
|
||||
assertSupported(DOC,1234, JPEG, emptyMap(), null, "");
|
||||
assertSupported(DOC,1234, TIFF, emptyMap(), null, "");
|
||||
|
||||
Map<String, String> actualOptions = new HashMap<>();
|
||||
actualOptions.put("thumbnail", "true");
|
||||
actualOptions.put("resizeWidth", "100");
|
||||
actualOptions.put("resizeHeight", "100");
|
||||
actualOptions.put("allowEnlargement", "false");
|
||||
actualOptions.put("maintainAspectRatio", "true");
|
||||
assertSupported(DOC,1234, PNG, actualOptions, null, "");
|
||||
}
|
||||
|
||||
private TransformOption retrieveTransformOptionByPropertyName (TransformOptionGroup transformOptionGroup, String propertyName, String propertyType)
|
||||
{
|
||||
Iterator<TransformOption> iterator = transformOptionGroup.getTransformOptions().iterator();
|
||||
|
||||
List<TransformOption> transformOptionsList = new ArrayList<>();
|
||||
while(iterator.hasNext())
|
||||
{
|
||||
transformOptionsList.add(iterator.next());
|
||||
}
|
||||
|
||||
for (TransformOption t : transformOptionsList)
|
||||
{
|
||||
if (t instanceof TransformOptionValue)
|
||||
{
|
||||
TransformOptionValue value = (TransformOptionValue) t;
|
||||
if (propertyType.equalsIgnoreCase("TransformOptionValue"))
|
||||
{
|
||||
if (value.getName().equalsIgnoreCase(propertyName))
|
||||
return value;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (value.getName().contains(propertyName))
|
||||
return transformOptionGroup;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
TransformOption result = retrieveTransformOptionByPropertyName((TransformOptionGroup)t, propertyName, propertyType);
|
||||
if (result != null)
|
||||
return result;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private boolean containsTransformOptionValueName (TransformOptionGroup transformOptionGroup, String propertyName)
|
||||
{
|
||||
return retrieveTransformOptionByPropertyName(transformOptionGroup, propertyName, "TransformOptionValue") != null;
|
||||
}
|
||||
|
||||
protected int getExpectedTransformsForTestJsonPipeline()
|
||||
{
|
||||
return 4;
|
||||
}
|
||||
|
||||
private int countSupportedTransforms(boolean unique)
|
||||
{
|
||||
int count = 0;
|
||||
int uniqueCount = 0;
|
||||
for (Map<String, List<SupportedTransform>> targetMap : registry.getData().getTransforms().values())
|
||||
{
|
||||
for (List<SupportedTransform> supportedTransforms : targetMap.values())
|
||||
{
|
||||
uniqueCount++;
|
||||
count += supportedTransforms.size();
|
||||
}
|
||||
}
|
||||
return unique ? uniqueCount : count;
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user