时间戳转化工具类

1.时间工具类

public class DataUtil {

    private static final Logger logger = LoggerFactory.getLogger(DataUtil.class);

    private static final ThreadLocal<SimpleDateFormat> DATE_FORMAT= new ThreadLocal<SimpleDateFormat>() {
        @Override
        protected synchronized SimpleDateFormat initialValue() {
            return new SimpleDateFormat("yyyyMMdd");
        }
    };

    private static final ThreadLocal<SimpleDateFormat> DATE_TIME_FORMAT= new ThreadLocal<SimpleDateFormat>() {
        @Override
        protected synchronized SimpleDateFormat initialValue() {
            return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        }
    };

    //lang3 需要导入lang3包,如果是lang中的,则没有parse方法
    private static   FastDateFormat SOURCE_TIME_FORMAT = FastDateFormat.getInstance("yyyy-MM-dd'T'HH:mm:ss+08:00");
    private static   FastDateFormat GMT_TIME_FORMAT=FastDateFormat.getInstance("yyyy-MM-dd HH:mm:ss");
    private static   FastDateFormat UTC_TIME_FORMAT = FastDateFormat.getInstance("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");

    /**
     * 将yyyy-MM-dd HH:mm:ss 转化成 yyyyMMdd 格式
     * @param datetime
     * @return
     */
    public static String  date(String datetime){

        String date="";
        try {
            Date parseDate = DATE_TIME_FORMAT.get().parse(datetime);
            date =  DATE_FORMAT.get().format(parseDate);
        } catch (ParseException e) {
           logger.error("将yyyy-MM-dd HH:mm:ss 转化成 yyyyMMdd 格式 解析错误 "+e.getMessage());
        }
        return date;
    }

    /**
     * 将时间(yyyyMMdd格式字符串)转化为时间戳
     * @param date
     * @return
     */
    public static Long getTimeStamp(String date){
        long time=0L;
        try {
            Date parse = DATE_FORMAT.get().parse(date);
             time = parse.getTime();
        } catch (ParseException e) {
            logger.error("将时间转化为时间戳错误"+e.getMessage());
        }

        return  time;
    }


    /**
     * 将时间转化为东八区时间
     * @param date
     * @return
     */
    public static String getGMTTime(String date){
        String GMTTime=null;
        try {
            Long timestamp=UTC_TIME_FORMAT.parse(date).getTime();
            GMTTime  = GMT_TIME_FORMAT.format(new Date(timestamp + 8 * 3600 * 1000));
        } catch (ParseException e) {
            e.printStackTrace();
        }
        return GMTTime;
    }
   
 /**
 * 将时间转化为canal ES adapter的输出格式  yyyy-MM-dd'T'HH:mm:ss+08:00
 * @param data
 * @return
 */
public static String getFormatTime(String data){
    String format=null;
    try {
        format = SOURCE_TIME_FORMAT.format(GMT_TIME_FORMAT.parse(data));
    } catch (ParseException e) {
        e.printStackTrace();
    }
    return format;
}

    /**
     * 验证指定时间格式
     * @param str   时间
     * @param timeFormat   时间格式
     * @return
     */
    public static boolean isValidDate(String str,String timeFormat) {
        boolean convertSuccess = true;
        // 指定日期格式为四位年-两位月份-两位日期  yyyy-MM-dd HH:mm:ss
        SimpleDateFormat format = new SimpleDateFormat(timeFormat);
        try {
            // 设置lenient为false.
            format.setLenient(false);

            format.parse(str);
            //时间格式必须一模一样(过滤掉时间中带T AM PM等样式时间)
            if(timeFormat.length() != str.length()){
                convertSuccess=false;
                logger.error("时间格式长度不一致错误,源数据:[{}]",str);
            }
        } catch (Exception e) {
            logger.error("时间格式解析错误,Exception:[{}] ,源数据:[{}]",e.getMessage(),str);
            convertSuccess = false;
        }
        return convertSuccess;
    }

    public static void main(String[] args) {
        System.out.println(getGMTTime("2020-12-20T01:34:56.526Z"));
    }
}

备注:fastDateFormat需要导入commons-lang3包

     <dependency>
          <groupId>org.apache.commons</groupId>
          <artifactId>commons-lang3</artifactId>
          <version>3.5</version>
      </dependency>

2.canal adapter to es的时间类型

 /**
 * 2020-12-23T19:09:37.150+08:00 --> 其实还是 2020-12-23 19:09:37.150  为什么要这种时间??
 * @param args
 */
