mybatis的工具类

mybatis的工具类

  1.SQL:使用JDBC拼接SQL的开发中,空格操作和逗号是噩梦.使用sql类生成sql语句

  源码实现:SQL类继承自AbstractSQL。AbstractSQL:SQL工具类所有的功能都由AbstractSQL类实现。这个类的作用就是拼接sql语句

public class SQL extends AbstractSQL<SQL> {

  @Override
  public SQL getSelf() {
    return this;
  }

}

SQLStatement内部类: SqlStatementType判断sql的类型
            sqlCause:进行sql语句拼接
AbstractSQL重写sql.toString方法,用来拼接sql     
  优点:避免忘了空格或者逗号
可以方便的在java代码中拼接动态sql语句     

  2.ScriptRunner执行脚本

    a.作用:读取文件中的sql并执行

    b.代码演示:  

@Test
    public void testScriptRunner() {
        try {
            Connection connection = DriverManager.getConnection("jdbc:hsqldb:mem:mybatis",
                    "sa", "");
            ScriptRunner scriptRunner = new ScriptRunner(connection);
            scriptRunner.runScript(Resources.getResourceAsReader("create-table.sql"));
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

public void runScript(Reader reader) {
  // 设置事务是否自动提交
  setAutoCommit();
  try {
    // 是否一次性批量执行脚本文件中的所有SQL语句
    if (sendFullScript) {
      // 调用executeFullScript()方法一次性执行脚本文件中的所有SQL语句
      executeFullScript(reader);
    } else {
      // 调用executeLineByLine()方法逐条执行脚本中的SQL语句
      executeLineByLine(reader);
    }
  } finally {
    rollbackConnection();
  }
}
View Code

3.使用SQLRunner操作数据库

MyBatis中提供了一个非常实用的、用于操作数据库的SqlRunner工具类,该类对JDBC做了很好的封装,结合SQL工具类,能够很方便地通过Java代码执行SQL语句并检索SQL执行结果。
SqlRunner类提供了几个操作数据库的方法,分别说明如下。

● SqlRunner#closeConnection():用于关闭Connection对象。
● SqlRunner#selectOne(String sql, Object.. args):执行SELECT语句,SQL语句中可以使用占位符,如果SQL中包含占位符,则可变参数用于为参数占位符赋值,该方法只返回一条记录。若查询结果行数不等于一,则会抛出SQL Exception异常。
● SqlRunnen#selectAll(String sq|, Object.. args): 该方法和selectOne()方法的作用相同,只不过该方法可以返回多条记录,方法返回值是一个List对象, List中包含 多个Map对象,每个Map对象对应数据库中的一行记录。
● SqlRunner#insert(String sql, Object.. args):执行一条INSERT语句,插入一条记录。
● SqlRunnen#update(String sql, Object.. args):更新若干条记录。
● SqlRunner#delete(String sql, Object.. args):删除若干条记录。
● SqlRunner#run(String sq):执行任意一条SQL语句, 最好为DDL语句。

操作案例:

public class SqlRunnerExample {

    Connection connection = null;

    @Before
    public void initTable() throws SQLException, IOException {
        connection = DriverManager.getConnection("jdbc:hsqldb:mem:mybatis",
                "sa", "");
        ScriptRunner scriptRunner = new ScriptRunner(connection);
        scriptRunner.setLogWriter(null);
        scriptRunner.runScript(Resources.getResourceAsReader("create-table.sql"));
        scriptRunner.runScript(Resources.getResourceAsReader("init-data.sql"));
    }

    @Test
    public void testSelectOne() throws SQLException {
        SqlRunner sqlRunner = new SqlRunner(connection);
        String qryUserSql = new SQL() {{
            SELECT("*");
            FROM("user");
            WHERE("id = ?");
        }}.toString();
        Map<String, Object> resultMap = sqlRunner.selectOne(qryUserSql, Integer.valueOf(1));
        System.out.println(JSON.toJSONString(resultMap));
    }

    @Test
    public void testDelete() throws SQLException {
        SqlRunner sqlRunner = new SqlRunner(connection);
        String deleteUserSql = new SQL() {{
            DELETE_FROM("user");
            WHERE("id = ?");
        }}.toString();
        sqlRunner.delete(deleteUserSql, Integer.valueOf(1));
    }

    @Test
    public void testUpdate() throws SQLException {
        SqlRunner sqlRunner = new SqlRunner(connection);
        String updateUserSql = new SQL() {{
            UPDATE("user");
            SET("nick_name = ?");
            WHERE("id = ?");
        }}.toString();
        sqlRunner.update(updateUserSql, "Jane", Integer.valueOf(1));
    }

    @Test
    public void testInsert() throws SQLException {
        SqlRunner sqlRunner = new SqlRunner(connection);
        String insertUserSql = new SQL() {{
            INSERT_INTO("user");
            INTO_COLUMNS("create_time,name,password,phone,nick_name");
            INTO_VALUES("?,?,?,?,?");
        }}.toString();
        String createTime = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
        sqlRunner.insert(insertUserSql, createTime, "Jane", "test", "18700000000", "J");
    }

    @After
    public void closeConnection() {
        IOUtils.closeQuietly(connection);
    }


}
View Code

 4.MetaObject工具类优雅的获取和设置对象的属性值

 5.MetaClass工具类:作用:获取类相关信息

   代码相关案例:

public class MetaClassExample {

    @Data
    @AllArgsConstructor
    private static class Order {
        String orderNo;
        String goodsName;
    }

    @Test
    public void testMetaClass() {
        MetaClass metaClass = MetaClass.forClass(Order.class, new DefaultReflectorFactory());
        // 获取所有有Getter方法的属性名
        String[] getterNames = metaClass.getGetterNames();
        System.out.println(JSON.toJSONString(getterNames));
        // 是否有默认构造方法
        System.out.println("是否有默认构造方法:" + metaClass.hasDefaultConstructor());
        // 某属性是否有对应的Getter/Setter方法
        System.out.println("orderNo属性是否有对应的Getter方法:" + metaClass.hasGetter("orderNo"));
        System.out.println("orderNo属性是否有对应的Setter方法:" + metaClass.hasSetter("orderNo"));

        System.out.println("orderNo属性类型:" + metaClass.getGetterType("orderNo"));

        // 获取属性Getter方法
        Invoker invoker = metaClass.getGetInvoker("orderNo");
        try {
            // 通过Invoker对象调用Getter方法获取属性值
            Object orderNo = invoker.invoke(new Order("order20171024010248", "《Mybatis源码深度解析》图书"), null);
            System.out.println(orderNo);
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        } catch (InvocationTargetException e) {
            e.printStackTrace();
        }

    }
}
View Code

6.ObjectFactory

7.ProxyFactory

  ProxyFactory是MyBatis中的代理工厂,主要用于创建动态代理对象,ProxyFactory接口有两个不同的实现,分别为CglibProxyFactory和JavassistProxyFactory。从实现类的名称可以看出,MyBatis支持两种动态代理策略,分别为Cglib和Javassist动态代理。ProxyFactory主要用于实现MyBatis的懒加载功能。当开启懒加载后,MyBatis创建Mapper映射结果对象后,会通过ProxyFactory创建映射结果对象的代理对象。当我们调用代理对象的Getter方法获取数据时,会执行CglibProxyFactory或JavassistProxyFactory中定义的拦截逻辑,然后执行一-次额外的查询。

原文地址:https://www.cnblogs.com/yingxiaocao/p/13671518.html