文档章节

对SpringJDBC的简单扩展

Oneself丶x
 Oneself丶x
发布于 2015/12/22 21:26
字数 699
阅读 111
收藏 9
点赞 0
评论 0
public <T> int save(T t) {
    return batchSave(Collections.singletonList(t));
}

public <T> int batchSave(List<T> list) {
    BeanBatchSavePSCC<T> pscc = new BeanBatchSavePSCC<>(list);
    return getJdbcTemplate().execute(pscc, pscc);
}

public <T> int update(T t) {
    return batchUpdate(Collections.singletonList(t));
}

protected <T> int update(T t, String where, Object... values) {
    BeanBatchUpdatePSCC<T> pscc = new BeanBatchUpdatePSCC<>(Collections.singletonList(t), where, values);
    return getJdbcTemplate().execute(pscc, pscc);
}

public <T> int batchUpdate(List<T> list) {
    BeanBatchUpdatePSCC<T> pscc = new BeanBatchUpdatePSCC<>(list);
    return getJdbcTemplate().execute(pscc, pscc);
}

public <T> List<T> list(Class clazz){
    return getJdbcTemplate().query("select * from table", BeanRowMapper.createRowMapper(clazz));
}

public class BeanBatchSavePSCC<T> implements PreparedStatementCreator, PreparedStatementCallback<Integer> {

    private Class clazz;
    private PropertyDescriptor[] pds;
    private Map<Integer, Method> methodMap;
    private List<T> list;
    private Method methodSetterPK;

    public BeanBatchSavePSCC(List<T> list) {
        this.list = list;
        if (list == null || list.isEmpty()) {
            throw new NullPointerException("");
        }
        this.clazz = list.get(0).getClass();
        methodMap = new HashMap<>();
        pds = BeanUtils.getPropertyDescriptors(clazz);
    }

    @Override
    public PreparedStatement createPreparedStatement(Connection con) throws SQLException {
        PreparedStatement statement = con.prepareStatement(getInsertSql(), Statement.RETURN_GENERATED_KEYS);
        for (T t : list) {
            for (Map.Entry<Integer, Method> entry : methodMap.entrySet()) {
                Object value = ReflectionUtils.invokeMethod(entry.getValue(), t);
                statement.setObject(entry.getKey(), value);
            }
            statement.addBatch();
        }
        statement.executeBatch();
        return statement;
    }

    /**
     * 返回更新数量
     *
     * @param statement
     * @return
     * @throws SQLException
     * @throws DataAccessException
     */
    @Override
    public Integer doInPreparedStatement(PreparedStatement statement) throws SQLException, DataAccessException {
        ResultSet rs = statement.getGeneratedKeys();
        int index = 0;
        while (rs.next()) {
            Object id = rs.getObject(1);
            ReflectionUtils.invokeMethod(methodSetterPK, list.get(index), id);
            index++;
        }
        JdbcUtils.closeResultSet(rs);
        return list.size();
    }

    protected String getInsertSql() {
        StringBuilder sql = new StringBuilder("INSERT INTO ");
        sql.append(FieldUtils.underscoreName(clazz.getName()));
        sql.append("(");
        int index = 1;
        for (PropertyDescriptor pd : pds) {
            String name = pd.getName();
            if (!name.equals("class")) {
                Method method = pd.getReadMethod();
                if (method.getAnnotation(PK.class) != null && methodSetterPK == null) {
                    methodSetterPK = pd.getWriteMethod();
                }
                methodMap.put(index, method);
                sql.append("`").append(FieldUtils.underscoreName(name)).append("`,");
                index++;
            }
        }
        sql.deleteCharAt(sql.lastIndexOf(",")).append(")");
        sql.append(" VALUES ").append("(");
        for (int i = 1; i < index; i++) {
            sql.append("?,");
        }
        sql.deleteCharAt(sql.lastIndexOf(",")).append(");");
        System.out.println(sql.toString());
        return sql.toString();
    }
}

public class BeanBatchUpdatePSCC<T> implements PreparedStatementCreator, PreparedStatementCallback<Integer> {

    private Class clazz;
    private PropertyDescriptor[] pds;
    private Map<Integer, Method> methodMap;
    private List<T> list;
    private Method pkReadMethod;
    private String where;
    private Object[] values;

    public BeanBatchUpdatePSCC(List<T> list) {
        this.list = list;
        init();
    }

    public BeanBatchUpdatePSCC(List<T> list, String where, Object... values) {
        this.list = list;
        this.where = where;
        this.values = values;
        init();
    }

    private void init() {
        if (list == null || list.isEmpty()) {
            throw new NullPointerException("");
        }
        this.clazz = list.get(0).getClass();
        methodMap = new HashMap<>();
        pds = BeanUtils.getPropertyDescriptors(clazz);
    }

