in shell/src/main/java/org/apache/accumulo/shell/commands/SetIterCommand.java [200:342]
private static String setUpOptions(ClassLoader classloader, final LineReader reader,
final PrintWriter writer, final String className, final Map<String,String> options)
throws IOException, ShellCommandException {
String input;
SortedKeyValueIterator<Key,Value> skvi;
String clazzName;
try {
@SuppressWarnings("unchecked")
var clazz = (Class<? extends SortedKeyValueIterator<Key,Value>>) classloader
.loadClass(className).asSubclass(SortedKeyValueIterator.class);
clazzName = clazz.getName();
skvi = clazz.getDeclaredConstructor().newInstance();
} catch (ReflectiveOperationException e) {
StringBuilder msg = new StringBuilder("Unable to load ").append(className);
if (className.indexOf('.') < 0) {
msg.append("; did you use a fully qualified package name?");
} else {
msg.append("; class not found.");
}
throw new ShellCommandException(ErrorCode.INITIALIZATION_FAILURE, msg.toString());
} catch (ClassCastException e) {
String msg = className + " loaded successfully but does not implement SortedKeyValueIterator."
+ " This class cannot be used with this command.";
throw new ShellCommandException(ErrorCode.INITIALIZATION_FAILURE, msg);
}
OptionDescriber iterOptions = null;
if (OptionDescriber.class.isAssignableFrom(skvi.getClass())) {
iterOptions = (OptionDescriber) skvi;
}
String iteratorName;
if (iterOptions != null) {
final IteratorOptions itopts = iterOptions.describeOptions();
iteratorName = itopts.getName();
if (iteratorName == null) {
throw new IllegalArgumentException(
className + " described its default distinguishing name as null");
}
String shortClassName = className;
if (className.contains(".")) {
shortClassName = className.substring(className.lastIndexOf('.') + 1);
}
final Map<String,String> localOptions = new HashMap<>();
do {
// clean up the overall options that caused things to fail
for (String key : localOptions.keySet()) {
options.remove(key);
}
localOptions.clear();
writer.println(itopts.getDescription());
String prompt;
if (itopts.getNamedOptions() != null) {
for (Entry<String,String> e : itopts.getNamedOptions().entrySet()) {
prompt = Shell.repeat("-", 10) + "> set " + shortClassName + " parameter " + e.getKey()
+ ", " + e.getValue() + ": ";
writer.flush();
input = reader.readLine(prompt);
if (input == null) {
writer.println();
throw new IOException("Input stream closed");
}
// Places all Parameters and Values into the LocalOptions, even if the value is "".
// This allows us to check for "" values when setting the iterators and allows us to
// remove
// the parameter and value from the table property.
localOptions.put(e.getKey(), input);
}
}
if (itopts.getUnnamedOptionDescriptions() != null) {
for (String desc : itopts.getUnnamedOptionDescriptions()) {
writer.println(Shell.repeat("-", 10) + "> entering options: " + desc);
input = "start";
prompt = Shell.repeat("-", 10) + "> set " + shortClassName
+ " option (<name> <value>, hit enter to skip): ";
while (true) {
writer.flush();
input = reader.readLine(prompt);
if (input == null) {
writer.println();
throw new IOException("Input stream closed");
} else {
input = new String(input);
}
if (input.isEmpty()) {
break;
}
String[] sa = input.split(" ", 2);
localOptions.put(sa[0], sa[1]);
}
}
}
options.putAll(localOptions);
if (!iterOptions.validateOptions(options)) {
writer.println("invalid options for " + clazzName);
}
} while (!iterOptions.validateOptions(options));
} else {
writer.flush();
writer.println("The iterator class does not implement OptionDescriber."
+ " Consider this for better iterator configuration using this setiter command.");
iteratorName = reader.readLine("Name for iterator (enter to skip): ");
if (iteratorName == null) {
writer.println();
throw new IOException("Input stream closed");
} else if (iteratorName.isBlank()) {
// Treat whitespace or empty string as no name provided
iteratorName = null;
}
writer.flush();
writer.println("Optional, configure name-value options for iterator:");
String prompt = Shell.repeat("-", 10) + "> set option (<name> <value>, hit enter to skip): ";
final HashMap<String,String> localOptions = new HashMap<>();
while (true) {
writer.flush();
input = reader.readLine(prompt);
if (input == null) {
writer.println();
throw new IOException("Input stream closed");
} else if (input.isBlank()) {
break;
}
String[] sa = input.split(" ", 2);
localOptions.put(sa[0], sa[1]);
}
options.putAll(localOptions);
}
return iteratorName;
}