数据分片(任务执行)

 

String data = dataAllotService.getMachineAllotData();
paramMap.put("TRANS_NO_SUB", data);
List<TblChannelsTransaction> list = channelsTransExceptionLogicImpl.queryTransExceptionList(paramMap);

<if test="TRANS_NO_SUB != null and TRANS_NO_SUB !='' ">
AND SUBSTRB(TRANS_NO,-1) in (${TRANS_NO_SUB})
</if>

  

 

@Service
public class DataAllotServiceImpl implements DataAllotService {
	
	private static Logger logger = LoggerFactory.getLogger("DataAllotServiceImpl");
   
	private final static String MACHINENAME_SUFFIX = "_IS_LIVE";
	
	private final static String MACHINENAME_REG = "TASK_NODE_REG";
	
	private String REDIS_KEY = BasisConstants.Redis_Basic_key;
	
	private static String machineName;
	
	@Autowired
    private  CacheService cacheService;
	
	private ScheduledExecutorService scheduledExecutorService = Executors.newScheduledThreadPool(1);

    @PostConstruct
    public void startDataSplit() {
        scheduledExecutorService.scheduleAtFixedRate(new Runnable() {
            public void run() {
            	sendHeartBeat();
            }
        }, 1, 6, TimeUnit.SECONDS);
    }
	
	/**
	 * 节点注册和心跳设置
	 */
	public void sendHeartBeat() {
		try {
			if(StringUtils.isEmpty(getMachineName())){
				logger.error("[DataAllotServiceImpl]未获取到应用名称");
			}else{
				String taskSplitSync = cacheService.get(REDIS_KEY,"TASK_SPLIT_SYNC");
				if(StringUtils.isEmpty(taskSplitSync)) {
					cacheService.setex(REDIS_KEY, getMachineName() + MACHINENAME_SUFFIX, 20, getMachineName());//心跳写入
					cacheService.sadd(REDIS_KEY, MACHINENAME_REG, getMachineName());//注册
					logger.info("[DataAllotServiceImpl]sendHeartBeat,心跳写入成功");
				}else{
					logger.info("[DataAllotServiceImpl]sendHeartBeat,正在等待心跳写入,同步标示taskSplitSync为:" + taskSplitSync);
				}
			}
		} catch (Exception e) {
			logger.error("[DataAllotServiceImpl].sendHeartBeat出现异常:", e);
		}
	}
	
	public String getMachineAllotData(){
		String machineAllotData = "";
		try {
			machineAllotData = cacheService.get(REDIS_KEY, getMachineName());
		} catch (Exception e) {
			logger.error("[DataAllotServiceImpl].getMachineAllotData出现异常:", e);
		}
		return machineAllotData;
	}
	
	public  String getMachineName(){
		if(!StringUtils.isEmpty(machineName)){
			return machineName;
		}
		InetAddress inet;
		String ip = "";
		try {
			inet = InetAddress.getLocalHost();
			ip = inet.getHostAddress();
		} catch (UnknownHostException e) {
			logger.error("[DataAllotServiceImpl]获取IP出现异常,e:" + e.getMessage(), e);
		}
		
		String fullPath = Thread.currentThread().getContextClassLoader().getResource("").toString();
		logger.info("[DataAllotServiceImpl]fullPath:" + fullPath);
		if(fullPath.indexOf("/webapps") == -1){
			return null;
		}
		String lPath = fullPath.substring(0,fullPath.indexOf("/webapps"));
		String projectName = lPath.substring(lPath.lastIndexOf("/") + 1);
		logger.info("[DataAllotServiceImpl]ip:" + ip + ",projectName:" + projectName);
		if(StringUtils.isEmpty(ip)){
			return null;
		}
		machineName = ip.replaceAll("\\.", "") + projectName;
		return machineName;
	}
}

  

/**
 * @Title FormatDateUtils
 * @package cn.com.gome.pay.admin.logic.impl
 * @author tianlong
 * @company cn.com.gome
 * @Date 2016/12/6
 * @version V1.0
 */
package cn.com.gome.pay.admin.logic.impl;