    @Override
    public PreparedStatement createPreparedStatement(Connection con) throws SQLException {
        String sql = getUpdateSql();
        PreparedStatement statement = con.prepareStatement(sql);
        for (T t : list) {
            int index = 1;
            for (Map.Entry<Integer, Method> entry : methodMap.entrySet()) {
                Object value = ReflectionUtils.invokeMethod(entry.getValue(), t);
                statement.setObject(entry.getKey(), value);
                index ++;
            }
            if (where != null) {
                for (Object value : values) {
                    statement.setObject(index, value);
                    index++;
                }
            } else if (pkReadMethod != null) {
                Object value = ReflectionUtils.invokeMethod(pkReadMethod, t);
                statement.setObject(methodMap.size() + 1, value);
            }
            statement.addBatch();
        }
        statement.executeBatch();
        return statement;
    }

    /**
     * 返回更新数量
     *
     * @param statement
     * @return
     * @throws SQLException
     * @throws DataAccessException
     */
    @Override
    public Integer doInPreparedStatement(PreparedStatement statement) throws SQLException, DataAccessException {
        return list.size();
    }

    protected String getUpdateSql() {
        StringBuilder sql = new StringBuilder("UPDATE ");
        sql.append(FieldUtils.underscoreName(clazz.getName()));
        sql.append(" SET ");
        int index = 1;
        String pkColumn = null;
        for (PropertyDescriptor pd : pds) {
            String name = pd.getName();
            if (!name.equals("class")) {
                Method method = pd.getReadMethod();
                if (method.getAnnotation(PK.class) != null && pkColumn == null) {
                    pkColumn = FieldUtils.underscoreName(name);
                    pkReadMethod = method;
                    continue;
                }
                methodMap.put(index, method);
                sql.append("`").append(FieldUtils.underscoreName(name)).append("`=?,");
                index++;
            }
        }
        sql.deleteCharAt(sql.lastIndexOf(","));
        if (where != null) {
            sql.append(" WHERE ").append(where).append(";");
        } else if (pkColumn != null) {
            sql.append(" WHERE `").append(pkColumn).append("`=?;");
        } else {
            throw new NullPointerException("");
        }
        System.out.println(sql.toString());
        return sql.toString();
    }
}

//用户查询后转换成pojo
public class BeanRowMapper extends BeanPropertyRowMapper {

    public BeanRowMapper(Class clazz){
        super(clazz);
    }

    /**
     * java属性和数据库字段对应方法
     *
     * @param name
     * @return
     */
    @Override
    protected String underscoreName(String name) {
        return super.underscoreName(name);
    }

    public static BeanRowMapper createRowMapper(Class clazz) {
        return new BeanRowMapper(clazz);
    }
}

public class FieldUtils {

    public static String underscoreName(String name) {
        if (!StringUtils.hasLength(name)) {
            return "";
        }
        name = name.substring(name.lastIndexOf(".") + 1);
        StringBuilder result = new StringBuilder();
        result.append(name.substring(0, 1).toLowerCase(Locale.US));
        for (int i = 1; i < name.length(); i++) {
            String s = name.substring(i, i + 1);
            String slc = s.toLowerCase(Locale.US);
            if (!s.equals(slc)) {
                result.append("_").append(slc);
            } else {
                result.append(s);
            }
        }
        return result.toString();
    }

}


© 著作权归作者所有

Oneself丶x
粉丝 34
博文 22
码字总数 8139
作品 2
海淀
高级程序员
关于ORM选型问题,分享下我对spring jdbc的使用经验

由于不太喜欢hibernate和mybatis,更多使用spring jdbc来开发,针对spring jdbc一些不便捷的地方,做了写整合,写了sborm,具体可以看项目介绍。 osc项目地址:http://www.oschina.net/p/sb...

franticwind ⋅ 2015/03/30 ⋅ 16

SpringJDBC

Spring的JDBC框架 Spring JDBC提供了一套JDBC抽象框架,用于简化JDBC开发。 Spring主要提供JDBC模板方式、关系数据库对象化方式、SimpleJdbc方式、事务管理来简化JDBC编程 Spring提供了3个模...

宛珩 ⋅ 2016/07/20 ⋅ 0

基于 Spring-JDBC 的 ORM 简单封装--zd-web-utils

一直以来关于持久层框架选择的讨论都比较多,网上查了下比较,大致得出的结果:hibernate太繁,springjdbc太简, mybatis 刚好,可见如今选用mybatis的势头也越来越明显。毕竟mybatis有DAO模版...

我是一只鱼_ ⋅ 2017/07/25 ⋅ 4

SpringJDBC可以单独使用吗?

@苗哥 你好,想跟你请教个问题: 我现在在做一个应用,需要用到数据库,我之前使用过spring和springJDBC,然后感觉springJDBC实在是太方便了 - - 但是现在感觉无法熟练驾驭Spring,所以不打算...

Timco ⋅ 2014/04/24 ⋅ 9

求springjdbc封装

最近了解下springjdbc 谁有好的springjdbc封装分享下谢谢

jfork ⋅ 2012/05/28 ⋅ 1

Snaker 2.0.0 发布,Java轻量级工作流引擎

