ACCUMULO-802 Fixed NullPointerException during CloneTable due to loadbalancer trying to get the configuration before the namespace is put under the table in zookeeper. Fixed another NullPointerException with the -tn shell option for online, offline, and du. Added -tn option to shell config command. First attempt at adding a randomwalk test for namespaces, fails currently.
Project: http://git-wip-us.apache.org/repos/asf/accumulo/repo Commit: http://git-wip-us.apache.org/repos/asf/accumulo/commit/8e1b5090 Tree: http://git-wip-us.apache.org/repos/asf/accumulo/tree/8e1b5090 Diff: http://git-wip-us.apache.org/repos/asf/accumulo/diff/8e1b5090 Branch: refs/heads/ACCUMULO-802 Commit: 8e1b509097338249eebb3814596e72151fef1e53 Parents: d4c3e6a Author: Sean Hickey <[email protected]> Authored: Wed Jul 10 08:50:59 2013 -0400 Committer: Christopher Tubbs <[email protected]> Committed: Thu Oct 31 21:11:25 2013 -0400 ---------------------------------------------------------------------- .../accumulo/core/client/impl/Tables.java | 2 +- .../core/util/shell/commands/ConfigCommand.java | 40 ++++++++++++++--- .../shell/commands/CreateNamespaceCommand.java | 35 ++++++++++----- .../util/shell/commands/TableOperation.java | 6 +-- .../master/balancer/TableLoadBalancer.java | 6 ++- .../accumulo/master/tableOps/CloneTable.java | 6 +-- .../test/randomwalk/concurrent/CreateTable.java | 5 +++ .../test/randomwalk/concurrent/RenameTable.java | 5 +++ .../test/randomwalk/concurrent/Setup.java | 7 ++- .../accumulo/test/TableNamespacesTest.java | 46 ++++++++++++++++++++ 10 files changed, 130 insertions(+), 28 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/core/src/main/java/org/apache/accumulo/core/client/impl/Tables.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/accumulo/core/client/impl/Tables.java b/core/src/main/java/org/apache/accumulo/core/client/impl/Tables.java index 1573303..60ea973 100644 --- a/core/src/main/java/org/apache/accumulo/core/client/impl/Tables.java +++ b/core/src/main/java/org/apache/accumulo/core/client/impl/Tables.java @@ -110,6 +110,7 @@ public class Tables { public static void clearCache(Instance instance) { getZooCache(instance).clear(ZooUtil.getRoot(instance) + Constants.ZTABLES); + getZooCache(instance).clear(ZooUtil.getRoot(instance) + Constants.ZNAMESPACES); } public static String getPrintableTableNameFromId(Map<String,String> tidToNameMap, String tableId) { @@ -174,7 +175,6 @@ public class Tables { public static String getNamespace(Instance instance, String tableId) { ZooCache zc = getZooCache(instance); - zc.clear(); byte[] n = zc.get(ZooUtil.getRoot(instance) + Constants.ZTABLES + "/" + tableId + Constants.ZTABLE_NAMESPACE); return new String(n, Constants.UTF8); } http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java b/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java index 73d21ef..dcfc48c 100644 --- a/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java +++ b/core/src/main/java/org/apache/accumulo/core/util/shell/commands/ConfigCommand.java @@ -28,6 +28,7 @@ import jline.console.ConsoleReader; import org.apache.accumulo.core.client.AccumuloException; import org.apache.accumulo.core.client.AccumuloSecurityException; +import org.apache.accumulo.core.client.TableNamespaceNotFoundException; import org.apache.accumulo.core.client.TableNotFoundException; import org.apache.accumulo.core.conf.AccumuloConfiguration; import org.apache.accumulo.core.conf.Property; @@ -43,7 +44,7 @@ import org.apache.commons.cli.OptionGroup; import org.apache.commons.cli.Options; public class ConfigCommand extends Command { - private Option tableOpt, deleteOpt, setOpt, filterOpt, disablePaginationOpt, outputFileOpt; + private Option tableOpt, deleteOpt, setOpt, filterOpt, disablePaginationOpt, outputFileOpt, tableNamespaceOpt; private int COL1 = 8, COL2 = 7; private ConsoleReader reader; @@ -62,13 +63,17 @@ public class ConfigCommand extends Command { } public int execute(final String fullCommand, final CommandLine cl, final Shell shellState) throws AccumuloException, AccumuloSecurityException, - TableNotFoundException, IOException, ClassNotFoundException { + TableNotFoundException, IOException, ClassNotFoundException, TableNamespaceNotFoundException { reader = shellState.getReader(); final String tableName = cl.getOptionValue(tableOpt.getOpt()); if (tableName != null && !shellState.getConnector().tableOperations().exists(tableName)) { throw new TableNotFoundException(null, tableName, null); } + final String tableNamespace = cl.getOptionValue(tableNamespaceOpt.getOpt()); + if (tableNamespace != null && !shellState.getConnector().tableNamespaceOperations().exists(tableNamespace)) { + throw new TableNotFoundException(null, tableName, null); + } if (cl.hasOption(deleteOpt.getOpt())) { // delete property from table String property = cl.getOptionValue(deleteOpt.getOpt()); @@ -81,6 +86,12 @@ public class ConfigCommand extends Command { } shellState.getConnector().tableOperations().removeProperty(tableName, property); Shell.log.debug("Successfully deleted table configuration option."); + } else if (tableNamespace != null) { + if (!Property.isValidTablePropertyKey(property)) { + Shell.log.warn("Invalid per-table property : " + property + ", still removing from zookeeper if it's there."); + } + shellState.getConnector().tableNamespaceOperations().removeProperty(tableNamespace, property); + Shell.log.debug("Successfully deleted table namespace configuration option."); } else { if (!Property.isValidZooPropertyKey(property)) { Shell.log.warn("Invalid per-table property : " + property + ", still removing from zookeeper if it's there."); @@ -107,6 +118,15 @@ public class ConfigCommand extends Command { } shellState.getConnector().tableOperations().setProperty(tableName, property, value); Shell.log.debug("Successfully set table configuration option."); + } else if (tableNamespace != null) { + if (!Property.isValidTablePropertyKey(property)) { + throw new BadArgumentException("Invalid per-table property.", fullCommand, fullCommand.indexOf(property)); + } + if (property.equals(Property.TABLE_DEFAULT_SCANTIME_VISIBILITY.getKey())) { + new ColumnVisibility(value); // validate that it is a valid expression + } + shellState.getConnector().tableNamespaceOperations().setProperty(tableNamespace, property, value); + Shell.log.debug("Successfully set table configuration option."); } else { if (!Property.isValidZooPropertyKey(property)) { throw new BadArgumentException("Property cannot be modified in zookeeper", fullCommand, fullCommand.indexOf(property)); @@ -132,6 +152,8 @@ public class ConfigCommand extends Command { Iterable<Entry<String,String>> acuconf = shellState.getConnector().instanceOperations().getSystemConfiguration().entrySet(); if (tableName != null) { acuconf = shellState.getConnector().tableOperations().getProperties(tableName); + } else if (tableNamespace != null) { + acuconf = shellState.getConnector().tableNamespaceOperations().getProperties(tableNamespace); } final TreeMap<String,String> sortedConf = new TreeMap<String,String>(); for (Entry<String,String> propEntry : acuconf) { @@ -145,7 +167,7 @@ public class ConfigCommand extends Command { if (cl.hasOption(filterOpt.getOpt()) && !key.contains(cl.getOptionValue(filterOpt.getOpt()))) { continue; } - if (tableName != null && !Property.isValidTablePropertyKey(key)) { + if ((tableName != null || tableNamespace != null) && !Property.isValidTablePropertyKey(key)) { continue; } COL2 = Math.max(COL2, propEntry.getKey().length() + 3); @@ -162,7 +184,7 @@ public class ConfigCommand extends Command { if (cl.hasOption(filterOpt.getOpt()) && !key.contains(cl.getOptionValue(filterOpt.getOpt()))) { continue; } - if (tableName != null && !Property.isValidTablePropertyKey(key)) { + if ((tableName != null || tableNamespace != null) && !Property.isValidTablePropertyKey(key)) { continue; } String siteVal = siteConfig.get(key); @@ -190,7 +212,7 @@ public class ConfigCommand extends Command { } // show per-table value only if it is different (overridden) - if (tableName != null && !curVal.equals(sysVal)) { + if ((tableName != null || tableNamespace != null) && !curVal.equals(sysVal)) { printConfLine(output, "table", printed ? " @override" : key, curVal); } } @@ -231,6 +253,7 @@ public class ConfigCommand extends Command { public Options getOptions() { final Options o = new Options(); final OptionGroup og = new OptionGroup(); + final OptionGroup tgroup = new OptionGroup(); tableOpt = new Option(Shell.tableOption, "table", true, "table to display/set/delete properties for"); deleteOpt = new Option("d", "delete", true, "delete a per-table property"); @@ -238,18 +261,23 @@ public class ConfigCommand extends Command { filterOpt = new Option("f", "filter", true, "show only properties that contain this string"); disablePaginationOpt = new Option("np", "no-pagination", false, "disables pagination of output"); outputFileOpt = new Option("o", "output", true, "local file to write the scan output to"); + tableNamespaceOpt = new Option("tn", "table-namespace", true, "table namespace to display/set/delete properties for"); tableOpt.setArgName("table"); deleteOpt.setArgName("property"); setOpt.setArgName("property=value"); filterOpt.setArgName("string"); outputFileOpt.setArgName("file"); + tableNamespaceOpt.setArgName("tableNamespace"); og.addOption(deleteOpt); og.addOption(setOpt); og.addOption(filterOpt); - o.addOption(tableOpt); + tgroup.addOption(tableOpt); + tgroup.addOption(tableNamespaceOpt); + + o.addOptionGroup(tgroup); o.addOptionGroup(og); o.addOption(disablePaginationOpt); o.addOption(outputFileOpt); http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateNamespaceCommand.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateNamespaceCommand.java b/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateNamespaceCommand.java index 4e35fcb..a869070 100644 --- a/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateNamespaceCommand.java +++ b/core/src/main/java/org/apache/accumulo/core/util/shell/commands/CreateNamespaceCommand.java @@ -30,10 +30,11 @@ import org.apache.accumulo.core.util.shell.Shell; import org.apache.accumulo.core.util.shell.Shell.Command; import org.apache.commons.cli.CommandLine; import org.apache.commons.cli.Option; +import org.apache.commons.cli.OptionGroup; import org.apache.commons.cli.Options; public class CreateNamespaceCommand extends Command { - private Option createTableOptCopyConfig; + private Option createTableOptCopyConfig, createTableNamespaceOptCopyConfig; private Option base64Opt; public int execute(final String fullCommand, final CommandLine cl, final Shell shellState) throws AccumuloException, AccumuloSecurityException, @@ -48,14 +49,22 @@ public class CreateNamespaceCommand extends Command { shellState.getConnector().tableNamespaceOperations().create(namespace); // Copy options if flag was set - if (cl.hasOption(createTableOptCopyConfig.getOpt())) { + Iterable<Entry<String,String>> configuration = null; + if (cl.hasOption(createTableNamespaceOptCopyConfig.getOpt())) { + String copy = cl.getOptionValue(createTableNamespaceOptCopyConfig.getOpt()); + if (shellState.getConnector().tableNamespaceOperations().exists(namespace)) { + configuration = shellState.getConnector().tableNamespaceOperations().getProperties(copy); + } + } else if (cl.hasOption(createTableOptCopyConfig.getOpt())) { String copy = cl.getOptionValue(createTableOptCopyConfig.getOpt()); if (shellState.getConnector().tableNamespaceOperations().exists(namespace)) { - Iterable<Entry<String,String>> configuration = shellState.getConnector().tableNamespaceOperations().getProperties(copy); - for (Entry<String,String> entry : configuration) { - if (Property.isValidTablePropertyKey(entry.getKey())) { - shellState.getConnector().tableNamespaceOperations().setProperty(namespace, entry.getKey(), entry.getValue()); - } + configuration = shellState.getConnector().tableOperations().getProperties(copy); + } + } + if (configuration != null) { + for (Entry<String,String> entry : configuration) { + if (Property.isValidTablePropertyKey(entry.getKey())) { + shellState.getConnector().tableNamespaceOperations().setProperty(namespace, entry.getKey(), entry.getValue()); } } } @@ -77,13 +86,19 @@ public class CreateNamespaceCommand extends Command { public Options getOptions() { final Options o = new Options(); - createTableOptCopyConfig = new Option("cc", "copy-config", true, "table namespace to copy configuration from"); + createTableNamespaceOptCopyConfig = new Option("cc", "copy-config", true, "table namespace to copy configuration from"); + createTableNamespaceOptCopyConfig.setArgName("tableNamespace"); - createTableOptCopyConfig.setArgName("tableNamespace"); + createTableOptCopyConfig = new Option("ctc", "copy-table-config", true, "table to copy configuration from"); + createTableOptCopyConfig.setArgName("tableName"); base64Opt = new Option("b64", "base64encoded", false, "decode encoded split points"); o.addOption(base64Opt); - o.addOption(createTableOptCopyConfig); + OptionGroup ogp = new OptionGroup(); + ogp.addOption(createTableOptCopyConfig); + ogp.addOption(createTableNamespaceOptCopyConfig); + + o.addOptionGroup(ogp); return o; } http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/core/src/main/java/org/apache/accumulo/core/util/shell/commands/TableOperation.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/accumulo/core/util/shell/commands/TableOperation.java b/core/src/main/java/org/apache/accumulo/core/util/shell/commands/TableOperation.java index 8c73674..4b8b304 100644 --- a/core/src/main/java/org/apache/accumulo/core/util/shell/commands/TableOperation.java +++ b/core/src/main/java/org/apache/accumulo/core/util/shell/commands/TableOperation.java @@ -51,7 +51,7 @@ public abstract class TableOperation extends Command { tableSet.add(cl.getOptionValue(optTableName.getOpt())); } else if (cl.hasOption(optTableNamespace.getOpt())) { Instance instance = shellState.getInstance(); - String namespaceId = TableNamespaces.getNamespaceId(instance, optTableNamespace.getValue()); + String namespaceId = TableNamespaces.getNamespaceId(instance, cl.getOptionValue(optTableNamespace.getOpt())); for (String tableId : TableNamespaces.getTableIds(instance, namespaceId)) { tableSet.add(Tables.getTableName(instance, tableId)); } @@ -108,8 +108,8 @@ public abstract class TableOperation extends Command { optTableName = new Option(Shell.tableOption, "table", true, "name of a table to operate on"); optTableName.setArgName("tableName"); - optTableNamespace = new Option("tn", "table-namespace", true, "name of a table namespace to operate on"); - optTableName.setArgName("table-namespace"); + optTableNamespace = new Option("tn", "tableNamespace", true, "name of a table namespace to operate on"); + optTableNamespace.setArgName("tableNamespace"); final OptionGroup opg = new OptionGroup(); http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/server/base/src/main/java/org/apache/accumulo/server/master/balancer/TableLoadBalancer.java ---------------------------------------------------------------------- diff --git a/server/base/src/main/java/org/apache/accumulo/server/master/balancer/TableLoadBalancer.java b/server/base/src/main/java/org/apache/accumulo/server/master/balancer/TableLoadBalancer.java index 3e0a2bf..9de6ec2 100644 --- a/server/base/src/main/java/org/apache/accumulo/server/master/balancer/TableLoadBalancer.java +++ b/server/base/src/main/java/org/apache/accumulo/server/master/balancer/TableLoadBalancer.java @@ -30,10 +30,12 @@ import org.apache.accumulo.core.client.AccumuloSecurityException; import org.apache.accumulo.core.client.admin.TableOperations; import org.apache.accumulo.core.conf.Property; import org.apache.accumulo.core.data.KeyExtent; +import org.apache.accumulo.core.master.state.tables.TableState; import org.apache.accumulo.core.master.thrift.TabletServerStatus; import org.apache.accumulo.server.master.state.TServerInstance; import org.apache.accumulo.server.master.state.TabletMigration; import org.apache.accumulo.server.security.SystemCredentials; +import org.apache.accumulo.server.master.state.tables.TableManager; import org.apache.accumulo.start.classloader.vfs.AccumuloVFSClassLoader; import org.apache.log4j.Logger; @@ -50,7 +52,9 @@ public class TableLoadBalancer extends TabletBalancer { } protected String getLoadBalancerClassNameForTable(String table) { - return configuration.getTableConfiguration(table).get(Property.TABLE_LOAD_BALANCER); + if (TableManager.getInstance().getTableState(table).equals(TableState.ONLINE)) + return configuration.getTableConfiguration(table).get(Property.TABLE_LOAD_BALANCER); + return null; } protected TabletBalancer getBalancerForTable(String table) { http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/server/master/src/main/java/org/apache/accumulo/master/tableOps/CloneTable.java ---------------------------------------------------------------------- diff --git a/server/master/src/main/java/org/apache/accumulo/master/tableOps/CloneTable.java b/server/master/src/main/java/org/apache/accumulo/master/tableOps/CloneTable.java index b4c8aa2..3841463 100644 --- a/server/master/src/main/java/org/apache/accumulo/master/tableOps/CloneTable.java +++ b/server/master/src/main/java/org/apache/accumulo/master/tableOps/CloneTable.java @@ -151,11 +151,7 @@ class CloneZookeeper extends MasterRepo { String namespace = Tables.extractNamespace(cloneInfo.tableName); String namespaceId = TableNamespaces.getNamespaceId(instance, namespace); - TableManager tm = TableManager.getInstance(); - if (!TableNamespaces.getNameToIdMap(instance).containsKey(namespace)) { - tm.addNamespace(namespaceId, namespace, NodeExistsPolicy.SKIP); - } - tm.addNamespaceToTable(cloneInfo.tableId, namespaceId); + TableManager.getInstance().addNamespaceToTable(cloneInfo.tableId, namespaceId); return new CloneMetadata(cloneInfo); } finally { http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/CreateTable.java ---------------------------------------------------------------------- diff --git a/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/CreateTable.java b/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/CreateTable.java index 0aa7f7a..bbd18a9 100644 --- a/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/CreateTable.java +++ b/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/CreateTable.java @@ -22,6 +22,7 @@ import java.util.Random; import org.apache.accumulo.core.client.Connector; import org.apache.accumulo.core.client.TableExistsException; +import org.apache.accumulo.core.client.impl.Tables; import org.apache.accumulo.test.randomwalk.State; import org.apache.accumulo.test.randomwalk.Test; @@ -39,6 +40,10 @@ public class CreateTable extends Test { String tableName = tableNames.get(rand.nextInt(tableNames.size())); try { + String n = Tables.extractNamespace(tableName); + if (!conn.tableNamespaceOperations().exists(n)) { + conn.tableNamespaceOperations().create(n); + } conn.tableOperations().create(tableName); log.debug("Created table " + tableName); } catch (TableExistsException e) { http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/RenameTable.java ---------------------------------------------------------------------- diff --git a/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/RenameTable.java b/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/RenameTable.java index d4a4e95..690d6cf 100644 --- a/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/RenameTable.java +++ b/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/RenameTable.java @@ -23,6 +23,7 @@ import java.util.Random; import org.apache.accumulo.core.client.Connector; import org.apache.accumulo.core.client.TableExistsException; import org.apache.accumulo.core.client.TableNotFoundException; +import org.apache.accumulo.core.client.impl.Tables; import org.apache.accumulo.test.randomwalk.State; import org.apache.accumulo.test.randomwalk.Test; @@ -41,6 +42,10 @@ public class RenameTable extends Test { String newTableName = tableNames.get(rand.nextInt(tableNames.size())); try { + String n = Tables.extractNamespace(newTableName); + if (!conn.tableNamespaceOperations().exists(n)) { + conn.tableNamespaceOperations().create(n); + } conn.tableOperations().rename(srcTableName, newTableName); log.debug("Renamed table " + srcTableName + " " + newTableName); } catch (TableExistsException e) { http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/Setup.java ---------------------------------------------------------------------- diff --git a/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/Setup.java b/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/Setup.java index 2cf37ce..5a9edca 100644 --- a/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/Setup.java +++ b/test/src/main/java/org/apache/accumulo/test/randomwalk/concurrent/Setup.java @@ -34,8 +34,11 @@ public class Setup extends Test { int numTables = Integer.parseInt(props.getProperty("numTables", "5")); log.debug("numTables = " + numTables); List<String> tables = new ArrayList<String>(); - for (int i = 0; i < numTables; i++) - tables.add(String.format("ctt_%03d", i)); + for (int i = 0; i < numTables - 1; i++) { + tables.add(String.format("nspace_%03d.ctt_%03d", i, i)); + } + tables.add(String.format("ctt_%03d", numTables - 1)); + state.set("tables", tables); int numUsers = Integer.parseInt(props.getProperty("numUsers", "5")); http://git-wip-us.apache.org/repos/asf/accumulo/blob/8e1b5090/test/src/test/java/org/apache/accumulo/test/TableNamespacesTest.java ---------------------------------------------------------------------- diff --git a/test/src/test/java/org/apache/accumulo/test/TableNamespacesTest.java b/test/src/test/java/org/apache/accumulo/test/TableNamespacesTest.java index 6685103..8c1a54a 100644 --- a/test/src/test/java/org/apache/accumulo/test/TableNamespacesTest.java +++ b/test/src/test/java/org/apache/accumulo/test/TableNamespacesTest.java @@ -278,4 +278,50 @@ public class TableNamespacesTest { String tnamespace = TableNamespaces.getNamespaceName(instance, tnid); assertTrue(namespace2.equals(tnamespace)); } + + /** + * This test clones a table to a different namespace and ensures it's properties are correct + */ + @Test + public void testCloneTableProperties() throws Exception { + String n1 = "namespace1"; + String n2 = "namespace2"; + String t1 = n1 + ".table"; + String t2 = n2 + ".table"; + + String propKey = Property.TABLE_FILE_MAX.getKey(); + String propVal1 = "55"; + String propVal2 = "66"; + + Connector c = accumulo.getConnector("root", secret); + + c.tableNamespaceOperations().create(n1); + c.tableOperations().create(t1); + + c.tableOperations().removeProperty(t1, Property.TABLE_FILE_MAX.getKey()); + c.tableNamespaceOperations().setProperty(n1, propKey, propVal1); + + boolean itWorked = false; + for (Entry<String,String> prop : c.tableOperations().getProperties(t1)) { + if (prop.getKey().equals(propKey) && prop.getValue().equals(propVal1)) { + itWorked = true; + break; + } + } + assertTrue(itWorked); + + c.tableNamespaceOperations().create(n2); + c.tableNamespaceOperations().setProperty(n2, propKey, propVal2); + c.tableOperations().clone(t1, t2, true, null, null); + c.tableOperations().removeProperty(t2, propKey); + + itWorked = false; + for (Entry<String,String> prop : c.tableOperations().getProperties(t2)) { + if (prop.getKey().equals(propKey) && prop.getValue().equals(propVal2)) { + itWorked = true; + break; + } + } + assertTrue(itWorked); + } }
