use of org.apache.ignite.internal.cache.query.index.sorted.IndexRow in project ignite by apache.
the class IndexQueryProcessor method queryLocal.
/**
* Run query on local node.
*
* @return Query result that contains data iterator and related metadata.
*/
public <K, V> IndexQueryResult<K, V> queryLocal(GridCacheContext<K, V> cctx, IndexQueryDesc idxQryDesc, @Nullable IgniteBiPredicate<K, V> filter, IndexingQueryFilter cacheFilter, boolean keepBinary) throws IgniteCheckedException {
SortedSegmentedIndex idx = findSortedIndex(cctx, idxQryDesc);
IndexRangeQuery qry = prepareQuery(idx, idxQryDesc);
GridCursor<IndexRow> cursor = querySortedIndex(cctx, idx, cacheFilter, qry);
SortedIndexDefinition def = (SortedIndexDefinition) idxProc.indexDefinition(idx.id());
IndexQueryResultMeta meta = new IndexQueryResultMeta(def, qry.criteria.length);
// Map IndexRow to Cache Key-Value pair.
return new IndexQueryResult<>(meta, new GridCloseableIteratorAdapter<IgniteBiTuple<K, V>>() {
private IgniteBiTuple<K, V> currVal;
private final CacheObjectContext coctx = cctx.cacheObjectContext();
/**
* {@inheritDoc}
*/
@Override
protected boolean onHasNext() throws IgniteCheckedException {
if (currVal != null)
return true;
while (currVal == null && cursor.next()) {
IndexRow r = cursor.get();
K k = unwrap(r.cacheDataRow().key(), true);
V v = unwrap(r.cacheDataRow().value(), true);
if (filter != null) {
K k0 = keepBinary ? k : unwrap(r.cacheDataRow().key(), false);
V v0 = keepBinary ? v : unwrap(r.cacheDataRow().value(), false);
if (!filter.apply(k0, v0))
continue;
}
currVal = new IgniteBiTuple<>(k, v);
}
return currVal != null;
}
/**
* {@inheritDoc}
*/
@Override
protected IgniteBiTuple<K, V> onNext() {
if (currVal == null)
if (!hasNext())
throw new NoSuchElementException();
IgniteBiTuple<K, V> row = currVal;
currVal = null;
return row;
}
/**
*/
private <T> T unwrap(CacheObject o, boolean keepBinary) {
return (T) CacheObjectUtils.unwrapBinaryIfNeeded(coctx, o, keepBinary, false);
}
});
}
use of org.apache.ignite.internal.cache.query.index.sorted.IndexRow in project ignite by apache.
the class DefragIndexFactory method createIndexSegment.
/**
* {@inheritDoc}
*/
@Override
protected InlineIndexTree createIndexSegment(GridCacheContext<?, ?> cctx, SortedIndexDefinition def, RootPage rootPage, IoStatisticsHolder stats, InlineRecommender recommender, int segmentNum) throws Exception {
InlineIndexTree tree = new InlineIndexTree(def, cctx.group(), def.treeName(), offheap, offheap.reuseListForIndex(def.treeName()), newCachePageMemory, // Use old row handler to have access to inline index key types.
pageIoResolver(), rootPage.pageId().pageId(), rootPage.isAllocated(), oldIdx.inlineSize(), cctx.config().getSqlIndexMaxInlineSize(), def.keyTypeSettings(), null, stats, rowHndFactory, null);
final MetaPageInfo oldInfo = oldIdx.segment(segmentNum).metaInfo();
// Set IO wrappers for the new tree.
BPlusInnerIO<IndexRow> innerIO = (BPlusInnerIO<IndexRow>) wrap(tree.latestInnerIO(), tree.rowHandler());
BPlusLeafIO<IndexRow> leafIo = (BPlusLeafIO<IndexRow>) wrap(tree.latestLeafIO(), tree.rowHandler());
tree.setIos(new IOVersions<>(innerIO), new IOVersions<>(leafIo));
tree.copyMetaInfo(oldInfo);
tree.enableSequentialWriteMode();
return tree;
}
use of org.apache.ignite.internal.cache.query.index.sorted.IndexRow in project ignite by apache.
the class InlineIndexTree method compare.
/**
* {@inheritDoc}
*/
@Override
protected int compare(BPlusIO<IndexRow> io, long pageAddr, int idx, IndexRow row) throws IgniteCheckedException {
if (inlineSize == 0) {
IndexRow currRow = getRow(io, pageAddr, idx);
int cmp = compareFullRows(currRow, row, 0);
return cmp == 0 ? mvccCompare(currRow, row) : cmp;
}
int fieldOff = 0;
// Use it when can't compare values (variable length, for example).
int keyIdx;
IndexRow currRow = null;
int off = io.offset(idx);
List<IndexKeyDefinition> keyDefs = rowHnd.indexKeyDefinitions();
List<InlineIndexKeyType> keyTypes = rowHandler().inlineIndexKeyTypes();
for (keyIdx = 0; keyIdx < keyTypes.size(); keyIdx++) {
try {
// possible keys for that comparison).
if (row.key(keyIdx) == null)
return 0;
// Other keys are not inlined. Should compare as rows.
if (keyIdx >= keyTypes.size())
break;
int maxSize = inlineSize - fieldOff;
InlineIndexKeyType keyType = keyTypes.get(keyIdx);
int cmp = def.rowComparator().compareKey(pageAddr, off + fieldOff, maxSize, row.key(keyIdx), keyType);
if (cmp == CANT_BE_COMPARE || cmp == COMPARE_UNSUPPORTED)
break;
else
fieldOff += keyType.inlineSize(pageAddr, off + fieldOff);
if (cmp != 0) {
IndexKeyDefinition keyDef = keyDefs.get(keyIdx);
return applySortOrder(cmp, keyDef.order().sortOrder());
}
} catch (Exception e) {
throw new IgniteException("Failed to store new index row.", e);
}
}
if (keyIdx < keyDefs.size()) {
recommender.recommend(row, inlineSize);
if (currRow == null)
currRow = getRow(io, pageAddr, idx);
int ret = compareFullRows(currRow, row, keyIdx);
if (ret != 0)
return ret;
}
return mvccCompare((MvccIO) io, pageAddr, idx, row);
}
use of org.apache.ignite.internal.cache.query.index.sorted.IndexRow in project ignite by apache.
the class IndexingDefragmentation method defragmentTable.
/**
* Defragment one given table.
*/
private boolean defragmentTable(CacheGroupContext newCtx, IntMap<LinkMap> mappingByPartition, CheckpointTimeoutLock cpLock, Runnable cancellationChecker, int pageSize, PageMemoryEx oldCachePageMem, PageMemory newCachePageMemory, long cpLockThreshold, AtomicLong lastCpLockTs, TableIndexes indexes) throws IgniteCheckedException {
cpLock.checkpointReadLock();
try {
TreeIterator treeIterator = new TreeIterator(pageSize);
GridCacheContext<?, ?> cctx = indexes.cctx;
cancellationChecker.run();
for (InlineIndex oldIdx : indexes.idxs) {
InlineIndexRowHandler oldRowHnd = oldIdx.segment(0).rowHandler();
SortedIndexDefinition idxDef = (SortedIndexDefinition) indexing.indexDefinition(oldIdx.id());
InlineIndexImpl newIdx = new DefragIndexFactory(newCtx.offheap(), newCachePageMemory, oldIdx).createIndex(cctx, idxDef).unwrap(InlineIndexImpl.class);
int segments = oldIdx.segmentsCount();
for (int i = 0; i < segments; ++i) {
treeIterator.iterate(oldIdx.segment(i), oldCachePageMem, (theTree, io, pageAddr, idx) -> {
cancellationChecker.run();
if (System.currentTimeMillis() - lastCpLockTs.get() >= cpLockThreshold) {
cpLock.checkpointReadUnlock();
cpLock.checkpointReadLock();
lastCpLockTs.set(System.currentTimeMillis());
}
assert 1 == io.getVersion() : "IO version " + io.getVersion() + " is not supported by current defragmentation algorithm." + " Please implement copying of tree in a new format.";
BPlusIO<IndexRow> h2IO = DefragIndexFactory.wrap(io, oldRowHnd);
IndexRow row = theTree.getRow(h2IO, pageAddr, idx);
if (row instanceof DefragIndexRowImpl) {
DefragIndexRowImpl r = (DefragIndexRowImpl) row;
CacheDataRow cacheDataRow = r.cacheDataRow();
int partition = cacheDataRow.partition();
long link = r.link();
LinkMap map = mappingByPartition.get(partition);
long newLink = map.get(link);
// Use old row handler, as MetaInfo is copied from old tree.
DefragIndexRowImpl newRow = DefragIndexRowImpl.create(oldRowHnd, newLink, r, ((MvccIO) io).storeMvccInfo());
newIdx.putIndexRow(newRow);
}
return true;
});
}
}
return true;
} catch (Throwable t) {
newCtx.cacheObjectContext().kernalContext().failure().process(new FailureContext(CRITICAL_ERROR, t));
throw t;
} finally {
cpLock.checkpointReadUnlock();
}
}
use of org.apache.ignite.internal.cache.query.index.sorted.IndexRow in project ignite by apache.
the class InlineIndexImpl method findLast.
/**
* {@inheritDoc}
*/
@Override
public GridCursor<IndexRow> findLast(int segment, IndexQueryContext qryCtx) throws IgniteCheckedException {
InlineTreeFilterClosure closure = filterClosure(qryCtx);
IndexRow found = segments[segment].findLast(closure);
if (found == null || isExpired(found))
return IndexValueCursor.EMPTY;
return new SingleCursor<>(found);
}
Aggregations