use of org.opensearch.transport.TransportResponseHandler in project OpenSearch by opensearch-project.
the class FollowersCheckerTests method testResponder.
public void testResponder() {
final DiscoveryNode leader = new DiscoveryNode("leader", buildNewFakeTransportAddress(), Version.CURRENT);
final DiscoveryNode follower = new DiscoveryNode("follower", buildNewFakeTransportAddress(), Version.CURRENT);
final Settings settings = Settings.builder().put(NODE_NAME_SETTING.getKey(), follower.getName()).build();
final DeterministicTaskQueue deterministicTaskQueue = new DeterministicTaskQueue(settings, random());
final MockTransport mockTransport = new MockTransport() {
@Override
protected void onSendRequest(long requestId, String action, TransportRequest request, DiscoveryNode node) {
throw new AssertionError("no requests expected");
}
};
final TransportService transportService = mockTransport.createTransportService(settings, deterministicTaskQueue.getThreadPool(), TransportService.NOOP_TRANSPORT_INTERCEPTOR, boundTransportAddress -> follower, null, emptySet());
transportService.start();
transportService.acceptIncomingRequests();
final AtomicBoolean calledCoordinator = new AtomicBoolean();
final AtomicReference<RuntimeException> coordinatorException = new AtomicReference<>();
final FollowersChecker followersChecker = new FollowersChecker(settings, transportService, fcr -> {
assertTrue(calledCoordinator.compareAndSet(false, true));
final RuntimeException exception = coordinatorException.get();
if (exception != null) {
throw exception;
}
}, (node, reason) -> {
assert false : node;
}, () -> new StatusInfo(HEALTHY, "healthy-info"));
{
// Does not call into the coordinator in the normal case
final long term = randomNonNegativeLong();
followersChecker.updateFastResponseState(term, Mode.FOLLOWER);
final ExpectsSuccess expectsSuccess = new ExpectsSuccess();
transportService.sendRequest(follower, FOLLOWER_CHECK_ACTION_NAME, new FollowerCheckRequest(term, leader), expectsSuccess);
deterministicTaskQueue.runAllTasks();
assertTrue(expectsSuccess.succeeded());
assertFalse(calledCoordinator.get());
}
{
// Does not call into the coordinator for a term that's too low, just rejects immediately
final long leaderTerm = randomLongBetween(1, Long.MAX_VALUE - 1);
final long followerTerm = randomLongBetween(leaderTerm + 1, Long.MAX_VALUE);
followersChecker.updateFastResponseState(followerTerm, Mode.FOLLOWER);
final AtomicReference<TransportException> receivedException = new AtomicReference<>();
transportService.sendRequest(follower, FOLLOWER_CHECK_ACTION_NAME, new FollowerCheckRequest(leaderTerm, leader), new TransportResponseHandler<TransportResponse.Empty>() {
@Override
public TransportResponse.Empty read(StreamInput in) {
return TransportResponse.Empty.INSTANCE;
}
@Override
public void handleResponse(TransportResponse.Empty response) {
fail("unexpected success");
}
@Override
public void handleException(TransportException exp) {
assertThat(exp, not(nullValue()));
assertTrue(receivedException.compareAndSet(null, exp));
}
@Override
public String executor() {
return Names.SAME;
}
});
deterministicTaskQueue.runAllTasks();
assertFalse(calledCoordinator.get());
assertThat(receivedException.get(), not(nullValue()));
}
{
// Calls into the coordinator if the term needs bumping
final long leaderTerm = randomLongBetween(2, Long.MAX_VALUE);
final long followerTerm = randomLongBetween(1, leaderTerm - 1);
followersChecker.updateFastResponseState(followerTerm, Mode.FOLLOWER);
final ExpectsSuccess expectsSuccess = new ExpectsSuccess();
transportService.sendRequest(follower, FOLLOWER_CHECK_ACTION_NAME, new FollowerCheckRequest(leaderTerm, leader), expectsSuccess);
deterministicTaskQueue.runAllTasks();
assertTrue(expectsSuccess.succeeded());
assertTrue(calledCoordinator.get());
calledCoordinator.set(false);
}
{
// Calls into the coordinator if not a follower
final long term = randomNonNegativeLong();
followersChecker.updateFastResponseState(term, randomFrom(Mode.LEADER, Mode.CANDIDATE));
final ExpectsSuccess expectsSuccess = new ExpectsSuccess();
transportService.sendRequest(follower, FOLLOWER_CHECK_ACTION_NAME, new FollowerCheckRequest(term, leader), expectsSuccess);
deterministicTaskQueue.runAllTasks();
assertTrue(expectsSuccess.succeeded());
assertTrue(calledCoordinator.get());
calledCoordinator.set(false);
}
{
// If it calls into the coordinator and the coordinator throws an exception then it's passed back to the caller
final long term = randomNonNegativeLong();
followersChecker.updateFastResponseState(term, randomFrom(Mode.LEADER, Mode.CANDIDATE));
final String exceptionMessage = "test simulated exception " + randomNonNegativeLong();
coordinatorException.set(new OpenSearchException(exceptionMessage));
final AtomicReference<TransportException> receivedException = new AtomicReference<>();
transportService.sendRequest(follower, FOLLOWER_CHECK_ACTION_NAME, new FollowerCheckRequest(term, leader), new TransportResponseHandler<TransportResponse.Empty>() {
@Override
public TransportResponse.Empty read(StreamInput in) {
return TransportResponse.Empty.INSTANCE;
}
@Override
public void handleResponse(TransportResponse.Empty response) {
fail("unexpected success");
}
@Override
public void handleException(TransportException exp) {
assertThat(exp, not(nullValue()));
assertTrue(receivedException.compareAndSet(null, exp));
}
@Override
public String executor() {
return Names.SAME;
}
});
deterministicTaskQueue.runAllTasks();
assertTrue(calledCoordinator.get());
assertThat(receivedException.get(), not(nullValue()));
assertThat(receivedException.get().getRootCause().getMessage(), equalTo(exceptionMessage));
}
}
use of org.opensearch.transport.TransportResponseHandler in project OpenSearch by opensearch-project.
the class TransportReplicationAllPermitsAcquisitionTests method setUp.
@Override
@Before
public void setUp() throws Exception {
super.setUp();
globalBlock = randomBoolean();
RestStatus restStatus = randomFrom(RestStatus.values());
block = new ClusterBlock(randomIntBetween(1, 10), randomAlphaOfLength(5), false, true, false, restStatus, ClusterBlockLevel.ALL);
clusterService = createClusterService(threadPool);
final ClusterState.Builder state = ClusterState.builder(clusterService.state());
Set<DiscoveryNodeRole> roles = new HashSet<>(DiscoveryNodeRole.BUILT_IN_ROLES);
DiscoveryNode node1 = new DiscoveryNode("_name1", "_node1", buildNewFakeTransportAddress(), emptyMap(), roles, Version.CURRENT);
DiscoveryNode node2 = new DiscoveryNode("_name2", "_node2", buildNewFakeTransportAddress(), emptyMap(), roles, Version.CURRENT);
state.nodes(DiscoveryNodes.builder().add(node1).add(node2).localNodeId(node1.getId()).masterNodeId(node1.getId()));
shardId = new ShardId("index", UUID.randomUUID().toString(), 0);
ShardRouting shardRouting = newShardRouting(shardId, node1.getId(), true, ShardRoutingState.INITIALIZING, RecoverySource.EmptyStoreRecoverySource.INSTANCE);
Settings indexSettings = Settings.builder().put(SETTING_VERSION_CREATED, Version.CURRENT).put(SETTING_INDEX_UUID, shardId.getIndex().getUUID()).put(SETTING_NUMBER_OF_SHARDS, 1).put(SETTING_NUMBER_OF_REPLICAS, 1).put(SETTING_CREATION_DATE, System.currentTimeMillis()).build();
primary = newStartedShard(p -> newShard(shardRouting, indexSettings, new InternalEngineFactory()), true);
for (int i = 0; i < 10; i++) {
final String id = Integer.toString(i);
indexDoc(primary, "_doc", id, "{\"value\":" + id + "}");
}
IndexMetadata indexMetadata = IndexMetadata.builder(shardId.getIndexName()).settings(indexSettings).primaryTerm(shardId.id(), primary.getOperationPrimaryTerm()).putMapping("_doc", "{ \"properties\": { \"value\": { \"type\": \"short\"}}}").build();
state.metadata(Metadata.builder().put(indexMetadata, false).generateClusterUuidIfNeeded());
replica = newShard(primary.shardId(), false, node2.getId(), indexMetadata, null);
recoverReplica(replica, primary, true);
IndexRoutingTable.Builder routing = IndexRoutingTable.builder(indexMetadata.getIndex());
routing.addIndexShard(new IndexShardRoutingTable.Builder(shardId).addShard(primary.routingEntry()).build());
state.routingTable(RoutingTable.builder().add(routing.build()).build());
setState(clusterService, state.build());
final Settings transportSettings = Settings.builder().put("node.name", node1.getId()).build();
MockTransport transport = new MockTransport() {
@Override
protected void onSendRequest(long requestId, String action, TransportRequest request, DiscoveryNode node) {
assertThat(action, allOf(startsWith("cluster:admin/test/"), endsWith("[r]")));
assertThat(node, equalTo(node2));
// node2 doesn't really exist, but we are performing some trickery in mockIndicesService() to pretend that node1 holds both
// the primary and the replica, so redirect the request back to node1.
transportService.sendRequest(transportService.getLocalNode(), action, request, new TransportResponseHandler<TransportReplicationAction.ReplicaResponse>() {
@Override
public TransportReplicationAction.ReplicaResponse read(StreamInput in) throws IOException {
return new TransportReplicationAction.ReplicaResponse(in);
}
@SuppressWarnings("unchecked")
private TransportResponseHandler<TransportReplicationAction.ReplicaResponse> getResponseHandler() {
return (TransportResponseHandler<TransportReplicationAction.ReplicaResponse>) getResponseHandlers().onResponseReceived(requestId, TransportMessageListener.NOOP_LISTENER);
}
@Override
public void handleResponse(TransportReplicationAction.ReplicaResponse response) {
getResponseHandler().handleResponse(response);
}
@Override
public void handleException(TransportException exp) {
getResponseHandler().handleException(exp);
}
@Override
public String executor() {
return ThreadPool.Names.SAME;
}
});
}
};
transportService = transport.createTransportService(transportSettings, threadPool, TransportService.NOOP_TRANSPORT_INTERCEPTOR, bta -> node1, null, emptySet());
transportService.start();
transportService.acceptIncomingRequests();
shardStateAction = new ShardStateAction(clusterService, transportService, null, null, threadPool);
}
use of org.opensearch.transport.TransportResponseHandler in project OpenSearch by opensearch-project.
the class MockTransport method handleResponse.
/**
* simulate a response for the given requestId
*/
@SuppressWarnings("unchecked")
public <Response extends TransportResponse> void handleResponse(final long requestId, final Response response) {
final TransportResponseHandler<Response> transportResponseHandler = (TransportResponseHandler<Response>) getResponseHandlers().onResponseReceived(requestId, listener);
if (transportResponseHandler != null) {
final Response deliveredResponse;
try (BytesStreamOutput output = new BytesStreamOutput()) {
response.writeTo(output);
deliveredResponse = transportResponseHandler.read(new NamedWriteableAwareStreamInput(output.bytes().streamInput(), writeableRegistry()));
} catch (IOException | UnsupportedOperationException e) {
throw new AssertionError("failed to serialize/deserialize response " + response, e);
}
transportResponseHandler.handleResponse(deliveredResponse);
}
}
Aggregations