-
mybatis的拦截器实现分页(动态代理) 拦截sql语句来实现分页 1.拦截什么样的对象(以page作为参数传入;page对象) 2.拦截对象什么行为 3.什么时候拦截 (在prepareStatement的时候拦截) (源码) 1.RoutingStatementHandler 2.通过RoutingStatementHandler对象的属性delegate找到statement实现类BaseStatementHandler 3.通过BaseStatementHandler类的反射得到对象的MappedStatement对象 4.通过MappedStatement的属性getID得到配置文件sql语句的ID 5.通过BaseStatementHandler属性的到原始sql语句 6.拼接分页sql( 1.需要查询总数的sql 2.通过拦截Connection对象得到PrepareStatement对象 3.得到对应的参数 4.把参数设到prepareStatement对象里的?(该?号在配置文件以#{}形式存在,mybatis会把它转为?号) 5.执行噶sql语句 6.得到总数 ) 7.把属性值为新的sql查看全部
-
mybatis获取statement其实是在statementHandler中,这是一个处理接口,有个prepare方法,返回Statement,这个方法是在BaseStatementHandler中实现的,statement是在instantiateStatement这个方法中获取的,这个方法是一个抽象方法,看它的PrepareStatementHandler实现,在这里边看到了connection.prepareStatement(sql,PreparedStatement.),也就是和JDBC类似的代码了,这就是分页拦截器要拦截的位置了。如何实现拦截呢?mybatis提供了相应的注解:@Intercept({@Signnature(type=StatementHandler.class),method=“prepare”,args={Connection.class}}) 1.type指向要连接的接口class,这里指向StatementHandler.class 2.Method指向要拦截的方法,这里是prepare 3.args[]拦截的方法的参数类型,这里是Connection.class 这样就准确描述了要拦截StatementHandler接口下的prepare方法。目标确定,接下来就可以做手脚了,在PrepareStatementHandler拿到sql语句之前将这个sql语句改装成我们的分页sql,然后在塞回去,让程序继续执行,这样就成功了。 实现拦截器需要实现三个方法: 1.intercept(Invocation invacation) 2.plugin(Object target)方法参数就是被拦截的对象target,返回的就是满足条件的代理类,Plugin.wrap(target,this):this也就是自定义拦截器实例,通过获取注解得到要拦截的类型,比较target的类型与this获取的要拦截的类型是不是一致,如果满足条件就获取代理对象,并执行intercept方法,没有获取代理对象的将直接返回,不会经过intercept方法。 3.setProperties(Properties properties)查看全部
-
过早过迟的拦截都不合适。所以在PreparedStatement pstmt=conn.prepareStatement(sql.toString());之前拦截即可(把SQL语句处理再放进去提交); 通过拦截器实现分页的思路:在获取sql语句前拦截。查看全部
-
前端校验等于没有校验,为了保证安全,最好后端做校验。查看全部
-
@SQL语句里的limit使用方法 SELECT * FROM table LIMIT [offset,] rows | rows OFFSET offset 在我们使用查询语句的时候,经常要返回前几条或者中间某几行数据,这个时候怎么办呢?不用担心,mysql已经为我们提供了上面这样一个功能。 LIMIT 子句可以被用于强制 SELECT 语句返回指定的记录数。LIMIT 接受一个或两个数字参数。参数必须是一个整数常量。如果给定两个参数,第一个参数指定第一个返回记录行的偏移量,第二个参数指定返回记录行的最大数目。初始记录行的偏移量是 0(而不是 1): 为了与 PostgreSQL 兼容,MySQL 也支持句法: LIMIT # OFFSET #。 mysql> SELECT * FROM table LIMIT 5,10; //检索记录行6-15 //为了检索从某一个偏移量到记录集的结束所有的记录行,可以指定第二个参数为 -1: mysql> SELECT * FROM table LIMIT 95,-1; // 检索记录行 96-last. //如果只给定一个参数,它表示返回最大的记录行数目: mysql> SELECT * FROM table LIMIT 5; //检索前 5 个记录行 //换句话说,LIMIT n 等价于 LIMIT 0,n。 案例: SELECT * FROM table LIMIT 0,5;//0、1、2、3、4 SELECT * FROM table LIMIT 5,5;//5、6、7、8、9 SELECT * FROM table LIMIT 10,5;//10、11、12、13、14查看全部
-
接口式编程作业要求查看全部
-
大概过程查看全部
-
查看一个接口的所有实现类:选中接口名,Ctrl+T 或者选中该接口名,按F4,即 Open Type Hierarchy IMessage imessage=sqlSession.getMapper(IMessage.class);//获取到的就是代理实例 messageList =imessage.queryMessageList(parameter);//代理实例执行接口方法时,就会触发调用处理程序,也就是第三个参数对象的invoke()方法,MapperProxy是实现了InvocationHandler接口的 MapperProxyFactory.newInstance(MapperProxy<T> mapperProxy){ --return (T) Proxy.newProxyInstance(mapperInterface.getClassLoader()//通过接口获取类加载器,new Class[]{mapperInterface}//代理类实现的接口数组,mapperProxy//调用代理实例的处理程序) --} 解决了三个问题: 1、为什么只定义了一个接口,没有实现类的情况下,接口方法可以被调用,因为动态代理。 2、为什么sqlSession.getMapper(.class)可以根据传入的参数,返回一个对应的类型,因为泛型。 3、Mybatis加载文件时,利用namespace加载了一个class,然后把这个class与代码中传入接口的class进行匹配,方法执行所需要的信息就是来自于已经匹配成功的配置文件中,当结果与配置文件对应上后,调用接口的方法执行sql语句。查看全部
-
imessage.queryMessageList(Parameter) = sqlSession.selectList(namespace.id,parameter)查看全部
-
接口全名称.方法名 = namespace.id查看全部
-
MapperProxy 代理类查看全部
-
为什么两个function在同一个js 里面实现不了分页,放在两个js可以,求大神解答查看全部
-
11444查看全部
-
动态代理,接口式编程查看全部
举报
0/150
提交
取消