基于mysql Jdbctemplate 的上层封装,maven中央库可引用

  一直以来关于持久层框架选择的讨论都比较多,网上查了下比较,大致得出的结果:hibernate太繁,springjdbc太简, mybatis 刚好,可见如今选用mybatis的势头也越来越明显。毕竟mybatis有DAO模版,强大的代码生成工具,这些都是在做开发的时候很容易提高效率的。

  但我个人偏向喜欢用Jdbctemplate,Jdbctemplate运行期更高效、内嵌Spring框架中、支持基于AOP的声明式事务,并且方便扩展,但是相信使用过Jdbctemplate的朋友应该知道,需要写一大堆的Rowmapper,而且开发完成后,由于sql是手写的,很可能会出现低级错误,这些都是Jdbctemplate的弊端,稍微有心的朋友这里肯定会选择自己封装一次。

  切入正题,现在我分享一下自己实现的基于mysql Jdbctemplate 的上层封装,费了九牛二虎之力,我将自己的代码上传到了maven中央库。

<dependency>
	<groupId>com.github.11dong</groupId>
	<artifactId>codes-common</artifactId>
	<version>1.0.1</version>
</dependency>

  这里的实现我不做详解,下面讲讲如何使用。

  项目若使用此jar包无需做过多配置,项目数据源配置按正常的Jdbctemplate配置即可:

<bean name="dataSource" class="com.alibaba.druid.pool.DruidDataSource"
		init-method="init" destroy-method="close">
		<property name="driverClassName" value="${jdbc.driver}" />
		<property name="url" value="${jdbc.url}" />
		<property name="username" value="${jdbc.username}" />
		<property name="password" value="${jdbc.password}" />

		<!-- 初始化连接大小 -->
		<property name="initialSize" value="20" />
		<!-- 连接池最大使用连接数量 -->
		<property name="maxActive" value="100" />
		<!-- 连接池最小空闲 -->
		<property name="minIdle" value="20" />
		<!-- 获取连接最大等待时间 -->
		<property name="maxWait" value="60000" />
		<property name="poolPreparedStatements" value="true" />
		<property name="maxPoolPreparedStatementPerConnectionSize"
			value="33" />
		<!-- 用来检测有效sql <property name="validationQuery" value="${validationQuery}" 
			/> <property name="testOnBorrow" value="false" /> <property name="testOnReturn" 
			value="false" /> <property name="testWhileIdle" value="true" /> -->
		<!-- 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒 -->
		<property name="timeBetweenEvictionRunsMillis" value="60000" />
		<!-- 配置一个连接在池中最小生存的时间,单位是毫秒 -->
		<property name="minEvictableIdleTimeMillis" value="25200000" />
		<!-- 打开removeAbandoned功能 -->
		<property name="removeAbandoned" value="true" />
		<!-- 1800秒,也就是30分钟 -->
		<property name="removeAbandonedTimeout" value="1800" />
		<!-- 关闭abanded连接时输出错误日志 -->
		<property name="logAbandoned" value="true" />
		<!-- 监控数据库 -->
		<property name="filters" value="mergeStat" />
	</bean>
	<!-- 数据源 -->
	<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
		<property name="dataSource" ref="dataSource" />
	</bean>
	
</beans>  	
  实体类的创建:

package cc.dto;

import java.io.Serializable;
import java.util.Date;

import com.zd.jdbcutil.DbColumn;
import com.zd.jdbcutil.DbColumn.ColumType;
import com.zd.jdbcutil.DbTable;

@DbTable("sys_user")
public class UserDto implements Serializable {
    /**
     * 用户信息
     */
    private static final long serialVersionUID = 4100310788962936416L;

    @DbColumn(key = true)
    private String id;
    
    @DbColumn("username") //与数据库字段不同需要注解说明
    private String userName;
    
    private Date created;
    private Integer state;
    private Integer sex;
    
    //-----非本数据库的额外字段------
    @DbColumn(type = ColumType.QUERY_ONLY) //只允许查询不允许写入,如 left join 时使用
    private String roleid;
    
    @DbColumn(type = ColumType.IGNORE) //直接忽略,不查不写
    private String flag;
    
    

    public String getRoleid() {
        return roleid;
    }

    public void setRoleid(String roleid) {
        this.roleid = roleid;
    }

    public String getFlag() {
        return flag;
    }

