Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 19b82642 authored by Jeff Sharkey's avatar Jeff Sharkey Committed by Automerger Merge Worker
Browse files

Merge "Add ability to execute per-connection SQL." into rvc-dev am: 071e55a0

Change-Id: I7889d286fee519f690a8e39c43dbcd01702e0c5a
parents 4ecd8561 071e55a0
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -13389,6 +13389,7 @@ package android.database.sqlite {
    method public void disableWriteAheadLogging();
    method public boolean enableWriteAheadLogging();
    method public void endTransaction();
    method public void execPerConnectionSQL(@NonNull String, @Nullable Object[]) throws android.database.SQLException;
    method public void execSQL(String) throws android.database.SQLException;
    method public void execSQL(String, Object[]) throws android.database.SQLException;
    method public static String findEditTable(String);
+26 −0
Original line number Diff line number Diff line
@@ -28,6 +28,7 @@ import android.os.SystemClock;
import android.os.Trace;
import android.util.Log;
import android.util.LruCache;
import android.util.Pair;
import android.util.Printer;

import dalvik.system.BlockGuard;
@@ -230,6 +231,7 @@ public final class SQLiteConnection implements CancellationSignal.OnCancelListen
        setAutoCheckpointInterval();
        setLocaleFromConfiguration();
        setCustomFunctionsFromConfiguration();
        executePerConnectionSqlFromConfiguration(0);
    }

    private void dispose(boolean finalized) {
@@ -468,6 +470,24 @@ public final class SQLiteConnection implements CancellationSignal.OnCancelListen
        }
    }

    private void executePerConnectionSqlFromConfiguration(int startIndex) {
        for (int i = startIndex; i < mConfiguration.perConnectionSql.size(); i++) {
            final Pair<String, Object[]> statement = mConfiguration.perConnectionSql.get(i);
            final int type = DatabaseUtils.getSqlStatementType(statement.first);
            switch (type) {
                case DatabaseUtils.STATEMENT_SELECT:
                    executeForString(statement.first, statement.second, null);
                    break;
                case DatabaseUtils.STATEMENT_PRAGMA:
                    execute(statement.first, statement.second, null);
                    break;
                default:
                    throw new IllegalArgumentException(
                            "Unsupported configuration statement: " + statement);
            }
        }
    }

    private void checkDatabaseWiped() {
        if (!SQLiteGlobal.checkDbWipe()) {
            return;
@@ -513,6 +533,9 @@ public final class SQLiteConnection implements CancellationSignal.OnCancelListen
                .equals(mConfiguration.customScalarFunctions);
        boolean customAggregateFunctionsChanged = !configuration.customAggregateFunctions
                .equals(mConfiguration.customAggregateFunctions);
        final int oldSize = mConfiguration.perConnectionSql.size();
        final int newSize = configuration.perConnectionSql.size();
        boolean perConnectionSqlChanged = newSize > oldSize;

        // Update configuration parameters.
        mConfiguration.updateParametersFrom(configuration);
@@ -532,6 +555,9 @@ public final class SQLiteConnection implements CancellationSignal.OnCancelListen
        if (customScalarFunctionsChanged || customAggregateFunctionsChanged) {
            setCustomFunctionsFromConfiguration();
        }
        if (perConnectionSqlChanged) {
            executePerConnectionSqlFromConfiguration(oldSize);
        }
    }

    // Called by SQLiteConnectionPool only.
+46 −0
Original line number Diff line number Diff line
@@ -1046,6 +1046,40 @@ public final class SQLiteDatabase extends SQLiteClosable {
        }
    }

    /**
     * Execute the given SQL statement on all connections to this database.
     * <p>
     * This statement will be immediately executed on all existing connections,
     * and will be automatically executed on all future connections.
     * <p>
     * Some example usages are changes like {@code PRAGMA trusted_schema=OFF} or
     * functions like {@code SELECT icu_load_collation()}. If you execute these
     * statements using {@link #execSQL} then they will only apply to a single
     * database connection; using this method will ensure that they are
     * uniformly applied to all current and future connections.
     *
     * @param sql The SQL statement to be executed. Multiple statements
     *            separated by semicolons are not supported.
     * @param bindArgs The arguments that should be bound to the SQL statement.
     */
    public void execPerConnectionSQL(@NonNull String sql, @Nullable Object[] bindArgs)
            throws SQLException {
        Objects.requireNonNull(sql);

        synchronized (mLock) {
            throwIfNotOpenLocked();

            final int index = mConfigurationLocked.perConnectionSql.size();
            mConfigurationLocked.perConnectionSql.add(Pair.create(sql, bindArgs));
            try {
                mConnectionPoolLocked.reconfigure(mConfigurationLocked);
            } catch (RuntimeException ex) {
                mConfigurationLocked.perConnectionSql.remove(index);
                throw ex;
            }
        }
    }

    /**
     * Gets the database version.
     *
@@ -1788,6 +1822,12 @@ public final class SQLiteDatabase extends SQLiteClosable {
     * using "PRAGMA journal_mode'<value>" statement if your app is using
     * {@link #enableWriteAheadLogging()}
     * </p>
     * <p>
     * Note that {@code PRAGMA} values which apply on a per-connection basis
     * should <em>not</em> be configured using this method; you should instead
     * use {@link #execPerConnectionSQL} to ensure that they are uniformly
     * applied to all current and future connections.
     * </p>
     *
     * @param sql the SQL statement to be executed. Multiple statements separated by semicolons are
     * not supported.
@@ -1834,6 +1874,12 @@ public final class SQLiteDatabase extends SQLiteClosable {
     * using "PRAGMA journal_mode'<value>" statement if your app is using
     * {@link #enableWriteAheadLogging()}
     * </p>
     * <p>
     * Note that {@code PRAGMA} values which apply on a per-connection basis
     * should <em>not</em> be configured using this method; you should instead
     * use {@link #execPerConnectionSQL} to ensure that they are uniformly
     * applied to all current and future connections.
     * </p>
     *
     * @param sql the SQL statement to be executed. Multiple statements separated by semicolons are
     * not supported.
+9 −1
Original line number Diff line number Diff line
@@ -18,9 +18,10 @@ package android.database.sqlite;

import android.compat.annotation.UnsupportedAppUsage;
import android.util.ArrayMap;
import android.util.Pair;

import java.util.ArrayList;
import java.util.Locale;
import java.util.Map;
import java.util.function.BinaryOperator;
import java.util.function.UnaryOperator;
import java.util.regex.Pattern;
@@ -101,6 +102,11 @@ public final class SQLiteDatabaseConfiguration {
    public final ArrayMap<String, BinaryOperator<String>> customAggregateFunctions
            = new ArrayMap<>();

    /**
     * The statements to execute to initialize each connection.
     */
    public final ArrayList<Pair<String, Object[]>> perConnectionSql = new ArrayList<>();

    /**
     * The size in bytes of each lookaside slot
     *
@@ -194,6 +200,8 @@ public final class SQLiteDatabaseConfiguration {
        customScalarFunctions.putAll(other.customScalarFunctions);
        customAggregateFunctions.clear();
        customAggregateFunctions.putAll(other.customAggregateFunctions);
        perConnectionSql.clear();
        perConnectionSql.addAll(other.perConnectionSql);
        lookasideSlotSize = other.lookasideSlotSize;
        lookasideSlotCount = other.lookasideSlotCount;
        idleConnectionTimeoutMs = other.idleConnectionTimeoutMs;