You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
			
				
					118 lines
				
				3.3 KiB
			
		
		
			
		
	
	
					118 lines
				
				3.3 KiB
			| 
											3 years ago
										 | package com.ynxbd.common.helper.common;
 | ||
|  | 
 | ||
|  | import lombok.extern.slf4j.Slf4j;
 | ||
|  | import org.slf4j.MDC;
 | ||
|  | 
 | ||
|  | import java.util.ArrayList;
 | ||
|  | import java.util.List;
 | ||
|  | import java.util.Map;
 | ||
|  | import java.util.concurrent.ConcurrentHashMap;
 | ||
|  | import java.util.concurrent.Executors;
 | ||
|  | import java.util.concurrent.ScheduledExecutorService;
 | ||
|  | import java.util.concurrent.TimeUnit;
 | ||
|  | 
 | ||
|  | /**
 | ||
|  |  * 排重:重复通知处理
 | ||
|  |  */
 | ||
|  | @Slf4j
 | ||
|  | public class RepeatKeyHelper {
 | ||
|  |     // 默认key有效时间 30分钟
 | ||
|  |     public final static int DEFAULT_EXPIRE_TIME = 1800;
 | ||
|  | 
 | ||
|  |     private final Map<String, Long> KEY_MAP = new ConcurrentHashMap<>();
 | ||
|  | 
 | ||
|  |     private ScheduledExecutorService scheduledExecutorService;
 | ||
|  | 
 | ||
|  |     // 清理key 间隔时间 60秒
 | ||
|  |     private Integer period = 60;
 | ||
|  | 
 | ||
|  |     public RepeatKeyHelper() {
 | ||
|  |         timerTask();
 | ||
|  |     }
 | ||
|  | 
 | ||
|  |     public RepeatKeyHelper(int period) {
 | ||
|  |         this.period = period;
 | ||
|  |         timerTask();
 | ||
|  |     }
 | ||
|  | 
 | ||
|  |     private void timerTask() {
 | ||
|  |         log.info("创建keyList");
 | ||
|  |         if (scheduledExecutorService != null) {
 | ||
|  |             scheduledExecutorService.shutdownNow();
 | ||
|  |         }
 | ||
|  |         // 守护线程 自动清理过期key,间隔时间60秒
 | ||
|  |         scheduledExecutorService = Executors.newSingleThreadScheduledExecutor(r -> {
 | ||
|  |             MDC.remove("ip");
 | ||
|  |             MDC.put("ip", "Keys守护线程");
 | ||
|  | 
 | ||
|  |             Thread thread = Executors.defaultThreadFactory().newThread(r);
 | ||
|  |             thread.setDaemon(true);
 | ||
|  |             return thread;
 | ||
|  |         });
 | ||
|  | 
 | ||
|  |         scheduledExecutorService.scheduleWithFixedDelay(() -> {
 | ||
|  |             MDC.remove("ip");
 | ||
|  |             MDC.put("ip", "定时任务");
 | ||
|  |             List<String> removeKey = new ArrayList<>();
 | ||
|  |             for (String key : KEY_MAP.keySet()) {
 | ||
|  |                 Long value = KEY_MAP.get(key);
 | ||
|  |                 long current = System.currentTimeMillis() / 1000;
 | ||
|  |                 if (value != null && value <= current) {
 | ||
|  |                     // log.info("delete:current=" + current + ", value=" + value);
 | ||
|  |                     removeKey.add(key);
 | ||
|  |                 }
 | ||
|  |             }
 | ||
|  |             for (String key : removeKey) {
 | ||
|  |                 KEY_MAP.remove(key);
 | ||
|  |             }
 | ||
|  |             if (removeKey.size() > 0) {
 | ||
|  |                 log.info("clean {} keys, remain {} keys", removeKey.size(), KEY_MAP.size());
 | ||
|  |             }
 | ||
|  |         }, 10, period, TimeUnit.SECONDS);
 | ||
|  |     }
 | ||
|  | 
 | ||
|  |     /**
 | ||
|  |      * 排重处理,是否存在key
 | ||
|  |      *
 | ||
|  |      * @param key key
 | ||
|  |      * @return 吃饭
 | ||
|  |      */
 | ||
|  |     public synchronized boolean isContainsKey(String key) {
 | ||
|  |         return isContainsKey(key, DEFAULT_EXPIRE_TIME);
 | ||
|  |     }
 | ||
|  | 
 | ||
|  |     /**
 | ||
|  |      * 排重处理,是否存在key
 | ||
|  |      *
 | ||
|  |      * @param key key
 | ||
|  |      * @return 是否过期或重复
 | ||
|  |      */
 | ||
|  |     public synchronized boolean isContainsKey(String key, int expire) {
 | ||
|  |         Long value = KEY_MAP.get(key);
 | ||
|  |         if (value != null) {
 | ||
|  |             if (value > System.currentTimeMillis() / 1000) { // 存在且没过时
 | ||
|  |                 return true;
 | ||
|  |             }
 | ||
|  |         }
 | ||
|  | 
 | ||
|  |         log.info("add key=" + key);
 | ||
|  |         KEY_MAP.put(key, (System.currentTimeMillis() / 1000) + expire);
 | ||
|  |         return false;
 | ||
|  |     }
 | ||
|  | 
 | ||
|  |     /**
 | ||
|  |      * key数量
 | ||
|  |      *
 | ||
|  |      * @return 数量
 | ||
|  |      */
 | ||
|  |     public int count() {
 | ||
|  |         return KEY_MAP.size();
 | ||
|  |     }
 | ||
|  | 
 | ||
|  |     public void print() {
 | ||
|  |         for (String key : KEY_MAP.keySet()) {
 | ||
|  |             log.info("key=" + key + ", value=" + KEY_MAP.get(key));
 | ||
|  |         }
 | ||
|  |     }
 | ||
|  | }
 |