mybatis动态sql一对多查询

在数据库设计中,一对多关系是非常多的,例如消息通知和附件,一个消息通知中往往会包含多个附件,这种情况下使用mybatis动态sql可以很方便的查询出来。

1、数据库设计

消息表:sys_message

CREATE TABLE `sys_message` (
  `id` varchar(40) COLLATE utf8mb4_unicode_ci NOT NULL,
  `title` varchar(200) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '标题',
  `content` mediumtext COLLATE utf8mb4_unicode_ci COMMENT '内容',
  `message_fk` varchar(40) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '附件fk'
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='消息管理';

附件表:sys_attachment

CREATE TABLE `sys_attachment` (
  `id` varchar(40) NOT NULL COMMENT '主键',
  `file_name` varchar(50) NOT NULL COMMENT '原文件名',
  `storing_name` varchar(100) NOT NULL COMMENT '存储文件名',
  `size` bigint(20) NOT NULL COMMENT '大小',
  `fk` varchar(40) NOT NULL COMMENT '业务主键',
  `suffix_type` tinyint(4) DEFAULT NULL COMMENT '类型(后缀)',
  `file_type` tinyint(4) DEFAULT '0' COMMENT '文件类型:0其他 1图片 2视频',
  `url` varchar(200) NOT NULL COMMENT '访问地址',
  `absolute_path` varchar(200) NOT NULL COMMENT '绝对路径',
  PRIMARY KEY (`id`)
)

一条消息对应多个附件,附件表中的 fk引用消息表的message_fk


2、实现

返回类型是Message对象,其中有一个 List fileList,存储附件信息。

public class SysMessage extends LaboratoryBaseModel<SysMessage> {
    private static final long serialVersionUID=1L;       
    
    @TableField("id")
    private String id;
    
    @TableField("title")
    private String title;
        
    @TableField("content")
    private String content;
        
        
    @TableField("message_fk")
    private String messageFk;
        

    @TableField(exist = false)
    private List<SysAttachment> fileList;
                
}

这种情况下,在动态sql的标签中,返回值只能使用resultMap属性接收:

 <select id="selectMessagePage" resultMap="sysMessageMap">
        SELECT
            *
        FROM
            sys_message a
select>

resultMap是一个外部结果映射关系的引用,描述了结果数据的映射关系,在resultMap中有一个 collection标签,分别是:

  • column:message表的message_fk,即一对多的一中被引用的字段名
  • property:SysMessage中fileList属性,属性名是fileList
  • javaType:SysMessage中fileList属性的对应的java类型Arraylist
  • ofType:javaType的数据类型SysAttachment
  • select:需要引用的select标签的名字,标签中。

    	<resultMap id="sysMessageMap" type="cn.xxx.model.SysMessage">
            <result property="id" column="id"/>
            <result property="title" column="title"/>
            <result property="content" column="content"/>
            <result property="messageFk" column="message_fk"/>
            <collection column="message_fk"
                        property="fileList"
                        javaType="Arraylist"
                        ofType="cn.yibiao163.laboratory.model.SysAttachment"
                        select="selectFileByFk">
            collection>
        resultMap>
    
    <select id="selectFileByFk" resultMap="cn.xxx.repository.SysAttachmentMapper.sysAttachmentMap">
            select * from sys_attachment where is_deleted = 0 and fk = #{message_fk}
    </select>