/** * Filter the given nodes to only include nodes with the service on it, and sort all those nodes by node number. * * @param clusterNodes Set of all cluster nodes. * @return Sorted list of nodes with the service on it. */ protected List<Node> sortServiceNodes(Set<Node> clusterNodes) { List<Node> filteredNodes = nodesForService(clusterNodes); Collections.sort(filteredNodes, NODE_NUM_COMPARATOR); return filteredNodes; }
@Override public List<String> evaluate(Cluster cluster, Set<Node> clusterNodes, Node node) throws IncompleteClusterException { int instanceNum = getServiceInstanceNum(node, sortServiceNodes(clusterNodes)); if (instanceNum < 0) { return null; } return ImmutableList.of(String.valueOf(instanceNum)); } }
public static Evaluator evaluatorFor(String macroName, Integer instanceNum) throws SyntaxException { if (macroName.equals(Type.CLUSTER_OWNER.prefix)) { return new ClusterOwnerEvaluator(); } else if (macroName.equals(Type.HOST_SELF.prefix)) { return new HostSelfEvaluator(); } else if (macroName.startsWith(Type.HOST_OF_SERVICE.prefix)) { String service = Type.HOST_OF_SERVICE.stripPrefix(macroName); checkService(service); return new HostServiceEvaluator(service, instanceNum); } else if (macroName.startsWith(Type.NUM_OF_NODES_WITH_SERVICE.prefix)) { String service = Type.NUM_OF_NODES_WITH_SERVICE.stripPrefix(macroName); checkService(service); return new ServiceCardinalityEvaluator(service); } else if (macroName.startsWith(Type.INSTANCE_OF_SERVICE.prefix)) { String service = Type.INSTANCE_OF_SERVICE.stripPrefix(macroName); checkService(service); return new ServiceInstanceEvaluator(service); } else if (macroName.startsWith(Type.IP.prefix)) { String ipStripped = Type.IP.stripPrefix(macroName); return new IPSelfEvaluator(DEFAULT_IP_TYPE); } else if (numParts == 2 && "service".equals(ipMacroParts[0])) { return new IPServiceEvaluator(ipMacroParts[1], DEFAULT_IP_TYPE, instanceNum); } else if (numParts == 2 && ipMacroParts[1].equals("self")) { return new IPSelfEvaluator(ipMacroParts[0]); } else if (numParts == 3 && ipMacroParts[1].equals("service")) { return new IPServiceEvaluator(service, ipMacroParts[0], instanceNum);
@Test public void testParseOK() throws SyntaxException { assertEquals(new Expression(new HostServiceEvaluator("abc", null), null, null), new Parser("host.service.abc").parse()); assertEquals(new Expression(new IPServiceEvaluator("namenode", "access_v4", null), null, null), new Parser("ip.access_v4.service.namenode").parse()); assertEquals(new Expression(new IPServiceEvaluator("a-b-c", "bind_v4", null), null, null), new Parser("ip.bind_v4.service.a-b-c").parse()); assertEquals(new Expression(new IPSelfEvaluator("access_v4"), null, null), new Parser("ip.access_v4.self").parse()); assertEquals(new Expression(new IPSelfEvaluator("bind_v4"), null, null), new Parser("ip.self").parse()); assertEquals(new Expression(new IPServiceEvaluator("a-b-c", "bind_v4", null), null, null), new Parser("ip.service.a-b-c").parse()); assertEquals(new Expression(new IPServiceEvaluator("a.b.c", "external", null), null, null), new Parser("ip.external.service.a.b.c").parse()); assertEquals(new Expression(new IPServiceEvaluator("a_b_c", "internal", null), null, null), new Parser("ip.internal.service.a_b_c").parse()); assertEquals(new Expression(new IPServiceEvaluator("nn", "access", null), "$:80", null), new Parser("map(ip.access.service.nn,'$:80')").parse()); assertEquals(new Expression(new IPServiceEvaluator("nn", "access", null), "\"$\"", null), new Parser("map(ip.access.service.nn,'\"$\"')").parse()); assertEquals(new Expression(new IPServiceEvaluator("nn", "access", null), "$:80", null), new Parser("map(ip.access.service.nn,\"$:80\")").parse()); assertEquals(new Expression(new IPServiceEvaluator("nn", "access", null), "'$'", null), new Parser("map(ip.access.service.nn,\"'$'\")").parse()); assertEquals(new Expression(new IPServiceEvaluator("nn", "access", null), null, "-"), new Parser("join(ip.access.service.nn,'-')").parse());
@Test public void testParseMacroName() throws SyntaxException { Assert.assertEquals(new HostServiceEvaluator("abc", null), Evaluators.evaluatorFor("host.service.abc", null)); Assert.assertEquals(new IPServiceEvaluator("abc", "access_v4", null), Evaluators.evaluatorFor("ip.access_v4.service.abc", null)); Assert.assertEquals(new IPServiceEvaluator("abc", "bind_v4", null), Evaluators.evaluatorFor("ip.service.abc", null)); Assert.assertTrue(Evaluators.evaluatorFor("cluster.owner", null) instanceof ClusterOwnerEvaluator); for (String macro : ImmutableList.of("", "host.service.", "IP_OF_SERVICE.abc", "SERVICE_BULLSHIT_abc")) { try { Evaluators.evaluatorFor(macro, null); Assert.fail("'" + macro + "' should have thrown syntax exception."); } catch (SyntaxException e) { // expected } } } }
@Test(expected = IncompleteClusterException.class) public void testNoIp() throws Exception { new Expression(new IPServiceEvaluator("svc2", IP_TYPE, null), null, null).evaluate(cluster, clusterNodes, node1); }
@Test(expected = IncompleteClusterException.class) public void testNoHost() throws Exception { new Expression(new HostServiceEvaluator("svc3", null), null, null).evaluate(cluster, clusterNodes, node1); }
@Test public void testSelfServiceInstanceNum() throws Exception { Assert.assertEquals( "1", new Expression(new ServiceInstanceEvaluator("svc1"), null, null) .evaluate(cluster, clusterNodes, node1)); Assert.assertEquals( "2", new Expression(new ServiceInstanceEvaluator("svc1"), null, null) .evaluate(cluster, clusterNodes, node2)); }
@Test public void testSelfServiceHost() throws Exception { Assert.assertEquals( node1.getProperties().getHostname(), new Expression(new HostSelfEvaluator(), null, null) .evaluate(cluster, clusterNodes, node1)); Assert.assertEquals( node2.getProperties().getHostname(), new Expression(new HostSelfEvaluator(), null, null) .evaluate(cluster, clusterNodes, node2)); }
@Test public void testSelfServiceIp() throws Exception { Assert.assertEquals( node1.getProperties().getIPAddress(IP_TYPE), new Expression(new IPSelfEvaluator(IP_TYPE), null, null) .evaluate(cluster, clusterNodes, node1)); Assert.assertEquals( node2.getProperties().getIPAddress(IP_TYPE), new Expression(new IPSelfEvaluator(IP_TYPE), null, null) .evaluate(cluster, clusterNodes, node2)); }
@Test public void testClusterOwner() throws Exception { Assert.assertEquals( cluster.getAccount().getUserId(), new Expression(new ClusterOwnerEvaluator(), null, null).evaluate(cluster, clusterNodes, node1)); }
/** * Get the n'th node from the given cluster nodes that have the service. * * @param clusterNodes Nodes in the cluster. * @param n number of the node with the service on it. * @return N'th node on the cluster with the given service. * @throws IncompleteClusterException if there are not fewer than n + 1 nodes with the service */ protected Node getNthServiceNode(Set<Node> clusterNodes, int n) throws IncompleteClusterException { List<Node> sortedNodes = sortServiceNodes(clusterNodes); if (n >= sortedNodes.size()) { throw new IncompleteClusterException("There are fewer than " + (n + 1) + " nodes with " + serviceName + " on the cluster"); } return sortedNodes.get(n); }
@Test(expected = IncompleteClusterException.class) public void testOutOfBounds() throws Exception { new Expression(new IPServiceEvaluator("svc1", IP_TYPE, 3), null, null).evaluate(cluster, clusterNodes, node1); }
@Test public void testFormatOnly() throws Exception { Assert.assertEquals( "oof:2181,owt:2181", new Expression(new HostServiceEvaluator("svc2", null), "$:2181", null).evaluate(cluster, clusterNodes, node1)); }
@Test public void testPlain() throws Exception { Assert.assertEquals( "9.6.8.1,9.7.8.4,9.1.3.4", new Expression(new IPServiceEvaluator("svc1", IP_TYPE, null), null, null) .evaluate(cluster, clusterNodes, node1)); }
@Test public void testFormatJoin() throws Exception { Assert.assertEquals( "oof:2181++owt:2181", new Expression(new HostServiceEvaluator("svc2", null), "$:2181", "++").evaluate(cluster, clusterNodes, node1)); }
@Test public void testNoService() throws Exception { Assert.assertNull(new Expression( new IPServiceEvaluator("svc4", IP_TYPE, null), null, null).evaluate(cluster, clusterNodes, node1)); }
@Test public void testJoinOnly() throws Exception { Assert.assertEquals( "rab-oof-eno", new Expression(new HostServiceEvaluator("svc1", null), null, "-").evaluate(cluster, clusterNodes, node1)); }
@Test public void testServiceIpInstance() throws Exception { Assert.assertEquals( node1.getProperties().getIPAddress(IP_TYPE), new Expression(new IPServiceEvaluator("svc1", IP_TYPE, 0), null, null).evaluate(cluster, clusterNodes, node1)); Assert.assertEquals( node2.getProperties().getIPAddress(IP_TYPE), new Expression(new IPServiceEvaluator("svc1", IP_TYPE, 1), null, null).evaluate(cluster, clusterNodes, node1)); }
@Test public void testServiceInstanceHost() throws Exception { Assert.assertEquals( node1.getProperties().getHostname(), new Expression(new HostServiceEvaluator("svc1", 0), null, null).evaluate(cluster, clusterNodes, node1)); Assert.assertEquals( node2.getProperties().getHostname(), new Expression(new HostServiceEvaluator("svc1", 1), null, null).evaluate(cluster, clusterNodes, node1)); }