Merge "Allow PRAGMA statements that change and return a result in executeNonQuery()"
This commit is contained in:
committed by
Android (Google) Code Review
commit
18cece4377
@@ -153,7 +153,8 @@ public final class SQLiteConnection implements CancellationSignal.OnCancelListen
|
||||
int index, byte[] value);
|
||||
private static native void nativeResetStatementAndClearBindings(
|
||||
long connectionPtr, long statementPtr);
|
||||
private static native void nativeExecute(long connectionPtr, long statementPtr);
|
||||
private static native void nativeExecute(long connectionPtr, long statementPtr,
|
||||
boolean isPragmaStmt);
|
||||
private static native long nativeExecuteForLong(long connectionPtr, long statementPtr);
|
||||
private static native String nativeExecuteForString(long connectionPtr, long statementPtr);
|
||||
private static native int nativeExecuteForBlobFileDescriptor(
|
||||
@@ -699,6 +700,8 @@ public final class SQLiteConnection implements CancellationSignal.OnCancelListen
|
||||
|
||||
final int cookie = mRecentOperations.beginOperation("execute", sql, bindArgs);
|
||||
try {
|
||||
final boolean isPragmaStmt =
|
||||
DatabaseUtils.getSqlStatementType(sql) == DatabaseUtils.STATEMENT_PRAGMA;
|
||||
final PreparedStatement statement = acquirePreparedStatement(sql);
|
||||
try {
|
||||
throwIfStatementForbidden(statement);
|
||||
@@ -706,7 +709,7 @@ public final class SQLiteConnection implements CancellationSignal.OnCancelListen
|
||||
applyBlockGuardPolicy(statement);
|
||||
attachCancellationSignal(cancellationSignal);
|
||||
try {
|
||||
nativeExecute(mConnectionPtr, statement.mStatementPtr);
|
||||
nativeExecute(mConnectionPtr, statement.mStatementPtr, isPragmaStmt);
|
||||
} finally {
|
||||
detachCancellationSignal(cancellationSignal);
|
||||
}
|
||||
|
||||
@@ -518,23 +518,29 @@ static void nativeResetStatementAndClearBindings(JNIEnv* env, jclass clazz, jlon
|
||||
}
|
||||
}
|
||||
|
||||
static int executeNonQuery(JNIEnv* env, SQLiteConnection* connection, sqlite3_stmt* statement) {
|
||||
int err = sqlite3_step(statement);
|
||||
if (err == SQLITE_ROW) {
|
||||
static int executeNonQuery(JNIEnv* env, SQLiteConnection* connection, sqlite3_stmt* statement,
|
||||
bool isPragmaStmt) {
|
||||
int rc = sqlite3_step(statement);
|
||||
if (isPragmaStmt) {
|
||||
while (rc == SQLITE_ROW) {
|
||||
rc = sqlite3_step(statement);
|
||||
}
|
||||
}
|
||||
if (rc == SQLITE_ROW) {
|
||||
throw_sqlite3_exception(env,
|
||||
"Queries can be performed using SQLiteDatabase query or rawQuery methods only.");
|
||||
} else if (err != SQLITE_DONE) {
|
||||
} else if (rc != SQLITE_DONE) {
|
||||
throw_sqlite3_exception(env, connection->db);
|
||||
}
|
||||
return err;
|
||||
return rc;
|
||||
}
|
||||
|
||||
static void nativeExecute(JNIEnv* env, jclass clazz, jlong connectionPtr,
|
||||
jlong statementPtr) {
|
||||
static void nativeExecute(JNIEnv* env, jclass clazz, jlong connectionPtr, jlong statementPtr,
|
||||
jboolean isPragmaStmt) {
|
||||
SQLiteConnection* connection = reinterpret_cast<SQLiteConnection*>(connectionPtr);
|
||||
sqlite3_stmt* statement = reinterpret_cast<sqlite3_stmt*>(statementPtr);
|
||||
|
||||
executeNonQuery(env, connection, statement);
|
||||
executeNonQuery(env, connection, statement, isPragmaStmt);
|
||||
}
|
||||
|
||||
static jint nativeExecuteForChangedRowCount(JNIEnv* env, jclass clazz,
|
||||
@@ -542,7 +548,7 @@ static jint nativeExecuteForChangedRowCount(JNIEnv* env, jclass clazz,
|
||||
SQLiteConnection* connection = reinterpret_cast<SQLiteConnection*>(connectionPtr);
|
||||
sqlite3_stmt* statement = reinterpret_cast<sqlite3_stmt*>(statementPtr);
|
||||
|
||||
int err = executeNonQuery(env, connection, statement);
|
||||
int err = executeNonQuery(env, connection, statement, false);
|
||||
return err == SQLITE_DONE ? sqlite3_changes(connection->db) : -1;
|
||||
}
|
||||
|
||||
@@ -551,7 +557,7 @@ static jlong nativeExecuteForLastInsertedRowId(JNIEnv* env, jclass clazz,
|
||||
SQLiteConnection* connection = reinterpret_cast<SQLiteConnection*>(connectionPtr);
|
||||
sqlite3_stmt* statement = reinterpret_cast<sqlite3_stmt*>(statementPtr);
|
||||
|
||||
int err = executeNonQuery(env, connection, statement);
|
||||
int err = executeNonQuery(env, connection, statement, false);
|
||||
return err == SQLITE_DONE && sqlite3_changes(connection->db) > 0
|
||||
? sqlite3_last_insert_rowid(connection->db) : -1;
|
||||
}
|
||||
@@ -912,7 +918,7 @@ static const JNINativeMethod sMethods[] =
|
||||
(void*)nativeBindBlob },
|
||||
{ "nativeResetStatementAndClearBindings", "(JJ)V",
|
||||
(void*)nativeResetStatementAndClearBindings },
|
||||
{ "nativeExecute", "(JJ)V",
|
||||
{ "nativeExecute", "(JJZ)V",
|
||||
(void*)nativeExecute },
|
||||
{ "nativeExecuteForLong", "(JJ)J",
|
||||
(void*)nativeExecuteForLong },
|
||||
|
||||
Reference in New Issue
Block a user