最近项目中有一个功能需要先根据设定字段自定义排序,然后根据排序设定导出word文档。开发时我使用freemarker已经完成功能,但还是被测试提了个bug,说我排序没有生效。本想反驳的,奈何人实锤在手,只好乖乖调试,最终找到问题并解决。下面上解决步骤,谨记谨记。哈哈!
排序的页面长这样:
点击排序设置后,页面如这样:
选中根据出生日期排序并勾选逆序前复选框。
后台接口,长这样(第一个参数为主键,第二个参数为前台页面组装好的排序字段):
上面的步骤都是正常的,导致排序失败的原因就在下图:
导致排序失败错误时的mybatis的sql文件长这样:
修改后正常运行的mybatis的sql文件长这样:
仔细观察这两个sql文件,就能发现问题的原因了。原因就是#和$导致的。
第一个sql(错误实例)运行时,断点调试显示如下图:
第二个sql(正确实例)运行时,断点调试显示如下图:
总结:对比两条sql运行的断点调试实例,我们可以发现,二者区别在于:用$号时,在mybatis编译sql的阶段,$号位置的值已经由我们传过来的参数替换,而#号位置此时是用?号代替的(这时可以看到错误的sql实例有两个问号,而正确的sql实例只有一个问号,另一个排序字段已经变成我们前台传的值了)。在实际跟数据库交互时,正确的sql实例只会传一个值(既用#号标记的主键值),而错误实例会传两个值。而且此时错误实例的order by解析为order by '前台传的排序值',外面多了一层单引号,所以排序失败。
上面的总结说的太多,不如直接来图看的清楚,上图:
最最后,实际使用过程中,如果你需要传的参数原样出现在sql中,就用$符号,否则用占位符?,关于$和#的区别,#号更安全,至于为何更安全,百度一下二者区别,度娘会告诉你,特别详细。
码字不易,转载请注明出处!