Schedule config reads

This commit is contained in:
alandavis
2022-08-11 18:35:33 +01:00
parent ba711cb2da
commit fc2fa12c1f
7 changed files with 102 additions and 40 deletions

View File

@@ -28,6 +28,10 @@
<groupId>org.springframework.boot</groupId> <groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId> <artifactId>spring-boot-starter-actuator</artifactId>
</dependency> </dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-aop</artifactId>
</dependency>
<dependency> <dependency>
<groupId>org.springframework.retry</groupId> <groupId>org.springframework.retry</groupId>
<artifactId>spring-retry</artifactId> <artifactId>spring-retry</artifactId>

View File

@@ -32,9 +32,7 @@ import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value; import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.SpringApplication; import org.springframework.boot.SpringApplication;
import org.springframework.boot.actuate.autoconfigure.metrics.MeterRegistryCustomizer; import org.springframework.boot.actuate.autoconfigure.metrics.MeterRegistryCustomizer;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Bean;
import org.springframework.core.task.SimpleAsyncTaskExecutor; import org.springframework.core.task.SimpleAsyncTaskExecutor;
import org.springframework.core.task.TaskExecutor; import org.springframework.core.task.TaskExecutor;
@@ -44,10 +42,12 @@ import org.springframework.scheduling.annotation.EnableScheduling;
@SpringBootApplication @SpringBootApplication
@EnableAsync @EnableAsync
//@EnableScheduling @EnableScheduling
//@EnableRetry @EnableRetry
public class Application public class Application
{ {
private static final Logger logger = LoggerFactory.getLogger(Application.class);
@Value("${container.name}") @Value("${container.name}")
private String containerName; private String containerName;

View File

@@ -61,8 +61,7 @@ public class WebApplicationConfig implements WebMvcConfigurer
@Override @Override
public void addInterceptors(InterceptorRegistry registry) public void addInterceptors(InterceptorRegistry registry)
{ {
registry registry.addInterceptor(new TransformInterceptor())
.addInterceptor(new TransformInterceptor())
.addPathPatterns(ENDPOINT_TRANSFORM, "/live", "/ready"); .addPathPatterns(ENDPOINT_TRANSFORM, "/live", "/ready");
} }

View File

@@ -53,7 +53,7 @@ import static org.alfresco.transform.config.CoreVersionDecorator.setCoreVersionO
@Service @Service
public class TransformRegistry extends AbstractTransformRegistry public class TransformRegistry extends AbstractTransformRegistry
{ {
private static final Logger log = LoggerFactory.getLogger(TransformRegistry.class); private static final Logger logger = LoggerFactory.getLogger(TransformRegistry.class);
@Autowired @Autowired
private String coreVersion; private String coreVersion;
@@ -81,7 +81,7 @@ public class TransformRegistry extends AbstractTransformRegistry
// Ensures that read operations are blocked while config is being updated // Ensures that read operations are blocked while config is being updated
private ReadWriteLock configRefreshLock = new ReentrantReadWriteLock(); private ReadWriteLock configRefreshLock = new ReentrantReadWriteLock();
@EventListener @EventListener(ContextRefreshedEvent.class)
void handleContextRefreshedEvent(final ContextRefreshedEvent event) void handleContextRefreshedEvent(final ContextRefreshedEvent event)
{ {
final ApplicationContext context = event.getApplicationContext(); final ApplicationContext context = event.getApplicationContext();
@@ -93,26 +93,36 @@ public class TransformRegistry extends AbstractTransformRegistry
* Load the registry on application startup. This allows Components in projects that extend the t-engine base * Load the registry on application startup. This allows Components in projects that extend the t-engine base
* to use @PostConstruct to add to {@code transformConfigSources}, before the registry is loaded. * to use @PostConstruct to add to {@code transformConfigSources}, before the registry is loaded.
*/ */
// @Async @Async
// @Retryable(include = {IllegalStateException.class}, @Retryable(include = {IllegalStateException.class},
// maxAttemptsExpression = "#{${transform.engine.config.retry.attempts}}", maxAttemptsExpression = "#{${transform.engine.config.retry.attempts}}",
// backoff = @Backoff(delayExpression = "#{${transform.engine.config.retry.timeout} * 1000}")) backoff = @Backoff(delayExpression = "#{${transform.engine.config.retry.timeout} * 1000}"))
public void initRegistryOnAppStartup(final ContextRefreshedEvent event) void initRegistryOnAppStartup(final ContextRefreshedEvent event)
{ {
initRegistry(); retrieveConfig();
}
/**
* Recovery method in case all the retries fail. If not specified, the @Retryable method will cause the application
* to stop.
*/
@Recover
void recover(IllegalStateException e)
{
logger.warn(e.getMessage());
} }
/** /**
* Takes the schedule from a spring-boot property * Takes the schedule from a spring-boot property
*/ */
// @Scheduled(cron = "${transformer.engine.config.cron}") @Scheduled(cron = "${transform.engine.config.cron}")
public void retrieveEngineConfigs() public void retrieveEngineConfigs()
{ {
log.trace("Refresh TransformRegistry"); logger.trace("Refresh TransformRegistry");
initRegistry(); retrieveConfig();
} }
void initRegistry() void retrieveConfig()
{ {
CombinedTransformConfig combinedTransformConfig = new CombinedTransformConfig(); CombinedTransformConfig combinedTransformConfig = new CombinedTransformConfig();
@@ -130,16 +140,6 @@ public class TransformRegistry extends AbstractTransformRegistry
concurrentUpdate(combinedTransformConfig, transformConfigBeforeIncompleteTransformsAreRemoved); concurrentUpdate(combinedTransformConfig, transformConfigBeforeIncompleteTransformsAreRemoved);
} }
/**
* Recovery method in case all the retries fail. If not specified, the @Retryable method will cause the application
* to stop.
*/
// @Recover
private void recover(IllegalStateException e)
{
log.warn(e.getMessage());
}
public TransformConfig getTransformConfig() public TransformConfig getTransformConfig()
{ {
return getData().getTransformConfigBeforeIncompleteTransformsAreRemoved(); return getData().getTransformConfigBeforeIncompleteTransformsAreRemoved();
@@ -187,12 +187,12 @@ public class TransformRegistry extends AbstractTransformRegistry
@Override @Override
protected void logError(String msg) protected void logError(String msg)
{ {
log.error(msg); logger.error(msg);
} }
@Override @Override
protected void logWarn(String msg) protected void logWarn(String msg)
{ {
log.warn(msg); logger.warn(msg);
} }
} }

View File

@@ -111,9 +111,9 @@ import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.
@AutoConfigureMockMvc @AutoConfigureMockMvc
@SpringBootTest(classes={org.alfresco.transform.base.Application.class}) @SpringBootTest(classes={org.alfresco.transform.base.Application.class})
@ContextConfiguration(classes = { @ContextConfiguration(classes = {
FakeTransformEngineWithTwoCustomTransformers.class, FakeTransformEngineWithTwoCustomTransformers.class,
FakeTransformerTxT2Pdf.class, FakeTransformerTxT2Pdf.class,
FakeTransformerPdf2Png.class}) FakeTransformerPdf2Png.class})
public class TransformControllerTest public class TransformControllerTest
{ {
@Autowired @Autowired

View File

@@ -0,0 +1,59 @@
/*
* Copyright 2015-2022 Alfresco Software, Ltd. All rights reserved.
*
* License rights for this program may be obtained from Alfresco Software, Ltd.
* pursuant to a written agreement and any use of this program without such an
* agreement is prohibited.
*/
package org.alfresco.transform.base.registry;
import com.google.common.collect.ImmutableMap;
import org.alfresco.transform.base.fakes.FakeTransformEngineWithTwoCustomTransformers;
import org.alfresco.transform.base.fakes.FakeTransformerPdf2Png;
import org.alfresco.transform.base.fakes.FakeTransformerTxT2Pdf;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.boot.test.mock.mockito.SpyBean;
import org.springframework.test.annotation.DirtiesContext;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.util.ReflectionTestUtils;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.mockito.Mockito.atLeast;
import static org.mockito.Mockito.verify;
@AutoConfigureMockMvc
@SpringBootTest(classes={org.alfresco.transform.base.Application.class}, properties={"transform.engine.config.cron=*/1 * * * * *"})
@ContextConfiguration(classes = {
FakeTransformEngineWithTwoCustomTransformers.class,
FakeTransformerTxT2Pdf.class,
FakeTransformerPdf2Png.class})
@DirtiesContext(classMode = DirtiesContext.ClassMode.AFTER_CLASS)
public class TransformRegistryRefreshTest
{
@SpyBean
private TransformRegistry transformRegistry;
@Autowired
private TransformConfigFromFiles transformConfigFromFiles;
@Autowired
private AdditionalTransformConfigResources additionalTransformConfigResources;
@Test
public void checkRegistryRefreshes() throws InterruptedException
{
verify(transformRegistry, atLeast(1)).retrieveConfig();
assertEquals(4, transformRegistry.getTransformConfig().getTransformers().size());
// As we can't change the content of a classpath resource, lets change what is read.
ReflectionTestUtils.setField(additionalTransformConfigResources, "config", ImmutableMap.of(
"a", "config/addA2B.json",
"foo", "config/addB2C.json"));
transformConfigFromFiles.initFileConfig();
Thread.sleep(3000); // to give it a chance to refresh a few (at least 2 more) times
verify(transformRegistry, atLeast(1+2)).retrieveConfig();
assertEquals(6, transformRegistry.getTransformConfig().getTransformers().size());
}
}

View File

@@ -70,7 +70,7 @@ public class TransformRegistryTest
ReflectionTestUtils.setField(transformConfigFromTransformEngines, "transformEngines", Collections.emptyList()); ReflectionTestUtils.setField(transformConfigFromTransformEngines, "transformEngines", Collections.emptyList());
ReflectionTestUtils.setField(additionalTransformConfigResources, "config", Collections.emptyMap()); ReflectionTestUtils.setField(additionalTransformConfigResources, "config", Collections.emptyMap());
ReflectionTestUtils.setField(additionalTransformConfigResourcesHistoric, "additional", Collections.emptyMap()); ReflectionTestUtils.setField(additionalTransformConfigResourcesHistoric, "additional", Collections.emptyMap());
transformRegistry.initRegistry(); transformRegistry.retrieveConfig();
} }
private String getTransformerNames(TransformConfig transformConfig) private String getTransformerNames(TransformConfig transformConfig)
@@ -93,7 +93,7 @@ public class TransformRegistryTest
ReflectionTestUtils.setField(transformConfigFromTransformEngines, "transformEngines", ImmutableList.of( ReflectionTestUtils.setField(transformConfigFromTransformEngines, "transformEngines", ImmutableList.of(
new FakeTransformEngineWithOneCustomTransformer())); new FakeTransformEngineWithOneCustomTransformer()));
transformConfigFromTransformEngines.initTransformEngineConfig(); transformConfigFromTransformEngines.initTransformEngineConfig();
transformRegistry.initRegistry(); transformRegistry.retrieveConfig();
assertEquals("Pdf2Jpg", getTransformerNames(transformRegistry.getTransformConfig())); assertEquals("Pdf2Jpg", getTransformerNames(transformRegistry.getTransformConfig()));
} }
@@ -106,7 +106,7 @@ public class TransformRegistryTest
new FakeTransformEngineWithOneCustomTransformer(), new FakeTransformEngineWithOneCustomTransformer(),
new FakeTransformEngineWithTwoCustomTransformers())); new FakeTransformEngineWithTwoCustomTransformers()));
transformConfigFromTransformEngines.initTransformEngineConfig(); transformConfigFromTransformEngines.initTransformEngineConfig();
transformRegistry.initRegistry(); transformRegistry.retrieveConfig();
assertEquals("Pdf2Jpg, Pdf2Png, TxT2Pdf, Txt2JpgViaPdf, Txt2PngViaPdf", assertEquals("Pdf2Jpg, Pdf2Png, TxT2Pdf, Txt2JpgViaPdf, Txt2PngViaPdf",
getTransformerNames(transformRegistry.getTransformConfig())); getTransformerNames(transformRegistry.getTransformConfig()));
@@ -123,7 +123,7 @@ public class TransformRegistryTest
transformConfigFromTransformEngines.initTransformEngineConfig(); transformConfigFromTransformEngines.initTransformEngineConfig();
transformConfigFromFiles.initFileConfig(); transformConfigFromFiles.initFileConfig();
transformRegistry.initRegistry(); transformRegistry.retrieveConfig();
assertEquals("A2B, B2C, Pdf2Jpg", getTransformerNames(transformRegistry.getTransformConfig())); assertEquals("A2B, B2C, Pdf2Jpg", getTransformerNames(transformRegistry.getTransformConfig()));
} }
@@ -139,7 +139,7 @@ public class TransformRegistryTest
transformConfigFromTransformEngines.initTransformEngineConfig(); transformConfigFromTransformEngines.initTransformEngineConfig();
transformConfigFromFiles.initFileConfig(); transformConfigFromFiles.initFileConfig();
transformRegistry.initRegistry(); transformRegistry.retrieveConfig();
assertEquals("A2B, B2C, Pdf2Jpg", getTransformerNames(transformRegistry.getTransformConfig())); assertEquals("A2B, B2C, Pdf2Jpg", getTransformerNames(transformRegistry.getTransformConfig()));
} }
@@ -156,7 +156,7 @@ public class TransformRegistryTest
transformConfigFromTransformEngines.initTransformEngineConfig(); transformConfigFromTransformEngines.initTransformEngineConfig();
transformConfigFromFiles.initFileConfig(); transformConfigFromFiles.initFileConfig();
transformRegistry.initRegistry(); transformRegistry.retrieveConfig();
assertEquals("A2B, Pdf2Jpg", getTransformerNames(transformRegistry.getTransformConfig())); assertEquals("A2B, Pdf2Jpg", getTransformerNames(transformRegistry.getTransformConfig()));
} }
@@ -171,7 +171,7 @@ public class TransformRegistryTest
transformConfigFromTransformEngines.initTransformEngineConfig(); transformConfigFromTransformEngines.initTransformEngineConfig();
transformConfigFromFiles.initFileConfig(); transformConfigFromFiles.initFileConfig();
transformRegistry.initRegistry(); transformRegistry.retrieveConfig();
assertEquals("A2Z", getTransformerNames(transformRegistry.getTransformConfig())); assertEquals("A2Z", getTransformerNames(transformRegistry.getTransformConfig()));
} }