public static void main(String[] args) {
   //2020-12-23 19:09:37   1608721777150
    String res;
    DateTime dateTime = new DateTime(1608721777150L);
    if (dateTime.getMillisOfSecond() != 0) {
        res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss.SSS" + Util.timeZone);
    } else {
        res = dateTime.toString("yyyy-MM-dd'T'HH:mm:ss" + Util.timeZone);
    }
    System.out.println(res);
}

3.dataX中 写入es其中时间类型用到joda-time包

 <dependency>
            <groupId>joda-time</groupId>
            <artifactId>joda-time</artifactId>
            <version>2.9.4</version>
        </dependency>



import org.joda.time.DateTime;
import org.joda.time.DateTimeZone;
import java.util.TimeZone;

/**
 * @author: XXX
 * @date: 2020/12/24 16:54
 * @Description: 测试
 */
public class TimeTest {
    public final static String  timeZone;
    static {
        TimeZone localTimeZone = TimeZone.getDefault();
        int rawOffset = localTimeZone.getRawOffset();
        String symbol = "+";
        if (rawOffset < 0) {
            symbol = "-";
        }
        rawOffset = Math.abs(rawOffset);
        int offsetHour = rawOffset / 3600000;
        int offsetMinute = rawOffset % 3600000 / 60000;
        String hour = String.format("%1$02d", offsetHour);
        String minute = String.format("%1$02d", offsetMinute);
        timeZone = symbol + hour + ":" + minute;
    }

    /**
     * 将13位时间戳转化为 东八区时间国际写法
     * @param args
     */
    public static void main(String[] args) {
        String time="1597298196000";
        //2020-08-13T13:56:36.000+08:00
        DateTimeZone dtz = DateTimeZone.getDefault();
        DateTime date = new DateTime(Long.valueOf(time), dtz);
        System.out.println(date.toString());  //2020-08-13T13:56:36.000+08:00    ES东八区时间到毫秒国际写法
        System.out.println(date.toString("yyyy-MM-dd'T'HH:mm:ss" + timeZone)); //2020-08-13T13:56:36+08:00   ES东八区时间到秒国际写法
    }
}

dataX ES writer插件中,会把Mysql中默认为null的字段赋值一个当前时间,并同步到ES中,显然这样是不符合业务要求的,此处进行修改.

package com.alibaba.datax.plugin.writer.elasticsearchwriter;
public class ESWriter extends Writer 类中修改getDateStr方法

//为了dataX 离线同步ES时间与canal adapter实时同步到ES的时间格式一致性
    public final static String  timeZone;
    static {
        TimeZone localTimeZone = TimeZone.getDefault();
        int rawOffset = localTimeZone.getRawOffset();
        String symbol = "+";
        if (rawOffset < 0) {
            symbol = "-";
        }
        rawOffset = Math.abs(rawOffset);
        int offsetHour = rawOffset / 3600000;
        int offsetMinute = rawOffset % 3600000 / 60000;
        String hour = String.format("%1$02d", offsetHour);
        String minute = String.format("%1$02d", offsetMinute);
        timeZone = symbol + hour + ":" + minute;
    }

	/**
     * ES 时间字段解析
     * @param esColumn
     * @param column
     * @return
     */
    private String getDateStr(ESColumn esColumn, Column column) {
        DateTime date = null;
        DateTimeZone dtz = DateTimeZone.getDefault();
       
        if (esColumn.getTimezone() != null) {
          
            dtz = DateTimeZone.forID(esColumn.getTimezone());
        }
        if (column.getType() != Column.Type.DATE && esColumn.getFormat() != null) {
            //根据json配置中的format来解析 { "name": "createTime","type": "date", "format": "yyyy-MM-dd HH:mm:ss" }
     
            DateTimeFormatter formatter = DateTimeFormat.forPattern(esColumn.getFormat());
            date = formatter.withZone(dtz).parseDateTime(column.asString());
           
            return date.toString();
        } else if (column.getType() == Column.Type.DATE) {
            //es中的字段类型为date,走的是此方法
            if(column.asLong() != null){            
                date = new DateTime(column.asLong(), dtz);
               //为了dataX 离线同步ES时间与canal adapter实时同步到ES的时间格式一致性,将date格式化为东八区国际时间到秒
                return date.toString("yyyy-MM-dd'T'HH:mm:ss" + timeZone);
            }
            return null;
        } else {
            return column.asString();
        }
    }
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值