Search in sources :

Example 1 with UniqueConstraintException

use of org.cojen.tupl.UniqueConstraintException in project Tupl by cojen.

the class BasicRowUpdater method doUpdateAsDeleteInsert.

/**
 * Called when the primary key changed.
 *
 * @param c positioned at key to delete; position isn't changed
 * @param key key to insert
 * @param value value to insert
 * @throws UniqueConstraintException
 */
private void doUpdateAsDeleteInsert(R row, Cursor c, byte[] key, byte[] value) throws IOException {
    Index source = mTable.mSource;
    Transaction txn = ViewUtils.enterScope(source, c.link());
    try {
        Trigger<R> trigger = mTable.getTrigger();
        if (trigger != null)
            while (true) {
                trigger.acquireShared();
                try {
                    int mode = trigger.mode();
                    if (mode == Trigger.SKIP) {
                        break;
                    }
                    if (mode != Trigger.DISABLED) {
                        byte[] oldValue = c.value();
                        if (oldValue != null) {
                            // Don't pass the row because the key columns were modified.
                            trigger.delete(txn, c.key(), oldValue);
                        }
                        trigger.insertP(txn, row, key, value);
                        break;
                    }
                } finally {
                    trigger.releaseShared();
                }
                trigger = mTable.trigger();
            }
        boolean result;
        RowPredicateLock<R> lock = mTable.mIndexLock;
        if (lock == null) {
            result = source.insert(txn, key, value);
        } else {
            lock.redoPredicateMode(txn);
            try (RowPredicateLock.Closer closer = lock.openAcquireP(txn, row, key, value)) {
                result = source.insert(txn, key, value);
            }
        }
        if (!result) {
            throw new UniqueConstraintException("Primary key");
        }
        c.commit(null);
    } finally {
        txn.exit();
    }
    postStoreKeyValue(txn);
}
Also used : UniqueConstraintException(org.cojen.tupl.UniqueConstraintException) Transaction(org.cojen.tupl.Transaction) Index(org.cojen.tupl.Index) RowPredicateLock(org.cojen.tupl.core.RowPredicateLock)

Example 2 with UniqueConstraintException

use of org.cojen.tupl.UniqueConstraintException in project Tupl by cojen.

the class BasicRowUpdater method joinedUpdateCurrent.

// Called by JoinedRowUpdater.
final void joinedUpdateCurrent() throws IOException {
    try {
        R current = mRow;
        if (current == null) {
            throw new IllegalStateException("No current row");
        }
        Cursor c = mCursor;
        byte[] key, value;
        {
            RowEvaluator<R> evaluator = mEvaluator;
            key = evaluator.updateKey(current, c.key());
            value = evaluator.updateValue(current, c.value());
        }
        if (Arrays.equals(key, c.key())) {
            doUpdateAsStore(c, value);
        } else {
            doUpdateAsDeleteInsert(current, c, key, value);
        }
    } catch (UnpositionedCursorException e) {
        finished();
        throw new IllegalStateException("No current row");
    } catch (UniqueConstraintException e) {
        throw e;
    } catch (Throwable e) {
        throw RowUtils.fail(this, e);
    }
    // prevent subclass from attempting to release the lock
    unlocked();
}
Also used : UnpositionedCursorException(org.cojen.tupl.UnpositionedCursorException) UniqueConstraintException(org.cojen.tupl.UniqueConstraintException) Cursor(org.cojen.tupl.Cursor)

Example 3 with UniqueConstraintException

use of org.cojen.tupl.UniqueConstraintException in project Tupl by cojen.

the class BasicRowUpdater method doUpdateCurrent.

private void doUpdateCurrent(R row) throws IOException {
    Cursor c = mCursor;
    byte[] key, value;
    {
        RowEvaluator<R> evaluator = mEvaluator;
        key = evaluator.updateKey(row, c.key());
        value = evaluator.updateValue(row, c.value());
    }
    int cmp;
    if (key == null || (cmp = c.compareKeyTo(key)) == 0) {
        // Key didn't change.
        doUpdateAsStore(c, value);
        return;
    }
    if (cmp < 0 && (!mController.predicate().testP(row, key, value) || !addKeyToSkip(key))) {
        // No need to remember it because the updated row is filtered out, or don't try
        // removing it from the set in case of UniqueConstraintException.
        cmp = 0;
    }
    try {
        doUpdateAsDeleteInsert(row, c, key, value);
    } catch (UniqueConstraintException e) {
        if (cmp < 0) {
            mKeysToSkip.remove(key);
        }
        throw e;
    }
}
Also used : UniqueConstraintException(org.cojen.tupl.UniqueConstraintException) Cursor(org.cojen.tupl.Cursor)

Aggregations

UniqueConstraintException (org.cojen.tupl.UniqueConstraintException)3 Cursor (org.cojen.tupl.Cursor)2 Index (org.cojen.tupl.Index)1 Transaction (org.cojen.tupl.Transaction)1 UnpositionedCursorException (org.cojen.tupl.UnpositionedCursorException)1 RowPredicateLock (org.cojen.tupl.core.RowPredicateLock)1