Author: xedin
Date: Wed Dec  7 18:25:00 2011
New Revision: 1211581

URL: http://svn.apache.org/viewvc?rev=1211581&view=rev
Log:
'describe ring' moved from CLI to nodetool and available through JMX
patch by Jackson Chung; reviewed by Pavel Yaskevich for CASSANDRA-3220

Modified:
    cassandra/branches/cassandra-1.0/CHANGES.txt
    cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/Cli.g
    
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/CliClient.java
    
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageService.java
    
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageServiceMBean.java
    
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/thrift/CassandraServer.java
    
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeCmd.java
    
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeProbe.java
    
cassandra/branches/cassandra-1.0/src/resources/org/apache/cassandra/cli/CliHelp.yaml

Modified: cassandra/branches/cassandra-1.0/CHANGES.txt
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/CHANGES.txt?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- cassandra/branches/cassandra-1.0/CHANGES.txt (original)
+++ cassandra/branches/cassandra-1.0/CHANGES.txt Wed Dec  7 18:25:00 2011
@@ -16,6 +16,7 @@
  * fix compression "chunk_length_kb" option to set correct kb value for 
thrift/avro
    (CASSANDRA-3558)
  * fix missing response during range slice repair (CASSANDRA-3551)
+ * 'describe ring' moved from CLI to nodetool and available through JMX 
(CASSANDRA-3220)
 Merged from 0.8:
  * use cannonical host for local node in nodetool info (CASSANDRA-3556)
  * remove nonlocal DC write optimization since it only worked with

Modified: 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/Cli.g
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/Cli.g?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/Cli.g 
(original)
+++ cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/Cli.g 
Wed Dec  7 18:25:00 2011
@@ -63,7 +63,6 @@ tokens {
     NODE_ASSUME;
     NODE_CONSISTENCY_LEVEL;
     NODE_DROP_INDEX;
-    NODE_DESCRIBE_RING;
 
     // Internal Nodes.
     NODE_COLUMN_ACCESS;
@@ -164,7 +163,6 @@ statement
     | assumeStatement
     | consistencyLevelStatement
     | dropIndex
-    | describeRing
     | -> ^(NODE_NO_OP)
     ;
 
@@ -212,8 +210,6 @@ helpStatement
         -> ^(NODE_HELP NODE_DEL_COLUMN_FAMILY)
     | HELP DROP INDEX
         -> ^(NODE_HELP NODE_DROP_INDEX)
-    | HELP DESCRIBE RING
-        -> ^(NODE_HELP NODE_DESCRIBE_RING)
     | HELP GET 
         -> ^(NODE_HELP NODE_THRIFT_GET)
     | HELP SET 
@@ -354,11 +350,6 @@ dropIndex
         -> ^(NODE_DROP_INDEX columnFamily columnName)
     ;
 
-describeRing
-    : DESCRIBE RING (keyspace)?
-        -> ^(NODE_DESCRIBE_RING (keyspace)?)
-    ;
-
 showVersion
     : SHOW API_VERSION
         -> ^(NODE_SHOW_VERSION)
@@ -589,7 +580,6 @@ CONSISTENCYLEVEL:   'CONSISTENCYLEVEL';
 INDEX:       'INDEX';
 ON:          'ON';
 SCHEMA:      'SCHEMA';
-RING:    'RING';
 
 IP_ADDRESS 
     : IntegerPositiveLiteral '.' IntegerPositiveLiteral '.' 
IntegerPositiveLiteral '.' IntegerPositiveLiteral

Modified: 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/CliClient.java
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/CliClient.java?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/CliClient.java
 (original)
+++ 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/cli/CliClient.java
 Wed Dec  7 18:25:00 2011
@@ -284,9 +284,6 @@ public class CliClient
                 case CliParser.NODE_DROP_INDEX:
                     executeDropIndex(tree);
                     break;
-                case CliParser.NODE_DESCRIBE_RING:
-                    executeDescribeRing(tree);
-                    break;
 
                 case CliParser.NODE_NO_OP:
                     // comment lines come here; they are treated as no ops.
@@ -1433,59 +1430,6 @@ public class CliClient
         keyspacesMap.put(keySpace, thriftClient.describe_keyspace(keySpace));
     }
 