import cn.com.gome.common.security.md5.MD5Util;
import cn.com.gome.frame.cache.ApplicationCache;
import cn.com.gome.pay.admin.logic.TaskDataAllotListenerLogic;
import com.alibaba.dubbo.common.utils.StringUtils;
import com.gome.service.CacheService;
import org.apache.commons.collections.CollectionUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;
import java.util.*;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;

/**
 * @author tianlong
 * @ClassName TaskDataAllotListenerLogicImpl
 * @Description 后台管理定时任务分片监听器
 * @Date 2017/06/12
 */
@Service
public class TaskDataAllotListenerLogicImpl implements TaskDataAllotListenerLogic {

    private Logger logger = LoggerFactory.getLogger(this.getClass().getSimpleName());

    @Autowired
    private CacheService cacheService;

    private ScheduledExecutorService scheduledExecutorService = Executors.newScheduledThreadPool(1);

    @PostConstruct
    public void startDataSplit() {
        scheduledExecutorService.scheduleAtFixedRate(new Runnable() {
            public void run() {
                taskDataSplit();
            }
        }, 1, 15, TimeUnit.SECONDS);
    }

    public void taskDataSplit() {
        logger.info("定时任务监听数据分片TaskDataAllotListenerLogic.startDataSplit开始运行");
        String REDIS_KEY = ApplicationCache.getInstance().getStr("REDIS_KEY");
        try {
            //1.获取注册的定时任务实例
            Set<String> regNodes = cacheService.smembers(REDIS_KEY, "TASK_NODE_REG");
            if(CollectionUtils.isNotEmpty(regNodes)){
                logger.info("定时任务监听数据分片TaskDataAllotListenerLogic.startDataSplit注册实例:" + Arrays.toString(regNodes.toArray()));
            }else {
                logger.info("定时任务监听数据分片TaskDataAllotListenerLogic.startDataSplit注册实例:0");
                return;
            }
            String liveNode = "";
            List<String> liveNodes = new ArrayList<String>();
            //2.获取存活的实例
            for (String reg : regNodes) {
                String nodeLive = cacheService.get(REDIS_KEY,reg+"_IS_LIVE");
                if(StringUtils.isNotEmpty(nodeLive)){
                    liveNodes.add(nodeLive);
                    liveNode += reg;
                }
            }
            logger.info("定时任务监听数据分片TaskDataAllotListenerLogic.startDataSplit存活的实例:" + liveNode);
            //3.判断是否需要重新分配分片数据
            if(StringUtils.isNotEmpty(liveNode)){
                String md5LiveNode = cacheService.get(REDIS_KEY,"TASK_NODE_MD5");
                String md5Node = MD5Util.encodeMessage(liveNode.getBytes());
                if(!md5Node.equals(md5LiveNode)){
                    cacheService.setex(REDIS_KEY, "TASK_NODE_MD5",120, md5Node);//存活120秒强制计算
                    splitData(REDIS_KEY,liveNodes);
                }
            }

        } catch (Exception e) {
            logger.error("定时任务监听数据分片TaskDataAllotListenerLogic.startDataSplit运行异常", e);
        }
        logger.info("定时任务监听数据分片TaskDataAllotListenerLogic.startDataSplit结束运行");
    }

    private void splitData(String REDIS_KEY,List<String> liveNodes) {
        //1.分片数据
        Integer[] numbers = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 };
        Map<String, String> split = new HashMap<String, String>();
        for (int i = 0; i < numbers.length; i++) {
            int index = numbers[i] % liveNodes.size();
            if (split.containsKey(liveNodes.get(index))) {
                String s = split.get(liveNodes.get(index));
                split.put(liveNodes.get(index), s + "," + numbers[i]);
            } else {
                split.put(liveNodes.get(index), String.valueOf(numbers[i]));
            }
        }
        //2.输出数据分片
        for (Map.Entry<String, String> entry : split.entrySet()) {
            System.out.println("key= " + entry.getKey() + " and value= " + entry.getValue());
            cacheService.setex(REDIS_KEY,entry.getKey(),150,entry.getValue());//存活150秒
            logger.info("定时任务监听数据分片TaskDataAllotListenerLogic.startDataSplit的result:" + " key= " + entry.getKey() + " and value= " + entry.getValue());
        }
    }
}

  

 

posted @ 2018-12-15 17:56  苍天一穹  阅读(897)  评论(0编辑  收藏  举报