(jdbcType)mybatis 查询Oracle Date类型字段只精确到年月日

解决Oracle Date精度问题
本文介绍了解决使用MyBatis Generator生成代码后,在Oracle数据库中Date类型字段精度仅限于年月日的问题。通过将JDBC类型从DATE改为TIMESTAMP,可以确保日期时间包括时分秒部分。
部署运行你感兴趣的模型镜像

用mybatis generator生成代码后,执行查询语句时,oracle里的Date类型字段只精确到年月日,后面时分秒都为零。


后来发现是jdbcType问题,改成 jdbcType="TIMESTAMP" 就可以。(原先默认生成时是jdbcType="DATE")


ps:实体类里Date是java.util.Date包里的,不是java.sql.Date,否则也会只精确到年月日

您可能感兴趣的与本文相关的镜像

Wan2.2-T2V-A5B

Wan2.2-T2V-A5B

文生视频
Wan2.2

Wan2.2是由通义万相开源高效文本到视频生成模型,是有​50亿参数的轻量级视频生成模型,专为快速内容创作优化。支持480P视频生成,具备优秀的时序连贯性和运动推理能力

在使用 MyBatis 操作 Oracle 数据库时,处理 `DATE` 类型字段时常常会遇到精度丢失或映射不正确的问题。Oracle 的 `DATE` 类型默认包含年、月、日、时、分、秒信息,但在 MyBatis 中映射到 Java 的 `java.util.Date` 或 `java.sql.Date` 时,可能会出现只保留年月日的情况,导致时间部分被截断。 ### 问题分析 MyBatis 在处理 Oracle 的 `DATE` 类型时,默认使用 `java.sql.Date` 类型进行映射,而 `java.sql.Date` 只保留年月日部分,忽略时分秒[^1]。这会导致查询结果中日期字段的时间部分丢失。此外,MyBatis Generator 自动生成的代码中,对于 `DATE` 类型字段通常会使用 `addCriterionForJDBCDate` 方法,该方法在处理时间精度上也在局限性[^1]。 ### 解决方案 #### 1. 使用 `java.sql.Timestamp` 替代 `java.sql.Date` 为了保留完整的日期时间信息,应将 Java 实体类中的日期字段类型改为 `java.sql.Timestamp`。该类型可以完整保留 Oracle `DATE` 字段中的时间信息。同时,在 MyBatis 的映射文件中,将字段的 `jdbcType` 设置为 `TIMESTAMP`: ```xml <resultMap id="BaseResultMap" type="com.example.User"> <id column="ID" property="id" jdbcType="DECIMAL"/> <result column="NAME" property="name" jdbcType="VARCHAR"/> <result column="BIRS" property="birs" jdbcType="TIMESTAMP"/> </resultMap> ``` #### 2. 修改 MyBatis 查询语句中的字段别名与类型处理 在 SQL 查询语句中,可以显式地将 `DATE` 类型字段转换为 `TIMESTAMP`,以确保返回完整的时间信息: ```xml <select id="selectUserById" resultType="com.example.User"> SELECT ID, NAME, BIRS AS BIRS_TIMESTAMP FROM T_USERS WHERE ID = #{id} </select> ``` #### 3. 自定义类型处理器(TypeHandler) 为了更灵活地控制日期类型的转换逻辑,可以实现自定义的 `TypeHandler`,将 Oracle 的 `DATE` 映射为 `Timestamp` 并进行格式化输出: ```java public class CustomDateTypeHandler extends BaseTypeHandler<Date> { @Override public void setNonNullParameter(PreparedStatement ps, int i, Date parameter, JdbcType jdbcType) throws SQLException { ps.setTimestamp(i, new Timestamp(parameter.getTime())); } @Override public Date getNullableResult(ResultSet rs, String columnName) throws SQLException { Timestamp timestamp = rs.getTimestamp(columnName); return timestamp != null ? new Date(timestamp.getTime()) : null; } @Override public Date getNullableResult(ResultSet rs, int columnIndex) throws SQLException { Timestamp timestamp = rs.getTimestamp(columnIndex); return timestamp != null ? new Date(timestamp.getTime()) : null; } } ``` 在 MyBatis 配置文件中注册该处理器: ```xml <typeHandlers> <typeHandler handler="com.example.CustomDateTypeHandler" javaType="java.util.Date"/> </typeHandlers> ``` #### 4. 查询结果返回为 Map 并手动处理 如果不想修改实体类字段类型,也可以将查询结果设置为 `map` 类型,并通过指定 `jdbcType="TIMESTAMP"` 来获取完整时间信息: ```xml <select id="selectUserAsMap" resultType="map"> SELECT ID, NAME, BIRS FROM T_USERS WHERE ID = #{id} </select> ``` 查询结果中的日期字段将返回为 `Timestamp` 类型,可在业务逻辑中进一步处理。 ### 示例表结构与映射 以下为示例表结构及对应的 MyBatis 映射配置: ```sql CREATE TABLE T_USERS ( ID NUMBER NOT NULL, NAME VARCHAR2(30), SEX VARCHAR2(3), BIRS DATE, MESSAGE CLOB ); ``` 对应的 MyBatis 映射文件: ```xml <resultMap id="UserResultMap" type="com.example.User"> <id column="ID" property="id" jdbcType="DECIMAL"/> <result column="NAME" property="name" jdbcType="VARCHAR"/> <result column="BIRS" property="birs" jdbcType="TIMESTAMP"/> <result column="MESSAGE" property="message" jdbcType="CLOB"/> </resultMap> ``` ### 总结 在 MyBatis 中处理 Oracle 的 `DATE` 类型时,关键在于确保 Java 端使用 `Timestamp` 类型,并在映射文件中正确设置 `jdbcType` 为 `TIMESTAMP`。此外,使用自定义 `TypeHandler` 或返回 `map` 结构可以进一步增强灵活性和控制力[^2]。 ---
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值