You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@accumulo.apache.org by ec...@apache.org on 2012/01/11 14:24:43 UTC
svn commit: r1230006 - in
/incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core:
conf/ util/shell/ util/shell/commands/
Author: ecn
Date: Wed Jan 11 13:24:42 2012
New Revision: 1230006
URL: http://svn.apache.org/viewvc?rev=1230006&view=rev
Log:
ACCUMULO-303: applying patch to allow per-table formatters in the shell
Modified:
incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/conf/Property.java
incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/Shell.java
incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java
incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateTableCommand.java
incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/FormatterCommand.java
Modified: incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/conf/Property.java
URL: http://svn.apache.org/viewvc/incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/conf/Property.java?rev=1230006&r1=1230005&r2=1230006&view=diff
==============================================================================
--- incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/conf/Property.java (original)
+++ incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/conf/Property.java Wed Jan 11 13:24:42 2012
@@ -286,7 +286,9 @@ public enum Property {
+ "with the category prefix, followed by a name, followed by a period, and followed by a property for that group.<br />"
+ "For example table.group.group1=x,y,z sets the column families for a group called group1. Once configured, "
+ "group1 can be enabled by adding it to the list of groups in the " + TABLE_LOCALITY_GROUPS.getKey() + " property.<br />"
- + "Additional group options may be specified for a named group by setting table.group.<name>.opt.<key>=<value>."), ;
+ + "Additional group options may be specified for a named group by setting table.group.<name>.opt.<key>=<value>."),
+ TABLE_FORMATTER_CLASS("table.formatter", "org.apache.accumulo.core.util.format.DefaultFormatter", PropertyType.STRING,
+ "The Formatter class to apply on results in the shell");
private String key, defaultValue, description;
private PropertyType type;
Modified: incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/Shell.java
URL: http://svn.apache.org/viewvc/incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/Shell.java?rev=1230006&r1=1230005&r2=1230006&view=diff
==============================================================================
--- incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/Shell.java (original)
+++ incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/Shell.java Wed Jan 11 13:24:42 2012
@@ -163,8 +163,9 @@ public class Shell {
private Connector connector;
private ConsoleReader reader;
private AuthInfo credentials;
- private Class<? extends Formatter> formatterClass = DefaultFormatter.class;
+ private Class<? extends Formatter> defaultFormatterClass = DefaultFormatter.class;
private Class<? extends Formatter> binaryFormatterClass = BinaryFormatter.class;
+ private Map<String, Class<? extends Formatter>> tableFormatters = new HashMap<String, Class<? extends Formatter>>();
public Map<String,List<IteratorSetting>> scanIteratorOptions = new HashMap<String,List<IteratorSetting>>();
private Token rootToken;
@@ -217,7 +218,7 @@ public class Shell {
Option execCommandOpt = new Option("e", "execute-command", true, "executes a command, and then exits");
opts.addOption(execCommandOpt);
-
+
OptionGroup execFileGroup = new OptionGroup();
Option execfileOption = new Option("f", "execute-file", true, "executes commands from a file at startup");
@@ -459,8 +460,13 @@ public class Shell {
else
sb.append("- Authorization timeout: ").append(String.format("%.2fs\n", authTimeout / 1000.0));
sb.append("- Debug: ").append(isDebuggingEnabled() ? "on" : "off").append("\n");
- if (formatterClass != null && formatterClass != DefaultFormatter.class) {
- sb.append("- Active formatter class: ").append(formatterClass.getSimpleName()).append("\n");
+ if (!tableFormatters.isEmpty()) {
+ sb.append("- Active Formatters");
+ for (Entry<String, Class<? extends Formatter>> entry : tableFormatters.entrySet()) {
+ if (null != entry.getValue()) {
+ sb.append("- Table: ").append(entry.getKey()).append(", ").append(entry.getValue().getName()).append("\n");
+ }
+ }
}
if (!scanIteratorOptions.isEmpty()) {
for (Entry<String,List<IteratorSetting>> entry : scanIteratorOptions.entrySet()) {
@@ -905,6 +911,8 @@ public class Shell {
}
public final void printRecords(Iterable<Entry<Key,Value>> scanner, boolean printTimestamps, boolean paginate) throws IOException {
+ Class<? extends Formatter> formatterClass = getFormatterClass(this.tableName);
+
printLines(FormatterFactory.getFormatter(formatterClass, scanner, printTimestamps), paginate);
}
@@ -989,12 +997,27 @@ public class Shell {
return credentials;
}
- public void setFormatterClass(Class<? extends Formatter> formatterClass) {
- this.formatterClass = formatterClass;
+ public void setFormatterClass(String tableName, Class<? extends Formatter> formatter) {
+ this.tableFormatters.put(tableName, formatter);
}
- public Class<? extends Formatter> getFormatterClass() {
- return formatterClass;
+ /**
+ * Pull the current formatter for the given table and cache it.
+ * @param tableName
+ * @return The formatter class for the given table
+ */
+ public Class<? extends Formatter> getFormatterClass(String tableName) {
+ if (this.tableFormatters.containsKey(tableName) && null != this.tableFormatters.get(tableName)) {
+ return this.tableFormatters.get(tableName);
+ } else {
+ Class<? extends Formatter> formatter = FormatterCommand.getCurrentFormatter(tableName, this);
+
+ if (null == formatter) {
+ return this.defaultFormatterClass;
+ } else {
+ return formatter;
+ }
+ }
}
}
Modified: incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java
URL: http://svn.apache.org/viewvc/incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java?rev=1230006&r1=1230005&r2=1230006&view=diff
==============================================================================
--- incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java (original)
+++ incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java Wed Jan 11 13:24:42 2012
@@ -32,9 +32,11 @@ import org.apache.accumulo.core.conf.Acc
import org.apache.accumulo.core.conf.Property;
import org.apache.accumulo.core.security.ColumnVisibility;
import org.apache.accumulo.core.util.BadArgumentException;
+import org.apache.accumulo.core.util.format.Formatter;
import org.apache.accumulo.core.util.shell.Shell;
import org.apache.accumulo.core.util.shell.Shell.Command;
import org.apache.accumulo.core.util.shell.Token;
+import org.apache.accumulo.start.classloader.AccumuloClassLoader;
import org.apache.commons.cli.CommandLine;
import org.apache.commons.cli.Option;
import org.apache.commons.cli.OptionGroup;
@@ -59,7 +61,7 @@ public class ConfigCommand extends Comma
}
public int execute(String fullCommand, CommandLine cl, Shell shellState) throws AccumuloException, AccumuloSecurityException, TableNotFoundException,
- IOException {
+ IOException, ClassNotFoundException {
reader = shellState.getReader();
String tableName = cl.getOptionValue(tableOpt.getOpt());
@@ -74,6 +76,12 @@ public class ConfigCommand extends Comma
if (tableName != null) {
if (!Property.isValidTablePropertyKey(property))
Shell.log.warn("Invalid per-table property : " + property + ", still removing from zookeeper if its there.");
+
+ // Fall back to the default formatter
+ if (property.equals(Property.TABLE_FORMATTER_CLASS.getKey())) {
+ shellState.setFormatterClass(tableName, AccumuloClassLoader.loadClass(Property.TABLE_FORMATTER_CLASS.getDefaultValue(), Formatter.class));
+ }
+
shellState.getConnector().tableOperations().removeProperty(tableName, property);
Shell.log.debug("Successfully deleted table configuration option.");
} else {
@@ -100,6 +108,11 @@ public class ConfigCommand extends Comma
new ColumnVisibility(value); // validate that it is a valid
// expression
+ // Load the formatter before setting the parameter
+ if (property.equals(Property.TABLE_FORMATTER_CLASS.getKey())) {
+ shellState.setFormatterClass(tableName, AccumuloClassLoader.loadClass(value, Formatter.class));
+ }
+
shellState.getConnector().tableOperations().setProperty(tableName, property, value);
Shell.log.debug("Successfully set table configuration option.");
} else {
Modified: incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateTableCommand.java
URL: http://svn.apache.org/viewvc/incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateTableCommand.java?rev=1230006&r1=1230005&r2=1230006&view=diff
==============================================================================
--- incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateTableCommand.java (original)
+++ incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateTableCommand.java Wed Jan 11 13:24:42 2012
@@ -36,8 +36,11 @@ import org.apache.accumulo.core.iterator
import org.apache.accumulo.core.iterators.conf.PerColumnIteratorConfig;
import org.apache.accumulo.core.security.VisibilityConstraint;
import org.apache.accumulo.core.util.BadArgumentException;
+import org.apache.accumulo.core.util.format.DefaultFormatter;
+import org.apache.accumulo.core.util.format.Formatter;
import org.apache.accumulo.core.util.shell.Shell;
import org.apache.accumulo.core.util.shell.Shell.Command;
+import org.apache.accumulo.start.classloader.AccumuloClassLoader;
import org.apache.commons.cli.CommandLine;
import org.apache.commons.cli.Option;
import org.apache.commons.cli.OptionGroup;
@@ -56,10 +59,11 @@ public class CreateTableCommand extends
private Option createTableNoDefaultIters;
private Option createTableOptEVC;
private Option base64Opt;
+ private Option createTableOptFormatter;
public static String testTable;
public int execute(String fullCommand, CommandLine cl, Shell shellState) throws AccumuloException, AccumuloSecurityException, TableExistsException,
- TableNotFoundException, IOException {
+ TableNotFoundException, IOException, ClassNotFoundException {
String testTableName = cl.getArgs()[0];
@@ -128,11 +132,13 @@ public class CreateTableCommand extends
TimeType timeType = TimeType.MILLIS;
if (cl.hasOption(createTableOptTimeLogical.getOpt()))
timeType = TimeType.LOGICAL;
+
// create table
shellState.getConnector().tableOperations().create(tableName, true, timeType);
shellState.getConnector().tableOperations().addSplits(tableName, partitions);
shellState.getConnector().tableOperations().addAggregators(tableName, aggregators);
+
shellState.setTableName(tableName); // switch shell to new table
// context
@@ -173,6 +179,15 @@ public class CreateTableCommand extends
shellState.getConnector().tableOperations()
.setProperty(tableName, Property.TABLE_CONSTRAINT_PREFIX.getKey() + (max + 1), VisibilityConstraint.class.getName());
}
+
+ // Load custom formatter if set
+ if (cl.hasOption(createTableOptFormatter.getOpt())) {
+ String formatterClass = cl.getOptionValue(createTableOptFormatter.getOpt());
+
+ shellState.setFormatterClass(tableName, AccumuloClassLoader.loadClass(formatterClass, Formatter.class));
+
+ shellState.getConnector().tableOperations().setProperty(tableName, Property.TABLE_FORMATTER_CLASS.toString(), formatterClass);
+ }
return 0;
}
@@ -200,6 +215,7 @@ public class CreateTableCommand extends
createTableNoDefaultIters = new Option("ndi", "no-default-iterators", false, "prevents creation of the normal default iterator set");
createTableOptEVC = new Option("evc", "enable-visibility-constraint", false,
"prevents users from writing data they can not read. When enabling this may want to consider disabling bulk import and alter table");
+ createTableOptFormatter = new Option("f", "formatter", false, "default formatter to set");
createTableOptCopyConfig.setArgName("table");
createTableOptCopySplits.setArgName("table");
@@ -226,6 +242,7 @@ public class CreateTableCommand extends
o.addOption(createTableOptCopyConfig);
o.addOption(createTableNoDefaultIters);
o.addOption(createTableOptEVC);
+ o.addOption(createTableOptFormatter);
return o;
}
Modified: incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/FormatterCommand.java
URL: http://svn.apache.org/viewvc/incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/FormatterCommand.java?rev=1230006&r1=1230005&r2=1230006&view=diff
==============================================================================
--- incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/FormatterCommand.java (original)
+++ incubator/accumulo/branches/1.4/src/core/src/main/java/org/apache/accumulo/core/util/shell/commands/FormatterCommand.java Wed Jan 11 13:24:42 2012
@@ -16,7 +16,12 @@
*/
package org.apache.accumulo.core.util.shell.commands;
-import org.apache.accumulo.core.util.format.DefaultFormatter;
+import java.util.Iterator;
+import java.util.Map.Entry;
+
+import org.apache.accumulo.core.client.AccumuloException;
+import org.apache.accumulo.core.client.TableNotFoundException;
+import org.apache.accumulo.core.conf.Property;
import org.apache.accumulo.core.util.format.Formatter;
import org.apache.accumulo.core.util.shell.Shell;
import org.apache.accumulo.core.util.shell.Shell.Command;
@@ -27,39 +32,106 @@ import org.apache.commons.cli.OptionGrou
import org.apache.commons.cli.Options;
public class FormatterCommand extends Command {
- private Option resetOption, formatterClassOption, listClassOption;
+ private Option removeFormatterOption, formatterClassOption, listClassOption, tableOption;
@Override
public String description() {
- return "specifies a formatter to use for displaying database entries";
+ return "specifies a formatter to use for displaying table entries";
}
@Override
public int execute(String fullCommand, CommandLine cl, Shell shellState) throws Exception {
- if (cl.hasOption(resetOption.getOpt()))
- shellState.setFormatterClass(DefaultFormatter.class);
- else if (cl.hasOption(formatterClassOption.getOpt()))
- shellState.setFormatterClass(AccumuloClassLoader.loadClass(cl.getOptionValue(formatterClassOption.getOpt()), Formatter.class));
- else if (cl.hasOption(listClassOption.getOpt()))
- shellState.getReader().printString(shellState.getFormatterClass().getName() + "\n");
+ String tableName = shellState.getTableName();
+
+ if (cl.hasOption(tableOption.getOpt())) {
+ tableName = cl.getOptionValue(tableOption.getOpt());
+ }
+
+ if (cl.hasOption(removeFormatterOption.getOpt())) {
+ // Remove the property
+ shellState.getConnector().tableOperations().removeProperty(tableName, Property.TABLE_FORMATTER_CLASS.toString());
+
+ // Reset the shell formatter on this table
+ shellState.setFormatterClass(tableName, AccumuloClassLoader.loadClass(Property.TABLE_FORMATTER_CLASS.getDefaultValue(), Formatter.class));
+
+ shellState.getReader().printString("Removed formatter on " + tableName + "\n");
+ } else if (cl.hasOption(listClassOption.getOpt())) {
+ // Get the options for this table
+ Iterator<Entry<String,String>> iter = shellState.getConnector().tableOperations().getProperties(tableName).iterator();
+
+ while (iter.hasNext()) {
+ Entry<String, String> ent = iter.next();
+
+ // List all parameters with the property name
+ if (ent.getKey().startsWith(Property.TABLE_FORMATTER_CLASS.toString())) {
+ shellState.getReader().printString(ent.getKey() + ": " + ent.getValue() + "\n");
+ }
+ }
+ } else {
+ // Set the formatter with the provided options
+ String className = cl.getOptionValue(formatterClassOption.getOpt());
+
+ // Update the shell formatter for this table
+ shellState.setFormatterClass(tableName, AccumuloClassLoader.loadClass(className, Formatter.class));
+
+ shellState.getConnector().tableOperations().setProperty(tableName, Property.TABLE_FORMATTER_CLASS.toString(), className);
+ }
+
return 0;
}
+ public static Class<? extends Formatter> getCurrentFormatter(String tableName, Shell shellState) {
+ Iterator<Entry<String, String>> props;
+ try {
+ props = shellState.getConnector().tableOperations().getProperties(tableName).iterator();
+ } catch (AccumuloException e) {
+ return null;
+ } catch (TableNotFoundException e) {
+ return null;
+ }
+
+ while (props.hasNext()) {
+ Entry<String, String> ent = props.next();
+ if (ent.getKey().equals(Property.TABLE_FORMATTER_CLASS.toString())) {
+ Class<? extends Formatter> formatter;
+ try {
+ formatter = AccumuloClassLoader.loadClass(ent.getValue(), Formatter.class);
+ shellState.setFormatterClass(tableName, formatter);
+ } catch (ClassNotFoundException e) {
+ return null;
+ }
+
+ return formatter;
+ }
+ }
+
+ return null;
+ }
+
@Override
public Options getOptions() {
Options o = new Options();
- OptionGroup formatGroup = new OptionGroup();
+ OptionGroup actionGroup = new OptionGroup();
+
+ // Table and formatter class name
+ tableOption = new Option("t", "table", true, "table to set the formatter on");
+ tableOption.setArgName("table");
+ tableOption.setRequired(false);
- resetOption = new Option("r", "reset", false, "reset to default formatter");
- formatterClassOption = new Option("f", "formatter", true, "fully qualified name of formatter class to use");
+ formatterClassOption = new Option("f", "formatter", true, "fully qualified name of the formatter class to use");
formatterClassOption.setArgName("className");
+
+ // Action to take: apply (default), remove, list
+ removeFormatterOption = new Option("r", "remove", false, "remove the current formatter");
listClassOption = new Option("l", "list", false, "display the current formatter");
- formatGroup.addOption(resetOption);
- formatGroup.addOption(formatterClassOption);
- formatGroup.addOption(listClassOption);
- formatGroup.setRequired(true);
- o.addOptionGroup(formatGroup);
+ actionGroup.addOption(formatterClassOption);
+ actionGroup.addOption(removeFormatterOption);
+ actionGroup.addOption(listClassOption);
+ actionGroup.setRequired(true);
+
+ o.addOptionGroup(actionGroup);
+ o.addOption(tableOption);
return o;
}