This is an automated email from the ASF dual-hosted git repository. ddanielr pushed a commit to branch main in repository https://gitbox.apache.org/repos/asf/accumulo.git
commit a893ee5c5327748e101369850b983248cabf6153 Merge: 44c3e553d3 f4cb86cd67 Author: Daniel Roberts ddanielr <[email protected]> AuthorDate: Fri Aug 15 14:05:55 2025 +0000 Merge branch '2.1' shell/pom.xml | 4 ++ .../java/org/apache/accumulo/shell/ShellUtil.java | 40 ++++++++++++++ .../accumulo/shell/commands/ConfigCommand.java | 30 +++++++++- .../shell/commands/CreateTableCommand.java | 17 +++++- .../org/apache/accumulo/test/shell/ShellIT.java | 64 +++++++++++++++++++++- 5 files changed, 149 insertions(+), 6 deletions(-) diff --cc shell/src/main/java/org/apache/accumulo/shell/ShellUtil.java index c406ebed50,5afcbe66cf..1a12587b6b --- a/shell/src/main/java/org/apache/accumulo/shell/ShellUtil.java +++ b/shell/src/main/java/org/apache/accumulo/shell/ShellUtil.java @@@ -20,8 -20,9 +20,10 @@@ package org.apache.accumulo.shell import static java.nio.charset.StandardCharsets.UTF_8; -import java.io.File; -import java.io.FileReader; ++import java.io.BufferedReader; import java.io.IOException; ++import java.nio.file.Files; +import java.nio.file.Path; import java.util.ArrayList; import java.util.Arrays; import java.util.Base64; @@@ -74,6 -81,38 +82,38 @@@ public class ShellUtil } else { return Collections.emptyMap(); } + } + + public static Map<String,String> readPropertiesFromFile(String filename) + throws IOException, AccumuloException { + PropertiesConfiguration config = new PropertiesConfiguration(); - try (FileReader out = new FileReader(filename, UTF_8)) { - config.read(out); ++ try (BufferedReader bufferedReader = Files.newBufferedReader(Path.of(filename))) { ++ config.read(bufferedReader); + } catch (ConfigurationException e) { + Shell.log.error("Property file {} contains invalid configuration. Please verify file format", + filename, e); + } + Iterator<String> keysIterator = config.getKeys(); + Map<String,String> propertiesMap = new HashMap<>(); + boolean foundErrors = false; + while (keysIterator.hasNext()) { + String key = keysIterator.next(); + String value = config.getString(key); + if (!Property.isValidPropertyKey(key)) { + Shell.log.error("Property: \"{}\" is invalid", key); + foundErrors = true; + } else if (!Property.isValidProperty(key, value)) { + Shell.log.error("Property: \"{}\" has an invalid value: \"{}\"", key, value); + foundErrors = true; + } else { + propertiesMap.put(key, value); + } + } + if (foundErrors) { + Shell.log.error("Property file {} contains invalid properties", filename); + throw new AccumuloException("InvalidPropertyFile: " + filename); + } + return propertiesMap; } } diff --cc shell/src/main/java/org/apache/accumulo/shell/commands/CreateTableCommand.java index 623fe3fcab,633b419973..02aad9badf --- a/shell/src/main/java/org/apache/accumulo/shell/commands/CreateTableCommand.java +++ b/shell/src/main/java/org/apache/accumulo/shell/commands/CreateTableCommand.java @@@ -348,14 -336,14 +357,17 @@@ public class CreateTableCommand extend createTableOptFormatter = new Option("f", "formatter", true, "default formatter to set"); createTableOptInitProp = new Option("prop", "init-properties", true, "comma-separated user-defined initial key=value pairs"); + createTableOptInitPropFile = + new Option("pf", "propFile", true, "user-defined initial properties file"); + createTableOptInitialTabletAvailability = + new Option("a", "availability", true, "initial tablet availability (defaults to ONDEMAND)"); createTableOptCopyConfig.setArgName("table"); createTableOptCopySplits.setArgName("table"); createTableOptSplit.setArgName("filename"); createTableOptFormatter.setArgName("className"); createTableOptInitProp.setArgName("properties"); + createTableOptInitPropFile.setArgName("properties-file"); + createTableOptInitialTabletAvailability.setArgName("availability"); createTableOptLocalityProps = new Option("l", "locality", true, "create locality groups at table creation"); diff --cc test/src/main/java/org/apache/accumulo/test/shell/ShellIT.java index 2f2bf1218a,d8fc412d90..9a5bccafe4 --- a/test/src/main/java/org/apache/accumulo/test/shell/ShellIT.java +++ b/test/src/main/java/org/apache/accumulo/test/shell/ShellIT.java @@@ -18,7 -18,9 +18,8 @@@ */ package org.apache.accumulo.test.shell; -import static org.apache.accumulo.core.conf.Property.TSERV_COMPACTION_WARN_TIME; ++import static org.apache.accumulo.core.conf.Property.COMPACTION_WARN_TIME; import static org.apache.accumulo.harness.AccumuloITBase.MINI_CLUSTER_ONLY; -import static org.apache.accumulo.harness.AccumuloITBase.SUNNY_DAY; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertTrue; @@@ -25,8 -28,10 +27,9 @@@ import java.io.File import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; + import java.io.PrintWriter; import java.nio.file.Files; -import java.text.DateFormat; -import java.text.SimpleDateFormat; +import java.nio.file.Path; import java.time.Duration; import java.util.ArrayList; import java.util.Arrays; @@@ -495,7 -533,7 +501,7 @@@ public class ShellIT extends SharedMini void configTest() throws IOException { Shell.log.debug("Starting config property type test -------------------------"); -- String testTable = "test"; ++ String testTable = "testConfig"; exec("createtable " + testTable, true); for (Property property : Property.values()) { @@@ -614,6 -645,57 +620,58 @@@ assertGoodExit("Unknown command", false); } + @TempDir + private static File tempDir; + + @Test + public void propFileNotFoundTest() throws IOException { - String fileName = new File(tempDir, "propFile.shellit").getAbsolutePath(); ++ ++ Path fileName = Path.of(tempDir.getPath(), "propFile.shellit"); + + Shell.log.debug("Starting prop file not found test --------------------------"); - exec("config --propFile " + fileName, false, - "FileNotFoundException: " + fileName + " (No such file or directory)"); ++ exec("config --propFile " + fileName, false, "NoSuchFileException: " + fileName); + } + + @Test + public void setpropsViaFile() throws Exception { + File file = File.createTempFile("propFile", ".conf", tempDir); + PrintWriter writer = new PrintWriter(file.getAbsolutePath()); - writer.println(TSERV_COMPACTION_WARN_TIME.getKey() + "=11m"); ++ writer.println(COMPACTION_WARN_TIME.getKey() + "=11m"); + writer.close(); + exec("config --propFile " + file.getAbsolutePath(), true); + } + + @Test + public void createTableWithPropsFile() throws Exception { ++ String tableName = "testProps"; + File file = File.createTempFile("propFile", ".conf", tempDir); + PrintWriter writer = new PrintWriter(file.getAbsolutePath()); + writer.println("table.custom.test1=true"); + writer.println("table.custom.test2=false"); + writer.close(); - exec("createtable test --propFile " + file.getAbsolutePath() ++ exec("createtable " + tableName + " --propFile " + file.getAbsolutePath() + + " -prop table.custom.test3=optional", true); + - assertTrue(shell.getAccumuloClient().tableOperations().exists("test")); ++ assertTrue(shell.getAccumuloClient().tableOperations().exists(tableName)); + Map<String,String> tableIds = shell.getAccumuloClient().tableOperations().tableIdMap(); + + TableConfiguration tableConf = - getCluster().getServerContext().getTableConfiguration(TableId.of(tableIds.get("test"))); ++ getCluster().getServerContext().getTableConfiguration(TableId.of(tableIds.get(tableName))); + assertEquals("true", tableConf.get("table.custom.test1")); + assertEquals("false", tableConf.get("table.custom.test2")); + assertEquals("optional", tableConf.get("table.custom.test3")); + } + + @Test + public void invalidPropFileTest() throws Exception { + File file = File.createTempFile("invalidPropFile", ".conf", tempDir); + PrintWriter writer = new PrintWriter(file.getAbsolutePath()); + writer.println("this is not a valid property file"); + writer.close(); + exec("config --propFile " + file.getAbsolutePath(), false, + "InvalidPropertyFile: " + file.getAbsolutePath()); + } + @Test public void setIterTest() throws IOException { Shell.log.debug("Starting setiter test --------------------------");
