use of org.zalando.nakadi.domain.NakadiCursor in project nakadi by zalando.
the class MultiTimelineEventConsumer method selectCorrectTopicRepo.
private TopicRepository selectCorrectTopicRepo(final NakadiCursor cursor, final Consumer<NakadiCursor> cursorReplacer, final Consumer<NakadiCursor> lastTimelinePosition) throws ServiceUnavailableException {
final List<Timeline> eventTimelines = eventTypeTimelines.get(cursor.getEventType());
final ListIterator<Timeline> itTimeline = eventTimelines.listIterator(eventTimelines.size());
// select last timeline, and then move back until position was found.
Timeline electedTimeline = itTimeline.previous();
while (itTimeline.hasPrevious()) {
final Timeline toCheck = itTimeline.previous();
final NakadiCursor latest = toCheck.calculateNakadiLatestPosition(cursor.getPartition());
if (latest == null) {
electedTimeline = toCheck;
} else if (comparator.compare(latest, cursor) > 0) {
// There is a border case - latest is equal to begin (that means that there are no available events
// there), and one should position on timeline that have something inside.
final NakadiCursor firstItem = timelineService.getTopicRepository(toCheck).loadPartitionStatistics(toCheck, cursor.getPartition()).get().getFirst();
if (comparator.compare(latest, firstItem) >= 0) {
electedTimeline = toCheck;
} else {
LOG.info("Timeline {} is empty, skipping", toCheck);
}
} else {
break;
}
}
final TopicRepository result = timelineService.getTopicRepository(electedTimeline);
if (electedTimeline.getOrder() != cursor.getTimeline().getOrder()) {
// It seems that cursor jumped to different timeline. One need to fetch very first cursor in timeline.
final NakadiCursor replacement = getBeforeFirstCursor(result, electedTimeline, cursor.getPartition());
LOG.info("Replacing cursor because of jumping between timelines from {} to {}", cursor, replacement);
cursorReplacer.accept(replacement);
}
lastTimelinePosition.accept(electedTimeline.calculateNakadiLatestPosition(cursor.getPartition()));
return result;
}
Aggregations