|
@@ -23,8 +23,6 @@ import com.fasterxml.jackson.databind.ObjectMapper;
|
|
|
import com.fasterxml.jackson.databind.ObjectReader;
|
|
|
import org.apache.hadoop.conf.Configuration;
|
|
|
import org.apache.hadoop.hdfs.HdfsConfiguration;
|
|
|
-import org.apache.hadoop.hdfs.server.blockmanagement.SlowPeerTracker
|
|
|
- .ReportForJson;
|
|
|
import org.apache.hadoop.util.FakeTimer;
|
|
|
import org.junit.Before;
|
|
|
import org.junit.Rule;
|
|
@@ -37,6 +35,7 @@ import java.io.IOException;
|
|
|
import java.util.Set;
|
|
|
|
|
|
import static org.hamcrest.core.Is.is;
|
|
|
+import static org.junit.Assert.assertEquals;
|
|
|
import static org.junit.Assert.assertFalse;
|
|
|
import static org.junit.Assert.assertThat;
|
|
|
import static org.junit.Assert.assertTrue;
|
|
@@ -59,7 +58,7 @@ public class TestSlowPeerTracker {
|
|
|
private FakeTimer timer;
|
|
|
private long reportValidityMs;
|
|
|
private static final ObjectReader READER =
|
|
|
- new ObjectMapper().readerFor(new TypeReference<Set<ReportForJson>>() {});
|
|
|
+ new ObjectMapper().readerFor(new TypeReference<Set<SlowPeerJsonReport>>() {});
|
|
|
|
|
|
@Before
|
|
|
public void setup() {
|
|
@@ -80,9 +79,9 @@ public class TestSlowPeerTracker {
|
|
|
|
|
|
@Test
|
|
|
public void testReportsAreRetrieved() {
|
|
|
- tracker.addReport("node2", "node1");
|
|
|
- tracker.addReport("node3", "node1");
|
|
|
- tracker.addReport("node3", "node2");
|
|
|
+ tracker.addReport("node2", "node1", 1.2);
|
|
|
+ tracker.addReport("node3", "node1", 2.1);
|
|
|
+ tracker.addReport("node3", "node2", 1.22);
|
|
|
|
|
|
assertThat(tracker.getReportsForAllDataNodes().size(), is(2));
|
|
|
assertThat(tracker.getReportsForNode("node2").size(), is(1));
|
|
@@ -95,9 +94,9 @@ public class TestSlowPeerTracker {
|
|
|
*/
|
|
|
@Test
|
|
|
public void testAllReportsAreExpired() {
|
|
|
- tracker.addReport("node2", "node1");
|
|
|
- tracker.addReport("node3", "node2");
|
|
|
- tracker.addReport("node1", "node3");
|
|
|
+ tracker.addReport("node2", "node1", 0.123);
|
|
|
+ tracker.addReport("node3", "node2", 0.2334);
|
|
|
+ tracker.addReport("node1", "node3", 1.234);
|
|
|
|
|
|
// No reports should expire after 1ms.
|
|
|
timer.advance(1);
|
|
@@ -117,13 +116,14 @@ public class TestSlowPeerTracker {
|
|
|
*/
|
|
|
@Test
|
|
|
public void testSomeReportsAreExpired() {
|
|
|
- tracker.addReport("node3", "node1");
|
|
|
- tracker.addReport("node3", "node2");
|
|
|
+ tracker.addReport("node3", "node1", 1.234);
|
|
|
+ tracker.addReport("node3", "node2", 1.222);
|
|
|
timer.advance(reportValidityMs);
|
|
|
- tracker.addReport("node3", "node4");
|
|
|
+ tracker.addReport("node3", "node4", 1.20);
|
|
|
assertThat(tracker.getReportsForAllDataNodes().size(), is(1));
|
|
|
assertThat(tracker.getReportsForNode("node3").size(), is(1));
|
|
|
- assertTrue(tracker.getReportsForNode("node3").contains("node4"));
|
|
|
+ assertEquals(1, tracker.getReportsForNode("node3").stream()
|
|
|
+ .filter(e -> e.getReportingNode().equals("node4")).count());
|
|
|
}
|
|
|
|
|
|
/**
|
|
@@ -131,24 +131,24 @@ public class TestSlowPeerTracker {
|
|
|
*/
|
|
|
@Test
|
|
|
public void testReplacement() {
|
|
|
- tracker.addReport("node2", "node1");
|
|
|
+ tracker.addReport("node2", "node1", 2.1);
|
|
|
timer.advance(reportValidityMs); // Expire the report.
|
|
|
assertThat(tracker.getReportsForAllDataNodes().size(), is(0));
|
|
|
|
|
|
// This should replace the expired report with a newer valid one.
|
|
|
- tracker.addReport("node2", "node1");
|
|
|
+ tracker.addReport("node2", "node1", 0.001);
|
|
|
assertThat(tracker.getReportsForAllDataNodes().size(), is(1));
|
|
|
assertThat(tracker.getReportsForNode("node2").size(), is(1));
|
|
|
}
|
|
|
|
|
|
@Test
|
|
|
public void testGetJson() throws IOException {
|
|
|
- tracker.addReport("node1", "node2");
|
|
|
- tracker.addReport("node2", "node3");
|
|
|
- tracker.addReport("node2", "node1");
|
|
|
- tracker.addReport("node4", "node1");
|
|
|
+ tracker.addReport("node1", "node2", 1.1);
|
|
|
+ tracker.addReport("node2", "node3", 1.23);
|
|
|
+ tracker.addReport("node2", "node1", 2.13);
|
|
|
+ tracker.addReport("node4", "node1", 1.244);
|
|
|
|
|
|
- final Set<ReportForJson> reports = getAndDeserializeJson();
|
|
|
+ final Set<SlowPeerJsonReport> reports = getAndDeserializeJson();
|
|
|
|
|
|
// And ensure its contents are what we expect.
|
|
|
assertThat(reports.size(), is(3));
|
|
@@ -161,19 +161,19 @@ public class TestSlowPeerTracker {
|
|
|
|
|
|
@Test
|
|
|
public void testGetJsonSizeIsLimited() throws IOException {
|
|
|
- tracker.addReport("node1", "node2");
|
|
|
- tracker.addReport("node1", "node3");
|
|
|
- tracker.addReport("node2", "node3");
|
|
|
- tracker.addReport("node2", "node4");
|
|
|
- tracker.addReport("node3", "node4");
|
|
|
- tracker.addReport("node3", "node5");
|
|
|
- tracker.addReport("node4", "node6");
|
|
|
- tracker.addReport("node5", "node6");
|
|
|
- tracker.addReport("node5", "node7");
|
|
|
- tracker.addReport("node6", "node7");
|
|
|
- tracker.addReport("node6", "node8");
|
|
|
-
|
|
|
- final Set<ReportForJson> reports = getAndDeserializeJson();
|
|
|
+ tracker.addReport("node1", "node2", 1.634);
|
|
|
+ tracker.addReport("node1", "node3", 2.3566);
|
|
|
+ tracker.addReport("node2", "node3", 3.869);
|
|
|
+ tracker.addReport("node2", "node4", 4.1356);
|
|
|
+ tracker.addReport("node3", "node4", 1.73057);
|
|
|
+ tracker.addReport("node3", "node5", 2.4956730);
|
|
|
+ tracker.addReport("node4", "node6", 3.29847);
|
|
|
+ tracker.addReport("node5", "node6", 4.13444);
|
|
|
+ tracker.addReport("node5", "node7", 5.10845);
|
|
|
+ tracker.addReport("node6", "node8", 2.37464);
|
|
|
+ tracker.addReport("node6", "node7", 1.29475656);
|
|
|
+
|
|
|
+ final Set<SlowPeerJsonReport> reports = getAndDeserializeJson();
|
|
|
|
|
|
// Ensure that node4 is not in the list since it was
|
|
|
// tagged by just one peer and we already have 5 other nodes.
|
|
@@ -185,22 +185,46 @@ public class TestSlowPeerTracker {
|
|
|
assertTrue(isNodeInReports(reports, "node3"));
|
|
|
assertTrue(isNodeInReports(reports, "node5"));
|
|
|
assertTrue(isNodeInReports(reports, "node6"));
|
|
|
+
|
|
|
+ assertEquals(1, reports.stream().filter(
|
|
|
+ e -> e.getSlowNode().equals("node1") && e.getSlowPeerLatencyWithReportingNodes().size() == 2
|
|
|
+ && e.getSlowPeerLatencyWithReportingNodes().first().getReportedLatency().equals(1.634)
|
|
|
+ && e.getSlowPeerLatencyWithReportingNodes().last().getReportedLatency().equals(2.3566))
|
|
|
+ .count());
|
|
|
+
|
|
|
+ assertEquals(1, reports.stream().filter(
|
|
|
+ e -> e.getSlowNode().equals("node2") && e.getSlowPeerLatencyWithReportingNodes().size() == 2
|
|
|
+ && e.getSlowPeerLatencyWithReportingNodes().first().getReportedLatency().equals(3.869)
|
|
|
+ && e.getSlowPeerLatencyWithReportingNodes().last().getReportedLatency().equals(4.1356))
|
|
|
+ .count());
|
|
|
+
|
|
|
+ assertEquals(1, reports.stream().filter(
|
|
|
+ e -> e.getSlowNode().equals("node3") && e.getSlowPeerLatencyWithReportingNodes().size() == 2
|
|
|
+ && e.getSlowPeerLatencyWithReportingNodes().first().getReportedLatency().equals(1.73057)
|
|
|
+ && e.getSlowPeerLatencyWithReportingNodes().last().getReportedLatency()
|
|
|
+ .equals(2.4956730)).count());
|
|
|
+
|
|
|
+ assertEquals(1, reports.stream().filter(
|
|
|
+ e -> e.getSlowNode().equals("node6") && e.getSlowPeerLatencyWithReportingNodes().size() == 2
|
|
|
+ && e.getSlowPeerLatencyWithReportingNodes().first().getReportedLatency()
|
|
|
+ .equals(1.29475656) && e.getSlowPeerLatencyWithReportingNodes().last()
|
|
|
+ .getReportedLatency().equals(2.37464)).count());
|
|
|
}
|
|
|
|
|
|
@Test
|
|
|
public void testLowRankedElementsIgnored() throws IOException {
|
|
|
// Insert 5 nodes with 2 peer reports each.
|
|
|
for (int i = 0; i < 5; ++i) {
|
|
|
- tracker.addReport("node" + i, "reporter1");
|
|
|
- tracker.addReport("node" + i, "reporter2");
|
|
|
+ tracker.addReport("node" + i, "reporter1", 1.295673);
|
|
|
+ tracker.addReport("node" + i, "reporter2", 2.38560);
|
|
|
}
|
|
|
|
|
|
// Insert 10 nodes with 1 peer report each.
|
|
|
for (int i = 10; i < 20; ++i) {
|
|
|
- tracker.addReport("node" + i, "reporter1");
|
|
|
+ tracker.addReport("node" + i, "reporter1", 3.4957);
|
|
|
}
|
|
|
|
|
|
- final Set<ReportForJson> reports = getAndDeserializeJson();
|
|
|
+ final Set<SlowPeerJsonReport> reports = getAndDeserializeJson();
|
|
|
|
|
|
// Ensure that only the first 5 nodes with two reports each were
|
|
|
// included in the JSON.
|
|
@@ -210,8 +234,8 @@ public class TestSlowPeerTracker {
|
|
|
}
|
|
|
|
|
|
private boolean isNodeInReports(
|
|
|
- Set<ReportForJson> reports, String node) {
|
|
|
- for (ReportForJson report : reports) {
|
|
|
+ Set<SlowPeerJsonReport> reports, String node) {
|
|
|
+ for (SlowPeerJsonReport report : reports) {
|
|
|
if (report.getSlowNode().equalsIgnoreCase(node)) {
|
|
|
return true;
|
|
|
}
|
|
@@ -219,7 +243,7 @@ public class TestSlowPeerTracker {
|
|
|
return false;
|
|
|
}
|
|
|
|
|
|
- private Set<ReportForJson> getAndDeserializeJson()
|
|
|
+ private Set<SlowPeerJsonReport> getAndDeserializeJson()
|
|
|
throws IOException {
|
|
|
final String json = tracker.getJson();
|
|
|
LOG.info("Got JSON: {}", json);
|