mybatis实现的curd
项目层次
总体项目结构如图所示
springboot实现的情况下,一般分为一下几层
(我按实际编写的层次来顺序书写
-
entity/pojo层
编写一些数据库表格中的名词,作为变量名
@data和@AllArgsConstructor是依赖包lombok的一个功能函数,通getter和setter -
dao层(文件类型:接口
控制层,通过该层去调用下面的resources的mapper层,实现对数据库的curd。
使用前面的功能函数@Repository表示是一个仓库,用于后面的Autowired。
-
mapper层
不知道这个是不是能明确定义为层,whatever,但是不可或缺
在孩层,我们需要在这里写下sql语句,是真正意义上的对数据库的操作
基本格式值得注意。
<?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="com.waterai.dao.IaEgcDikeDao"> ... </mapper>
在MyBatis映射文件中, 元素用于定义结果映射规则,将查询结果的列与Java对象的属性进行映射。 like this:
-
service层
常见的主要有接口文件和实现接口的类。
(简单的化,直接使用类,like 图中UserService
该层主要是调用dao层,就是在该层书写运作函数,返回的是controller想要的值。
该层必须逻辑清晰,主要业务函数就是在这里。@Service的装饰器。
-
controller层
调用service层的函数以实现。
该层也是总体的项目入口ServerApplication就是通过调用controller运作。
@RestController来调用和@RequestMapping来匹配路径
这应该也是最靠近前端的一层,返回的是前端要的值。
基本层次介绍就到这里结束,下面用(回顾)一个具体例子来实际操作一下。
具体例子
-
连接自己的数据库
在application中,连接属于自己的数据库信息,包括账号密码,数据库厂商名等
-
其他配置环境 pom.xml
-
然后按需编写自己的各层。
下面以数据库user信息为例子。
-
直接查看所有信息。
~在UserDao的接口文件中,写下该方法。
List<UserDTO> querySelectList(@Param("params") Map<String, Object> mapper);
~接着对应resources中,在UserDao.xml文件中
<select id="querySelectList" resultMap="userDTO"> SELECT id, name, pwd, create_time, update_time FROM test WHERE del_flag = '0' <if test="params.name != null and params.name != 'null' and params.name != ''"> AND name LIKE concat('%', #{params.name}, '%') </if> ORDER BY update_time DESC <if test="params.pagenum != 'null' and params.pagenum != '' and params.pagenum != null and params.pagesize != 'null' and params.pagesize != '' and params.pagesize != null "> limit CAST(${params.pagesize} AS INT) offset (CAST(${params.pagenum} AS INT) - 1) * CAST(${params.pagesize} AS INT) </if> </select>
在该文件中,我们实现了模糊查询以及对分页查询的实现。
~编写UserService文件,并在该文件中,我们实现了后续的导入导出功能,这个我们在后续会提到
PageData<UserDTO> all(Map<String, Object> params);
~ 编写UserServiceImpl.java文件,实现UserService文件中的方法。首先先@Autowired创建一个userDao;接着运用已经编写的服务类文件–Pagedata.(
后文我会给大家提供该文件信息,实现我们impl返回的函数信息。@Autowired private UserDao userDao; @Override public PageData<UserDTO> all(Map<String, Object> params) { List<UserDTO> dtos = userDao.querySelectList(params); int count = userDao.queryListCount(params); return new PageData<>(count, dtos); }
~准备编写UserController,先@Autowired一个serviceimpl对象,编写 业务逻辑实现要返回给前端的信息。
@Autowired private UserService userService; @PostMapping("all") @ApiOperation("分页查询所有用户")public Result<PageData<UserDTO>> all(@ApiIgnore @RequestParam Map<String, Object> params) { return new Result<PageData<UserDTO>>().ok(userService.all(params)); }
-
其他的增删改
基本业务逻辑类似,看一下基本的文件即可明白,值得注意的是因为这要进行对数据库信息的更改,所以在ServiceImpl文件中,实现接口文件的方法之前可以添加一句@Transactional(rollbackFor = Exception.class),这类似于sql语言中的rollback,确保当运行失败后,数据库不会出现脏读等事件。
-
补充提高:导入、导出功能。
这是这次项目中算比较耳目一新,让我学习到的知识点,我觉得还是可以在这里补充一下。
~首先项目负责人是先编写了一个服务包,在项目文件结构章如下。
-
!!!先写一下导出功能(相对导入较简单,泛型的思想
来看一下解释,只能说这好像是一种基本的写法??记住就行。
然后直接在controller文件中,使用该类,完成导出。
ps:注意在这里,Class<?> clazz要根据自身导出的表格数据来先新建你自己所要导出表格的文件信息。
差一张照片!
!!!导入功能的实现
相对于导出功能的只需将所选信息直接导出,导入功能则需要根据列表信息,判断每条信息是否跟表中原数据冲突,如主键已存在等,需要分类导入.
第一步:并编写一个接口ExcelImportService,便于后续每个表格都继承
java public interface ExcelImportService<T> { void batchSave(List<T> data); }
第二步:在各类的service接口文件extends ExcelImportService,然后在ServiceImpl文件中实现该方法。
实现思想:先定义两个Arraylist,因为本函数的参数为对于UserExcel的列表,所以根据列表中的不同数据对象,分类是否存在id(数据库设计和excel表的设计问题,区分成不同的列表集–haveId和NoID,在根据在dao层设计的importBatch*(有id,出现冲突后更改表中数据和importBatchNoId(无Id,直接添加除了id的其他信息,应该在这里,数据库表中是设置了自动增长功能*
UserDao中的importBatch和importBatchNoId如下图
第三步:编写UploadDataListener.java类,这个类我也不是很懂,必须懂!这个类是为了实现ReadListener,包含的三个实例变量:BATCH_COUNT
:表示批量要处理的最大条目数;cacheData
是数据;dao
表示调用的服务层。然后初始化,重写每次发生的invoke和完成事件后的doAfterAllAnalysed.相关解析:
现看一下该UploadDataListener文件截图,之后运用时候好像大体不变。除非业务逻辑的invoke要改变。
最后使用:在controller中,使用EasyExcel.read功能,实现导入功能。
其中精华就是:这一行代码:
java EasyExcel.read(file.getInputStream(),UserExcel.class, new UploadDataListener<>(userService, 200)).sheet().doRead();
总结:上述例子好多都是在本次项目中,根据项目负责任给的example来依葫芦画瓢实现了后续的其他表的相关功能。确实学到了很多,但是一个问题:这些功能函数等,是惊艳累计才能灵活运用是嘛?不然我甚至不知道相关库还有这种功能,害,果然还得多看。