Snaker是一个基于Java的开源工作流引擎,适用于企业应用中常见的业务流程。本着轻量、简单、灵巧理念设计,定位于简单集成,多环境支持 轻量:核心代码行数大约7000行,强大的扩展性,支持Spr...

Dead_knight ⋅ 2014/07/21 ⋅ 31

spring配置中的p标签

Spring2.0中还有一个非常实用的解析器,SimplePropertyNamespaceHandle,若配置文件中引用http://www.springframework.org/schema/p命令空间,则将会使用SimplePropertyNamespaceHandle来处理...

shengguimin ⋅ 2015/01/16 ⋅ 0

工作流引擎--Snaker

Snaker是一个基于Java的开源工作流引擎,适用于企业应用中常见的业务流程。本着轻量、简单、灵巧理念设计,定位于简单集成,多环境支持 轻量: 核心代码行数大约7000行,强大的扩展性,支持S...

Dead_knight ⋅ 2013/11/21 ⋅ 10

对 DAO 框架的初步构思

对 DAO 框架的初步构思 基础: 内置支持JDBC、Spring JDBC和MyBatis数据库访问 -- 抽象提供一致的使用接口 默认三种DAO代理对象访,支持XML动态配置 不依赖Spring 升级: 插件式连接池 插件式...

泥沙砖瓦浆木匠 ⋅ 2016/04/05 ⋅ 1

基于SpringJdbc的泛型Dao

使用的Spring是3.1版本,不是3.0版本。两者还是有区别的,其中一点就是:SimpleJdbcTemplate在3.1版本被标记为过时了,而SimpleJdbcTemplate的一些方法,被JdbcTemplate吸收了。所以,个人推荐...

executor ⋅ 2014/07/20 ⋅ 0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

CENTOS7防火墙命令记录

安装Firewall命令: yum install firewalld firewalld-config Firewall开启常见端口命令: firewall-cmd --zone=public --add-port=80/tcp --permanent firewall-cmd --zone=public --add-po......

cavion ⋅ 今天 ⋅ 0

【C++】【STL】利用chromo来测量程序运行时间与日志时间打印精确到微秒

直接上代码吧,没啥好说的。头疼。 #include <iostream>#include <string>#include <ctime>#include <sstream>#include <iomanip>#include <thread>#include <chrono>using ......

muqiusangyang ⋅ 今天 ⋅ 0

Mac环境下svn的使用

在Windows环境中,我们一般使用TortoiseSVN来搭建svn环境。在Mac环境下,由于Mac自带了svn的服务器端和客户端功能,所以我们可以在不装任何第三方软件的前提下使用svn功能,不过还需做一下简...

故久呵呵 ⋅ 今天 ⋅ 0

破解公司回应苹果“USB限制模式”:已攻破

本周四,苹果发表声明称 iOS 中加入了一项名为“USB 限制模式”的功能,可以防止 iPhone 在连接其他设备的时候被破解,并且强调这一功能并不是针对 FBI 等执法部门,为的是保护用户数据安全。...

六库科技 ⋅ 今天 ⋅ 0

MyBtais整合Spring Boot整合,TypeHandler对枚举类(enum)处理

概要 问题描述 我想用枚举类来表示用户当前状态,枚举类由 code 和 msg 组成,但我只想把 code 保存到数据库,查询处理,能知道用户当前状态,这应该怎么做呢?在 Spring 整合MyBatis 的时候...

Wenyi_Feng ⋅ 今天 ⋅ 0

synchronized与Lock的区别

# <center>王梦龙的读书笔记第一篇</center> ## <center>-synchronized与Lock的区别</centre> ###一、从使用场景来说 + synchronized 是能够注释代码块、类、方法但是它的加锁是和解锁使用一......

我不想加班 ⋅ 今天 ⋅ 0

VConsole的使用

手机端控制台打印输出,方便bug的排查。 首先需要引入vconsole.min.js 文件,然后在文件中创造实例。就能直接使用了。 var vConsole = new VConsole(); vConsole的文件地址...

大美琴 ⋅ 今天 ⋅ 0

Java NIO之字符集

1 字符集和编解码的概念 首先,解释一下什么是字符集。顾名思义,就是字符的集合。它的初衷是把现实世界的符号映射为计算机可以理解的字节。比如我创造一个字符集,叫做sex字符集,就包含两个...

士别三日 ⋅ 今天 ⋅ 0

Spring Bean基础

1、Bean之间引用 <!--如果Bean配置在同一个XML文件中,使用local引用--><ref bean="someBean"/><!--如果Bean配置在不同的XML文件中,使用ref引用--><ref local="someBean"/> 其实两种......

霍淇滨 ⋅ 今天 ⋅ 0

05、基于Consul+Upsync+Nginx实现动态负载均衡

1、Consul环境搭建 下载consul_0.7.5_linux_amd64.zip到/usr/local/src目录 cd /usr/local/srcwget https://releases.hashicorp.com/consul/0.7.5/consul_0.7.5_linux_amd64.zip 解压consu......

北岩 ⋅ 今天 ⋅ 0

没有更多内容

加载失败,请刷新页面

加载更多

下一页

返回顶部
顶部