Is there anyway to convert json to java bean through mybatis mapper?

Tags: ,



In case I have a mysql join query result set, it is in json format, like this:

[
    {
        "user_id": 5294147,
        "user_name": "rtm",
        "user_created": "2020-11-11 12:27:41",
        "user_updated": "2020-11-11 12:27:41",
        "tag_id": 10002,
        "tag_user_id": 5294147,
        "tag": "lazy",
        "tag_created": "2020-11-11 12:27:41",
        "tag_updated": "2020-11-11 12:27:41"
    },
    {
        "user_id": 5294147,
        "user_name": "rtm",
        "user_created": "2020-11-11 12:27:41",
        "user_updated": "2020-11-11 12:27:41",
        "tag_id": 10003,
        "tag_user_id": 5294147,
        "tag": "weak",
        "tag_created": "2020-11-11 12:27:41",
        "tag_updated": "2020-11-11 12:27:41"
    }
]

and the mybatis mapper

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
  "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="org.example.mybatis.mapper.UserMapper">
  <resultMap id="UserTag" type="org.example.mybatis.dto.UserTag">
    <id column="tag_id" jdbcType="INTEGER" property="id"/>
    <result column="tag_user_id" jdbcType="INTEGER" property="userId"/>
    <result column="tag" jdbcType="VARCHAR" property="tag"/>
    <result column="tag_created" jdbcType="TIMESTAMP" property="created"/>
    <result column="tag_updated" jdbcType="TIMESTAMP" property="updated"/>
  </resultMap>

  <resultMap id="User" type="org.example.mybatis.dto.User">
    <id column="user_id" jdbcType="INTEGER" property="id"/>
    <result column="user_name" jdbcType="VARCHAR" property="name"/>
    <result column="user_created" jdbcType="TIMESTAMP" property="created"/>
    <result column="user_updated" jdbcType="TIMESTAMP" property="updated"/>
    <collection property="tagList" column="user_id"
      notNullColumn="tag_user_id"
      javaType="java.util.ArrayList"
      ofType="org.example.mybatis.dto.UserTag"
      resultMap="UserTag"/>
  </resultMap>

  <select id="getUserById" parameterType="hashmap" resultMap="User">
    select
    u.id as user_id,
    u.name as user_name,
    u.created as user_created,
    u.updated as user_updated,
    t.id as tag_id,
    t.user_id as tag_user_id,
    t.tag,
    t.created as tag_created,
    t.updated as tag_updated
    from user u
    left join
    user_tag t
    on
    u.id = t.user_id
    where u.id = #{userId,jdbcType=INTEGER}
  </select>
</mapper>

I can’t access this mysql instance directly, I can only export query result in json format through some “proxy platform”, is there anyway convert the json to org.example.mybatis.dto.User through the existing mybatis mapper easily?

PS: I tried to use mybatis Interceptor to intercept ResultSetHandler.handleResultSets, but it seems that I must mock Statement and ResultSet

Answer

JOOQ can convert txt/json/csv to ResultSet

String json = ... // json;
DSLContext dsl = DSL.using(SQLDialect.MYSQL);
Result<?> result= dsl.fetchFromJSON(json);
ResultSet rs = result.intoResultSet();

// mybaits Configuration
Configuration dummyConfiguration = new Configuration();
dummyConfiguration .addMappers("org.example.mybatis.mapper");
MappedStatement ms = dummyConfiguration.getMappedStatement("getUserById");

// just copy mybaits DefaultResultSetHandler and remove some code
FakeResultSetHandler resultHandler = new FakeResultSetHandler(ms, null, RowBounds.DEFAULT);
List<Object> list = resultHandler.handleResultSets(rs);
System.out.println(list);

// output 
// [User(id=5294147, name=rtm, created=Wed Nov 11 12:27:41 CST 2020, updated=Wed Nov 11 12:27:41 CST 2020, tagList=[UserTag(id=10002, userId=5294147, tag=lazy, created=Wed Nov 11 12:27:41 CST 2020, updated=Wed Nov 11 12:27:41 CST 2020), UserTag(id=10003, userId=5294147, tag=weak, created=Wed Nov 11 12:27:41 CST 2020, updated=Wed Nov 11 12:27:41 CST 2020)])]


Source: stackoverflow