Search in sources :

Example 1 with RangeIterator

use of org.apache.cassandra.index.sasi.utils.RangeIterator in project cassandra by apache.

the class TermIterator method build.

@SuppressWarnings("resource")
public static TermIterator build(final Expression e, Set<SSTableIndex> perSSTableIndexes) {
    final List<RangeIterator<Long, Token>> tokens = new CopyOnWriteArrayList<>();
    final AtomicLong tokenCount = new AtomicLong(0);
    RangeIterator<Long, Token> memtableIterator = e.index.searchMemtable(e);
    if (memtableIterator != null) {
        tokens.add(memtableIterator);
        tokenCount.addAndGet(memtableIterator.getCount());
    }
    final Set<SSTableIndex> referencedIndexes = new CopyOnWriteArraySet<>();
    try {
        final CountDownLatch latch = new CountDownLatch(perSSTableIndexes.size());
        final ExecutorService searchExecutor = SEARCH_EXECUTOR.get();
        for (final SSTableIndex index : perSSTableIndexes) {
            if (e.getOp() == Expression.Op.PREFIX && index.mode() == OnDiskIndexBuilder.Mode.CONTAINS && !index.hasMarkedPartials())
                throw new UnsupportedOperationException(String.format("The index %s has not yet been upgraded " + "to support prefix queries in CONTAINS mode. " + "Wait for compaction or rebuild the index.", index.getPath()));
            if (!index.reference()) {
                latch.countDown();
                continue;
            }
            // add to referenced right after the reference was acquired,
            // that helps to release index if something goes bad inside of the search
            referencedIndexes.add(index);
            searchExecutor.submit((Runnable) () -> {
                try {
                    e.checkpoint();
                    RangeIterator<Long, Token> keyIterator = index.search(e);
                    if (keyIterator == null) {
                        releaseIndex(referencedIndexes, index);
                        return;
                    }
                    tokens.add(keyIterator);
                    tokenCount.getAndAdd(keyIterator.getCount());
                } catch (Throwable e1) {
                    releaseIndex(referencedIndexes, index);
                    if (logger.isDebugEnabled())
                        logger.debug(String.format("Failed search an index %s, skipping.", index.getPath()), e1);
                } finally {
                    latch.countDown();
                }
            });
        }
        Uninterruptibles.awaitUninterruptibly(latch);
        // checkpoint right away after all indexes complete search because we might have crossed the quota
        e.checkpoint();
        RangeIterator<Long, Token> ranges = RangeUnionIterator.build(tokens);
        return new TermIterator(e, ranges, referencedIndexes);
    } catch (Throwable ex) {
        // if execution quota was exceeded while opening indexes or something else happened
        // local (yet to be tracked) indexes should be released first before re-throwing exception
        referencedIndexes.forEach(TermIterator::releaseQuietly);
        throw ex;
    }
}
Also used : RangeIterator(org.apache.cassandra.index.sasi.utils.RangeIterator) Token(org.apache.cassandra.index.sasi.disk.Token) AtomicLong(java.util.concurrent.atomic.AtomicLong) AtomicLong(java.util.concurrent.atomic.AtomicLong)

Example 2 with RangeIterator

use of org.apache.cassandra.index.sasi.utils.RangeIterator in project cassandra by apache.

the class ColumnIndex method searchMemtable.

public RangeIterator<Long, Token> searchMemtable(Expression e) {
    RangeIterator.Builder<Long, Token> builder = new RangeUnionIterator.Builder<>();
    builder.add(getCurrentMemtable().search(e));
    for (IndexMemtable memtable : getPendingMemtables()) builder.add(memtable.search(e));
    return builder.build();
}
Also used : RangeIterator(org.apache.cassandra.index.sasi.utils.RangeIterator) OnDiskIndexBuilder(org.apache.cassandra.index.sasi.disk.OnDiskIndexBuilder) Token(org.apache.cassandra.index.sasi.disk.Token) IndexMemtable(org.apache.cassandra.index.sasi.memory.IndexMemtable)

Example 3 with RangeIterator

use of org.apache.cassandra.index.sasi.utils.RangeIterator in project cassandra by apache.

the class SkipListMemIndex method search.

