所以我正在开发一个项目(JSF2,Spring3 Core,MVC,Webflow,MyBatis3,RichFaces和旧版Oracle 10g)。我所有麻烦的根源都与数据库的设计有关。问题是大多数数据库表都有不断变化的模式(可能是糟糕的设计?)。所以我需要能够支持添加&删除额外的列。
为了适应这种情况,我将MyBatis数据拉入自定义的“通用”域对象,基本上只是扩展了一个hashmap。我目前的问题是更新这些hashmap对象。应该有办法让它发挥作用,但我似乎可以让MyBatis合作。我尝试过使用HashMap.entrySet()& MyBatis的,但无济于事。例如
UPDATE MYTABLE
SET
<foreach collection="entries" index="i" item="entry" close="" open="" separator=", ">
#{entry.key} = #{entry.value}
</foreach>
WHERE FOO='BAR';
我尝试过自定义TypeHandler但是setParameter()没有给我足够的访问权限来做我需要的事情。 ResultHandler没有给我足够的访问权限,因此我也无法使用它。
现在我知道我可以做像Obj.createUpdateSqlString()这样的东西,并将其作为文字字符串插入到映射器中,但这有点像黑客攻击并让我对SQL注入开放。更不用说这将涉及逃避大量的字符串,并考虑到各种可能的输入,除非涵盖所有可能性,为一些严重的错误打开了大门。
那么有一种既定的方法可以做到这一点吗?或者至少中途体面的方式?我听说过一些铁杆MyBatis的支持者说他们还没有遇到MyBatis无法优雅处理的情况;所以MyBatis专家,请帮帮我!!
答案 0 :(得分:3)
MyBatis或Hibernate都对疯狂的数据库方案感到厌恶。我会使用SpringJDBC或类似的。
不要试图将圆形钉固定在方孔中,即使它是一个非常好的圆形钉。
答案 1 :(得分:1)
听起来他们试图避免使用EAV表。
在动态添加字段时,你必须选择毒药。从理论的角度来看,EAV是好的,但在大型桌面上存在严重的性能问题。虽然动态添加列对于查询性能更好,但您必须处理更改的表接口和动态sql。我不会把数据库写成一个糟糕的设计。
您可能想要绕过您正在使用的框架。查询表模式(对于Oracle查看USER_TAB_COLUMNS)并生成插入/更新脚本。对它们进行参数化,以确保您不会注射。这将是一个令人头疼但我没有看到替代方案。