-    private void executeDescribeRing(Tree statement) throws TException, 
InvalidRequestException
-    {
-        if (!CliMain.isConnected())
-            return;
-
-        int argCount = statement.getChildCount();
-
-        if (argCount > 1) // in case somebody changes Cli grammar
-            throw new RuntimeException("`describe ring` command takes maximum 
one argument. See `help describe ring;`");
-
-        KsDef currentKeySpace = keyspacesMap.get(keySpace);
-
-        if (argCount == 0 && currentKeySpace != null)
-        {
-            describeRing(currentKeySpace.name);
-        }
-        else if (argCount == 1)
-        {
-            String entityName = statement.getChild(0).getText();
-            KsDef inputKsDef = CliUtils.getKeySpaceDef(entityName, 
thriftClient.describe_keyspaces());
-
-            if (inputKsDef == null)
-            {
-                sessionState.out.println("Sorry, no Keyspace was found with 
name: " + entityName);
-                return;
-            }
-
-            describeRing(inputKsDef.name);
-        }
-        else
-        {
-            sessionState.out.println("Authenticate to a Keyspace before using 
`describe ring` or `describe ring <keyspace>`");
-        }
-    }
-
-    private void describeRing(String name) throws TException
-    {
-        List<TokenRange> tokenRangeList;
-
-        try
-        {
-            for (TokenRange tokenRange : thriftClient.describe_ring(name))
-                sessionState.out.println(tokenRange);
-        }
-        catch (InvalidRequestException e)
-        {
-            sessionState.err.println(e.getWhy());
-
-            if (sessionState.debug)
-                e.printStackTrace(sessionState.err);
-        }
-    }
-
     // TRUNCATE <columnFamily>
     private void executeTruncate(String columnFamily) throws TException, 
InvalidRequestException, UnavailableException
     {

Modified: 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageService.java
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageService.java?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageService.java
 (original)
+++ 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageService.java
 Wed Dec  7 18:25:00 2011
@@ -60,6 +60,9 @@ import org.apache.cassandra.net.Response
 import org.apache.cassandra.service.AntiEntropyService.TreeRequestVerbHandler;
 import org.apache.cassandra.streaming.*;
 import org.apache.cassandra.thrift.Constants;
+import org.apache.cassandra.thrift.EndpointDetails;
+import org.apache.cassandra.thrift.InvalidRequestException;
+import org.apache.cassandra.thrift.TokenRange;
 import org.apache.cassandra.thrift.UnavailableException;
 import org.apache.cassandra.utils.FBUtilities;
 import org.apache.cassandra.utils.NodeId;
@@ -734,6 +737,72 @@ public class StorageService implements I
         return constructRangeToEndpointMap(keyspace, ranges);
     }
 
+    /**
+     * The same as {@code describeRing(String)} but converts TokenRange to the 
String for JMX compatibility
+     *
+     * @param keyspace The keyspace to fetch information about
+     *
+     * @return a List of TokenRange(s) converted to String for the given 
keyspace
+     *
+     * @throws InvalidRequestException if there is no ring information 
available about keyspace
+     */
+    public List<String> describeRingJMX(String keyspace) throws 
InvalidRequestException
+    {
+        List<String> result = new ArrayList<String>();
+
+        for (TokenRange tokenRange : describeRing(keyspace))
+            result.add(tokenRange.toString());
+
+        return result;
+    }
+
+    /**
+     * The TokenRange for a given keyspace.
+     *
+     * @param keyspace The keyspace to fetch information about
+     *
+     * @return a List of TokenRange(s) for the given keyspace
+     *
+     * @throws InvalidRequestException if there is no ring information 
available about keyspace
+     */
+    public List<TokenRange> describeRing(String keyspace) throws 
InvalidRequestException
+    {
+        if (keyspace == null || 
!Schema.instance.getNonSystemTables().contains(keyspace))
+            throw new InvalidRequestException("There is no ring for the 
keyspace: " + keyspace);
+
+        List<TokenRange> ranges = new ArrayList<TokenRange>();
+        Token.TokenFactory tf = getPartitioner().getTokenFactory();
+
+        for (Map.Entry<Range, List<InetAddress>> entry : 
getRangeToAddressMap(keyspace).entrySet())
+        {
+            Range range = entry.getKey();
+            List<String> endpoints = new ArrayList<String>();
+            List<String> rpc_endpoints = new ArrayList<String>();
+            List<EndpointDetails> epDetails = new ArrayList<EndpointDetails>();
+
+            for (InetAddress endpoint : entry.getValue())
+            {
+                EndpointDetails details = new EndpointDetails();
+                details.host = endpoint.getHostAddress();
+                details.datacenter = 
DatabaseDescriptor.getEndpointSnitch().getDatacenter(endpoint);
+                details.rack = 
DatabaseDescriptor.getEndpointSnitch().getRack(endpoint);
+
+                endpoints.add(details.host);
+                rpc_endpoints.add(getRpcaddress(endpoint));
+
+                epDetails.add(details);
+            }
+
+            TokenRange tr = new TokenRange(tf.toString(range.left), 
tf.toString(range.right), endpoints)
+                                    .setEndpoint_details(epDetails)
+                                    .setRpc_endpoints(rpc_endpoints);
+
+            ranges.add(tr);
+        }
+
+        return ranges;
+    }
+
     public Map<Token, String> getTokenToEndpointMap()
     {
         Map<Token, InetAddress> mapInetAddress = 
tokenMetadata_.getTokenToEndpointMap();

Modified: 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageServiceMBean.java
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageServiceMBean.java?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageServiceMBean.java
 (original)
+++ 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/service/StorageServiceMBean.java
 Wed Dec  7 18:25:00 2011
@@ -30,6 +30,8 @@ import java.util.concurrent.TimeoutExcep
 import org.apache.cassandra.config.ConfigurationException;
 import org.apache.cassandra.dht.Range;
 import org.apache.cassandra.dht.Token;
+import org.apache.cassandra.thrift.InvalidRequestException;
+import org.apache.cassandra.thrift.TokenRange;
 import org.apache.cassandra.thrift.UnavailableException;
 
 
@@ -127,6 +129,17 @@ public interface StorageServiceMBean
     public Map<Range, List<String>> getRangeToRpcaddressMap(String keyspace);
 
     /**
+     * The same as {@code describeRing(String)} but converts TokenRange to the 
String for JMX compatibility
+     *
+     * @param keyspace The keyspace to fetch information about
+     *
+     * @return a List of TokenRange(s) converted to String for the given 
keyspace
+     *
+     * @throws InvalidRequestException if there is no ring information 
available about keyspace
+     */
+    public List <String> describeRingJMX(String keyspace) throws 
InvalidRequestException;
+
+    /**
      * Retrieve a map of pending ranges to endpoints that describe the ring 
topology
      * @param keyspace the keyspace to get the pending range map for.
      * @return a map of pending ranges to endpoints

Modified: 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/thrift/CassandraServer.java
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/thrift/CassandraServer.java?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/thrift/CassandraServer.java
 (original)
+++ 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/thrift/CassandraServer.java
 Wed Dec  7 18:25:00 2011
@@ -20,7 +20,6 @@ package org.apache.cassandra.thrift;
 
 import java.io.IOException;
 import java.io.UnsupportedEncodingException;
-import java.net.InetAddress;
 import java.net.SocketAddress;
 import java.nio.ByteBuffer;
 import java.nio.charset.CharacterCodingException;
@@ -49,10 +48,6 @@ import org.apache.cassandra.db.marshal.M
 import org.apache.cassandra.db.migration.*;
 import org.apache.cassandra.db.context.CounterContext;
 import org.apache.cassandra.dht.*;
-import org.apache.cassandra.gms.ApplicationState;
-import org.apache.cassandra.gms.EndpointState;
-import org.apache.cassandra.gms.Gossiper;
-import org.apache.cassandra.gms.VersionedValue;
 import org.apache.cassandra.io.util.FastByteArrayOutputStream;
 import org.apache.cassandra.locator.*;
 import org.apache.cassandra.scheduler.IRequestScheduler;
@@ -61,7 +56,6 @@ import org.apache.cassandra.service.Sock
 import org.apache.cassandra.service.StorageProxy;
 import org.apache.cassandra.service.StorageService;
 import org.apache.cassandra.utils.ByteBufferUtil;
-import org.apache.cassandra.utils.FBUtilities;
 import org.apache.thrift.TException;
 
 public class CassandraServer implements Cassandra.Iface
@@ -788,41 +782,7 @@ public class CassandraServer implements 
 
     public List<TokenRange> describe_ring(String keyspace)throws 
InvalidRequestException
     {
-        if (keyspace == null || 
!Schema.instance.getNonSystemTables().contains(keyspace))
-            throw new InvalidRequestException("There is no ring for the 
keyspace: " + keyspace);
-
-        List<TokenRange> ranges = new ArrayList<TokenRange>();
-        Token.TokenFactory tf = 
StorageService.getPartitioner().getTokenFactory();
-
-        for (Map.Entry<Range, List<InetAddress>> entry : 
StorageService.instance.getRangeToAddressMap(keyspace).entrySet())
-        {
-            Range range = entry.getKey();
-            List<String> endpoints = new ArrayList<String>();
-            List<String> rpc_endpoints = new ArrayList<String>();
-            List<EndpointDetails> epDetails = new ArrayList<EndpointDetails>();
-
-            for (InetAddress endpoint : entry.getValue())
-            {
-                EndpointState eps = 
Gossiper.instance.getEndpointStateForEndpoint(endpoint);
-                EndpointDetails details = new EndpointDetails();
-
-                details.host = endpoint.getHostAddress();
-                details.datacenter = 
DatabaseDescriptor.getEndpointSnitch().getDatacenter(endpoint);
-                details.rack = 
DatabaseDescriptor.getEndpointSnitch().getRack(endpoint);
-
-                endpoints.add(details.host);
-                
rpc_endpoints.add(StorageService.instance.getRpcaddress(endpoint));
-
-                epDetails.add(details);
-            }
-
-            TokenRange tr = new TokenRange(tf.toString(range.left), 
tf.toString(range.right), endpoints)
-                            .setEndpoint_details(epDetails)
-                            .setRpc_endpoints(rpc_endpoints);
-            ranges.add(tr);
-        }
-
-        return ranges;
+        return StorageService.instance.describeRing(keyspace);
     }
 
     public String describe_partitioner() throws TException

Modified: 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeCmd.java
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeCmd.java?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeCmd.java
 (original)
+++ 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeCmd.java
 Wed Dec  7 18:25:00 2011
@@ -41,6 +41,7 @@ import org.apache.cassandra.db.compactio
 import org.apache.cassandra.db.compaction.CompactionManagerMBean;
 import org.apache.cassandra.dht.Token;
 import org.apache.cassandra.net.MessagingServiceMBean;
+import org.apache.cassandra.thrift.InvalidRequestException;
 import org.apache.cassandra.utils.EstimatedHistogram;
 import org.apache.cassandra.utils.Pair;
 
@@ -112,6 +113,7 @@ public class NodeCmd
         TPSTATS,
         UPGRADESSTABLES,
         VERSION,
+        DESCRIBERING,
     }
 
     
@@ -145,6 +147,7 @@ public class NodeCmd
         addCmdHelp(header, "move <new token>", "Move node on the token ring to 
a new token");
         addCmdHelp(header, "removetoken status|force|<token>", "Show status of 
current token removal, force completion of pending removal or remove providen 
token");
         addCmdHelp(header, "setcompactionthroughput <value_in_mb>", "Set the 
MB/s throughput cap for compaction in the system, or 0 to disable throttling.");
+        addCmdHelp(header, "describering [keyspace]", "Shows the token ranges 
info of a given keyspace.");
 
         // Two args
         addCmdHelp(header, "snapshot [keyspaces...] -t [snapshotName]", "Take 
a snapshot of the specified keyspaces using optional name snapshotName");
@@ -746,6 +749,11 @@ public class NodeCmd
 
                 case GOSSIPINFO : nodeCmd.printGossipInfo(System.out); break;
 
+                case DESCRIBERING :
+                    if (arguments.length != 1) { badUse("Missing keyspace 
argument for describering."); }
+                    nodeCmd.printDescribeRing(arguments[0], System.out);
+                    break;
+
                 default :
                     throw new RuntimeException("Unreachable code.");
             }
@@ -767,6 +775,22 @@ public class NodeCmd
         System.exit(0);
     }
 
+    private void printDescribeRing(String keyspaceName, PrintStream out)
+    {
+        out.println("TokenRange: ");
+        try
+        {
+            for (String tokenRangeString : probe.describeRing(keyspaceName))
+            {
+                out.println("\t" + tokenRangeString);
+            }
+        }
+        catch (InvalidRequestException e)
+        {
+            err(e, e.getWhy());
+        }
+    }
+
     private void printGossipInfo(PrintStream out) {
         out.println(probe.getGossipInfo());
     }

Modified: 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeProbe.java
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeProbe.java?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeProbe.java
 (original)
+++ 
cassandra/branches/cassandra-1.0/src/java/org/apache/cassandra/tools/NodeProbe.java
 Wed Dec  7 18:25:00 2011
@@ -55,8 +55,8 @@ import org.apache.cassandra.net.Messagin
 import org.apache.cassandra.service.StorageServiceMBean;
 import org.apache.cassandra.streaming.StreamingService;
 import org.apache.cassandra.streaming.StreamingServiceMBean;
+import org.apache.cassandra.thrift.InvalidRequestException;
 import org.apache.cassandra.thrift.UnavailableException;
-import org.apache.cassandra.utils.Pair;
 
 /**
  * JMX client operations for Cassandra.
@@ -635,6 +635,11 @@ public class NodeProbe
     {
         return fdProxy.getAllEndpointStates();
     }
+
+    public List<String> describeRing(String keyspaceName) throws 
InvalidRequestException
+    {
+        return ssProxy.describeRingJMX(keyspaceName);
+    }
 }
 
 class ColumnFamilyStoreMBeanIterator implements Iterator<Map.Entry<String, 
ColumnFamilyStoreMBean>>

Modified: 
cassandra/branches/cassandra-1.0/src/resources/org/apache/cassandra/cli/CliHelp.yaml
URL: 
http://svn.apache.org/viewvc/cassandra/branches/cassandra-1.0/src/resources/org/apache/cassandra/cli/CliHelp.yaml?rev=1211581&r1=1211580&r2=1211581&view=diff
==============================================================================
--- 
cassandra/branches/cassandra-1.0/src/resources/org/apache/cassandra/cli/CliHelp.yaml
 (original)
+++ 
cassandra/branches/cassandra-1.0/src/resources/org/apache/cassandra/cli/CliHelp.yaml
 Wed Dec  7 18:25:00 2011
@@ -38,7 +38,6 @@ help: |
     create keyspace         Add a keyspace to the cluster.
     del                     Delete a column, super column or row.
     decr                    Decrements a counter column.
-    describe ring           Describe the token range information.
     describe cluster        Describe the cluster configuration.
     describe                Describe a keyspace and it's column families or 
column family in current keyspace.
     drop column family      Remove a column family and it's data.
@@ -131,18 +130,6 @@ commands:
         describe; - Describes current authenticated keyspace
         describe <keyspace>; - Describe this keyspace
         describe <column_family>; - Describe the colum family in the current 
authenticated keyspace
-    - name: NODE_DESCRIBE_RING
-      help: |
-        describe ring <keyspace>;
-
-        Describes the token range settings for the named keyspace.
-
-        Optional Parameters:
-        - keyspace: Name of the keyspace to describe.
-
-        Examples:
-        describe ring; - Describes the token range settings for the current 
authenticated keyspace
-        describe <keyspace>; - Describe the token range settings for this 
keyspace
     - name:
       help: |
         describe cluster;


Reply via email to