非分佈式鎖的簡易使用

1 Lock鎖的設計
/**
* 全局的鎖
*/
public class LockHelper {
 
 
    private static final Logger log = LoggerFactory.getLogger(LockHelper.class);
 
 
    /**
     * 鎖類型
     */
    public enum LockType {
        /**
         * 鎖 的測試枚舉類型
         */
        TEST_LOCK_1,
        TEST_LOCK_2;
        LockType() {
            locks.put(this, new ReentrantLock());
        }
    }
 
 
    /**
     * 保存了所有的鎖
     */
    private static final Map<LockType, Lock> locks = new HashMap<>();
 
 
    /**
     * 加鎖時間,防止死鎖
     */
    private static final Map<LockType, Date> lockTimeMap = new HashMap<>();
 
 
    /**
     * 如果時長超過兩分鐘,就去給它解鎖
     * TODO:這個方法應該放到定時任務,至於怎麼繼承,就看使用定時任務的人怎麼用了
     */
    public void run(String args) {
        Date now = new Date();
        lockTimeMap.forEach((lockType, lockTime) -> {
            if (now.getTime() - lockTime.getTime() > TimeUnit.MINUTES.toMillis(2)) {
                log.error("這個鎖{}兩分鐘都還沒有釋放,可能死鎖了", lockType);
                LockHelper.unlock(lockType);
            }
        });
    }
 
 
    /**
     * 加鎖(不帶時間,run()方法定時釋放鎖,避免死鎖)
     */
    public static void lock(LockType lockType) {
        locks.get(lockType).lock();
        lockTimeMap.put(lockType, new Date());
    }
 
 
    /**
     * 加鎖(不帶時間,run()方法定時釋放鎖,避免死鎖)
     */
    public static boolean tryLock(LockType lockType) {
        boolean result = locks.get(lockType).tryLock();
        if (result) {
            lockTimeMap.put(lockType, new Date());
        }
        return result;
    }
 
 
    /**
     * 加鎖(帶時間,run()方法定時釋放鎖,避免死鎖)
     */
    public static boolean tryLock(LockType lockType, long time, TimeUnit unit) throws InterruptedException {
        boolean result = locks.get(lockType).tryLock(time, unit);
        if (result) {
            lockTimeMap.put(lockType, new Date());
        }
        return result;
    }
 
 
    /**
     * 釋放鎖(不帶時間,需要手動釋放,可能會造成死鎖)
     */
    public static void unlock(LockType lockType) {
        locks.get(lockType).unlock();
        lockTimeMap.remove(lockType);
    }
}
 
2 使用
@Test
public void testLockHelper() throws InterruptedException {
    LockHelper.lock(LockHelper.LockType.TEST_LOCK_1);
 
 
    // 做一些邏輯處理--------------------------
    System.out.println("處理前 testSynchronized");
    Thread.sleep(1000);
    System.out.println("處理後 testSynchronized");
 
 
    LockHelper.unlock(LockHelper.LockType.TEST_LOCK_1);
}
 
 
@Test
public void testSynchronized() throws InterruptedException {
    String orderId = "20190304234124102";
    synchronized (orderId.intern()) {
        // 做一些邏輯處理--------------------------
        System.out.println("處理前 testSynchronized");
        Thread.sleep(1000);
        System.out.println("處理後 testSynchronized");
    }
}
 
 
 
 
 
 
 
 
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章