    public void setFlag(String flag) {
        this.flag = flag;
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getUserName() {
        return userName;
    }

    public void setUserName(String userName) {
        this.userName = userName;
    }

    public Date getCreated() {
        return created;
    }

    public void setCreated(Date created) {
        this.created = created;
    }

    public Integer getState() {
        return state;
    }

    public void setState(Integer state) {
        this.state = state;
    }

    public Integer getSex() {
        return sex;
    }

    public void setSex(Integer sex) {
        this.sex = sex;
    }

}


  这里的实体类类名上需要声明该类对应的数据库名称,数据库字段名称与实体类名称一一对应,区分大小写,若有字段不对应需要注解说明(userName),如果有非次表内的数据也需要注解说明它的使用情况。

  建好实体类后,接下来的工作就非常简单了。

  持久层:

  1、需要创建一个自己的BaseDao来继承工具包里的BaseDao,主要提供JdbcTemplate对象,若项目有多个库,可以构建多个MyBaseDaoImpl来实现,只需声明jdbcTemplate注解名,相互无干扰。

package cc.dao.impl;

import java.io.Serializable;

import javax.annotation.Resource;

import org.springframework.jdbc.core.JdbcTemplate;

import com.zd.jdbcutil.BaseDaoImpl;


public abstract class MyBaseDaoImpl<T extends Serializable> extends BaseDaoImpl<T> {
	@Resource(name = "jdbcTemplate")//以配置文件名称为准
	private JdbcTemplate jdbcTemplate;

	public JdbcTemplate getJdbcTemplate() {
		return jdbcTemplate;
	}

}

  2、单表的接口与实现类,无需任何方法

package cc.dao;

import com.zd.jdbcutil.IBaseDao;

import cc.dto.UserDto;

public interface IUserDao extends IBaseDao<UserDto> {

}

package cc.dao.impl;

import org.springframework.stereotype.Repository;

import cc.dao.IUserDao;
import cc.dto.UserDto;

@Repository
public class UserDaoImpl extends MyBaseDaoImpl<UserDto> implements IUserDao {

}

  业务层接口与实现:

 

package cc.service;

import com.zd.jdbcutil.IBaseService;

import cc.dto.UserDto;

public interface IUserDataService extends IBaseService<UserDto> {

}

package cc.service.impl;

import java.util.Map;

import org.springframework.stereotype.Service;

import com.zd.jdbcutil.BaseServiceImpl;
import cc.dto.UserDto;
import cc.service.IUserDataService;

@Service
public class UserDataServiceImpl extends BaseServiceImpl<UserDto> implements IUserDataService {

	public Map<String, Object> genMapCondition(UserDto obj) {
		// TODO Auto-generated method stub
		return null;
	}

}

这里的map是提供查询的筛选条件

--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------


以上创建完后就可以编写测试接口了:

package cc.controller;

import java.util.Date;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

import com.zd.jdbcutil.ConditionBuilder;

import cc.dto.UserDto;
import cc.service.IUserDataService;

@Controller
@RequestMapping("/test")
public class TestController {

	@Autowired
	private IUserDataService service;

	/**
	 * 插入
	 * 
	 * @return
	 */
	@RequestMapping("/insert.do")
	@ResponseBody
	public Object insert() {
		UserDto user = new UserDto();
		user.setId("0dce718273b54d9ea635adaacb6642ea");
		user.setUserName("周杰伦");
		user.setCreated(new Date());
		user.setSex(0);
		user.setState(1);
		return service.insert(user);
	}

	/**
	 * 修改
	 * 
	 * @return
	 */
	@RequestMapping("/update.do")
	@ResponseBody
	public Object update() {
		UserDto user = new UserDto();
		user.setId("0dce718273b54d9ea635adaacb6642ea");
		user.setUserName("林俊杰");
		return service.updateById(user);
	}

	/**
	 * 查询
	 * 
	 * @return
	 */
	@RequestMapping("/query.do")
	@ResponseBody
	public Object query() {
		return service.query(new ConditionBuilder.Builder().equalTo("username", "周杰伦").build());
	}

	/**
	 * 修改
	 * 
	 * @return
	 */
	@RequestMapping("/delete.do")
	@ResponseBody
	public Object delete() {
		return service.deleteById("0dce718273b54d9ea635adaacb6642ea");
	}
}
  这里如果按照我写的方式来继承工具包里的接口与实现,开发就会变得很简单。

  相信朋友会有疑问,如果我要多表联查,或者复杂条件的话,怎么实现,我这里提供了两个工具类(ConditionBuilder,JoinQuery)与对应接口,可以实现,具体怎么做,可以查看我的源代码


 




 

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 6
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值