datax采用standalone模式多任务并发时 Communication 统计有异常,输出统计日志错乱

一、源码分析后结论:

1、由于taskGroupCommunicationMap是一个静态map,在standalone模式多个任务并行执行任务时,其数据会叠加,或者被重置(key都是taskGroupId相同时)
2、修改方案,将jobid作为taskGroupCommunicationMap的key,在注册和update和获取Communication时都加上jobid
3、关键需要修改updateTaskGroupCommunication和getJobCommunication方法

二、修改方法:

package com.alibaba.datax.core.statistics.communication;

import com.alibaba.datax.dataxservice.face.domain.enums.State;
import org.apache.commons.lang3.Validate;

import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;

/**
 * 1、由于taskGroupCommunicationMap是一个静态map,在standalone模式多个任务并行执行任务时,其数据会叠加,或者被重置(key都是taskGroupId相同时)
 * 2、修改方案,将jobid作为taskGroupCommunicationMap的key,在注册和update和获取Communication时都加上jobid
 * 3、关键需要修改updateTaskGroupCommunication和getJobCommunication方法
 */
public final class LocalTGCommunicationManager {
    private static Map<Integer, Communication> taskGroupCommunicationMap =
            new ConcurrentHashMap<Integer, Communication>();

    public static void registerTaskGroupCommunication(
            int jobId, Communication communication) {
        taskGroupCommunicationMap.put(jobId, communication);
    }

    public static Communication getJobCommunication(Integer jobId) {
        Communication communication = new Communication();
        communication.setState(State.SUCCEEDED);
        /*for (Communication taskGroupCommunication :
                taskGroupCommunicationMap.values()) {
            communication.mergeFrom(taskGroupCommunication);
        }*/
        communication.mergeFrom(taskGroupCommunicationMap.get(jobId));

        return communication;
    }

    /**
     * 采用获取taskGroupId后再获取对应communication的方式,
     * 防止map遍历时修改,同时也防止对map key-value对的修改
     *
     * @return
     */
    public static Set<Integer> getTaskGroupIdSet() {
        return taskGroupCommunicationMap.keySet();
    }

    public static Communication getTaskGroupCommunication(int jobId) {
        Validate.isTrue(jobId >= 0, "taskGroupId不能小于0");

        return taskGroupCommunicationMap.get(jobId);
    }

    public static void updateTaskGroupCommunication(final int jobId,
                                                    final Communication communication) {
        Validate.isTrue(taskGroupCommunicationMap.containsKey(
                jobId), String.format("taskGroupCommunicationMap中没有注册taskGroupId[%d]的Communication," +
                "无法更新该taskGroup的信息", jobId));
        taskGroupCommunicationMap.put(jobId, communication);
    }

    public static void clear() {
        taskGroupCommunicationMap.clear();
    }

    public static Map<Integer, Communication> getTaskGroupCommunicationMap() {
        return taskGroupCommunicationMap;
    }
}

提醒:关键在于datax.core.statistics.communication.LocalTGCommunicationManager类的修改,其中各个方法中入参jobId对应在调用类里面修改,尽量用super.getJobId()获取jobId,修改起来容易

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值