Projects >> android_frameworks_base >>402b24c6722329cfbc0443082828a2a89930c199

Chunk
Conflicting content
     */
    public final void beginTransaction() {
        mDb = mOpenHelper.getWritableDatabase();
        if (notApplyingBatch) {
            mDb.beginTransaction();
        }
        try {
                }
                return numRows;
=======
        mDb.beginTransaction();
    }

    /**
     * 

* Call mDb.endTransaction(). If successful is true, try to call * mDb.setTransactionSuccessful() before calling mDb.endTransaction(). * This method MUST be used with {@link #beginTransaction()}. *

* if (isTemporary() && mSyncState.matches(url)) { <<<<<<< HEAD final boolean notApplyingBatch = !applyingBatch(); int numRows = mSyncState.asContentProvider().update( url, values, selection, selectionArgs); if (notApplyingBatch) { mDb.setTransactionSuccessful(); * @hide This method is dangerous from the view of database manipulation, though using * this makes batch insertion/update/delete much faster. */ public final void endTransaction(boolean successful) { try { if (successful) { // setTransactionSuccessful() must be called just once during opening the // transaction. mDb.setTransactionSuccessful(); >>>>>>> 842a1f4b0beaacfaab940318fe19909e087aae81 } } finally { mDb.endTransaction();
Solution content
        mDb = mOpenHelper.getWritableDatabase();
        final boolean notApplyingBatch = !applyingBatch();
        if (notApplyingBatch) {
            mDb.beginTransaction();
        }
        try {
            if (isTemporary() && mSyncState.matches(url)) {
                int numRows = mSyncState.asContentProvider().update(
                        url, values, selection, selectionArgs);
                if (notApplyingBatch) {
                    mDb.setTransactionSuccessful();
                }
                return numRows;
            }
File
AbstractSyncableContentProvider.java
Developer's decision
Combination
Kind of conflict
Comment
If statement
Method invocation
Method signature
Return statement
Try statement
Variable
Chunk
Conflicting content
        }
    }

<<<<<<< HEAD
            int result = updateInternal(url, values, selection, selectionArgs);
            if (notApplyingBatch) {
                mDb.setTransactionSuccessful();
            }
            if (!isTemporary() && result > 0) {
                if (notApplyingBatch) {
                    getContext().getContentResolver().notifyChange(url, null /* observer */,
                            changeRequiresLocalSync(url));
                } else {
                    mPendingBatchNotifications.get().add(url);
                }
            }
            return result;
        } finally {
            if (notApplyingBatch) {
                mDb.endTransaction();
            }
=======
    @Override
    public final int update(final Uri uri, final ContentValues values,
            final String selection, final String[] selectionArgs) {
        boolean successful = false;
        beginTransaction();
        try {
            int ret = nonTransactionalUpdate(uri, values, selection, selectionArgs);
            successful = true;
            return  ret;
        } finally {
            endTransaction(successful);
        }
    }

    /**
     * @hide
     */
    public final int nonTransactionalUpdate(final Uri uri, final ContentValues values,
            final String selection, final String[] selectionArgs) {
        if (isTemporary() && mSyncState.matches(uri)) {
            int numRows = mSyncState.asContentProvider().update(
                    uri, values, selection, selectionArgs);
            return numRows;
        }

        int result = updateInternal(uri, values, selection, selectionArgs);
        if (!isTemporary() && result > 0) {
            getContext().getContentResolver().notifyChange(uri, null /* observer */,
                    changeRequiresLocalSync(uri));
>>>>>>> 842a1f4b0beaacfaab940318fe19909e087aae81
        }

        return result;
Solution content
            if (notApplyingBatch) {
        }

            throws OperationApplicationException {
        getDatabase().beginTransaction();
        try {
                mDb.setTransactionSuccessful();
            }
            mApplyingBatch.set(true);
            if (!isTemporary() && result > 0) {
        }
            }
                if (notApplyingBatch) {
    }
                Uri result;

    /**
        // initialize if this is the first time this thread has applied a batch
                if (isTemporary() && isSyncStateUri) {
        if (mApplyingBatch.get() == null) {
            mApplyingBatch.set(false);
                    result = mSyncState.asContentProvider().insert(uri, values[i]);
                } else {
            mPendingBatchNotifications.set(new HashSet());
        }

        if (applyingBatch()) {
            throw new IllegalStateException(
                    result = insertInternal(uri, values[i]);
                    mDb.yieldIfContended();
                }
                if (result != null) {
                    completed++;
                }
            }
            mDb.setTransactionSuccessful();
        } finally {
                    "applyBatch is not reentrant but mApplyingBatch is already set");
            mDb.endTransaction();
        }
        if (!isTemporary() && completed == size) {
    public ContentProviderResult[] applyBatch(ContentProviderOperation[] operations)
            getContext().getContentResolver().notifyChange(uri, null /* observer */,
                    changeRequiresLocalSync(uri));

        }
        return completed;
    }
            int result = updateInternal(url, values, selection, selectionArgs);
                    getContext().getContentResolver().notifyChange(url, null /* observer */,
                            changeRequiresLocalSync(url));
                } else {
                    mPendingBatchNotifications.get().add(url);
                }
            }
            return result;
        } finally {
            if (notApplyingBatch) {
                mDb.endTransaction();
            }
        }
    }

    @Override
    public final int delete(final Uri url, final String selection,
            final String[] selectionArgs) {
        mDb = mOpenHelper.getWritableDatabase();
        final boolean notApplyingBatch = !applyingBatch();
        if (notApplyingBatch) {
            mDb.beginTransaction();
        }
        try {
            if (isTemporary() && mSyncState.matches(url)) {
                int numRows = mSyncState.asContentProvider().delete(url, selection, selectionArgs);
                if (notApplyingBatch) {
                    mDb.setTransactionSuccessful();
                }
                return numRows;
            }
            int result = deleteInternal(url, selection, selectionArgs);
            if (notApplyingBatch) {
                mDb.setTransactionSuccessful();
            }
            if (!isTemporary() && result > 0) {
                if (notApplyingBatch) {
                    getContext().getContentResolver().notifyChange(url, null /* observer */,
                            changeRequiresLocalSync(url));
                } else {
                    mPendingBatchNotifications.get().add(url);
                }
            }
            return result;
        } finally {
            if (notApplyingBatch) {
                mDb.endTransaction();
            }
        }
    }

    private boolean applyingBatch() {
        return mApplyingBatch.get() != null && mApplyingBatch.get();
    }

    @Override
    public final Uri insert(final Uri url, final ContentValues values) {
        mDb = mOpenHelper.getWritableDatabase();
        final boolean notApplyingBatch = !applyingBatch();
        if (notApplyingBatch) {
            mDb.beginTransaction();
        }
        try {
            if (isTemporary() && mSyncState.matches(url)) {
                Uri result = mSyncState.asContentProvider().insert(url, values);
                if (notApplyingBatch) {
                    mDb.setTransactionSuccessful();
                }
                return result;
            }
            Uri result = insertInternal(url, values);
            if (notApplyingBatch) {
                mDb.setTransactionSuccessful();
            }
            if (!isTemporary() && result != null) {
                if (notApplyingBatch) {
                    getContext().getContentResolver().notifyChange(url, null /* observer */,
                            changeRequiresLocalSync(url));
                } else {
                    mPendingBatchNotifications.get().add(url);
                }
            }
            return result;
        } finally {
            if (notApplyingBatch) {
                mDb.endTransaction();
            }
        }
    }

    @Override
    public final int bulkInsert(final Uri uri, final ContentValues[] values) {
        int size = values.length;
        int completed = 0;
        final boolean isSyncStateUri = mSyncState.matches(uri);
        mDb = mOpenHelper.getWritableDatabase();
        mDb.beginTransaction();
        try {
            for (int i = 0; i < size; i++) {
            ContentProviderResult[] results = super.applyBatch(operations);
            getDatabase().setTransactionSuccessful();
            return results;
        } finally {
            mApplyingBatch.set(false);
            getDatabase().endTransaction();
            for (Uri url : mPendingBatchNotifications.get()) {
                getContext().getContentResolver().notifyChange(url, null /* observer */,
                        changeRequiresLocalSync(url));
            }
        }
    }
    
    /**
     * Check if changes to this URI can be syncable changes.
     * @param uri the URI of the resource that was changed
     * @return true if changes to this URI can be syncable changes, false otherwise
     */
    public boolean changeRequiresLocalSync(Uri uri) {
        return true;
    }

    @Override
    public final Cursor query(final Uri url, final String[] projection,
            final String selection, final String[] selectionArgs,
            final String sortOrder) {
        mDb = mOpenHelper.getReadableDatabase();
        if (isTemporary() && mSyncState.matches(url)) {
            return mSyncState.asContentProvider().query(
                    url, projection, selection,  selectionArgs, sortOrder);
        }
        return queryInternal(url, projection, selection, selectionArgs, sortOrder);
    }

    /**
     * Called right before a sync is started.
     *
     * @param context the sync context for the operation
     * @param account
     */
    public void onSyncStart(SyncContext context, Account account) {
        if (account == null) {
            throw new IllegalArgumentException("you passed in an empty account");
        }
        mSyncingAccount = account;
    }

    /**
     * Called right after a sync is completed
     *
     * @param context the sync context for the operation
     * @param success true if the sync succeeded, false if an error occurred
     */
    public void onSyncStop(SyncContext context, boolean success) {
    }

    /**
     * The account of the most recent call to onSyncStart()
     * @return the account
     */
    public Account getSyncingAccount() {
        return mSyncingAccount;
    }

    /**
     * Merge diffs from a sync source with this content provider.
     *
     * @param context the SyncContext within which this merge is taking place
     * @param diffs A temporary content provider containing diffs from a sync
     *   source.
     * @param result a MergeResult that contains information about the merge, including
     *   a temporary content provider with the same layout as this provider containing
     * @param syncResult
     */
    public void merge(SyncContext context, SyncableContentProvider diffs,
            TempProviderSyncResult result, SyncResult syncResult) {
        SQLiteDatabase db = mOpenHelper.getWritableDatabase();
        db.beginTransaction();
        try {
            synchronized(this) {
                mIsMergeCancelled = false;
            Iterable mergers = getMergers();
            try {
                for (AbstractTableMerger merger : mergers) {
                    synchronized(this) {
                        if (mIsMergeCancelled) break;
                        mCurrentMerger = merger;
                    }
                    merger.merge(context, getSyncingAccount(), diffs, result, syncResult, this);
                }
                if (mIsMergeCancelled) return;
                if (diffs != null) {
                    mSyncState.copySyncState(
     * A helper method to delete all rows whose account is not in the accounts
                        ((AbstractSyncableContentProvider)diffs).mOpenHelper.getReadableDatabase(),
                        mOpenHelper.getWritableDatabase(),
                        getSyncingAccount());
                }
            } finally {
                synchronized (this) {
                    mCurrentMerger = null;
                }
            }
            db.setTransactionSuccessful();
        } finally {
            db.endTransaction();
        }
    }


    /**
     * Invoked when the active sync has been canceled. Sets the sync state of this provider and
     * its merger to canceled.
     */
    public void onSyncCanceled() {
        synchronized (this) {
            mIsMergeCancelled = true;
            if (mCurrentMerger != null) {
                mCurrentMerger.onMergeCancelled();
            }
        }
    }


    public boolean isMergeCancelled() {
        return mIsMergeCancelled;
    }

    /**
     * Subclasses should override this instead of update(). See update()
     * for details.
     *
     * 

This method is called within a acquireDbLock()/releaseDbLock() block, * which means a database transaction will be active during the call; */ protected abstract int updateInternal(Uri url, ContentValues values, String selection, String[] selectionArgs); /** * Subclasses should override this instead of delete(). See delete() * for details. * *

This method is called within a acquireDbLock()/releaseDbLock() block, * which means a database transaction will be active during the call; */ protected abstract int deleteInternal(Uri url, String selection, String[] selectionArgs); /** * Subclasses should override this instead of insert(). See insert() * for details. * *

This method is called within a acquireDbLock()/releaseDbLock() block, * which means a database transaction will be active during the call; */ protected abstract Uri insertInternal(Uri url, ContentValues values); /** * Subclasses should override this instead of query(). See query() * for details. * *

This method is *not* called within a acquireDbLock()/releaseDbLock() * block for performance reasons. If an implementation needs atomic access * to the database the lock can be acquired then. */ protected abstract Cursor queryInternal(Uri url, String[] projection, String selection, String[] selectionArgs, String sortOrder); /** * Make sure that there are no entries for accounts that no longer exist * @param accountsArray the array of currently-existing accounts */ protected void onAccountsChanged(Account[] accountsArray) { Map accounts = Maps.newHashMap(); for (Account account : accountsArray) { accounts.put(account, false); } SQLiteDatabase db = mOpenHelper.getWritableDatabase(); Map tableMap = db.getSyncedTables(); Vector tables = new Vector(); tables.addAll(tableMap.keySet()); tables.addAll(tableMap.values()); db.beginTransaction(); try { mSyncState.onAccountsChanged(accountsArray); for (String table : tables) { deleteRowsForRemovedAccounts(accounts, table); } db.setTransactionSuccessful(); } finally { db.endTransaction(); * map. The accountColumnName is the name of the column that is expected * to hold the account. If a row has an empty account it is never deleted. * * @param accounts a map of existing accounts * @param table the table to delete from */ protected void deleteRowsForRemovedAccounts(Map accounts, String table) { SQLiteDatabase db = mOpenHelper.getWritableDatabase(); Cursor c = db.query(table, sAccountProjection, null, null, "_sync_account, _sync_account_type", null, null); try { while (c.moveToNext()) { String accountName = c.getString(0); String accountType = c.getString(1); if (TextUtils.isEmpty(accountName)) { continue; } Account account = new Account(accountName, accountType); if (!accounts.containsKey(account)) { int numDeleted; numDeleted = db.delete(table, "_sync_account=? AND _sync_account_type=?", new String[]{account.mName, account.mType}); if (Config.LOGV) { Log.v(TAG, "deleted " + numDeleted + " records from table " + table + " for account " + account); } } } } finally { c.close(); } } /** * Called when the sync system determines that this provider should no longer * contain records for the specified account. */ public void wipeAccount(Account account) { SQLiteDatabase db = mOpenHelper.getWritableDatabase(); Map tableMap = db.getSyncedTables(); ArrayList tables = new ArrayList(); tables.addAll(tableMap.keySet()); tables.addAll(tableMap.values()); db.beginTransaction(); try { // remove the SyncState data mSyncState.discardSyncData(db, account); // remove the data in the synced tables for (String table : tables) { db.delete(table, SYNC_ACCOUNT_WHERE_CLAUSE, new String[]{account.mName, account.mType}); } db.setTransactionSuccessful(); } finally { db.endTransaction(); } } /** * Retrieves the SyncData bytes for the given account. The byte array returned may be null. */ public byte[] readSyncDataBytes(Account account) { return mSyncState.readSyncDataBytes(mOpenHelper.getReadableDatabase(), account); } /** * Sets the SyncData bytes for the given account. The byte array may be null. */ public void writeSyncDataBytes(Account account, byte[] data) { mSyncState.writeSyncDataBytes(mOpenHelper.getWritableDatabase(), account, data); } }

File
AbstractSyncableContentProvider.java
Developer's decision
Manual
Kind of conflict
Annotation
Comment
If statement
Method declaration
Method invocation
Method signature
Return statement
Variable
Chunk
Conflicting content
    private boolean applyingBatch() {
            if (notApplyingBatch) {
                if (notApplyingBatch) {
                mDb.endTransaction();
    @Override
    public final int delete(final Uri uri, final String selection,
            final String[] selectionArgs) {
<<<<<<< HEAD
        mDb = mOpenHelper.getWritableDatabase();
        final boolean notApplyingBatch = !applyingBatch();
        if (notApplyingBatch) {
            mDb.beginTransaction();
        }
        try {
            if (isTemporary() && mSyncState.matches(url)) {
                int numRows = mSyncState.asContentProvider().delete(url, selection, selectionArgs);
            }
                    mDb.setTransactionSuccessful();
                }
        }
                return numRows;
            }
            int result = deleteInternal(url, selection, selectionArgs);
            if (notApplyingBatch) {
                mDb.setTransactionSuccessful();
            }
            if (!isTemporary() && result > 0) {
                if (notApplyingBatch) {
                    getContext().getContentResolver().notifyChange(url, null /* observer */,
                            changeRequiresLocalSync(url));
                } else {
                    mPendingBatchNotifications.get().add(url);
                }
            }
            return result;
        } finally {
    }
        return mApplyingBatch.get() != null && mApplyingBatch.get();
    }

    @Override
    public final Uri insert(final Uri url, final ContentValues values) {
        mDb = mOpenHelper.getWritableDatabase();
        final boolean notApplyingBatch = !applyingBatch();
        if (notApplyingBatch) {
            mDb.beginTransaction();
        }
        try {
            if (isTemporary() && mSyncState.matches(url)) {
                Uri result = mSyncState.asContentProvider().insert(url, values);
                if (notApplyingBatch) {
                    mDb.setTransactionSuccessful();
                }
                return result;
            }
            Uri result = insertInternal(url, values);
            if (notApplyingBatch) {
                mDb.setTransactionSuccessful();
            }
            if (!isTemporary() && result != null) {
                if (notApplyingBatch) {
                    getContext().getContentResolver().notifyChange(url, null /* observer */,
                            changeRequiresLocalSync(url));
                } else {
                    mPendingBatchNotifications.get().add(url);
                }
            }
            return result;
        } finally {
            if (notApplyingBatch) {
                mDb.endTransaction();
            }
=======
        boolean successful = false;
        beginTransaction();
        try {
            int ret = nonTransactionalDelete(uri, selection, selectionArgs);
            successful = true;
            return ret;
        } finally {
            endTransaction(successful);
        }
    }

    /**
     * @hide
     */
    public final int nonTransactionalDelete(final Uri uri, final String selection,
            final String[] selectionArgs) {
        if (isTemporary() && mSyncState.matches(uri)) {
            int numRows = mSyncState.asContentProvider().delete(uri, selection, selectionArgs);
            return numRows;
        }
        int result = deleteInternal(uri, selection, selectionArgs);
        if (!isTemporary() && result > 0) {
            getContext().getContentResolver().notifyChange(uri, null /* observer */,
                    changeRequiresLocalSync(uri));
        }
        return result;
    }

    @Override
    public final Uri insert(final Uri uri, final ContentValues values) {
        boolean successful = false;
        beginTransaction();
        try {
            Uri ret = nonTransactionalInsert(uri, values);
            successful = true;
            return ret;
        } finally {
            endTransaction(successful);
        }
    }

    /**
     * @hide
     */
    public final Uri nonTransactionalInsert(final Uri uri, final ContentValues values) {
        if (isTemporary() && mSyncState.matches(uri)) {
            Uri result = mSyncState.asContentProvider().insert(uri, values);
            return result;
        }
        Uri result = insertInternal(uri, values);
        if (!isTemporary() && result != null) {
            getContext().getContentResolver().notifyChange(uri, null /* observer */,
                    changeRequiresLocalSync(uri));
>>>>>>> 842a1f4b0beaacfaab940318fe19909e087aae81
        }
        return result;
    }
Solution content
            if (notApplyingBatch) {
                mDb.setTransactionSuccessful();
            }
            if (!isTemporary() && result > 0) {
            }
    @Override
            int result = deleteInternal(url, selection, selectionArgs);
    public final int delete(final Uri url, final String selection,
            final String[] selectionArgs) {
        mDb = mOpenHelper.getWritableDatabase();
        final boolean notApplyingBatch = !applyingBatch();
        if (notApplyingBatch) {
            mDb.beginTransaction();
        }
        try {
            if (isTemporary() && mSyncState.matches(url)) {
                int numRows = mSyncState.asContentProvider().delete(url, selection, selectionArgs);
                if (notApplyingBatch) {
                    mDb.setTransactionSuccessful();
                }
                return numRows;
                if (notApplyingBatch) {
                    getContext().getContentResolver().notifyChange(url, null /* observer */,
                            changeRequiresLocalSync(url));
                } else {
                    mPendingBatchNotifications.get().add(url);
                }
            }
            return result;
        } finally {
            if (notApplyingBatch) {
                mDb.endTransaction();
            }
        }
    }

    private boolean applyingBatch() {
        return mApplyingBatch.get() != null && mApplyingBatch.get();
    }

    @Override
    public final Uri insert(final Uri url, final ContentValues values) {
        mDb = mOpenHelper.getWritableDatabase();
        final boolean notApplyingBatch = !applyingBatch();
        if (notApplyingBatch) {
            mDb.beginTransaction();
        }
        try {
            if (isTemporary() && mSyncState.matches(url)) {
                Uri result = mSyncState.asContentProvider().insert(url, values);
                if (notApplyingBatch) {
                    mDb.setTransactionSuccessful();
                }
                return result;
            }
            Uri result = insertInternal(url, values);
            if (notApplyingBatch) {
                mDb.setTransactionSuccessful();
            }
            if (!isTemporary() && result != null) {
                if (notApplyingBatch) {
                    getContext().getContentResolver().notifyChange(url, null /* observer */,
                            changeRequiresLocalSync(url));
                } else {
                    mPendingBatchNotifications.get().add(url);
                }
            }
            return result;
        } finally {
            if (notApplyingBatch) {
                mDb.endTransaction();
            }
        }
    }
File
AbstractSyncableContentProvider.java
Developer's decision
Combination
Kind of conflict
Annotation
Attribute
Comment
If statement
Method declaration
Method invocation
Method signature
Return statement
Try statement
Variable