美文网首页WeLi的java学习Java学习笔记技术干货
从零搭建项目开发框架-09编写BaseDao及其他Dao

从零搭建项目开发框架-09编写BaseDao及其他Dao

作者: 孔垂云 | 来源:发表于2017-07-04 00:16 被阅读218次

    在编写dao之前,一定要编写一个BaseDao,封装一下原生的数据库处理方法。这个确实非常有用,比如做Hibernate的时候肯定会有一个BaseHibernateDao,里面封装了增删改查的各个方法,一般一个普通的dao只要继承BaseHibernateDao就不用写什么代码了。

    下面也秀一秀封装的BaseDao

    
    /**
     * 基础DAO,用于封装dao操作
     *
     * @author 孔垂云
     * @date 2017-06-13
     */
    @Component
    public class BaseDao<T, S> {
        @Autowired
        protected JdbcTemplate jdbcTemplate;
        @Autowired
        protected NamedParameterJdbcTemplate namedParameterJdbcTemplate;
    
        /**
         * 新增
         *
         * @param sql
         * @param t
         * @return
         */
        protected int insert(String sql, T t) {
            return namedParameterJdbcTemplate.update(sql, new BeanPropertySqlParameterSource(t));
        }
    
        /**
         * 新增并返回主键
         *
         * @param sql
         * @param t
         * @param pkField 主键字段
         * @return
         */
        protected int insertForId(String sql, T t, String pkField) {
            KeyHolder keyHolder = new GeneratedKeyHolder();
            int rc = namedParameterJdbcTemplate.update(sql, new BeanPropertySqlParameterSource(t), keyHolder, new String[]{pkField});
            if (rc > 0) {
                return keyHolder.getKey().intValue();
            } else {
                return 0;
            }
        }
    
        /**
         * 修改,参数为model类
         *
         * @param sql
         * @param t
         * @return
         */
        protected int update(String sql, T t) {
            return namedParameterJdbcTemplate.update(sql, new BeanPropertySqlParameterSource(t));
        }
    
        /**
         * 按照参数修改
         *
         * @param sql
         * @param objects
         * @return
         */
        protected int update(String sql, Object... objects) {
            return jdbcTemplate.update(sql, objects);
        }
    
        /**
         * 删除
         *
         * @param sql
         * @param objects
         * @return
         */
        protected int delete(String sql, Object... objects) {
            return jdbcTemplate.update(sql, objects);
        }
    
        /**
         * 根据参数获取model
         *
         * @param sql
         * @param objects
         * @return
         */
        protected T get(String sql, Object... objects) {
            List<T> list = jdbcTemplate.query(sql, objects, BeanPropertyRowMapper.newInstance(getClazz()));
            if (list.size() > 0)
                return list.get(0);
            else
                return null;
        }
    
        /**
         * 取得当前泛型的实际class名
         *
         * @return
         */
        private Class<T> getClazz() {
            return ((Class<T>) ((ParameterizedType) getClass()
                    .getGenericSuperclass()).getActualTypeArguments()[0]);
        }
    
        /**
         * 直接根据sql获取列表
         *
         * @param sql
         * @return
         */
        protected List<T> list(String sql) {
            List<T> list = jdbcTemplate.query(sql, BeanPropertyRowMapper.newInstance(getClazz()));
            return list;
        }
    
        /**
         * 根据sql和多参数获取列表
         *
         * @param sql
         * @param objects
         * @return
         */
        protected List<T> list(String sql, Object... objects) {
            List<T> list = jdbcTemplate.query(sql, objects, BeanPropertyRowMapper.newInstance(getClazz()));
            return list;
        }
    
        /**
         * 根据查询条件获取列表
         *
         * @param sql
         * @param s
         * @return
         */
        protected List<T> list(String sql, S s) {
            List<T> list = namedParameterJdbcTemplate.query(sql, new BeanPropertySqlParameterSource(s), BeanPropertyRowMapper.newInstance(getClazz()));
            return list;
        }
    
        /**
         * 查询总数,无参数
         *
         * @param sql
         * @return
         */
        protected int count(String sql) {
            return jdbcTemplate.queryForObject(sql, Integer.class);
        }
    
        /**
         * 查询总数,带参数
         *
         * @param sql
         * @return
         */
        protected int count(String sql, Object... objects) {
            return jdbcTemplate.queryForObject(sql, objects, Integer.class);
        }
    
        /**
         * 查询总数,带查询对象
         *
         * @param sql
         * @param s
         * @return
         */
        protected int count(String sql, S s) {
            return namedParameterJdbcTemplate.queryForObject(sql, new BeanPropertySqlParameterSource(s), Integer.class);
        }
    }
    

    这里面还需要引用一个namedParameterJdbcTemplate,所以需要在Spring的配置文件里面applicationContext.xml里面加入如下配置

    <!--注入namedParameterJdbcTemplate -->
        <bean id="namedParameterJdbcTemplate" class="org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate">
            <constructor-arg ref="dataSource"></constructor-arg>
        </bean>
    

    BaseDao的原理

    1、泛型类,BaseDao是一个泛型类,需要传入两个泛型对象<T S>,第一个是实体类,第二个是查询VO类,如果没有第二个,第二个也为实体类。
    2、该类里面添加或重写了insert、update、delete、get、list、count等方法,基本满足常见的数据库操作方法。

    SysUserDao.java

    @Repository
    public class SysUserDao extends BaseDao<SysUser, SysUserSearchVO> {
        /**
         * 新增用户
         * @param sysUser
         * @return
         */
        public int add(SysUser sysUser) {
            String sql = "insert into t_sys_user(username,password,randomcode,status,realname,mobile,created_at,created_by,role_id)";
            sql += " values(:username,:password,:randomcode,1,:realname,:mobile,sysdate,:createdBy,:roleId)";
            return insertForId(sql, sysUser, "id");
        }
    
        /**
         * 修改用户
         * @param sysUser
         * @return
         */
        public int update(SysUser sysUser) {
            String sql = "update t_sys_user set realname=:realname,role_id=:roleId,mobile=:mobile,last_modified_by=:lastModifiedBy,last_modified_at=sysdate where id=:id ";
            return update(sql, sysUser);
        }
    
    
        /**
         * 修改密码
         *
         * @param id
         * @param newPass
         * @param randowmcode
         * @return
         */
        public int updatePass(int id, String newPass, String randowmcode) {
            String sql = "update t_sys_user set password=?,randomcode=?  where id=? ";
            return update(sql, newPass, randowmcode, id);
        }
    
        /**
         * 修改个人信息,用户自己操作
         *
         * @param sysUser
         * @return
         */
        public int updateInfo(SysUser sysUser) {
            String sql = "update t_sys_user set realname=:realname,telephone=:telephone where id=:id";
            return update(sql, sysUser);
        }
    
        /**
         * 修改状态
         *
         * @param id
         * @param status
         * @return
         */
        public int updateStatus(int id, int status) {
            String sql = "update t_sys_user set status=?  where id=?";
            return update(sql, status, id);
        }
    
        /**
         * 删除用户
         * @param id
         * @return
         */
        public int delete(int id) {
            String sql = "delete from t_sys_user where id=?";
            return delete(sql, id);
        }
    
        public SysUser get(int id) {
            String sql = "select t.id,t.id,t.username,t.password,t.randomcode,t.status,t.realname,t.mobile,t.created_at,t.created_by,t.role_id,t.last_modified_by,t.last_modified_at from t_sys_user t where id=?";
            return get(sql, id);
        }
    
        /**
         * 根据username获取sysUser
         *
         * @param username
         * @return
         */
        public SysUser getByUsername(String username) {
            String sql = "select t.id,t.username,t.password,t.randomcode,t.status,t.realname,t.mobile,t.created_at,t.created_by,t.role_id,t.last_modified_by,t.last_modified_at,(select name from t_sys_role where id=role_id) roleName from t_sys_user t where username=?";
            return get(sql, username);
        }
    
        /**
         * 查询用户信息
         *
         * @param sysUserSearchVO
         * @return
         */
        public List<SysUser> list(SysUserSearchVO sysUserSearchVO) {
            String sql = "select t.id,t.username,t.password,t.randomcode,t.status,t.realname,t.mobile,t.created_at,t.created_by,t.role_id,t.last_modified_by,t.last_modified_at,(select name from t_sys_role where id=t.role_id) roleName  from t_sys_user t where 1=1 ";
            sql += createSearchSql(sysUserSearchVO);
            sql += " order by id asc";
            sql = PageUtil.createMysqlPageSql(sql, sysUserSearchVO.getPageIndex());
            return list(sql, sysUserSearchVO);
        }
    
        public List<SysUser> listAll() {
            String sql = "select t.id,t.username,t.password,t.randomcode,t.status,t.realname,t.mobile,t.created_at,t.created_by,t.role_id,t.last_modified_by,t.last_modified_at,(select name from t_sys_role where id=role_id) roleName  from t_sys_user t ";
            sql += " order by id asc";
            return list(sql);
        }
    
        /**
         * 查询用户总数
         *
         * @param sysUserSearchVO
         * @return
         */
        public int count(SysUserSearchVO sysUserSearchVO) {
            String sql = "select count(*) from t_sys_user where 1=1 ";
            sql += createSearchSql(sysUserSearchVO);
            return count(sql, sysUserSearchVO);
        }
    
        private String createSearchSql(SysUserSearchVO sysUserSearchVO) {
            String sql = "";
            if (StringUtil.isNotNullOrEmpty(sysUserSearchVO.getUsername())) {
                sql += " and username=:username";
            }
            if (StringUtil.isNotNullOrEmpty(sysUserSearchVO.getRealname())) {
                sql += " and realname like :realnameStr";
            }
            if (sysUserSearchVO.getRoleId() != null) {
                sql += " and role_id=:roleId";
            }
            if (sysUserSearchVO.getStatus() != null) {
                sql += " and status=:status";
            }
            return sql;
        }
    
        /**
         * 所有人员列表,查询日志使用
         *
         * @return
         */
        public List<ComboboxVO> listAllUser() {
            String sql = "select id value,username content from t_sys_user  order by id";
            return listCombobox(sql);
        }
    }
    
    

    说明几点

    1、public class SysUserDao extends BaseDao<SysUser, SysUserSearchVO>继承BaseDao
    2、在PageUtil.java这个类中有公共的Mysql分页方法,只需要写正常的查询语句即可,分页由公共方法来做
    3、整个Dao中基本都是sql语句了,所以要规范sql的写法
    4、在新增或修改时,数据库字段比如是created_at,实体字段是createdAt,这两个是怎么映射起来的呢?在org.springframework.jdbc.core.BeanPropertyRowMapper类中,spring提供了两种字段映射方法,如果是驼峰写法,可以根据大写的分隔,自动映射至下划线分隔的字段,比如实体字段是createdAt,既可以映射数据库字段createdAt,也可以created_at。
    5、编写dao时还用到了几个工具类,比如StringUtil.java里面有判断是否为空的方法。
    6、多条件查询sql的写法和mybatis的动态sql写法类似,都是判断该字段是否为空,不为空则拼查询语句。

    源码下载

    本阶段详细源码

    相关文章

      网友评论

      • 颜之有雾:我想起了controller,service,dao都是泛型的梗:joy:
      • CatalinaX:很棒~,小小的支持一下,期待后续!
        孔垂云:@CatalinaX 谢谢!这个系列很快会写完,差不多一周左右,一套完整的开发框架

      本文标题:从零搭建项目开发框架-09编写BaseDao及其他Dao

      本文链接:https://www.haomeiwen.com/subject/yiwocxtx.html