use of io.pravega.client.connection.impl.ClientConnection in project pravega by pravega.
the class AsyncSegmentInputStreamTest method testRetryWithConnectionFailures.
@Test(timeout = 10000)
public void testRetryWithConnectionFailures() throws ConnectionFailedException {
Segment segment = new Segment("scope", "testRetry", 4);
PravegaNodeUri endpoint = new PravegaNodeUri("localhost", SERVICE_PORT);
@Cleanup MockConnectionFactoryImpl connectionFactory = new MockConnectionFactoryImpl();
@Cleanup MockController controller = new MockController(endpoint.getEndpoint(), endpoint.getPort(), connectionFactory, true);
ClientConnection c = mock(ClientConnection.class);
connectionFactory.provideConnection(endpoint, c);
MockConnectionFactoryImpl mockedCF = spy(connectionFactory);
Semaphore dataAvailable = new Semaphore(0);
@Cleanup AsyncSegmentInputStreamImpl in = new AsyncSegmentInputStreamImpl(controller, mockedCF, segment, DelegationTokenProviderFactory.createWithEmptyToken(), dataAvailable);
InOrder inOrder = Mockito.inOrder(c);
// Failed Connection
CompletableFuture<ClientConnection> failedConnection = new CompletableFuture<>();
failedConnection.completeExceptionally(new ConnectionFailedException("Netty error while establishing connection"));
// Successful Connection
CompletableFuture<ClientConnection> successfulConnection = new CompletableFuture<>();
successfulConnection.complete(c);
WireCommands.SegmentRead segmentRead = new WireCommands.SegmentRead(segment.getScopedName(), 1234, false, false, Unpooled.EMPTY_BUFFER, in.getRequestId());
// simulate a establishConnection failure to segment store.
Mockito.doReturn(failedConnection).doCallRealMethod().when(mockedCF).establishConnection(eq(endpoint), any(ReplyProcessor.class));
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) {
// Simulate a connection failure post establishing connection to SegmentStore.
throw Exceptions.sneakyThrow(new ConnectionFailedException("SendAsync exception since netty channel is null"));
}
}).doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) {
mockedCF.getProcessor(endpoint).process(segmentRead);
return null;
}
}).when(c).send(any(ReadSegment.class));
assertEquals(0, dataAvailable.availablePermits());
// Read invocation.
CompletableFuture<SegmentRead> readFuture = in.read(1234, 5678);
// Verification.
assertEquals(segmentRead, readFuture.join());
// read completes after 3 retries.
assertTrue(Futures.isSuccessful(readFuture));
assertEquals(1, dataAvailable.availablePermits());
// Verify that the reader attempts to establish connection 3 times ( 2 failures followed by a successful attempt).
verify(mockedCF, times(3)).establishConnection(eq(endpoint), any(ReplyProcessor.class));
// The second time sendAsync is invoked but it fail due to the exception.
inOrder.verify(c).send(eq(new WireCommands.ReadSegment(segment.getScopedName(), 1234, 5678, "", in.getRequestId())));
// Validate that the connection is closed in case of an error.
inOrder.verify(c).close();
// Validate that the read command is send again over the new connection.
inOrder.verify(c).send(eq(new WireCommands.ReadSegment(segment.getScopedName(), 1234, 5678, "", in.getRequestId())));
// No more interactions since the SSS responds and the ReplyProcessor.segmentRead is invoked by netty.
verifyNoMoreInteractions(c);
}
use of io.pravega.client.connection.impl.ClientConnection in project pravega by pravega.
the class AsyncSegmentInputStreamTest method testProcessingFailure.
@Test
public void testProcessingFailure() throws ConnectionFailedException {
Segment segment = new Segment("scope", "testRetry", 4);
PravegaNodeUri endpoint = new PravegaNodeUri("localhost", SERVICE_PORT);
@Cleanup MockConnectionFactoryImpl connectionFactory = new MockConnectionFactoryImpl();
@Cleanup MockController controller = new MockController(endpoint.getEndpoint(), endpoint.getPort(), connectionFactory, true);
DelegationTokenProvider tokenProvider = mock(DelegationTokenProvider.class);
// return empty token
when(tokenProvider.retrieveToken()).thenReturn(CompletableFuture.completedFuture(""));
Semaphore dataAvailable = new Semaphore(0);
@Cleanup AsyncSegmentInputStreamImpl in = new AsyncSegmentInputStreamImpl(controller, connectionFactory, segment, tokenProvider, dataAvailable);
ClientConnection c = mock(ClientConnection.class);
InOrder inOrder = Mockito.inOrder(c);
connectionFactory.provideConnection(endpoint, c);
WireCommands.SegmentRead segmentRead = new WireCommands.SegmentRead(segment.getScopedName(), 1234, false, false, Unpooled.EMPTY_BUFFER, in.getRequestId());
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
connectionFactory.getProcessor(endpoint).processingFailure(new ConnectionFailedException("Custom error"));
return null;
}
}).doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
connectionFactory.getProcessor(endpoint).process(segmentRead);
return null;
}
}).when(c).send(any(ReadSegment.class));
assertEquals(0, dataAvailable.availablePermits());
CompletableFuture<SegmentRead> readFuture = in.read(1234, 5678);
assertEquals(segmentRead, readFuture.join());
assertTrue(Futures.isSuccessful(readFuture));
assertEquals(1, dataAvailable.availablePermits());
inOrder.verify(c).send(eq(new WireCommands.ReadSegment(segment.getScopedName(), 1234, 5678, "", in.getRequestId())));
inOrder.verify(c).close();
inOrder.verify(c).send(eq(new WireCommands.ReadSegment(segment.getScopedName(), 1234, 5678, "", in.getRequestId())));
verifyNoMoreInteractions(c);
// ensure retrieve Token is invoked for every retry.
verify(tokenProvider, times(2)).retrieveToken();
}
use of io.pravega.client.connection.impl.ClientConnection in project pravega by pravega.
the class KeyValueTableManagerImplTest method setUp.
@Before
public void setUp() throws ConnectionFailedException {
this.connectionFactory = new MockConnectionFactoryImpl();
ClientConnection connection = mock(ClientConnection.class);
Mockito.doAnswer(invocation -> {
WireCommands.CreateTableSegment request = invocation.getArgument(0);
if (segments.add(request.getSegment())) {
this.connectionFactory.getProcessor(SERVER_LOCATION).process(new WireCommands.SegmentCreated(request.getRequestId(), request.getSegment()));
} else {
this.connectionFactory.getProcessor(SERVER_LOCATION).process(new WireCommands.SegmentAlreadyExists(request.getRequestId(), request.getSegment(), ""));
}
return null;
}).when(connection).send(Mockito.any(WireCommands.CreateTableSegment.class));
Mockito.doAnswer(invocation -> {
WireCommands.DeleteTableSegment request = invocation.getArgument(0);
if (segments.remove(request.getSegment())) {
this.connectionFactory.getProcessor(SERVER_LOCATION).process(new WireCommands.SegmentDeleted(request.getRequestId(), request.getSegment()));
} else {
this.connectionFactory.getProcessor(SERVER_LOCATION).process(new WireCommands.NoSuchSegment(request.getRequestId(), request.getSegment(), "", 0L));
}
return null;
}).when(connection).send(Mockito.any(WireCommands.DeleteTableSegment.class));
this.connectionFactory.provideConnection(SERVER_LOCATION, connection);
this.controller = new MockController(SERVER_LOCATION.getEndpoint(), SERVER_LOCATION.getPort(), this.connectionFactory, true);
this.controller.createScope(DEFAULT_SCOPE).join();
}
use of io.pravega.client.connection.impl.ClientConnection in project pravega by pravega.
the class StreamManagerImplTest method testForceDeleteScope.
@Test(timeout = 10000)
public void testForceDeleteScope() throws ConnectionFailedException, DeleteScopeFailedException {
// Setup Mocks
ClientConnection connection = mock(ClientConnection.class);
PravegaNodeUri location = new PravegaNodeUri("localhost", 0);
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.CreateSegment request = (WireCommands.CreateSegment) invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.SegmentCreated(request.getRequestId(), request.getSegment()));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.CreateSegment.class));
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.GetStreamSegmentInfo request = (WireCommands.GetStreamSegmentInfo) invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.StreamSegmentInfo(request.getRequestId(), request.getSegmentName(), true, false, false, 0, 0, 0));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.GetStreamSegmentInfo.class));
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.DeleteSegment request = (WireCommands.DeleteSegment) invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.SegmentDeleted(request.getRequestId(), request.getSegment()));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.DeleteSegment.class));
connectionFactory.provideConnection(location, connection);
MockController mockController = spy(new MockController(location.getEndpoint(), location.getPort(), connectionFactory, true));
ConnectionPoolImpl pool = new ConnectionPoolImpl(ClientConfig.builder().maxConnectionsPerSegmentStore(1).build(), connectionFactory);
@Cleanup final StreamManager streamManager = new StreamManagerImpl(mockController, pool);
String scope = "scope";
String stream1 = "stream1";
String stream2 = "stream2";
String stream3 = "stream3";
streamManager.createScope(scope);
streamManager.createStream(scope, stream1, StreamConfiguration.builder().scalingPolicy(ScalingPolicy.fixed(3)).build());
streamManager.createStream(scope, stream2, StreamConfiguration.builder().scalingPolicy(ScalingPolicy.fixed(3)).build());
streamManager.createStream(scope, stream3, StreamConfiguration.builder().scalingPolicy(ScalingPolicy.fixed(3)).build());
Set<Stream> streams = Sets.newHashSet(streamManager.listStreams(scope));
assertEquals(3, streams.size());
assertTrue(streams.stream().anyMatch(x -> x.getStreamName().equals(stream1)));
assertTrue(streams.stream().anyMatch(x -> x.getStreamName().equals(stream2)));
assertTrue(streams.stream().anyMatch(x -> x.getStreamName().equals(stream3)));
// mock controller client to throw exceptions when attempting to seal and delete for stream 1.
doAnswer(x -> Futures.failedFuture(new ControllerFailureException("Unable to seal stream"))).when(mockController).sealStream(scope, stream1);
doAnswer(x -> Futures.failedFuture(new IllegalArgumentException("Stream not sealed"))).when(mockController).deleteStream(scope, stream1);
AssertExtensions.assertThrows("Should have thrown exception", () -> streamManager.deleteScope(scope, true), e -> Exceptions.unwrap(e) instanceof DeleteScopeFailedException);
// reset mock controller
reset(mockController);
// throw invalid stream for stream 2. Delete should happen despite invalid stream exception.
doAnswer(x -> Futures.failedFuture(new InvalidStreamException("Stream does not exist"))).when(mockController).sealStream(scope, stream2);
assertTrue(streamManager.deleteScope(scope, true));
}
use of io.pravega.client.connection.impl.ClientConnection in project pravega by pravega.
the class StreamManagerImplTest method testForceDeleteScopeWithKeyValueTables.
@Test(timeout = 10000)
public void testForceDeleteScopeWithKeyValueTables() throws ConnectionFailedException, DeleteScopeFailedException {
// Setup Mocks
ClientConnection connection = mock(ClientConnection.class);
PravegaNodeUri location = new PravegaNodeUri("localhost", 0);
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.CreateSegment request = (WireCommands.CreateSegment) invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.SegmentCreated(request.getRequestId(), request.getSegment()));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.CreateSegment.class));
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.CreateTableSegment request = (WireCommands.CreateTableSegment) invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.SegmentCreated(request.getRequestId(), request.getSegment()));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.CreateTableSegment.class));
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.CreateTableSegment request = invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.SegmentCreated(request.getRequestId(), request.getSegment()));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.CreateTableSegment.class));
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.GetStreamSegmentInfo request = (WireCommands.GetStreamSegmentInfo) invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.StreamSegmentInfo(request.getRequestId(), request.getSegmentName(), true, false, false, 0, 0, 0));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.GetStreamSegmentInfo.class));
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.DeleteSegment request = (WireCommands.DeleteSegment) invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.SegmentDeleted(request.getRequestId(), request.getSegment()));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.DeleteSegment.class));
Mockito.doAnswer(new Answer<Void>() {
@Override
public Void answer(InvocationOnMock invocation) throws Throwable {
WireCommands.DeleteTableSegment request = invocation.getArgument(0);
connectionFactory.getProcessor(location).process(new WireCommands.SegmentDeleted(request.getRequestId(), request.getSegment()));
return null;
}
}).when(connection).send(Mockito.any(WireCommands.DeleteTableSegment.class));
connectionFactory.provideConnection(location, connection);
MockController mockController = spy(new MockController(location.getEndpoint(), location.getPort(), connectionFactory, true));
ConnectionPoolImpl pool = new ConnectionPoolImpl(ClientConfig.builder().maxConnectionsPerSegmentStore(1).build(), connectionFactory);
@Cleanup final StreamManager streamManager = new StreamManagerImpl(mockController, pool);
@Cleanup final KeyValueTableManager keyValueTableManager = new KeyValueTableManagerImpl(mockController, connectionFactory);
String scope = "scope";
String kvt1 = "kvt1";
String kvt2 = "kvt2";
streamManager.createScope(scope);
KeyValueTableConfiguration kvtConfig = KeyValueTableConfiguration.builder().partitionCount(1).primaryKeyLength(1).secondaryKeyLength(1).build();
keyValueTableManager.createKeyValueTable(scope, kvt1, kvtConfig);
keyValueTableManager.createKeyValueTable(scope, kvt2, kvtConfig);
Set<KeyValueTableInfo> keyValueTables = Sets.newHashSet(keyValueTableManager.listKeyValueTables(scope));
assertEquals(2, keyValueTables.size());
assertTrue(keyValueTables.stream().anyMatch(x -> x.getKeyValueTableName().equals(kvt1)));
assertTrue(keyValueTables.stream().anyMatch(x -> x.getKeyValueTableName().equals(kvt2)));
// mock controller client to throw exceptions when attempting to delete key value table 1.
doAnswer(x -> Futures.failedFuture(new ControllerFailureException("Unable to delete key value table"))).when(mockController).deleteKeyValueTable(scope, kvt1);
AssertExtensions.assertThrows("Should have thrown exception", () -> streamManager.deleteScope(scope, true), e -> Exceptions.unwrap(e) instanceof DeleteScopeFailedException);
// reset mock controller
reset(mockController);
assertTrue(streamManager.deleteScope(scope, true));
}
Aggregations