SupportSQLiteQueryBuilder的selection方法失效,Room RawQuery参数未正常添加
问题解决方案
你遇到的问题来源于三个使用误区,修正后即可正常运行:
SupportSQLiteQueryBuilder的selection方法第一个入参需要传入带占位符的完整条件片段,不是仅传入列名。如果要实现等值匹配,需要写成列名 = ?的格式,仅传入列名只会在SQL里拼接列名,不会生成匹配逻辑。- 多次调用
selection方法会覆盖之前的设置,不会自动用AND拼接多个条件,需要手动把所有条件拼接为一个完整的WHERE片段后,再调用一次selection方法。 - 你在构造
SimpleSQLiteQuery时仅传入了生成的SQL字符串,丢弃了queryBuilder.create()返回结果中携带的绑定参数,导致参数完全没有被传入查询逻辑。
修正后代码
修改QueryUtils类的getPlantsBasedOnOrigin方法即可:
fun getPlantsBasedOnOrigin(origin: String, showOnlyFav: Boolean): SimpleSQLiteQuery { // 收集所有条件和对应绑定参数 val selectionSegments = mutableListOf<String>() val bindArgs = mutableListOf<Any>() // 加产地条件 selectionSegments.add("$COL_ORIGIN = ?") bindArgs.add(origin) // 加收藏筛选条件 if (showOnlyFav) { selectionSegments.add("$COL_FAVORITE = ?") bindArgs.add("1") } // 拼接完整的WHERE条件片段 val finalSelection = selectionSegments.joinToString(" AND ") // 构造查询 val supportQuery = SupportSQLiteQueryBuilder .builder(TABLE_NAME) .selection(finalSelection, bindArgs.toTypedArray()) .create() // 日志打印SQL,此处看到的?是参数占位符,不会直接拼参数值 Log.d("Generated SQL query", supportQuery.sql) // 构造SimpleSQLiteQuery时必须同时传入SQL和绑定参数 return SimpleSQLiteQuery(supportQuery.sql, supportQuery.bindArgs) }
补充说明:SQLite采用参数预编译机制,不会直接把参数值拼接到SQL字符串中,这种设计可以避免SQL注入风险,你期望的把参数值直接拼入SQL的写法属于不安全写法,不推荐使用。
内容的提问来源于stack exchange,提问作者Shizuku
相关产品推荐
相关产品推荐

