use of org.zalando.nakadi.exceptions.TopicCreationException in project nakadi by zalando.
the class EventTypeServiceTest method shouldRemoveEventTypeWhenTimelineCreationFails.
@Test
public void shouldRemoveEventTypeWhenTimelineCreationFails() throws Exception {
final EventType eventType = buildDefaultEventType();
when(timelineService.createDefaultTimeline(anyString(), anyInt(), anyLong())).thenThrow(new TopicCreationException("Failed to create topic"));
try {
eventTypeService.create(eventType);
} catch (final TopicCreationException e) {
}
verify(eventTypeRepository, times(1)).removeEventType(eventType.getName());
}
use of org.zalando.nakadi.exceptions.TopicCreationException in project nakadi by zalando.
the class TimelineService method createDefaultTimeline.
public Timeline createDefaultTimeline(final String eventTypeName, final int partitionsCount, final long retentionTime) throws TopicCreationException, InconsistentStateException, RepositoryProblemException, DuplicatedTimelineException, TimelineException, DbWriteOperationsBlockedException {
if (featureToggleService.isFeatureEnabled(FeatureToggleService.Feature.DISABLE_DB_WRITE_OPERATIONS)) {
throw new DbWriteOperationsBlockedException("Cannot create default timeline: write operations on DB " + "are blocked by feature flag.");
}
final TopicRepository repository = topicRepositoryHolder.getTopicRepository(defaultStorage.getStorage());
final String topic = repository.createTopic(partitionsCount, retentionTime);
try {
final Timeline timeline = Timeline.createTimeline(eventTypeName, 1, defaultStorage.getStorage(), topic, new Date());
timeline.setSwitchedAt(new Date());
timelineDbRepository.createTimeline(timeline);
eventTypeCache.updated(eventTypeName);
return timeline;
} catch (final InconsistentStateException | RepositoryProblemException | DuplicatedTimelineException e) {
rollbackTopic(repository, topic);
throw e;
} catch (final Exception e) {
rollbackTopic(repository, topic);
throw new TimelineException("Failed to update event type cache, while creating timeline", e);
}
}
use of org.zalando.nakadi.exceptions.TopicCreationException in project nakadi by zalando.
the class TimelineService method createTimeline.
public void createTimeline(final String eventTypeName, final String storageId) throws AccessDeniedException, TimelineException, TopicRepositoryException, InconsistentStateException, RepositoryProblemException, DbWriteOperationsBlockedException {
if (featureToggleService.isFeatureEnabled(FeatureToggleService.Feature.DISABLE_DB_WRITE_OPERATIONS)) {
throw new DbWriteOperationsBlockedException("Cannot create timeline: write operations on DB " + "are blocked by feature flag.");
}
try {
final EventType eventType = eventTypeCache.getEventType(eventTypeName);
if (!adminService.isAdmin(AuthorizationService.Operation.WRITE)) {
final Resource resource = new EventTypeResource(eventTypeName, eventType.getAuthorization());
throw new AccessDeniedException(AuthorizationService.Operation.ADMIN, resource);
}
final Storage storage = storageDbRepository.getStorage(storageId).orElseThrow(() -> new UnableProcessException("No storage with id: " + storageId));
final Timeline activeTimeline = getActiveTimeline(eventType);
final TopicRepository currentTopicRepo = topicRepositoryHolder.getTopicRepository(activeTimeline.getStorage());
final TopicRepository nextTopicRepo = topicRepositoryHolder.getTopicRepository(storage);
final List<PartitionStatistics> partitionStatistics = currentTopicRepo.loadTopicStatistics(Collections.singleton(activeTimeline));
final String newTopic = nextTopicRepo.createTopic(partitionStatistics.size(), eventType.getOptions().getRetentionTime());
final Timeline nextTimeline = Timeline.createTimeline(activeTimeline.getEventType(), activeTimeline.getOrder() + 1, storage, newTopic, new Date());
switchTimelines(activeTimeline, nextTimeline);
} catch (final TopicCreationException | ServiceUnavailableException | InternalNakadiException e) {
throw new TimelineException("Internal service error", e);
} catch (final NoSuchEventTypeException e) {
throw new NotFoundException("EventType \"" + eventTypeName + "\" does not exist", e);
}
}
use of org.zalando.nakadi.exceptions.TopicCreationException in project nakadi by zalando.
the class KafkaTopicRepository method createTopic.
private void createTopic(final String topic, final int partitionsNum, final int replicaFactor, final long retentionMs, final long rotationMs) throws TopicCreationException {
try {
doWithZkUtils(zkUtils -> {
final Properties topicConfig = new Properties();
topicConfig.setProperty("retention.ms", Long.toString(retentionMs));
topicConfig.setProperty("segment.ms", Long.toString(rotationMs));
AdminUtils.createTopic(zkUtils, topic, partitionsNum, replicaFactor, topicConfig, RackAwareMode.Safe$.MODULE$);
});
} catch (final TopicExistsException e) {
throw new TopicCreationException("Topic with name " + topic + " already exists (or wasn't completely removed yet)", e);
} catch (final Exception e) {
throw new TopicCreationException("Unable to create topic " + topic, e);
}
// Next step is to wait for topic initialization. On can not skip this task, cause kafka instances may not
// receive information about topic creation, which in turn will block publishing.
// This kind of behavior was observed during tests, but may also present on highly loaded event types.
final long timeoutMillis = TimeUnit.SECONDS.toMillis(5);
final Boolean allowsConsumption = Retryer.executeWithRetry(() -> {
try (Consumer<byte[], byte[]> consumer = kafkaFactory.getConsumer()) {
return null != consumer.partitionsFor(topic);
}
}, new RetryForSpecifiedTimeStrategy<Boolean>(timeoutMillis).withWaitBetweenEachTry(100L).withResultsThatForceRetry(Boolean.FALSE));
if (!Boolean.TRUE.equals(allowsConsumption)) {
throw new TopicCreationException("Failed to confirm topic creation within " + timeoutMillis + " millis");
}
}
Aggregations