MySQL Spring JDBC API JdbcTemplate日期时间字段的测试使用

MySQL Spring JDBC API JdbcTemplate日期时间字段的测试使用

建测试表

CREATE TABLE `t_date`  (
  `id` int(11) NOT NULL AUTO_INCREMENT PRIMARY KEY,
  `f_date` date NULL,
  `f_datetime` datetime(0) NULL,
  `f_timestamp` timestamp(0) NULL  
)

实体类TData

TDate.java

package com.test.jdbcapi;
import com.fasterxml.jackson.annotation.JsonFormat;
import java.sql.Date;
import java.sql.Timestamp;
import lombok.Data;

@Data
public class TDate {
    private int id;
    @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd",timezone = "GMT+8")
    private Date f_date;
    @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd HH:mm:ss",timezone = "GMT+8")
    private Timestamp  f_datetime;
    @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd HH:mm:ss",timezone = "GMT+8")
    private Timestamp  f_timestamp;
}

添加测试数据


@Test
    void testInsert() throws JsonProcessingException, ParseException {
        System.out.println("testInsert");
        java.util.Date d = new java.util.Date();
        TDate tdate = new TDate();
        tdate.setF_date(new Date(d.getTime()));
        tdate.setF_datetime(new Timestamp(d.getTime()));
        tdate.setF_timestamp(new Timestamp(d.getTime()));

        String sql = "insert into t_date(f_date,f_datetime,f_timestamp) values(?,?,?)";
        int i = jdbcTemplate.update(sql, tdate.getF_date(), tdate.getF_datetime(), tdate.getF_timestamp());
        System.out.println("insert:" + i);

        ObjectMapper objectMapper = new ObjectMapper();
        String str = objectMapper.writeValueAsString(tdate);
        System.out.println(str);
    }


尝试使用JdbcTemplate.queryForObject来查询数据


@Test
    void testQueryForObjectByDateTime() throws JsonProcessingException, ParseException {
        System.out.println("testQueryForObjectByDateTime");
        int id = 1;
        String sql = "select * from  t_date where id=?";
        TDate tdate = jdbcTemplate.queryForObject(sql, new BeanPropertyRowMapper<>(TDate.class), id);

        ObjectMapper objectMapper = new ObjectMapper();
        String str = objectMapper.writeValueAsString(tdate);
        System.out.println(str);
    }


MySQL Spring JDBC API JdbcTemplate日期时间字段的测试使用_JdbcTemplate


单元测试及问题处理

在测试过程发现如果MySQL数据库字段使用了datatime类型时,这个数据库驱动SqlRowSet对象会字段转换为java.time.LocalDateTime类型,这里使用针对日期时间字段的取值 rowSet.getDate()或rowSet.getTimestamp()都是会出错的,这只在自行使用SqlRowSet时会出现这个错误


@Test
    void testDateQueryForRowSet() {
        System.out.println("testDateQueryForRowSet");
        String sql = "select * from t_date";
        SqlRowSet rowSet = jdbcTemplate.queryForRowSet(sql);
        while (rowSet.next()) {
            Date f_date = rowSet.getDate("f_date");
            Date f_datetime = rowSet.getDate("f_datetime");
            Timestamp f_timestamp = rowSet.getTimestamp("f_timestamp");
            System.out.println("日期:" + f_date);
            System.out.println("日期时间:" + f_datetime);
            System.out.println("timestamp:" + f_timestamp);

        }
    }


单元测试出现错误了

java.lang.ClassCastException: class java.time.LocalDateTime cannot be cast to class java.sql.Timestamp (java.time.LocalDateTime is in module java.base of loader 'bootstrap'; java.sql.Timestamp is in module java.sql of loader 'platform')

这里其实MySQL数据库表中类型为DataTime的字段f_datetime,通过JDBC SqlRowSet对象获取到的f_datetime字段类型为java.time.LocalDateTime 无法通过SqlRowSet.getTimestamp获取,对象类型不一致

在Timestamp f_datetime = rowSet.getTimestamp("f_datetime");这里设置断点,在前面增加一行Object obj=rowSet.getObject("f_datetime");使用Debug可以看到

MySQL Spring JDBC API JdbcTemplate日期时间字段的测试使用_JdbcTemplate_02


debug运行到断点后,在Threads & Variables 这里可以看到变量情况

MySQL Spring JDBC API JdbcTemplate日期时间字段的测试使用_JdbcTemplate_03



Timestamp f_datetime = rowSet.getTimestamp("f_datetime");改为

Timestamp f_datetime =Timestamp.valueOf( (java.time.LocalDateTime) rowSet.getObject("f_datetime"));

可以取出数据,需要自行转换,如果在MySQL中字段使用类型为Date或Timestamp则没有那么麻烦去自行转换

上一篇:Python将word文档内容替换为手写


下一篇:Spring 问题整理