use of de.invesdwin.util.time.range.TimeRange in project invesdwin-context-persistence by subes.
the class ASegmentedTimeSeriesStorageCache method getLatestValue.
public V getLatestValue(final FDate pDate) {
final FDate date = FDates.min(pDate, getLastAvailableSegmentTo(key, pDate));
final SingleValue value = storage.getOrLoad_latestValueLookupTable(hashKey, date, () -> {
final FDate firstAvailableSegmentFrom = getFirstAvailableSegmentFrom(key);
// already adjusted on the outside
final FDate adjFrom = date;
final FDate adjTo = firstAvailableSegmentFrom;
final FDate lastAvailableSegmentTo = getLastAvailableSegmentTo(key, adjFrom);
final ICloseableIterable<TimeRange> segmentsReverse = getSegmentsReverse(adjFrom, adjTo, lastAvailableSegmentTo);
try (ICloseableIterator<TimeRange> it = segmentsReverse.iterator()) {
V latestValue = null;
while (it.hasNext()) {
final TimeRange segment = it.next();
final SegmentedKey<K> segmentedKey = new SegmentedKey<K>(key, segment);
maybeInitSegment(segmentedKey);
final V newValue = segmentedTable.getLatestValue(segmentedKey, date);
if (newValue != null) {
final FDate newValueTime = segmentedTable.extractEndTime(newValue);
if (newValueTime.isBeforeOrEqualTo(date)) {
/*
* even if we got the first value in this segment and it is after the desired key we just
* continue to the beginning to search for an earlier value until we reach the overall
* firstValue
*/
latestValue = newValue;
break;
}
}
}
if (latestValue == null) {
latestValue = getFirstValue();
}
if (latestValue == null) {
return null;
}
return new SingleValue(valueSerde, latestValue);
}
});
if (value == null) {
return null;
}
return value.getValue(valueSerde);
}
use of de.invesdwin.util.time.range.TimeRange in project invesdwin-context-persistence by subes.
the class ASegmentedTimeSeriesStorageCache method initSegment.
private void initSegment(final SegmentedKey<K> segmentedKey, final Function<SegmentedKey<K>, ICloseableIterable<? extends V>> source) {
try {
final ITimeSeriesUpdater<SegmentedKey<K>, V> updater = newSegmentUpdater(segmentedKey, source);
final Callable<Void> task = new Callable<Void>() {
@Override
public Void call() throws Exception {
// write lock is reentrant
updater.update();
return null;
}
};
final String taskName = "Loading " + getElementsName() + " for " + hashKey;
final Callable<Percent> progress = new Callable<Percent>() {
@Override
public Percent call() throws Exception {
return updater.getProgress();
}
};
TaskInfoCallable.of(taskName, task, progress).call();
final FDate minTime = updater.getMinTime();
if (minTime != null) {
final FDate segmentFrom = segmentedKey.getSegment().getFrom();
final TimeRange prevSegment = getSegmentFinder(segmentedKey.getKey()).query().getValue(segmentFrom.addMilliseconds(-1));
if (prevSegment.getTo().equalsNotNullSafe(segmentFrom) && minTime.isBeforeOrEqualTo(segmentFrom)) {
throw new IllegalStateException(segmentedKey + ": minTime [" + minTime + "] should not be before or equal to segmentFrom [" + segmentFrom + "] when overlapping segments are used");
} else if (minTime.isBefore(segmentFrom)) {
throw new IllegalStateException(segmentedKey + ": minTime [" + minTime + "] should not be before segmentFrom [" + segmentFrom + "] when non overlapping segments are used");
}
final FDate maxTime = updater.getMaxTime();
final FDate segmentTo = segmentedKey.getSegment().getTo();
if (maxTime.isAfter(segmentTo)) {
throw new IllegalStateException(segmentedKey + ": maxTime [" + maxTime + "] should not be after segmentTo [" + segmentTo + "]");
}
}
} catch (final Throwable t) {
if (Throwables.isCausedByType(t, IncompleteUpdateFoundException.class)) {
segmentedTable.deleteRange(new SegmentedKey<K>(segmentedKey.getKey(), segmentedKey.getSegment()));
throw new RetryLaterRuntimeException(t);
} else {
throw Throwables.propagate(t);
}
}
}
use of de.invesdwin.util.time.range.TimeRange in project invesdwin-context-persistence by subes.
the class ASegmentedTimeSeriesStorageCache method deleteAll.
public synchronized void deleteAll() {
final ADelegateRangeTable<String, TimeRange, SegmentStatus> segmentStatusTable = storage.getSegmentStatusTable();
final List<TimeRange> rangeKeys;
try (ICloseableIterator<TimeRange> rangeKeysIterator = new ATransformingIterator<RangeTableRow<String, TimeRange, SegmentStatus>, TimeRange>(segmentStatusTable.range(hashKey)) {
@Override
protected TimeRange transform(final RangeTableRow<String, TimeRange, SegmentStatus> value) {
return value.getRangeKey();
}
}) {
rangeKeys = Lists.toListWithoutHasNext(rangeKeysIterator);
}
for (int i = 0; i < rangeKeys.size(); i++) {
final TimeRange rangeKey = rangeKeys.get(i);
segmentedTable.deleteRange(new SegmentedKey<K>(key, rangeKey));
}
segmentStatusTable.deleteRange(hashKey);
storage.deleteRange_latestValueLookupTable(hashKey);
storage.deleteRange_nextValueLookupTable(hashKey);
storage.deleteRange_previousValueLookupTable(hashKey);
clearCaches();
}
use of de.invesdwin.util.time.range.TimeRange in project invesdwin-context-persistence by subes.
the class PersistentLiveSegment method putNextLiveValues.
public void putNextLiveValues(final ICloseableIterable<V> memoryValues) {
final ADelegateRangeTable<String, TimeRange, SegmentStatus> segmentStatusTable = historicalSegmentTable.getStorage().getSegmentStatusTable();
final SegmentStatus existingStatus = segmentStatusTable.get(hashKey, segmentedKey.getSegment());
if (existingStatus == null) {
segmentStatusTable.put(hashKey, segmentedKey.getSegment(), SegmentStatus.INITIALIZING);
} else if (existingStatus != SegmentStatus.INITIALIZING) {
throw UnknownArgumentException.newInstance(SegmentStatus.class, existingStatus);
}
final ATimeSeriesUpdater<SegmentedKey<K>, V> updater = new ATimeSeriesUpdater<SegmentedKey<K>, V>(segmentedKey, table) {
@Override
protected ICloseableIterable<? extends V> getSource(final FDate updateFrom) {
return memoryValues;
}
@Override
protected void onUpdateFinished(final Instant updateStart) {
}
@Override
protected void onUpdateStart() {
}
@Override
protected FDate extractEndTime(final V element) {
return historicalSegmentTable.extractEndTime(element);
}
@Override
protected void onFlush(final int flushIndex, final ATimeSeriesUpdater<SegmentedKey<K>, V>.UpdateProgress updateProgress) {
}
@Override
protected boolean shouldRedoLastFile() {
return false;
}
@Override
public Percent getProgress() {
return null;
}
};
try {
Assertions.checkTrue(updater.update());
} catch (final IncompleteUpdateFoundException e) {
throw new RuntimeException(e);
}
empty = false;
}
use of de.invesdwin.util.time.range.TimeRange in project invesdwin-context-persistence by subes.
the class PeriodicalSegmentFinder method calculateNextTimeRange.
private TimeRange calculateNextTimeRange(final FDate curTimeRangeFrom) {
final FDate nextTimeRangeStart = incrementFunction.apply(curTimeRangeFrom);
final FDate nextTimeRangeEnd = incrementFunction.apply(nextTimeRangeStart).addMilliseconds(-1);
return new TimeRange(nextTimeRangeStart, nextTimeRangeEnd);
}
Aggregations