public RangeIterator<Long, Token> search(Expression expression) {
    ByteBuffer min = expression.lower == null ? null : expression.lower.value;
    ByteBuffer max = expression.upper == null ? null : expression.upper.value;
    SortedMap<ByteBuffer, ConcurrentSkipListSet<DecoratedKey>> search;
    if (min == null && max == null) {
        throw new IllegalArgumentException();
    }
    if (min != null && max != null) {
        search = index.subMap(min, expression.lower.inclusive, max, expression.upper.inclusive);
    } else if (min == null) {
        search = index.headMap(max, expression.upper.inclusive);
    } else {
        search = index.tailMap(min, expression.lower.inclusive);
    }
    RangeUnionIterator.Builder<Long, Token> builder = RangeUnionIterator.builder();
    search.values().stream().filter(keys -> !keys.isEmpty()).forEach(keys -> builder.add(new KeyRangeIterator(keys)));
    return builder.build();
}
Also used : RangeIterator(org.apache.cassandra.index.sasi.utils.RangeIterator) java.util(java.util) ConcurrentSkipListMap(java.util.concurrent.ConcurrentSkipListMap) DecoratedKey(org.apache.cassandra.db.DecoratedKey) ConcurrentSkipListSet(java.util.concurrent.ConcurrentSkipListSet) Expression(org.apache.cassandra.index.sasi.plan.Expression) Token(org.apache.cassandra.index.sasi.disk.Token) RangeUnionIterator(org.apache.cassandra.index.sasi.utils.RangeUnionIterator) AbstractType(org.apache.cassandra.db.marshal.AbstractType) ByteBuffer(java.nio.ByteBuffer) ColumnIndex(org.apache.cassandra.index.sasi.conf.ColumnIndex) ConcurrentSkipListSet(java.util.concurrent.ConcurrentSkipListSet) RangeUnionIterator(org.apache.cassandra.index.sasi.utils.RangeUnionIterator) Token(org.apache.cassandra.index.sasi.disk.Token) ByteBuffer(java.nio.ByteBuffer)

Example 4 with RangeIterator

use of org.apache.cassandra.index.sasi.utils.RangeIterator in project cassandra by apache.

the class TokenTreeTest method testMergingOfEqualTokenTrees.

public void testMergingOfEqualTokenTrees(SortedMap<Long, LongSet> tokensMap) throws Exception {
    TokenTreeBuilder tokensA = new DynamicTokenTreeBuilder(tokensMap);
    TokenTreeBuilder tokensB = new DynamicTokenTreeBuilder(tokensMap);
    TokenTree a = buildTree(tokensA);
    TokenTree b = buildTree(tokensB);
    TokenTreeBuilder tokensC = new StaticTokenTreeBuilder(new CombinedTerm(null, null) {

        public RangeIterator<Long, Token> getTokenIterator() {
            RangeIterator.Builder<Long, Token> union = RangeUnionIterator.builder();
            union.add(a.iterator(new KeyConverter()));
            union.add(b.iterator(new KeyConverter()));
            return union.build();
        }
    });
    TokenTree c = buildTree(tokensC);
    Assert.assertEquals(tokensMap.size(), c.getCount());
    Iterator<Token> tokenIterator = c.iterator(KEY_CONVERTER);
    Iterator<Map.Entry<Long, LongSet>> listIterator = tokensMap.entrySet().iterator();
    while (tokenIterator.hasNext() && listIterator.hasNext()) {
        Token treeNext = tokenIterator.next();
        Map.Entry<Long, LongSet> listNext = listIterator.next();
        Assert.assertEquals(listNext.getKey(), treeNext.get());
        Assert.assertEquals(convert(listNext.getValue()), convert(treeNext));
    }
    for (Map.Entry<Long, LongSet> entry : tokensMap.entrySet()) {
        TokenTree.OnDiskToken result = c.get(entry.getKey(), KEY_CONVERTER);
        Assert.assertNotNull("failed to find object for token " + entry.getKey(), result);
        LongSet found = result.getOffsets();
        Assert.assertEquals(entry.getValue(), found);
    }
}
Also used : RangeIterator(org.apache.cassandra.index.sasi.utils.RangeIterator) HashCodeBuilder(org.apache.commons.lang3.builder.HashCodeBuilder) LongSet(com.carrotsearch.hppc.LongSet) CombinedTerm(org.apache.cassandra.index.sasi.utils.CombinedTerm)

Aggregations

RangeIterator (org.apache.cassandra.index.sasi.utils.RangeIterator)4 Token (org.apache.cassandra.index.sasi.disk.Token)3 LongSet (com.carrotsearch.hppc.LongSet)1 ByteBuffer (java.nio.ByteBuffer)1 java.util (java.util)1 ConcurrentSkipListMap (java.util.concurrent.ConcurrentSkipListMap)1 ConcurrentSkipListSet (java.util.concurrent.ConcurrentSkipListSet)1 AtomicLong (java.util.concurrent.atomic.AtomicLong)1 DecoratedKey (org.apache.cassandra.db.DecoratedKey)1 AbstractType (org.apache.cassandra.db.marshal.AbstractType)1 ColumnIndex (org.apache.cassandra.index.sasi.conf.ColumnIndex)1 OnDiskIndexBuilder (org.apache.cassandra.index.sasi.disk.OnDiskIndexBuilder)1 IndexMemtable (org.apache.cassandra.index.sasi.memory.IndexMemtable)1 Expression (org.apache.cassandra.index.sasi.plan.Expression)1 CombinedTerm (org.apache.cassandra.index.sasi.utils.CombinedTerm)1 RangeUnionIterator (org.apache.cassandra.index.sasi.utils.RangeUnionIterator)1 HashCodeBuilder (org.apache.commons.lang3.builder.HashCodeBuilder)1