[英]How to run arbitrary sql with mybatis?
我有一个使用 mybatis 进行对象持久化的应用程序。 但是我有可能需要运行任意 sql(来自用户)。 我可以用mybatis做吗?
更新:
我选择使用dbutils(JDBC)来运行用户定义的sql,但是我需要一个DataSource的实例来创建QueryRunner。 有什么办法可以从mybatis中获取数据源吗?
我使用这个实用类:
import java.util.List;
import org.apache.ibatis.annotations.SelectProvider;
public interface SqlMapper {
static class PureSqlProvider {
public String sql(String sql) {
return sql;
}
public String count(String from) {
return "SELECT count(*) FROM " + from;
}
}
@SelectProvider(type = PureSqlProvider.class, method = "sql")
public List<?> select(String sql);
@SelectProvider(type = PureSqlProvider.class, method = "count")
public Integer count(String from);
@SelectProvider(type = PureSqlProvider.class, method = "sql")
public Integer execute(String query);
}
您的问题类似于如何使用 mybatis 直接从 java 代码执行查询?
我已经给出了这个问题的答案。 但我希望这个解决方案能帮助你。
Mybatis 已经有这个功能了,但是必须使用如下的适配器。
创建一个适配器类;
public class SQLAdapter { String sql; public SQLAdapter(String sql) { this.sql = sql; } public String getSql() { return sql; } public void setSql(String sql) { this.sql = sql; } }
创建类 SQLAdapter 的 typeAlias
<typeAlias alias="sqladapter" type="com.zj.xxx.xxx.SQLAdapter" />
在需要直接执行sql的每个对象xml中放置select标签。
<select id="findRecords" parameterType="SQLAdapter" resultMap="xxxxxResultMap"> ${sql} </select>
像这样调用这个选择方法
String _sql = "select * from table where... order by... limit..."; xxxxx.findRecords(new SQLAdapter(_sql));
根据提供的答案,它们都很好。 但是它们都需要使用Adapter
类。
使用Mybatis 版本 3 ,我成功地使用HashMap<String, String>
来保留和传递SQL 。
请参阅下面的代码。
在Mapper
类中
final String sql = "${sql}";
@Select(sql)
void execute(HashMap<String, String> m);
调用方法时:
String sql = "SELECT * FROM record limit 1";
HashMap<String, String> map = new HashMap<String, String>();
map.put("sql", sql);
mapper.execute(map);
HashMap
提供了一种方法,您不必在代码中定义 Class 属性或字段,您可以使用 Map 来重新定义它。
谢谢。
SQL 的可重用片段可用于动态创建查询的选择部分。 在您的映射器中,将查询作为普通参数传递:
@Param("sql")String sql
在您的查询中,只需使用${sql}而不是#{sql}访问参数。 参数 sql 中的值可以是完全有效的 sql 查询或 sql 查询的片段。
为了测试我使用
import org.apache.ibatis.jdbc.ScriptRunner;
import java.io.Reader;
import java.io.StringReader;
public class test {
private static final String conf = "mybatis.conf.xml";
private SqlSessionFactoryBuilder builder;
private SqlSessionFactory sessionFactory;
Reader reader;
private SqlSession session;
private ScriptRunner runner;
@Before
public void before() {
builder = new SqlSessionFactoryBuilder();
try {
reader = Resources.getResourceAsReader(conf);
} catch (IOException e) {
e.printStackTrace();
}
sessionFactory = builder.build(reader);
session = sessionFactory.openSession();
runner = new ScriptRunner(session.getConnection());
runner.setAutoCommit(true);
runner.setStopOnError(true);
}
@Test
public void testSelectChapelStatus() {
Reader populate = new StringReader("insert into person values (7553,0,'201002496','Wish','Jill','Rain',1,0,NULL,'xxx@LCU.EDU');\r\n"
+ "");
runner.runScript(populate);
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.