AbstractSimpleLock.java 2.0 KB
Newer Older
lakernote's avatar
lakernote 已提交
1 2 3 4
package com.laker.admin.framework.lock.core;

import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.StrUtil;
lakernote's avatar
lakernote 已提交
5
import com.laker.admin.framework.lock.api.LLock;
lakernote's avatar
lakernote 已提交
6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
import com.laker.admin.framework.lock.api.Lock;
import org.springframework.scheduling.TaskScheduler;

import java.time.Duration;
import java.util.concurrent.ScheduledFuture;

/**
 * @author laker
 */
public abstract class AbstractSimpleLock implements Lock {
    private TaskScheduler taskScheduler;

    protected AbstractSimpleLock(TaskScheduler taskScheduler) {
        this.taskScheduler = taskScheduler;
    }

    @Override
lakernote's avatar
lakernote 已提交
23
    public LLock acquire(final String key, final Duration expiration) {
lakernote's avatar
lakernote 已提交
24 25
        final String token = IdUtil.fastSimpleUUID();
        String acquire = acquire(key, token, expiration);
lakernote's avatar
lakernote 已提交
26 27
        if (StrUtil.isBlank(acquire)) {
            return null;
lakernote's avatar
lakernote 已提交
28
        }
lakernote's avatar
lakernote 已提交
29
        // 后台线程定时续租 一个锁一个后台线程续约
lakernote's avatar
lakernote 已提交
30 31
        ScheduledFuture<?> scheduledFuture = scheduleLockRefresh(key, acquire, expiration);
        return LLock.builder().key(key).token(token).scheduledFuture(scheduledFuture).build();
lakernote's avatar
lakernote 已提交
32 33 34
    }

    @Override
lakernote's avatar
lakernote 已提交
35 36 37
    public boolean release(LLock lock) {
        cancelSchedule(lock);
        return release0(lock);
lakernote's avatar
lakernote 已提交
38 39
    }

lakernote's avatar
lakernote 已提交
40
    private ScheduledFuture<?> scheduleLockRefresh(final String key, final String token, final Duration expiration) {
lakernote's avatar
lakernote 已提交
41 42
        return taskScheduler.scheduleAtFixedRate(() ->
                refresh(key, token, expiration), expiration.toMillis() / 3);
lakernote's avatar
lakernote 已提交
43 44 45

    }

lakernote's avatar
lakernote 已提交
46 47
    private void cancelSchedule(LLock lock) {
        final ScheduledFuture<?> scheduledFuture = lock.getScheduledFuture();
lakernote's avatar
lakernote 已提交
48 49 50 51 52 53 54
        if (scheduledFuture != null && !scheduledFuture.isCancelled() && !scheduledFuture.isDone()) {
            scheduledFuture.cancel(true);
        }
    }

    protected abstract String acquire(String key, String token, Duration expiration);

lakernote's avatar
lakernote 已提交
55
    protected abstract boolean release0(LLock lock);
lakernote's avatar
lakernote 已提交
56 57 58

    protected abstract boolean refresh(String key, String token, Duration expiration);
}