com.bigdata.service.NoCacheMetadataIndexView Maven / Gradle / Ivy
package com.bigdata.service;
import com.bigdata.btree.IRangeQuery;
import com.bigdata.btree.ITupleIterator;
import com.bigdata.btree.IndexMetadata;
import com.bigdata.btree.proc.IIndexProcedure;
import com.bigdata.btree.proc.RangeCountProcedure;
import com.bigdata.journal.ITx;
import com.bigdata.journal.WriteExecutorService;
import com.bigdata.mdi.IMetadataIndex;
import com.bigdata.mdi.PartitionLocator;
import com.bigdata.mdi.MetadataIndex.MetadataIndexMetadata;
import com.bigdata.service.ndx.RawDataServiceTupleIterator;
import cutthecrap.utils.striterators.IFilter;
/**
* An implementation that performs NO caching. All methods read through to the
* remote metadata index. Basically, this hides the RMI requests.
*
* @author Bryan Thompson
* @version $Id$
*/
public class NoCacheMetadataIndexView implements IMetadataIndex {
final private AbstractScaleOutFederation fed;
final private String name;
final private long timestamp;
final private MetadataIndexMetadata mdmd;
public MetadataIndexMetadata getIndexMetadata() {
return mdmd;
}
protected IMetadataService getMetadataService() {
return fed.getMetadataService();
}
/**
*
* @param name
* The name of the scale-out index.
* @param timestamp
*/
public NoCacheMetadataIndexView(AbstractScaleOutFederation fed,
String name, long timestamp, MetadataIndexMetadata mdmd) {
if (fed == null)
throw new IllegalArgumentException();
if (name == null)
throw new IllegalArgumentException();
if (mdmd == null)
throw new IllegalArgumentException();
this.fed = fed;
this.name = name;
this.timestamp = timestamp;
this.mdmd = mdmd;
}
// @todo re-fetch if READ_COMMITTED or UNISOLATED? it's very unlikely to change.
public IndexMetadata getScaleOutIndexMetadata() {
return mdmd;
}
// this could be cached easily, but its only used by the unit tests.
public PartitionLocator get(byte[] key) {
try {
return getMetadataService().get(name, timestamp, key);
} catch (Exception e) {
throw new RuntimeException(e);
}
}
// harder to cache - must look for "gaps"
public PartitionLocator find(byte[] key) {
try {
return getMetadataService().find(name, timestamp, key);
} catch (Exception e) {
throw new RuntimeException(e);
}
}
public long rangeCount() {
return rangeCount(null, null);
}
// only used by unit tests.
public long rangeCount(final byte[] fromKey, final byte[] toKey) {
final IIndexProcedure proc = new RangeCountProcedure(
false/* exact */, false/*deleted*/, fromKey, toKey);
final Long rangeCount;
try {
rangeCount = (Long) getMetadataService().submit(timestamp,
MetadataService.getMetadataIndexName(name), proc).get();
} catch (Exception e) {
throw new RuntimeException(e);
}
return rangeCount.longValue();
}
public long rangeCountExact(final byte[] fromKey, final byte[] toKey) {
final IIndexProcedure proc = new RangeCountProcedure(
true/* exact */, false/*deleted*/, fromKey, toKey);
final Long rangeCount;
try {
rangeCount = (Long) getMetadataService().submit(timestamp,
MetadataService.getMetadataIndexName(name), proc).get();
} catch (Exception e) {
throw new RuntimeException(e);
}
return rangeCount.longValue();
}
public long rangeCountExactWithDeleted(final byte[] fromKey, final byte[] toKey) {
final IIndexProcedure proc = new RangeCountProcedure(
true/* exact */, true/*deleted*/, fromKey, toKey);
final Long rangeCount;
try {
rangeCount = (Long) getMetadataService().submit(timestamp,
MetadataService.getMetadataIndexName(name), proc).get();
} catch (Exception e) {
throw new RuntimeException(e);
}
return rangeCount.longValue();
}
public ITupleIterator rangeIterator() {
return rangeIterator(null,null);
}
public ITupleIterator rangeIterator(final byte[] fromKey, final byte[] toKey) {
return rangeIterator(fromKey, toKey, 0/* capacity */,
IRangeQuery.DEFAULT, null/* filter */);
}
/**
* Note: Since this view is read-only this method forces the use of
* {@link ITx#READ_COMMITTED} IFF the timestamp for the view is
* {@link ITx#UNISOLATED}. This produces the same results on read and
* reduces contention for the {@link WriteExecutorService}. This is
* already done automatically for anything that gets run as an index
* procedure, so we only have to do this explicitly for the range
* iterator method.
*/
// not so interesting to cache, but could cache the iterator results on the scale-out index.
public ITupleIterator rangeIterator(byte[] fromKey, byte[] toKey,
int capacity, int flags, IFilter filter) {
return new RawDataServiceTupleIterator(getMetadataService(),//
MetadataService.getMetadataIndexName(name), //
(timestamp==ITx.UNISOLATED?ITx.READ_COMMITTED:timestamp),//
true, // read-consistent semantics.
fromKey,//
toKey,//
capacity,//
flags, //
filter
);
}
/**
* NOP since nothing is cached.
*/
public void staleLocator(PartitionLocator locator) {
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy