Spring Framework integration for ShedLock distributed locking system providing annotation-based task scheduling locks.
—
Configuration classes and annotations for enabling and setting up ShedLock in Spring applications.
The main configuration annotation that enables ShedLock integration in Spring applications.
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Import(SchedulerLockConfigurationSelector.class)
public @interface EnableSchedulerLock {
enum InterceptMode {
@Deprecated(forRemoval = true)
PROXY_SCHEDULER, // Wraps TaskScheduler in proxy
PROXY_METHOD // Proxies scheduled methods directly (recommended)
}
InterceptMode interceptMode() default InterceptMode.PROXY_METHOD;
String defaultLockAtMostFor(); // Required
String defaultLockAtLeastFor() default "PT0S"; // Optional
AdviceMode mode() default AdviceMode.PROXY; // Spring AOP mode
boolean proxyTargetClass() default false; // Use CGLIB proxies
int order() default Ordered.LOWEST_PRECEDENCE; // Advisor order
}PROXY_METHOD (recommended): Intercepts method calls directlyPROXY_SCHEDULER (deprecated): Intercepts TaskScheduler calls@Configuration
@EnableSchedulerLock(
interceptMode = InterceptMode.PROXY_METHOD,
defaultLockAtMostFor = "PT30M",
defaultLockAtLeastFor = "PT1M"
)
public class ShedLockConfig {
@Bean
public LockProvider lockProvider() {
return new JdbcTemplateLockProvider(dataSource);
}
}Selects appropriate configuration classes based on the intercept mode.
public class SchedulerLockConfigurationSelector implements ImportSelector {
public String[] selectImports(AnnotationMetadata metadata);
}Imports different configuration classes based on interceptMode:
PROXY_METHOD: Imports MethodProxyLockConfigurationPROXY_SCHEDULER: Imports SchedulerProxyLockConfigurationBase class for lock configuration beans that processes @EnableSchedulerLock metadata.
public abstract class AbstractLockConfiguration implements ImportAware {
protected AnnotationAttributes annotationAttributes;
public void setImportMetadata(AnnotationMetadata importMetadata);
protected int getOrder();
}Configuration for method-level lock interception.
@Configuration
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
public class MethodProxyLockConfiguration extends AbstractLockConfiguration {
@Bean
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
public MethodProxyScheduledLockAdvisor proxyScheduledLockAopBeanPostProcessor(
ListableBeanFactory beanFactory,
@Lazy ExtendedLockConfigurationExtractor lockConfigurationExtractor
);
}Configuration for scheduler-level lock interception (deprecated mode).
@Configuration
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
public class SchedulerProxyLockConfiguration extends AbstractLockConfiguration {
@Bean
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
public SchedulerProxyScheduledLockAdvisor proxyScheduledLockAopBeanPostProcessor(
ListableBeanFactory listableBeanFactory,
@Lazy ExtendedLockConfigurationExtractor lockConfigurationExtractor
);
}Defines the ExtendedLockConfigurationExtractor bean that handles lock configuration extraction.
@Configuration
public class LockConfigurationExtractorConfiguration extends AbstractLockConfiguration
implements EmbeddedValueResolverAware, BeanFactoryAware {
@Bean
public ExtendedLockConfigurationExtractor lockConfigurationExtractor();
public void setEmbeddedValueResolver(StringValueResolver resolver);
public void setBeanFactory(BeanFactory beanFactory) throws BeansException;
}ShedLock supports multiple duration formats through the StringToDurationConverter:
"PT30S" // 30 seconds
"PT10M" // 10 minutes
"PT1H" // 1 hour
"PT24H" // 24 hours"30s" // 30 seconds
"10m" // 10 minutes
"1h" // 1 hour
"1d" // 1 day
"500ms" // 500 milliseconds
"1000us" // 1000 microseconds
"1000ns" // 1000 nanosecondspublic class StringToDurationConverter implements Converter<String, Duration> {
public static final StringToDurationConverter INSTANCE;
public Duration convert(String source);
}The converter automatically detects the format and converts accordingly. Invalid formats throw IllegalStateException.
When using PROXY_SCHEDULER mode, a default TaskScheduler is automatically registered if none exists.
@Component
public class RegisterDefaultTaskSchedulerPostProcessor
implements BeanDefinitionRegistryPostProcessor, Ordered, BeanFactoryAware {
public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException;
public int getOrder(); // Returns LOWEST_PRECEDENCE
public void setBeanFactory(BeanFactory beanFactory) throws BeansException;
}This processor:
TaskScheduler beans existConcurrentTaskSchedulerScheduledExecutorService exists, uses it for the schedulerScheduledExecutorService beansInstall with Tessl CLI
npx tessl i tessl/maven-net-javacrumbs-shedlock--shedlock-spring