记录一个复合嵌套类的使用MyBatis取出数据的例子

这个目标是想取出两个表中的数据,A表的数据是主体,B表的数据是A表中的一个嵌合体。A表中有个自定义的数组字段,数组中的数据模型就是B表中的数据。AB表的数据关系是一对多的。项目使用的是框架是MyBatis,xml是需要自己写的。所以记录一下,防止以后遇到相同功能以便查找。

model 模型

  • A表数据模型有一个数组字段 List 和 一些其他日常字段 所以这个文章主要就是记录这个list 是这么从B表取出变成一个复合类型数据的
java 复制代码
/**
 * 收费规则对象 charge_rule
 *
 * @author zdcloud
 * @date 2024-09-19
 */
@ApiModel(description = "收费规则对象")
@Data
@NoArgsConstructor
@Accessors(chain = true)
@TableName("charge_account_rule")
public class ChargeAccountRule extends BaseEntity{
    private static final long serialVersionUID=1L;

    /** $column.columnComment */
    @TableId(value = "id" , type = IdType.AUTO)
    @ApiModelProperty(value = "${comment}")
    private Long id;

    /** 规则名称 */
    @Excel(name = "规则名称")
    @ApiModelProperty(value = "规则名称")
    private String ruleName;

    /** 计费规则详情信息 */

    @TableField(exist = false)
    @ApiModelProperty(value = "规则详情list")
    private List<ChargeAccountRuleDetail> chargeAccountRuleDetailList;

}
  • 这个是B表 其中包含数据库表的常规字段,同时还有B表中不存在的虚拟字段,这些字段需要从别的表中获取 使用@TableField(exist = false) 注解标记这是@TableName("charge_account_rule_detail")表中没有的虚拟字段。
java 复制代码
/**
 * 收费规则对象 charge_rule
 *
 * @author zdcloud
 * @date 2024-09-19
 */
@ApiModel(description = "收费规则详情对象")
@Data
@NoArgsConstructor
@Accessors(chain = true)
@TableName("charge_account_rule_detail")
public class ChargeAccountRuleDetail extends BaseEntity{
    private static final long serialVersionUID=1L;

    /** $column.columnComment */
    @TableId(value = "id" , type = IdType.AUTO)
    @ApiModelProperty(value = "${comment}")
    private Long id;

    /** 规则名称 */
    @Excel(name = "规则id")
    @ApiModelProperty(value = "规则id")
    private String ruleId;

    @Excel(name = "商户分账比例")
    @ApiModelProperty(value = "商户分账比例")
    private BigDecimal proportion;

    @Excel(name = "分账商户id")
    @ApiModelProperty(value = "规则id")
    private String tradeId;

    @TableField(exist = false)
    @Excel(name = "商户名称")
    @ApiModelProperty(value = "商户名称")
    private String tradeName;

    @TableField(exist = false)
    @Excel(name = "商户类型 0个人用户,1微信商户")
    @ApiModelProperty(value = "商户类型")
    private Integer tradeType;


    @TableField(exist = false)
    @Excel(name = "用户id")
    @ApiModelProperty(value = "用户id")
    private String userId;

    @TableField(exist = false)
    @Excel(name = "用户名")
    @ApiModelProperty(value = "用户名")
    private String userName;

}

controller

  • controller 调用service接口
java 复制代码
iChargeAccountRuleService.selectChargeAccountRuleById(id)

Service

  • service 创建一个接口
java 复制代码
public interface IChargeAccountRuleService extends IService<ChargeAccountRule>
{
    /**
     * 查询分账规则
     *
     * @param id 主键
     * @return 分账规则
     */
    public ChargeAccountRule selectChargeAccountRuleById(Long id);
}

impl

  • impl 实现接口方法 调用Mapper
java 复制代码
@Service
public class ChargeAccountRuleServiceImpl extends ServiceImpl<ChargeAccountRuleMapper, ChargeAccountRule> implements IChargeAccountRuleService {
    @Autowired
    private ChargeAccountRuleMapper chargeAccountRuleMapper;

    @Override
    public ChargeAccountRule selectChargeAccountRuleById(Long id) {
        return chargeAccountRuleMapper.selectChargeAccountRuleById(id);
    }
}

ChargeAccountRuleMapper

  • mapper
java 复制代码
public interface ChargeAccountRuleMapper extends BaseMapper<ChargeAccountRule>
{
    public ChargeAccountRule selectChargeAccountRuleById(Long id);

}

ChargeAccountRuleMapper.xml

  • 这里是重点
xml 复制代码
<resultMap type="com.charge.web.model.ChargeAccountRule" id="ChargeAccountRuleResult">
    <result property="id" column="id"/>
    <result property="ruleName" column="rule_name"/>
    <result property="createTime" column="create_time"/>
    <result property="updateTime" column="update_time"/>
    <result property="createBy" column="create_by"/>
    <result property="updateBy" column="update_by"/>
</resultMap>

