/** Throws an exception if write is not allowed or if a join cursor is in use. */ private void checkWriteAllowed(boolean allowSecondary) { checkNoJoinCursor(); if (!writeAllowed || (!allowSecondary && view.isSecondary())) { throw new UnsupportedOperationException("Writing is not allowed"); } }
/** Binding version of Cursor.getPrevDup(), no join cursor allowed. */ OperationStatus getPrevDup(boolean lockForWrite) throws DatabaseException { checkNoJoinCursor(); if (view.dupsView) { return null; } else { return cursor.getPrevDup(keyThang, primaryKeyThang, valueThang, getLockMode(lockForWrite)); } }
/** Calls Cursor.count(), no join cursor allowed. */ int count() throws DatabaseException { checkNoJoinCursor(); if (view.dupsView) { return 1; } else { return cursor.count(); } }
/** Binding version of Cursor.getSearchKeyRange(), no join cursor allowed. */ OperationStatus getSearchKeyRange(Object key, Object value, boolean lockForWrite) throws DatabaseException { checkNoJoinCursor(); LockMode lockMode = getLockMode(lockForWrite); if (view.dupsView) { if (view.useKey(key, value, primaryKeyThang, view.dupsRange)) { KeyRange.copy(view.dupsKey, keyThang); return cursor.getSearchBothRange(keyThang, primaryKeyThang, valueThang, lockMode); } } else { if (view.useKey(key, value, keyThang, range)) { return cursor.getSearchKeyRange(keyThang, primaryKeyThang, valueThang, lockMode); } } return OperationStatus.NOTFOUND; }
/** * Find the given key and value using getSearchBoth if possible or a sequential scan otherwise, no * join cursor allowed. */ OperationStatus findBoth(Object key, Object value, boolean lockForWrite) throws DatabaseException { checkNoJoinCursor(); LockMode lockMode = getLockMode(lockForWrite); view.useValue(value, valueThang, null); if (view.dupsView) { if (view.useKey(key, value, primaryKeyThang, view.dupsRange)) { KeyRange.copy(view.dupsKey, keyThang); if (otherThang == null) { otherThang = new DatabaseEntry(); } OperationStatus status = cursor.getSearchBoth(keyThang, primaryKeyThang, otherThang, lockMode); if (status == OperationStatus.SUCCESS && KeyRange.equalBytes(otherThang, valueThang)) { return status; } } } else if (view.useKey(key, value, keyThang, range)) { if (view.isSecondary()) { if (otherThang == null) { otherThang = new DatabaseEntry(); } OperationStatus status = cursor.getSearchKey(keyThang, primaryKeyThang, otherThang, lockMode); while (status == OperationStatus.SUCCESS) { if (KeyRange.equalBytes(otherThang, valueThang)) { return status; } status = cursor.getNextDup( keyThang, primaryKeyThang, otherThang, lockMode); } /* if status != SUCCESS set range cursor to invalid? */ } else { return cursor.getSearchBoth(keyThang, null, valueThang, lockMode); } } return OperationStatus.NOTFOUND; }
/** * Find the given value using getSearchBoth if possible or a sequential scan otherwise, no join * cursor allowed. */ OperationStatus findValue(Object value, boolean findFirst) throws DatabaseException { checkNoJoinCursor(); if (view.entityBinding != null && !view.isSecondary() && (findFirst || !view.dupsAllowed)) { return findBoth(null, value, false); } else { if (otherThang == null) { otherThang = new DatabaseEntry(); } view.useValue(value, otherThang, null); OperationStatus status = findFirst ? getFirst(false) : getLast(false); while (status == OperationStatus.SUCCESS) { if (KeyRange.equalBytes(valueThang, otherThang)) { break; } status = findFirst ? getNext(false) : getPrev(false); } return status; } }
/** Clones a cursor preserving the current position. */ DataCursor cloneCursor() throws DatabaseException { checkNoJoinCursor(); DataCursor o; try { o = (DataCursor) super.clone(); } catch (CloneNotSupportedException neverHappens) { return null; } o.initThangs(); KeyRange.copy(keyThang, o.keyThang); KeyRange.copy(valueThang, o.valueThang); if (primaryKeyThang != keyThang) { KeyRange.copy(primaryKeyThang, o.primaryKeyThang); } o.cursor = cursor.dup(true); return o; }
/** Binding version of Cursor.getPrev(), no join cursor allowed. */ OperationStatus getPrev(boolean lockForWrite) throws DatabaseException { checkNoJoinCursor(); return cursor.getPrev(keyThang, primaryKeyThang, valueThang, getLockMode(lockForWrite)); }