【问题标题】:SQLiteException on some Android 9, 10 devices when using CASE, WHEN TRUESQLiteException 在某些 Android 9、10 设备上使用 CASE,WHEN TRUE 时
【发布时间】:2023-02-25 12:34:06
【问题描述】:

以下 SQL 语句在我的 Android 测试设备 (Android 13) 上运行良好:

SELECT *
FROM portfolio
JOIN holdingCalculations
ON portfolio.uid = holdingCalculations.uid
ORDER BY calc_num_transactions = 0, CASE use_local_currency_for_totals WHEN TRUE THEN calc_total_change_percent_local ELSE calc_total_change_percent END DESC, portfolio.name COLLATE NOCASE

但是,在我将我的 Android 应用程序发布到生产环境后,我发现某些客户设备出现异常(例如运行 Android 10 的 POCO F1、运行 Android 9 的 Galaxy S8+):

Fatal Exception: android.database.sqlite.SQLiteException: no such column: TRUE (code 1 SQLITE_ERROR[1]): , while compiling: SELECT *
FROM portfolio
JOIN holdingCalculations
ON portfolio.uid = holdingCalculations.uid
ORDER BY calc_num_transactions = 0, CASE use_local_currency_for_totals WHEN TRUE THEN calc_total_change_percent_local ELSE calc_total_change_percent END DESC, portfolio.name COLLATE NOCASE
       at android.database.sqlite.SQLiteConnection.nativePrepareStatement(SQLiteConnection.java)
       at android.database.sqlite.SQLiteConnection.acquirePreparedStatement(SQLiteConnection.java:1229)
       at android.database.sqlite.SQLiteConnection.prepare(SQLiteConnection.java:703)
       at android.database.sqlite.SQLiteSession.prepare(SQLiteSession.java:588)
       at android.database.sqlite.SQLiteProgram.<init>(SQLiteProgram.java:59)
       at android.database.sqlite.SQLiteQuery.<init>(SQLiteQuery.java:37)
       at android.database.sqlite.SQLiteDirectCursorDriver.query(SQLiteDirectCursorDriver.java:46)
       at android.database.sqlite.SQLiteDatabase.rawQueryWithFactory(SQLiteDatabase.java:1865)
       at android.database.sqlite.SQLiteDatabase.rawQueryWithFactory(SQLiteDatabase.java:1840)
       at androidx.sqlite.db.framework.FrameworkSQLiteDatabase.query(FrameworkSQLiteDatabase.kt:156)
       at com.squareup.sqldelight.android.AndroidQuery.executeQuery(AndroidSqliteDriver.kt:253)
       at com.squareup.sqldelight.android.AndroidQuery.executeQuery(AndroidSqliteDriver.kt:228)
       at com.squareup.sqldelight.android.AndroidSqliteDriver$executeQuery$2.invoke(AndroidSqliteDriver.kt:149)
       at com.squareup.sqldelight.android.AndroidSqliteDriver$executeQuery$2.invoke(AndroidSqliteDriver.kt:149)
       at com.squareup.sqldelight.android.AndroidSqliteDriver.execute(AndroidSqliteDriver.kt:127)
       at com.squareup.sqldelight.android.AndroidSqliteDriver.executeQuery(AndroidSqliteDriver.kt:149)
       at com.squareup.sqldelight.db.SqlDriver$DefaultImpls.executeQuery$default(SqlDriver.kt:35)

我的猜测是某些设备不支持此 sqlite 语法。这可能是这些设备上安装的 sqlite 版本的问题,是否有向后兼容的方式来编写此查询?

【问题讨论】:

  • @MorrisonChang 现在是,但仅从 SQlite 3.23.0 开始,因此问题是它适用于 13 但不适用于 9 和 10(只有 11+ 具有足够高的 SQLite 版本)。

标签: android android-sqlite


【解决方案1】:

使用 true/false 需要 SQLite 3.23.0 或更高版本。只有从 API 30(Android 11)开始,SQLite 版本才足够高(3.28.0)。

除非您将分布限制为 11+,否则您应该使用 0 表示假,1 表示真。

您不妨参考:-

https://www.sqlite.org/lang_expr.html#boolean_expressions

Version of SQLite used in Android?

【讨论】:

    猜你喜欢
    • 2011-11-04
    • 1970-01-01
    • 1970-01-01
    • 2018-01-15
    • 2014-10-17
    • 1970-01-01
    • 2016-06-12
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多