<resultMap type="com.charge.web.model.ChargeAccountRuleDetail" id="ChargeAccountRuleDetailResult">
    <result property="id" column="detail_id"/>
    <result property="ruleId" column="rule_id"/>
    <result property="tradeId" column="trade_id"/>
    <result property="tradeName" column="trade_name"/>
    <result property="tradeType" column="trade_type"/>
    <result property="userId" column="user_id"/>
    <result property="userName" column="user_name"/>

    <result property="proportion" column="proportion"/>
    <result property="createTime" column="detail_create_time"/>
    <result property="updateTime" column="detail_update_time"/>
    <result property="createBy" column="detail_create_by"/>
    <result property="updateBy" column="detail_update_by"/>
</resultMap>

<resultMap type="com.charge.web.model.ChargeAccountRule" id="ChargeAccountRuleWithDetailResult"
           extends="ChargeAccountRuleResult">
    <collection property="chargeAccountRuleDetailList" notNullColumn="detail_id" javaType="java.util.List"
                resultMap="ChargeAccountRuleDetailResult"/>
</resultMap>
    
代码解释
这段XML代码定义了一个MyBatis的结果映射resultMap,其功能如下:
id为ChargeAccountRuleWithDetailResult,映射到Java类ChargeAccountRule。
继承了ChargeAccountRuleResult的映射规则。
定义了一个集合属性chargeAccountRuleDetailList,当数据库字段detail_id不为空时,将其映射为List类型,并使用ChargeAccountRuleDetailResult作为子项的映射规则。     
  • sql 查找了四个表进行数据的组合
xml 复制代码
<sql id="selectChargeAccountRuleWithDetailVo">
    select a.id,
           a.rule_name,
           a.create_time,
           a.update_time,
           a.create_by,
           a.update_by,
           b.id          as detail_id,
           b.rule_id,
           b.proportion,
           b.trade_id,
           b.create_time as detail_create_time,
           b.update_time as detail_update_time,
           b.create_by   as detail_create_by,
           b.update_by   as detail_update_by,
           c.trade_name,
           c.trade_type,
           c.user_id,
           d.USER_NAME   as user_name
    from charge_account_rule a
             left join charge_account_rule_detail b on b.rule_id = a.id
             left join charge_trade c on c.id = b.trade_id
             left join t_user d on c.user_id = d.id AND c.user_id IS NOT NULL

</sql>
  • 这里是方法的实现
xml 复制代码
<select id="selectChargeAccountRuleById" parameterType="Long" resultMap="ChargeAccountRuleWithDetailResult">
    <include refid="selectChargeAccountRuleWithDetailVo"/>
    where a.id = #{id}
</select>

ResultJson

json 复制代码
{
    "msg": "操作成功",
    "code": 200,
    "data": {
        "createBy": null,
        "createTime": "2024-11-27 16:24:30",
        "updateBy": null,
        "updateTime": null,
        "remark": null,
        "id": 5,
        "ruleName": "分账规则5",
        "chargeAccountRuleDetailList": [
            {
                "createBy": null,
                "createTime": "2024-11-26 14:19:43",
                "updateBy": null,
                "updateTime": null,
                "remark": null,
                "id": 7,
                "ruleId": "5",
                "proportion": 0.02,
                "tradeId": "1",
                "tradeName": "商户A",
                "tradeType": 1,
                "userId": null,
                "userName": null
            },
            {
                "createBy": null,
                "createTime": "2024-11-26 14:19:43",
                "updateBy": null,
                "updateTime": null,
                "remark": null,
                "id": 8,
                "ruleId": "5",
                "proportion": 0.03,
                "tradeId": "11",
                "tradeName": "kkk",
                "tradeType": 1,
                "userId": null,
                "userName": null
            },
            {
                "createBy": null,
                "createTime": "2024-11-26 14:19:43",
                "updateBy": null,
                "updateTime": null,
                "remark": null,
                "id": 9,
                "ruleId": "5",
                "proportion": 0.04,
                "tradeId": "13",
                "tradeName": "",
                "tradeType": 0,
                "userId": "318",
                "userName": null
            }
        ]
    }
}
相关推荐
uhakadotcom几秒前
Meta Horizon OS 开发工具:打造更好的 MR/VR 体验
javascript·后端·面试
程序员小刚14 分钟前
基于SpringBoot + Vue 的考勤管理系统
vue.js·spring boot·后端
星辰大海的精灵29 分钟前
SpringAI轻松构建MCP Client-Server架构
人工智能·后端·架构
uhakadotcom36 分钟前
Rust中的reqwest库:轻松实现HTTP请求
后端·面试·github
uhakadotcom1 小时前
Apache APISIX 简介与实践
后端·面试·github
Asthenia04121 小时前
面试官问“epoll的原理”,我该怎么回答?
后端
uhakadotcom1 小时前
Kong Gateway 简介与实践
后端·面试·github
潘多编程1 小时前
Spring Boot分布式项目实战:装饰模式的正确打开方式
spring boot·分布式·后端
uhakadotcom1 小时前
Apache SkyWalking:分布式系统的可观测性平台
后端·面试·github
uhakadotcom1 小时前
RocketMQ:解密阿里巴巴都在用的高性能消息队列
后端·面试·github