1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 package org.apache.hadoop.hbase.master;
19
20 import static org.junit.Assert.*;
21
22 import java.util.ArrayList;
23 import java.util.Collection;
24 import java.util.List;
25 import java.util.Map;
26 import java.util.Set;
27
28 import org.apache.commons.logging.Log;
29 import org.apache.commons.logging.LogFactory;
30 import org.apache.hadoop.conf.Configuration;
31 import org.apache.hadoop.hbase.HBaseIOException;
32 import org.apache.hadoop.hbase.HBaseTestingUtility;
33 import org.apache.hadoop.hbase.HConstants;
34 import org.apache.hadoop.hbase.HRegionInfo;
35 import org.apache.hadoop.hbase.ServerName;
36 import org.apache.hadoop.hbase.TableName;
37 import org.apache.hadoop.hbase.master.balancer.FavoredNodeLoadBalancer;
38 import org.apache.hadoop.hbase.master.balancer.LoadBalancerFactory;
39 import org.apache.hadoop.hbase.master.balancer.FavoredNodesPlan.Position;
40 import org.apache.hadoop.hbase.testclassification.MediumTests;
41 import org.junit.AfterClass;
42 import org.junit.BeforeClass;
43 import org.junit.Test;
44 import org.junit.experimental.categories.Category;
45
46 @Category({MediumTests.class})
47 public class TestRegionPlacement2 {
48 private static final Log LOG = LogFactory.getLog(TestRegionPlacement2.class);
49 private final static HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility();
50 private final static int SLAVES = 7;
51 private final static int PRIMARY = Position.PRIMARY.ordinal();
52 private final static int SECONDARY = Position.SECONDARY.ordinal();
53 private final static int TERTIARY = Position.TERTIARY.ordinal();
54
55 @BeforeClass
56 public static void setupBeforeClass() throws Exception {
57 Configuration conf = TEST_UTIL.getConfiguration();
58
59 conf.setClass(HConstants.HBASE_MASTER_LOADBALANCER_CLASS,
60 FavoredNodeLoadBalancer.class, LoadBalancer.class);
61 conf.setBoolean("hbase.tests.use.shortcircuit.reads", false);
62 TEST_UTIL.startMiniCluster(SLAVES);
63 }
64
65 @AfterClass
66 public static void tearDownAfterClass() throws Exception {
67 TEST_UTIL.shutdownMiniCluster();
68 }
69
70 @Test
71 public void testFavoredNodesPresentForRoundRobinAssignment() throws HBaseIOException {
72 LoadBalancer balancer = LoadBalancerFactory.getLoadBalancer(TEST_UTIL.getConfiguration());
73 balancer.setMasterServices(TEST_UTIL.getMiniHBaseCluster().getMaster());
74 List<ServerName> servers = new ArrayList<ServerName>();
75 for (int i = 0; i < SLAVES; i++) {
76 ServerName server = TEST_UTIL.getMiniHBaseCluster().getRegionServer(i).getServerName();
77 servers.add(server);
78 }
79 List<HRegionInfo> regions = new ArrayList<HRegionInfo>(1);
80 HRegionInfo region = new HRegionInfo(TableName.valueOf("foobar"));
81 regions.add(region);
82 Map<ServerName,List<HRegionInfo>> assignmentMap = balancer.roundRobinAssignment(regions,
83 servers);
84 Set<ServerName> serverBefore = assignmentMap.keySet();
85 List<ServerName> favoredNodesBefore =
86 ((FavoredNodeLoadBalancer)balancer).getFavoredNodes(region);
87 assertTrue(favoredNodesBefore.size() == 3);
88
89 assertTrue(ServerName.isSameHostnameAndPort(serverBefore.iterator().next(),
90 favoredNodesBefore.get(PRIMARY)));
91
92 List<ServerName> removedServers = removeMatchingServers(serverBefore, servers);
93
94 assignmentMap = balancer.roundRobinAssignment(regions, servers);
95 List<ServerName> favoredNodesAfter =
96 ((FavoredNodeLoadBalancer)balancer).getFavoredNodes(region);
97 assertTrue(favoredNodesAfter.size() == 3);
98
99
100
101 assertTrue(favoredNodesAfter.containsAll(favoredNodesBefore));
102 Set<ServerName> serverAfter = assignmentMap.keySet();
103
104
105 assertTrue(ServerName.isSameHostnameAndPort(serverAfter.iterator().next(),
106 favoredNodesBefore.get(SECONDARY)) ||
107 ServerName.isSameHostnameAndPort(serverAfter.iterator().next(),
108 favoredNodesBefore.get(TERTIARY)));
109
110
111 servers.addAll(removedServers);
112
113
114 assignmentMap = balancer.roundRobinAssignment(regions, servers);
115 Set<ServerName> serverWithPrimary = assignmentMap.keySet();
116 assertTrue(serverBefore.containsAll(serverWithPrimary));
117
118
119 removeMatchingServers(favoredNodesAfter, servers);
120
121 assignmentMap = balancer.roundRobinAssignment(regions, servers);
122 List<ServerName> favoredNodesNow =
123 ((FavoredNodeLoadBalancer)balancer).getFavoredNodes(region);
124 assertTrue(favoredNodesNow.size() == 3);
125 assertTrue(!favoredNodesNow.contains(favoredNodesAfter.get(PRIMARY)) &&
126 !favoredNodesNow.contains(favoredNodesAfter.get(SECONDARY)) &&
127 !favoredNodesNow.contains(favoredNodesAfter.get(TERTIARY)));
128 }
129
130 @Test
131 public void testFavoredNodesPresentForRandomAssignment() throws HBaseIOException {
132 LoadBalancer balancer = LoadBalancerFactory.getLoadBalancer(TEST_UTIL.getConfiguration());
133 balancer.setMasterServices(TEST_UTIL.getMiniHBaseCluster().getMaster());
134 List<ServerName> servers = new ArrayList<ServerName>();
135 for (int i = 0; i < SLAVES; i++) {
136 ServerName server = TEST_UTIL.getMiniHBaseCluster().getRegionServer(i).getServerName();
137 servers.add(server);
138 }
139 List<HRegionInfo> regions = new ArrayList<HRegionInfo>(1);
140 HRegionInfo region = new HRegionInfo(TableName.valueOf("foobar"));
141 regions.add(region);
142 ServerName serverBefore = balancer.randomAssignment(region, servers);
143 List<ServerName> favoredNodesBefore =
144 ((FavoredNodeLoadBalancer)balancer).getFavoredNodes(region);
145 assertTrue(favoredNodesBefore.size() == 3);
146
147 assertTrue(ServerName.isSameHostnameAndPort(serverBefore,favoredNodesBefore.get(PRIMARY)));
148
149 removeMatchingServers(serverBefore, servers);
150
151 ServerName serverAfter = balancer.randomAssignment(region, servers);
152 List<ServerName> favoredNodesAfter =
153 ((FavoredNodeLoadBalancer)balancer).getFavoredNodes(region);
154 assertTrue(favoredNodesAfter.size() == 3);
155
156
157
158 assertTrue(favoredNodesAfter.containsAll(favoredNodesBefore));
159
160
161 assertTrue(ServerName.isSameHostnameAndPort(serverAfter, favoredNodesBefore.get(SECONDARY)) ||
162 ServerName.isSameHostnameAndPort(serverAfter, favoredNodesBefore.get(TERTIARY)));
163
164 removeMatchingServers(favoredNodesAfter, servers);
165
166 balancer.randomAssignment(region, servers);
167 List<ServerName> favoredNodesNow =
168 ((FavoredNodeLoadBalancer)balancer).getFavoredNodes(region);
169 assertTrue(favoredNodesNow.size() == 3);
170 assertTrue(!favoredNodesNow.contains(favoredNodesAfter.get(PRIMARY)) &&
171 !favoredNodesNow.contains(favoredNodesAfter.get(SECONDARY)) &&
172 !favoredNodesNow.contains(favoredNodesAfter.get(TERTIARY)));
173 }
174
175 private List<ServerName> removeMatchingServers(Collection<ServerName> serversWithoutStartCode,
176 List<ServerName> servers) {
177 List<ServerName> serversToRemove = new ArrayList<ServerName>();
178 for (ServerName s : serversWithoutStartCode) {
179 serversToRemove.addAll(removeMatchingServers(s, servers));
180 }
181 return serversToRemove;
182 }
183
184 private List<ServerName> removeMatchingServers(ServerName serverWithoutStartCode,
185 List<ServerName> servers) {
186 List<ServerName> serversToRemove = new ArrayList<ServerName>();
187 for (ServerName s : servers) {
188 if (ServerName.isSameHostnameAndPort(s, serverWithoutStartCode)) {
189 serversToRemove.add(s);
190 }
191 }
192 servers.removeAll(serversToRemove);
193 return serversToRemove;
194 }
195 }