You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@rya.apache.org by mi...@apache.org on 2016/08/26 00:06:58 UTC
[37/52] [abbrv] incubator-rya git commit: Rya-82 Rya Console updated
to incorporate Rya Details for an instance and provide administrative
commands.
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/main/java/mvm/rya/shell/util/JLinePrompt.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/main/java/mvm/rya/shell/util/JLinePrompt.java b/extras/rya.console/src/main/java/mvm/rya/shell/util/JLinePrompt.java
new file mode 100644
index 0000000..5af4278
--- /dev/null
+++ b/extras/rya.console/src/main/java/mvm/rya/shell/util/JLinePrompt.java
@@ -0,0 +1,200 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell.util;
+
+import static java.util.Objects.requireNonNull;
+
+import java.io.IOException;
+import java.util.Set;
+
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.security.util.FieldUtils;
+import org.springframework.shell.core.Shell;
+
+import com.google.common.base.Optional;
+import com.google.common.collect.Sets;
+
+import jline.console.ConsoleReader;
+
+/**
+ * Provides access to the host {@link Shell}'s {@link ConsoleReader} and some
+ * utility functions for using it.
+ */
+@ParametersAreNonnullByDefault
+public abstract class JLinePrompt {
+
+ /**
+ * Defines things that may be typed in response to a boolean prompt that evaluate to true.
+ */
+ private static final Set<String> affirmativeStrings = Sets.newHashSet("true", "t", "yes", "y");
+
+ /**
+ * Defines things that may be typed in response to a boolean prompt that evaluate to false.
+ */
+ private static final Set<String> negativeStrings = Sets.newHashSet("false", "f", "no", "n");
+
+ @Autowired
+ private Shell shell;
+
+ /**
+ * @return The shell's {@link ConsoleReader}.
+ */
+ public ConsoleReader getReader() {
+ // XXX Spring Shell doesn't expose the reader that we need to use to
+ // read values from a terminal, so use reflection to pull it out.
+ return (ConsoleReader) FieldUtils.getProtectedFieldValue("reader", shell);
+ }
+
+ /**
+ * Formats a prompt that shows a default value.
+ *
+ * @param fieldName - The text portion that appears before the default. (not null)
+ * @param defaultValue - The default value that will be shown in the prompt.
+ * @return A prompt that shows the default value for a field.
+ */
+ public String makeFieldPrompt(final String fieldName, final boolean defaultValue) {
+ return String.format("%s [default: %s]: ", fieldName, defaultValue);
+ }
+
+ /**
+ * Checks if a user's input matches one of the affirmative strings.
+ *
+ * @param input - The user's input. (not null)
+ * @return {@code true} if the input is one of the affirmative values; otherwise {@code false}.
+ */
+ private boolean isAffirmative(final String input) {
+ requireNonNull(input);
+ for(final String affirmativeString : affirmativeStrings) {
+ if( input.equalsIgnoreCase(affirmativeString) ) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ /**
+ * Checks if a user's input matches one of the negative strings.
+ *
+ * @param input - The user's input. (not null)
+ * @return {@code true} if the input is one of the negative values; otherwise {@code false}.
+ */
+ private boolean isNegative(final String input) {
+ requireNonNull(input);
+ for(final String negativeString : negativeStrings) {
+ if( input.equalsIgnoreCase(negativeString) ) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ /**
+ * Prompts a user for a boolean value. The prompt will be repeated until
+ * a value true/false string has been submitted. If a default value is
+ * provided, then it will be used if the user doens't enter anything.
+ *
+ * @param prompt - The prompt for the input. (not null)
+ * @param defaultValue - The default value for the input if one is provided. (not null)
+ * @return The value the user entered.
+ * @throws IOException There was a problem reading values from the user.
+ */
+ protected boolean promptBoolean(final String prompt, final Optional<Boolean> defaultValue) throws IOException {
+ requireNonNull(prompt);
+ requireNonNull(defaultValue);
+
+ final ConsoleReader reader = getReader();
+ reader.setPrompt(prompt);
+
+ Boolean value = null;
+ boolean prompting = true;
+
+ while(prompting) {
+ // An empty input means to use the default value.
+ final String input = reader.readLine();
+ if(input.isEmpty() && defaultValue.isPresent()) {
+ value = defaultValue.get();
+ prompting = false;
+ }
+
+ // Check if it is one of the affirmative answers.
+ if(isAffirmative(input)) {
+ value = true;
+ prompting = false;
+ }
+
+ // Check if it is one of the negative answers.
+ if(isNegative(input)) {
+ value = false;
+ prompting = false;
+ }
+
+ // If we are still prompting, the input was invalid.
+ if(prompting) {
+ reader.println("Invalid response (true/false)");
+ }
+ }
+
+ return value;
+ }
+
+ /**
+ * Prompts a user for a String value. The prompt will be repeated until a
+ * value has been submitted. If a default value is provided, then it will be
+ * used if the user doesn't enter anything.
+ *
+ * @param prompt - The prompt for the input. (not null)
+ * @param defaultValue - The default value for the input if one is provided. (not null)
+ * @return The value the user entered.
+ * @throws IOException There was a problem reading values from the user.
+ */
+ protected String promptString(final String prompt, final Optional<String> defaultValue) throws IOException {
+ requireNonNull(prompt);
+ requireNonNull(defaultValue);
+
+ final ConsoleReader reader = getReader();
+ reader.setPrompt(prompt);
+
+ String value = null;
+ boolean prompting = true;
+
+ while(prompting) {
+ // Read a line of input.
+ final String input = reader.readLine();
+
+ if(!input.isEmpty()) {
+ // If a value was provided, return it.
+ value = input;
+ prompting = false;
+ } else {
+ // Otherwise, if a default value was provided, return it;
+ if(defaultValue.isPresent()) {
+ value = defaultValue.get();
+ prompting = false;
+ } else {
+ // Otherwise, the user must provide a value.
+ reader.println("Invalid response. Must provide a value.");
+ }
+ }
+ }
+
+ return value;
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/main/java/mvm/rya/shell/util/PasswordPrompt.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/main/java/mvm/rya/shell/util/PasswordPrompt.java b/extras/rya.console/src/main/java/mvm/rya/shell/util/PasswordPrompt.java
new file mode 100644
index 0000000..c4a7d90
--- /dev/null
+++ b/extras/rya.console/src/main/java/mvm/rya/shell/util/PasswordPrompt.java
@@ -0,0 +1,71 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell.util;
+
+import java.io.IOException;
+
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import jline.console.ConsoleReader;
+
+/**
+ * A mechanism for prompting a user of the application for a password.
+ */
+@ParametersAreNonnullByDefault
+public interface PasswordPrompt {
+
+ /**
+ * Prompt the user for a password, wait for their input, and then get the
+ * value they entered.
+ *
+ * @return A character array holding the entered password.
+ * @throws IOEXception There was a problem reading the password.
+ */
+ public char[] getPassword() throws IOException;
+
+ /**
+ * Prompts a user for their password using a JLine {@link ConsoleReader}.
+ * <p>
+ * This prompt has a known security issue. ConsoleReader only reads passwords
+ * into Strings, so they can't easily be cleared out. We many an attempt to
+ * garbage collect the String after converting it to a character array, but
+ * this could be improved.
+ */
+ public static class JLinePasswordPrompt extends JLinePrompt implements PasswordPrompt {
+
+ @Override
+ public char[] getPassword() throws IOException {
+ char[] password = new char[0];
+
+ final ConsoleReader reader = getReader();
+ reader.setPrompt("Password: ");
+ String passwordStr = reader.readLine('*');
+ password = passwordStr.toCharArray();
+
+ // Reading the password into memory as a String is less safe than a char[]
+ // because the String is immutable. We can't clear it out. At best, we can
+ // remove all references to it and suggest the GC clean it up. There are no
+ // guarantees though.
+ passwordStr = null;
+ System.gc();
+
+ return password;
+ }
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/main/java/mvm/rya/shell/util/RyaDetailsFormatter.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/main/java/mvm/rya/shell/util/RyaDetailsFormatter.java b/extras/rya.console/src/main/java/mvm/rya/shell/util/RyaDetailsFormatter.java
new file mode 100644
index 0000000..4c83b8d
--- /dev/null
+++ b/extras/rya.console/src/main/java/mvm/rya/shell/util/RyaDetailsFormatter.java
@@ -0,0 +1,117 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell.util;
+
+import static java.util.Objects.requireNonNull;
+
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import com.google.common.base.Optional;
+import com.google.common.collect.ImmutableMap;
+
+import mvm.rya.api.instance.RyaDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails.PCJDetails;
+
+/**
+ * Formats an instance of {@link RyaDetails}.
+ */
+@ParametersAreNonnullByDefault
+public class RyaDetailsFormatter {
+
+ /**
+ * Pretty formats an instance of {@link RyaDetails}.
+ *
+ * @param details - The object to format. (not null)
+ * @return A pretty render of the object.
+ */
+ public String format(final RyaDetails details) {
+ requireNonNull(details);
+
+ final StringBuilder report = new StringBuilder();
+
+ report.append("General Metadata:\n");
+ report.append(" Instance Name: ").append(details.getRyaInstanceName()).append("\n");
+ report.append(" RYA Version: ").append( details.getRyaVersion() ).append("\n");
+
+ report.append("Secondary Indicies:\n");
+ report.append(" Entity Centric Index:\n");
+ report.append(" Enabled: ").append( details.getEntityCentricIndexDetails().isEnabled() ).append("\n");
+ report.append(" Geospatial Index:\n");
+ report.append(" Enabled: ").append( details.getGeoIndexDetails().isEnabled() ).append("\n");
+ report.append(" Free Text Index:\n");
+ report.append(" Enabled: ").append( details.getFreeTextIndexDetails().isEnabled() ).append("\n");
+ report.append(" Temporal Index:\n");
+ report.append(" Enabled: ").append( details.getTemporalIndexDetails().isEnabled() ).append("\n");
+
+ report.append(" PCJ Index:\n");
+ final PCJIndexDetails pcjDetails = details.getPCJIndexDetails();
+ report.append(" Enabled: ").append( pcjDetails.isEnabled() ).append("\n");
+ if(pcjDetails.isEnabled()) {
+ if(pcjDetails.getFluoDetails().isPresent()) {
+ final String fluoAppName = pcjDetails.getFluoDetails().get().getUpdateAppName();
+ report.append(" Fluo App Name: ").append(fluoAppName).append("\n");
+ }
+
+ final ImmutableMap<String, PCJDetails> pcjs = pcjDetails.getPCJDetails();
+ report.append(" PCJs:\n");
+ if(pcjs.isEmpty()) {
+ report.append(" No PCJs have been added yet.\n");
+ } else {
+ for(final PCJDetails pcj : pcjs.values()) {
+ report.append(" ID: ").append(pcj.getId()).append("\n");
+
+ final String updateStrategy = format( pcj.getUpdateStrategy(), "None" );
+ report.append(" Update Strategy: ").append(updateStrategy).append("\n");
+
+ final String lastUpdateTime = format( pcj.getLastUpdateTime(), "unavailable");
+ report.append(" Last Update Time: ").append(lastUpdateTime).append("\n");
+ }
+ }
+ }
+
+ report.append("Statistics:\n");
+ report.append(" Prospector:\n");
+ final String prospectorLastUpdateTime = format(details.getProspectorDetails().getLastUpdated(), "unavailable");
+ report.append(" Last Update Time: ").append( prospectorLastUpdateTime).append("\n");
+
+ report.append(" Join Selectivity:\n");
+ final String jsLastUpdateTime = format(details.getJoinSelectivityDetails().getLastUpdated(), "unavailable");
+ report.append(" Last Updated Time: ").append( jsLastUpdateTime ).append("\n");
+
+ return report.toString();
+ }
+
+ /**
+ * Formats an optional value using the value's toString() value.
+ *
+ * @param value - The optional value that will be formatted. (not null)
+ * @param absentValue - The String that will be returned if the optional is absent. (not null)
+ * @return The String representation of the optional value.
+ */
+ private <T> String format(final Optional<T> value, final String absentValue) {
+ requireNonNull(value);
+
+ String formatted = "unavailable";
+ if(value.isPresent()) {
+ formatted = value.get().toString();
+ }
+ return formatted;
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/main/java/mvm/rya/shell/util/SparqlPrompt.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/main/java/mvm/rya/shell/util/SparqlPrompt.java b/extras/rya.console/src/main/java/mvm/rya/shell/util/SparqlPrompt.java
new file mode 100644
index 0000000..e47e292
--- /dev/null
+++ b/extras/rya.console/src/main/java/mvm/rya/shell/util/SparqlPrompt.java
@@ -0,0 +1,55 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell.util;
+
+import java.io.IOException;
+
+import javax.annotation.ParametersAreNonnullByDefault;
+
+import jline.console.ConsoleReader;
+
+/**
+ * A mechanism for prompting a user of the application for a SPARQL string.
+ */
+@ParametersAreNonnullByDefault
+public interface SparqlPrompt {
+
+ /**
+ * Prompt the user for a SPARQL query, wait for their input, and then get the
+ * value they entered.
+ *
+ * @return The user entered SPARQL query.
+ * @throws IOEXception There was a problem reading the user's input.
+ */
+ public String getSparql() throws IOException;
+
+ /**
+ * Prompts a user for a SPARQL query using a JLine {@link ConsoleReader}.
+ */
+ @ParametersAreNonnullByDefault
+ public static class JLineSparqlPrompt extends JLinePrompt implements SparqlPrompt {
+
+ @Override
+ public String getSparql() throws IOException {
+ final ConsoleReader reader = getReader();
+ reader.setPrompt("SPARQL: ");
+ return reader.readLine();
+ }
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/main/resources/LICENSE.txt
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/main/resources/LICENSE.txt b/extras/rya.console/src/main/resources/LICENSE.txt
new file mode 100644
index 0000000..4a9fe83
--- /dev/null
+++ b/extras/rya.console/src/main/resources/LICENSE.txt
@@ -0,0 +1,16 @@
+Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements. See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership. The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied. See the License for the
+specific language governing permissions and limitations
+under the License.
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/main/resources/META-INF/spring/spring-shell-plugin.xml
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/main/resources/META-INF/spring/spring-shell-plugin.xml b/extras/rya.console/src/main/resources/META-INF/spring/spring-shell-plugin.xml
index e593a48..b210311 100644
--- a/extras/rya.console/src/main/resources/META-INF/spring/spring-shell-plugin.xml
+++ b/extras/rya.console/src/main/resources/META-INF/spring/spring-shell-plugin.xml
@@ -1,30 +1,40 @@
<?xml version="1.0" encoding="UTF-8"?>
-
<!--
-Licensed to the Apache Software Foundation (ASF) under one
-or more contributor license agreements. See the NOTICE file
-distributed with this work for additional information
-regarding copyright ownership. The ASF licenses this file
-to you under the Apache License, Version 2.0 (the
-"License"); you may not use this file except in compliance
-with the License. You may obtain a copy of the License at
- http://www.apache.org/licenses/LICENSE-2.0
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements. See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership. The ASF licenses this file
+ to you under the Apache License, Version 2.0 (the
+ "License"); you may not use this file except in compliance
+ with the License. You may obtain a copy of the License at
-Unless required by applicable law or agreed to in writing,
-software distributed under the License is distributed on an
-"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-KIND, either express or implied. See the License for the
-specific language governing permissions and limitations
-under the License.
--->
+ http://www.apache.org/licenses/LICENSE-2.0
+ Unless required by applicable law or agreed to in writing,
+ software distributed under the License is distributed on an
+ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ KIND, either express or implied. See the License for the
+ specific language governing permissions and limitations
+ under the License.
+
+-->
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.1.xsd">
- <context:component-scan base-package="mvm.rya.console" />
+ <!-- Tell Spring where it can find all of the Command components. -->
+ <context:component-scan base-package="mvm.rya.shell"/>
-</beans>
+ <!-- Define the shell state bean that will be shared across all of the commands. -->
+ <bean id="sharedShellState" class="mvm.rya.shell.SharedShellState" />
+ <bean id="passwordPrompt" class="mvm.rya.shell.util.PasswordPrompt.JLinePasswordPrompt" />
+ <bean id="installPrompt" class="mvm.rya.shell.util.InstallPrompt.JLineAccumuloInstallPrompt" />
+ <bean id="sparqlPrompt" class="mvm.rya.shell.util.SparqlPrompt.JLineSparqlPrompt" />
+
+ <!-- Define each of the beans that hold onto commands used by the shell. -->
+ <bean id="ryaConnectionCommands" class="mvm.rya.shell.RyaConnectionCommands" />
+ <bean id="ryaAdminCommands" class="mvm.rya.shell.RyaAdminCommands" />
+</beans>
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/java/mvm/rya/shell/RyaAdminCommandsTest.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/java/mvm/rya/shell/RyaAdminCommandsTest.java b/extras/rya.console/src/test/java/mvm/rya/shell/RyaAdminCommandsTest.java
new file mode 100644
index 0000000..1baec41
--- /dev/null
+++ b/extras/rya.console/src/test/java/mvm/rya/shell/RyaAdminCommandsTest.java
@@ -0,0 +1,261 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell;
+
+import static org.junit.Assert.assertEquals;
+import static org.mockito.Matchers.eq;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
+
+import java.io.IOException;
+import java.util.Date;
+import java.util.List;
+
+import org.junit.Test;
+
+import com.google.common.base.Optional;
+import com.google.common.collect.Lists;
+
+import mvm.rya.api.client.RyaClientException;
+import mvm.rya.api.client.RyaClient;
+import mvm.rya.api.client.CreatePCJ;
+import mvm.rya.api.client.DeletePCJ;
+import mvm.rya.api.client.GetInstanceDetails;
+import mvm.rya.api.client.Install;
+import mvm.rya.api.client.InstanceDoesNotExistException;
+import mvm.rya.api.client.ListInstances;
+import mvm.rya.api.client.Install.DuplicateInstanceNameException;
+import mvm.rya.api.client.Install.InstallConfiguration;
+import mvm.rya.api.client.accumulo.AccumuloConnectionDetails;
+import mvm.rya.api.instance.RyaDetails;
+import mvm.rya.api.instance.RyaDetails.EntityCentricIndexDetails;
+import mvm.rya.api.instance.RyaDetails.FreeTextIndexDetails;
+import mvm.rya.api.instance.RyaDetails.GeoIndexDetails;
+import mvm.rya.api.instance.RyaDetails.JoinSelectivityDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails.FluoDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails.PCJDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails.PCJDetails.PCJUpdateStrategy;
+import mvm.rya.api.instance.RyaDetails.ProspectorDetails;
+import mvm.rya.api.instance.RyaDetails.TemporalIndexDetails;
+import mvm.rya.shell.util.InstallPrompt;
+import mvm.rya.shell.util.SparqlPrompt;
+
+/**
+ * Unit tests the methods of {@link RyaAdminCommands}.
+ */
+public class RyaAdminCommandsTest {
+
+ @Test
+ public void createPCJ() throws InstanceDoesNotExistException, RyaClientException, IOException {
+ // Mock the object that performs the create operation.
+ final String instanceName = "unitTest";
+ final String sparql = "SELECT * WHERE { ?person <http://isA> ?noun }";
+ final String pcjId = "123412342";
+ final CreatePCJ mockCreatePCJ = mock(CreatePCJ.class);
+ when(mockCreatePCJ.createPCJ( eq(instanceName), eq(sparql) ) ).thenReturn( pcjId );
+
+ final RyaClient mockCommands = mock(RyaClient.class);
+ when(mockCommands.getCreatePCJ()).thenReturn( mockCreatePCJ );
+
+ final SharedShellState state = new SharedShellState();
+ state.connectedToAccumulo(mock(AccumuloConnectionDetails.class), mockCommands);
+ state.connectedToInstance(instanceName);
+
+ final SparqlPrompt mockSparqlPrompt = mock(SparqlPrompt.class);
+ when(mockSparqlPrompt.getSparql()).thenReturn(sparql);
+
+ // Execute the command.
+ final RyaAdminCommands commands = new RyaAdminCommands(state, mock(InstallPrompt.class), mockSparqlPrompt);
+ final String message = commands.createPcj();
+
+ // Verify the values that were provided to the command were passed through to CreatePCJ.
+ verify(mockCreatePCJ).createPCJ(eq(instanceName), eq(sparql));
+
+ // Verify a message is returned that explains what was created.
+ final String expected = "The PCJ has been created. Its ID is '123412342'.";
+ assertEquals(expected, message);
+ }
+
+ @Test
+ public void deletePCJ() throws InstanceDoesNotExistException, RyaClientException {
+ // Mock the object that performs the delete operation.
+ final DeletePCJ mockDeletePCJ = mock(DeletePCJ.class);
+
+ final RyaClient mockCommands = mock(RyaClient.class);
+ when(mockCommands.getDeletePCJ()).thenReturn( mockDeletePCJ );
+
+ final SharedShellState state = new SharedShellState();
+ state.connectedToAccumulo(mock(AccumuloConnectionDetails.class), mockCommands);
+ final String instanceName = "unitTests";
+ state.connectedToInstance(instanceName);
+
+ // Execute the command.
+ final String pcjId = "123412342";
+
+ final RyaAdminCommands commands = new RyaAdminCommands(state, mock(InstallPrompt.class), mock(SparqlPrompt.class));
+ final String message = commands.deletePcj(pcjId);
+
+ // Verify the values that were provided to the command were passed through to the DeletePCJ.
+ verify(mockDeletePCJ).deletePCJ(eq(instanceName), eq(pcjId));
+
+ // Verify a message is returned that explains what was deleted.
+ final String expected = "The PCJ has been deleted.";
+ assertEquals(expected, message);
+ }
+
+ @Test
+ public void getInstanceDetails() throws InstanceDoesNotExistException, RyaClientException {
+ // Mock the object that performs the get operation.
+ final GetInstanceDetails mockGetInstanceDetails = mock(GetInstanceDetails.class);
+ final String instanceName = "test_instance";
+ final RyaDetails details = RyaDetails.builder().setRyaInstanceName(instanceName)
+ .setRyaVersion("1.2.3.4")
+ .setEntityCentricIndexDetails( new EntityCentricIndexDetails(true) )
+ .setGeoIndexDetails( new GeoIndexDetails(true) )
+ .setTemporalIndexDetails( new TemporalIndexDetails(true) )
+ .setFreeTextDetails( new FreeTextIndexDetails(true) )
+ .setPCJIndexDetails(
+ PCJIndexDetails.builder()
+ .setEnabled(true)
+ .setFluoDetails( new FluoDetails("test_instance_rya_pcj_updater") )
+ .addPCJDetails(
+ PCJDetails.builder()
+ .setId("pcj 1")
+ .setUpdateStrategy(PCJUpdateStrategy.BATCH)
+ .setLastUpdateTime( new Date(1252521351L) ))
+ .addPCJDetails(
+ PCJDetails.builder()
+ .setId("pcj 2")
+ .setUpdateStrategy(PCJUpdateStrategy.INCREMENTAL)))
+ .setProspectorDetails( new ProspectorDetails(Optional.of(new Date(12525211L))) )
+ .setJoinSelectivityDetails( new JoinSelectivityDetails(Optional.of(new Date(125221351L))) )
+ .build();
+
+ when(mockGetInstanceDetails.getDetails(eq(instanceName))).thenReturn( Optional.of(details) );
+
+ final RyaClient mockCommands = mock(RyaClient.class);
+ when(mockCommands.getGetInstanceDetails()).thenReturn( mockGetInstanceDetails );
+
+ final SharedShellState state = new SharedShellState();
+ state.connectedToAccumulo(mock(AccumuloConnectionDetails.class), mockCommands);
+ state.connectedToInstance(instanceName);
+
+ // Execute the command.
+ final RyaAdminCommands commands = new RyaAdminCommands(state, mock(InstallPrompt.class), mock(SparqlPrompt.class));
+ final String message = commands.getInstanceDetails();
+
+ // Verify the values that were provided to the command were passed through to the GetInstanceDetails.
+ verify(mockGetInstanceDetails).getDetails(eq(instanceName));
+
+ // Verify a message is returned that includes the details.
+ final String expected =
+ "General Metadata:\n" +
+ " Instance Name: test_instance\n" +
+ " RYA Version: 1.2.3.4\n" +
+ "Secondary Indicies:\n" +
+ " Entity Centric Index:\n" +
+ " Enabled: true\n" +
+ " Geospatial Index:\n" +
+ " Enabled: true\n" +
+ " Free Text Index:\n" +
+ " Enabled: true\n" +
+ " Temporal Index:\n" +
+ " Enabled: true\n" +
+ " PCJ Index:\n" +
+ " Enabled: true\n" +
+ " Fluo App Name: test_instance_rya_pcj_updater\n" +
+ " PCJs:\n" +
+ " ID: pcj 1\n" +
+ " Update Strategy: BATCH\n" +
+ " Last Update Time: Thu Jan 15 06:55:21 EST 1970\n" +
+ " ID: pcj 2\n" +
+ " Update Strategy: INCREMENTAL\n" +
+ " Last Update Time: unavailable\n" +
+ "Statistics:\n" +
+ " Prospector:\n" +
+ " Last Update Time: Wed Dec 31 22:28:45 EST 1969\n" +
+ " Join Selectivity:\n" +
+ " Last Updated Time: Fri Jan 02 05:47:01 EST 1970\n";
+ assertEquals(expected, message);
+ }
+
+ @Test
+ public void install() throws DuplicateInstanceNameException, RyaClientException, IOException {
+ // Mock the object that performs the install operation.
+ final Install mockInstall = mock(Install.class);
+
+ final RyaClient mockCommands = mock(RyaClient.class);
+ when(mockCommands.getInstall()).thenReturn( mockInstall );
+
+ final SharedShellState state = new SharedShellState();
+ state.connectedToAccumulo(mock(AccumuloConnectionDetails.class), mockCommands);
+
+ // Execute the command.
+ final String instanceName = "unitTests";
+ final InstallConfiguration installConfig = InstallConfiguration.builder()
+ .setEnableGeoIndex(true)
+ .setEnablePcjIndex(true)
+ .build();
+
+ final InstallPrompt mockInstallPrompt = mock(InstallPrompt.class);
+ when(mockInstallPrompt.promptInstanceName()).thenReturn( instanceName );
+ when(mockInstallPrompt.promptInstallConfiguration()).thenReturn( installConfig );
+ when(mockInstallPrompt.promptVerified(eq(instanceName), eq(installConfig))).thenReturn(true);
+
+ final RyaAdminCommands commands = new RyaAdminCommands(state, mockInstallPrompt, mock(SparqlPrompt.class));
+ final String message = commands.install();
+
+ // Verify the values that were provided to the command were passed through to the Install.
+ verify(mockInstall).install(eq(instanceName), eq(installConfig));
+
+ // Verify a message is returned that indicates the success of the operation.
+ final String expected = "The Rya instance named 'unitTests' has been installed.";
+ assertEquals(expected, message);
+ }
+
+ @Test
+ public void listInstances() throws RyaClientException, IOException {
+ // Mock the object that performs the list operation.
+ final ListInstances mockListInstances = mock(ListInstances.class);
+ final List<String> instanceNames = Lists.newArrayList("a", "b", "c", "d");
+ when(mockListInstances.listInstances()).thenReturn(instanceNames);
+
+ final RyaClient mockCommands = mock(RyaClient.class);
+ when(mockCommands.getListInstances()).thenReturn( mockListInstances );
+
+ final SharedShellState state = new SharedShellState();
+ state.connectedToAccumulo(mock(AccumuloConnectionDetails.class), mockCommands);
+ state.connectedToInstance("b");
+
+ // Execute the command.
+ final RyaAdminCommands commands = new RyaAdminCommands(state, mock(InstallPrompt.class), mock(SparqlPrompt.class));
+ final String message = commands.listInstances();
+
+ // Verify a message is returned that lists the the instances.
+ final String expected =
+ "Rya instance names:\n" +
+ " a\n" +
+ " * b\n" +
+ " c\n" +
+ " d\n";
+ assertEquals(expected, message);
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/java/mvm/rya/shell/RyaConnectionCommandsIT.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/java/mvm/rya/shell/RyaConnectionCommandsIT.java b/extras/rya.console/src/test/java/mvm/rya/shell/RyaConnectionCommandsIT.java
new file mode 100644
index 0000000..c755181
--- /dev/null
+++ b/extras/rya.console/src/test/java/mvm/rya/shell/RyaConnectionCommandsIT.java
@@ -0,0 +1,269 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+///**
+// * Licensed to the Apache Software Foundation (ASF) under one
+// * or more contributor license agreements. See the NOTICE file
+// * distributed with this work for additional information
+// * regarding copyright ownership. The ASF licenses this file
+// * to you under the Apache License, Version 2.0 (the
+// * "License"); you may not use this file except in compliance
+// * with the License. You may obtain a copy of the License at
+// *
+// * http://www.apache.org/licenses/LICENSE-2.0
+// *
+// * Unless required by applicable law or agreed to in writing,
+// * software distributed under the License is distributed on an
+// * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// * KIND, either express or implied. See the License for the
+// * specific language governing permissions and limitations
+// * under the License.
+// */
+package mvm.rya.shell;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+import static org.mockito.Mockito.when;
+
+import java.io.IOException;
+
+import org.apache.accumulo.minicluster.MiniAccumuloCluster;
+import org.junit.Test;
+import org.springframework.context.ApplicationContext;
+import org.springframework.shell.Bootstrap;
+import org.springframework.shell.core.CommandResult;
+import org.springframework.shell.core.JLineShellComponent;
+
+import mvm.rya.api.client.Install.InstallConfiguration;
+import mvm.rya.shell.SharedShellState.ConnectionState;
+import mvm.rya.shell.SharedShellState.ShellState;
+import mvm.rya.shell.util.InstallPrompt;
+import mvm.rya.shell.util.PasswordPrompt;
+
+/**
+ * Integration tests the methods of {@link RyaConnectionCommands}.
+ */
+public class RyaConnectionCommandsIT extends RyaShellITBase {
+
+ @Test
+ public void connectAccumulo() throws IOException {
+ final MiniAccumuloCluster cluster = getCluster();
+ final Bootstrap bootstrap = getTestBootstrap();
+ final JLineShellComponent shell = getTestShell();
+
+ // Mock the user entering the correct password.
+ final ApplicationContext context = bootstrap.getApplicationContext();
+ final PasswordPrompt mockPrompt = context.getBean( PasswordPrompt.class );
+ when(mockPrompt.getPassword()).thenReturn("password".toCharArray());
+
+ // Execute the connect command.
+ final String cmd =
+ RyaConnectionCommands.CONNECT_ACCUMULO_CMD + " " +
+ "--username root " +
+ "--instanceName " + cluster.getInstanceName() + " "+
+ "--zookeepers " + cluster.getZooKeepers();
+
+ final CommandResult connectResult = shell.executeCommand(cmd);
+
+ // Ensure the connection was successful.
+ assertTrue( connectResult.isSuccess() );
+ }
+
+ @Test
+ public void connectAccumulo_noAuths() throws IOException {
+ final MiniAccumuloCluster cluster = getCluster();
+ final Bootstrap bootstrap = getTestBootstrap();
+ final JLineShellComponent shell = getTestShell();
+
+ // Mock the user entering the correct password.
+ final ApplicationContext context = bootstrap.getApplicationContext();
+ final PasswordPrompt mockPrompt = context.getBean( PasswordPrompt.class );
+ when(mockPrompt.getPassword()).thenReturn("password".toCharArray());
+
+ // Execute the command
+ final String cmd =
+ RyaConnectionCommands.CONNECT_ACCUMULO_CMD + " " +
+ "--username root " +
+ "--instanceName " + cluster.getInstanceName() + " "+
+ "--zookeepers " + cluster.getZooKeepers();
+
+ final CommandResult connectResult = shell.executeCommand(cmd);
+
+ // Ensure the connection was successful.
+ assertTrue( connectResult.isSuccess() );
+ }
+
+ @Test
+ public void connectAccumulo_wrongCredentials() throws IOException {
+ final MiniAccumuloCluster cluster = getCluster();
+ final Bootstrap bootstrap = getTestBootstrap();
+ final JLineShellComponent shell = getTestShell();
+
+ // Mock the user entering the wrong password.
+ final ApplicationContext context = bootstrap.getApplicationContext();
+ final PasswordPrompt mockPrompt = context.getBean( PasswordPrompt.class );
+ when(mockPrompt.getPassword()).thenReturn("asjifo[ijwa".toCharArray());
+
+ // Execute the command
+ final String cmd =
+ RyaConnectionCommands.CONNECT_ACCUMULO_CMD + " " +
+ "--username root " +
+ "--instanceName " + cluster.getInstanceName() + " "+
+ "--zookeepers " + cluster.getZooKeepers();
+
+ final CommandResult connectResult = shell.executeCommand(cmd);
+
+ // Ensure the command failed.
+ assertFalse( connectResult.isSuccess() );
+ }
+
+ @Test
+ public void printConnectionDetails_notConnected() {
+ final JLineShellComponent shell = getTestShell();
+
+ // Run the print connection details command.
+ final CommandResult printResult = shell.executeCommand( RyaConnectionCommands.PRINT_CONNECTION_DETAILS_CMD );
+ final String msg = (String) printResult.getResult();
+
+ final String expected = "The shell is not connected to anything.";
+ assertEquals(expected, msg);
+ }
+
+ @Test
+ public void printConnectionDetails_connectedToAccumulo() throws IOException {
+ final MiniAccumuloCluster cluster = getCluster();
+ final Bootstrap bootstrap = getTestBootstrap();
+ final JLineShellComponent shell = getTestShell();
+
+ // Mock the user entering the correct password.
+ final ApplicationContext context = bootstrap.getApplicationContext();
+ final PasswordPrompt mockPrompt = context.getBean( PasswordPrompt.class );
+ when(mockPrompt.getPassword()).thenReturn("password".toCharArray());
+
+ // Connect to the mini accumulo instance.
+ final String cmd =
+ RyaConnectionCommands.CONNECT_ACCUMULO_CMD + " " +
+ "--username root " +
+ "--instanceName " + cluster.getInstanceName() + " "+
+ "--zookeepers " + cluster.getZooKeepers();
+ shell.executeCommand(cmd);
+
+ // Run the print connection details command.
+ final CommandResult printResult = shell.executeCommand( RyaConnectionCommands.PRINT_CONNECTION_DETAILS_CMD );
+ final String msg = (String) printResult.getResult();
+
+ final String expected =
+ "The shell is connected to an instance of Accumulo using the following parameters:\n" +
+ " Username: root\n" +
+ " Instance Name: " + cluster.getInstanceName() + "\n" +
+ " Zookeepers: " + cluster.getZooKeepers();
+ assertEquals(expected, msg);
+ }
+
+ @Test
+ public void connectToInstance() throws IOException {
+ final MiniAccumuloCluster cluster = getCluster();
+ final Bootstrap bootstrap = getTestBootstrap();
+ final JLineShellComponent shell = getTestShell();
+
+ // Mock the user entering the correct password.
+ final ApplicationContext context = bootstrap.getApplicationContext();
+ final PasswordPrompt mockPrompt = context.getBean( PasswordPrompt.class );
+ when(mockPrompt.getPassword()).thenReturn("password".toCharArray());
+
+ // Connect to the mini accumulo instance.
+ String cmd =
+ RyaConnectionCommands.CONNECT_ACCUMULO_CMD + " " +
+ "--username root " +
+ "--instanceName " + cluster.getInstanceName() + " "+
+ "--zookeepers " + cluster.getZooKeepers();
+ CommandResult result = shell.executeCommand(cmd);
+
+ // Install an instance of rya.
+ final String instanceName = "testInstance";
+ final InstallConfiguration installConf = InstallConfiguration.builder().build();
+
+ final InstallPrompt installPrompt = context.getBean( InstallPrompt.class );
+ when(installPrompt.promptInstanceName()).thenReturn("testInstance");
+ when(installPrompt.promptInstallConfiguration()).thenReturn( installConf );
+ when(installPrompt.promptVerified(instanceName, installConf)).thenReturn(true);
+
+ result = shell.executeCommand( RyaAdminCommands.INSTALL_CMD );
+ assertTrue( result.isSuccess() );
+
+ // Connect to the instance that was just installed.
+ cmd = RyaConnectionCommands.CONNECT_INSTANCE_CMD + " --instance " + instanceName;
+ result = shell.executeCommand(cmd);
+ assertTrue( result.isSuccess() );
+
+ // Verify the shell state indicates it is connected to an instance.
+ final SharedShellState sharedState = context.getBean( SharedShellState.class );
+ final ShellState state = sharedState.getShellState();
+ assertEquals(ConnectionState.CONNECTED_TO_INSTANCE, state.getConnectionState());
+ }
+
+ @Test
+ public void connectToInstance_instanceDoesNotExist() throws IOException {
+ final MiniAccumuloCluster cluster = getCluster();
+ final Bootstrap bootstrap = getTestBootstrap();
+ final JLineShellComponent shell = getTestShell();
+
+ // Mock the user entering the correct password.
+ final ApplicationContext context = bootstrap.getApplicationContext();
+ final PasswordPrompt mockPrompt = context.getBean( PasswordPrompt.class );
+ when(mockPrompt.getPassword()).thenReturn("password".toCharArray());
+
+ // Connect to the mini accumulo instance.
+ String cmd =
+ RyaConnectionCommands.CONNECT_ACCUMULO_CMD + " " +
+ "--username root " +
+ "--instanceName " + cluster.getInstanceName() + " "+
+ "--zookeepers " + cluster.getZooKeepers();
+ shell.executeCommand(cmd);
+
+ // Try to connect to a non-existing instance.
+ cmd = RyaConnectionCommands.CONNECT_INSTANCE_CMD + " --instance doesNotExist";
+ final CommandResult result = shell.executeCommand(cmd);
+ assertFalse( result.isSuccess() );
+ }
+
+ @Test
+ public void disconnect() throws IOException {
+ final MiniAccumuloCluster cluster = getCluster();
+ final Bootstrap bootstrap = getTestBootstrap();
+ final JLineShellComponent shell = getTestShell();
+
+ // Mock the user entering the correct password.
+ final ApplicationContext context = bootstrap.getApplicationContext();
+ final PasswordPrompt mockPrompt = context.getBean( PasswordPrompt.class );
+ when(mockPrompt.getPassword()).thenReturn("password".toCharArray());
+
+ // Connect to the mini accumulo instance.
+ final String cmd =
+ RyaConnectionCommands.CONNECT_ACCUMULO_CMD + " " +
+ "--username root " +
+ "--instanceName " + cluster.getInstanceName() + " "+
+ "--zookeepers " + cluster.getZooKeepers();
+ shell.executeCommand(cmd);
+
+ // Disconnect from it.
+ final CommandResult disconnectResult = shell.executeCommand( RyaConnectionCommands.DISCONNECT_COMMAND_NAME_CMD );
+ assertTrue( disconnectResult.isSuccess() );
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/java/mvm/rya/shell/RyaPromptProviderTest.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/java/mvm/rya/shell/RyaPromptProviderTest.java b/extras/rya.console/src/test/java/mvm/rya/shell/RyaPromptProviderTest.java
new file mode 100644
index 0000000..54a0bba
--- /dev/null
+++ b/extras/rya.console/src/test/java/mvm/rya/shell/RyaPromptProviderTest.java
@@ -0,0 +1,80 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell;
+
+import static org.junit.Assert.assertEquals;
+import static org.mockito.Mockito.mock;
+
+import org.junit.Test;
+
+import mvm.rya.api.client.RyaClient;
+import mvm.rya.api.client.accumulo.AccumuloConnectionDetails;
+
+/**
+ * Tests the methods of {@link RyaPromptProvider}.
+ */
+public class RyaPromptProviderTest {
+
+ @Test
+ public void notConnected() {
+ // Create a shared state that is disconnected.
+ final SharedShellState sharedState = new SharedShellState();
+ sharedState.disconnected();
+
+ // Create the prompt.
+ final String prompt = new RyaPromptProvider(sharedState).getPrompt();
+
+ // Verify the prompt is formatted correctly.
+ final String expected = "rya> ";
+ assertEquals(expected, prompt);
+ }
+
+ @Test
+ public void isConnected_noInstanceName() {
+ // Create a shared state that is connected to a storage, but not a rya instance.
+ final SharedShellState sharedState = new SharedShellState();
+
+ final AccumuloConnectionDetails connectionDetails = new AccumuloConnectionDetails("", new char[]{}, "testInstance", "");
+ sharedState.connectedToAccumulo(connectionDetails, mock(RyaClient.class));
+
+ // Create a prompt.
+ final String prompt = new RyaPromptProvider(sharedState).getPrompt();
+
+ // Verify the prompt is formatted correctly.
+ final String expected = "rya/testInstance> ";
+ assertEquals(expected, prompt);
+ }
+
+ @Test
+ public void isConnected_hasInstanceName() {
+ // Create a shared state that is connected to a specific instance.
+ final SharedShellState sharedState = new SharedShellState();
+
+ final AccumuloConnectionDetails connectionDetails = new AccumuloConnectionDetails("", new char[]{}, "testInstance", "");
+ sharedState.connectedToAccumulo(connectionDetails, mock(RyaClient.class));
+ sharedState.connectedToInstance("testRya");
+
+ // Create a prompt.
+ final String prompt = new RyaPromptProvider(sharedState).getPrompt();
+
+ // Verify the prompt is formatted correctly.
+ final String expected = "rya/testInstance:testRya> ";
+ assertEquals(expected, prompt);
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/java/mvm/rya/shell/RyaShellITBase.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/java/mvm/rya/shell/RyaShellITBase.java b/extras/rya.console/src/test/java/mvm/rya/shell/RyaShellITBase.java
new file mode 100644
index 0000000..162cecf
--- /dev/null
+++ b/extras/rya.console/src/test/java/mvm/rya/shell/RyaShellITBase.java
@@ -0,0 +1,103 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell;
+
+import java.io.IOException;
+
+import org.apache.accumulo.core.client.AccumuloException;
+import org.apache.accumulo.core.client.AccumuloSecurityException;
+import org.apache.accumulo.minicluster.MiniAccumuloCluster;
+import org.apache.log4j.Level;
+import org.apache.log4j.Logger;
+import org.apache.zookeeper.ClientCnxn;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.BeforeClass;
+import org.springframework.shell.Bootstrap;
+import org.springframework.shell.core.JLineShellComponent;
+
+import mvm.rya.accumulo.MiniAccumuloClusterInstance;
+
+/**
+ * All Rya Shell integration tests should extend this one. It provides startup
+ * and shutdown hooks for a Mini Accumulo Cluster when you start and stop testing.
+ * It also creates a new shell to test with between each test.
+ */
+public class RyaShellITBase {
+
+ /**
+ * The cluster that will be used.
+ */
+ private MiniAccumuloClusterInstance cluster = null;
+
+ /**
+ * The bootstrap that was used to initialize the Shell that will be tested.
+ */
+ private Bootstrap bootstrap;
+
+ /**
+ * The shell that will be tested.
+ */
+ private JLineShellComponent shell;
+
+ @BeforeClass
+ public static void killLoudLogs() {
+ Logger.getLogger(ClientCnxn.class).setLevel(Level.ERROR);
+ }
+
+ @Before
+ public void startShell() throws IOException, InterruptedException, AccumuloException, AccumuloSecurityException {
+ // Start the cluster.
+ cluster = new MiniAccumuloClusterInstance();
+ cluster.startMiniAccumulo();
+
+ // Bootstrap the shell with the test bean configuration.
+ bootstrap = new Bootstrap(new String[]{}, new String[]{"file:src/test/resources/RyaShellTest-context.xml"});
+ shell = bootstrap.getJLineShellComponent();
+ }
+
+ @After
+ public void stopShell() throws IOException, InterruptedException {
+ shell.stop();
+
+ // Stop the cluster.
+ cluster.stopMiniAccumulo();
+ }
+
+ /**
+ * @return The bootstrap that was used to initialize the Shell that will be tested.
+ */
+ public Bootstrap getTestBootstrap() {
+ return bootstrap;
+ }
+
+ /**
+ * @return The shell that will be tested.
+ */
+ public JLineShellComponent getTestShell() {
+ return shell;
+ }
+
+ /**
+ * @return The cluster that is hosting the test.
+ */
+ public MiniAccumuloCluster getCluster() {
+ return cluster.getCluster();
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/java/mvm/rya/shell/SharedShellStateTest.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/java/mvm/rya/shell/SharedShellStateTest.java b/extras/rya.console/src/test/java/mvm/rya/shell/SharedShellStateTest.java
new file mode 100644
index 0000000..e5f0341
--- /dev/null
+++ b/extras/rya.console/src/test/java/mvm/rya/shell/SharedShellStateTest.java
@@ -0,0 +1,167 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell;
+
+import static org.junit.Assert.assertEquals;
+import static org.mockito.Mockito.mock;
+
+import org.junit.Test;
+
+import mvm.rya.api.client.RyaClient;
+import mvm.rya.api.client.accumulo.AccumuloConnectionDetails;
+import mvm.rya.shell.SharedShellState.ConnectionState;
+import mvm.rya.shell.SharedShellState.ShellState;
+
+/**
+ * Tests the methods of {@link SharedShellState}.
+ */
+public class SharedShellStateTest {
+
+ @Test
+ public void initialStateIsDisconnected() {
+ final SharedShellState state = new SharedShellState();
+
+ // Verify disconnected and no values are set.
+ final ShellState expected = ShellState.builder()
+ .setConnectionState(ConnectionState.DISCONNECTED)
+ .build();
+
+ assertEquals(expected, state.getShellState());
+ }
+
+ @Test
+ public void disconnectedToConnectedToStorage() {
+ final SharedShellState state = new SharedShellState();
+
+ // Connect to Accumulo.
+ final AccumuloConnectionDetails connectionDetails = mock(AccumuloConnectionDetails.class);
+ final RyaClient connectedCommands = mock(RyaClient.class);
+ state.connectedToAccumulo(connectionDetails, connectedCommands);
+
+ // Verify the state.
+ final ShellState expected = ShellState.builder()
+ .setConnectionState(ConnectionState.CONNECTED_TO_STORAGE)
+ .setAccumuloConnectionDetails(connectionDetails)
+ .setConnectedCommands(connectedCommands)
+ .build();
+
+ assertEquals(expected, state.getShellState());
+ }
+
+ @Test(expected = IllegalStateException.class)
+ public void connectToStorageAgain() {
+ final SharedShellState state = new SharedShellState();
+
+ // Connect to Accumulo.
+ final AccumuloConnectionDetails connectionDetails = mock(AccumuloConnectionDetails.class);
+ final RyaClient connectedCommands = mock(RyaClient.class);
+ state.connectedToAccumulo(connectionDetails, connectedCommands);
+
+ // Try to set the information again.
+ state.connectedToAccumulo(connectionDetails, connectedCommands);
+ }
+
+ @Test
+ public void connectedToInstance() {
+ final SharedShellState state = new SharedShellState();
+
+ // Connect to Accumulo.
+ final AccumuloConnectionDetails connectionDetails = mock(AccumuloConnectionDetails.class);
+ final RyaClient connectedCommands = mock(RyaClient.class);
+ state.connectedToAccumulo(connectionDetails, connectedCommands);
+
+ // Connect to an Instance.
+ state.connectedToInstance("instance");
+
+ // Verify the state.
+ final ShellState expected = ShellState.builder()
+ .setConnectionState(ConnectionState.CONNECTED_TO_INSTANCE)
+ .setAccumuloConnectionDetails(connectionDetails)
+ .setConnectedCommands(connectedCommands)
+ .setRyaInstanceName("instance")
+ .build();
+
+ assertEquals(expected, state.getShellState());
+ }
+
+ @Test
+ public void ConnectedToInstanceAgain() {
+ final SharedShellState state = new SharedShellState();
+
+ // Connect to Accumulo.
+ final AccumuloConnectionDetails connectionDetails = mock(AccumuloConnectionDetails.class);
+ final RyaClient connectedCommands = mock(RyaClient.class);
+ state.connectedToAccumulo(connectionDetails, connectedCommands);
+
+ // Connect to an Instance.
+ state.connectedToInstance("instance");
+
+ // Connect to another instance.
+ state.connectedToInstance("secondInstance");
+
+ // Verify the state.
+ final ShellState expected = ShellState.builder()
+ .setConnectionState(ConnectionState.CONNECTED_TO_INSTANCE)
+ .setAccumuloConnectionDetails(connectionDetails)
+ .setConnectedCommands(connectedCommands)
+ .setRyaInstanceName("secondInstance")
+ .build();
+ assertEquals(expected, state.getShellState());
+ }
+
+ @Test(expected = IllegalStateException.class)
+ public void connectedToInstanceWhileDisconnectedFromStorage() {
+ final SharedShellState state = new SharedShellState();
+
+ state.connectedToInstance("instance");
+ }
+
+ @Test
+ public void disconnected() {
+ final SharedShellState state = new SharedShellState();
+
+ // Connect to Accumulo and an instance.
+ final AccumuloConnectionDetails connectionDetails = mock(AccumuloConnectionDetails.class);
+ final RyaClient connectedCommands = mock(RyaClient.class);
+ state.connectedToAccumulo(connectionDetails, connectedCommands);
+ state.connectedToInstance("instance");
+
+ // Disconnect.
+ state.disconnected();
+
+ // Verify the state.
+ final ShellState expected = ShellState.builder()
+ .setConnectionState(ConnectionState.DISCONNECTED)
+ .build();
+ assertEquals(expected, state.getShellState());
+ }
+
+ @Test
+ public void disconnectedAgain() {
+ // Indicate we have diconnected while already in the disconnected state.
+ final SharedShellState state = new SharedShellState();
+ state.disconnected();
+
+ // Verify the state.
+ final ShellState expected = ShellState.builder()
+ .setConnectionState(ConnectionState.DISCONNECTED)
+ .build();
+ assertEquals(expected, state.getShellState());
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/java/mvm/rya/shell/util/ConnectorFactoryIT.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/java/mvm/rya/shell/util/ConnectorFactoryIT.java b/extras/rya.console/src/test/java/mvm/rya/shell/util/ConnectorFactoryIT.java
new file mode 100644
index 0000000..e96b0ad
--- /dev/null
+++ b/extras/rya.console/src/test/java/mvm/rya/shell/util/ConnectorFactoryIT.java
@@ -0,0 +1,57 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell.util;
+
+import java.nio.CharBuffer;
+
+import org.apache.accumulo.core.client.AccumuloException;
+import org.apache.accumulo.core.client.AccumuloSecurityException;
+import org.junit.Test;
+
+import mvm.rya.accumulo.AccumuloITBase;
+
+/**
+ * Tests the methods of {@link ConnectorFactory}.
+ */
+public class ConnectorFactoryIT extends AccumuloITBase {
+
+ @Test
+ public void connect_successful() throws AccumuloException, AccumuloSecurityException {
+ // Setup the values that will be tested with.
+ final CharSequence password = CharBuffer.wrap( getPassword() );
+
+ final ConnectorFactory ac = new ConnectorFactory();
+ ac.connect(getUsername(),
+ password,
+ getInstanceName(),
+ getZookeepers());
+ }
+
+ @Test(expected = AccumuloSecurityException.class)
+ public void connect_wrongCredentials() throws AccumuloException, AccumuloSecurityException {
+ // Setup the values that will be tested with.
+ final CharSequence password = CharBuffer.wrap( new char[] {'w','r','o','n','g','p','a','s','s'} );
+
+ final ConnectorFactory ac = new ConnectorFactory();
+ ac.connect(getUsername(),
+ password,
+ getInstanceName(),
+ getZookeepers());
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/java/mvm/rya/shell/util/InstanceNamesFormatterTest.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/java/mvm/rya/shell/util/InstanceNamesFormatterTest.java b/extras/rya.console/src/test/java/mvm/rya/shell/util/InstanceNamesFormatterTest.java
new file mode 100644
index 0000000..f10b776
--- /dev/null
+++ b/extras/rya.console/src/test/java/mvm/rya/shell/util/InstanceNamesFormatterTest.java
@@ -0,0 +1,81 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell.util;
+
+import static org.junit.Assert.assertEquals;
+
+import java.util.List;
+
+import org.junit.Test;
+
+import com.beust.jcommander.internal.Lists;
+
+/**
+ * Tests an instance of {@link InstanceNamesFormatter}.
+ */
+public class InstanceNamesFormatterTest {
+
+ @Test
+ public void format_withConnectedName() {
+ final List<String> instanceNames = Lists.newArrayList("a", "b", "c", "d");
+
+ final String formatted = new InstanceNamesFormatter().format(instanceNames, "c");
+
+ final String expected =
+ "Rya instance names:\n" +
+ " a\n" +
+ " b\n" +
+ " * c\n" +
+ " d\n";
+
+ assertEquals(expected, formatted);
+ }
+
+ @Test
+ public void format_connectedNameNotInList() {
+ final List<String> instanceNames = Lists.newArrayList("a", "b", "c", "d");
+
+ final String formatted = new InstanceNamesFormatter().format(instanceNames, "not_in_list");
+
+ final String expected =
+ "Rya instance names:\n" +
+ " a\n" +
+ " b\n" +
+ " c\n" +
+ " d\n";
+
+ assertEquals(expected, formatted);
+ }
+
+ @Test
+ public void format() {
+ final List<String> instanceNames = Lists.newArrayList("a", "b", "c", "d");
+
+ final String formatted = new InstanceNamesFormatter().format(instanceNames);
+
+ final String expected =
+ "Rya instance names:\n" +
+ " a\n" +
+ " b\n" +
+ " c\n" +
+ " d\n";
+
+ assertEquals(expected, formatted);
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/java/mvm/rya/shell/util/RyaDetailsFormatterTest.java
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/java/mvm/rya/shell/util/RyaDetailsFormatterTest.java b/extras/rya.console/src/test/java/mvm/rya/shell/util/RyaDetailsFormatterTest.java
new file mode 100644
index 0000000..d618283
--- /dev/null
+++ b/extras/rya.console/src/test/java/mvm/rya/shell/util/RyaDetailsFormatterTest.java
@@ -0,0 +1,106 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package mvm.rya.shell.util;
+
+import static org.junit.Assert.assertEquals;
+
+import java.util.Date;
+
+import org.junit.Test;
+
+import com.google.common.base.Optional;
+
+import mvm.rya.api.instance.RyaDetails;
+import mvm.rya.api.instance.RyaDetails.EntityCentricIndexDetails;
+import mvm.rya.api.instance.RyaDetails.FreeTextIndexDetails;
+import mvm.rya.api.instance.RyaDetails.GeoIndexDetails;
+import mvm.rya.api.instance.RyaDetails.JoinSelectivityDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails.FluoDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails.PCJDetails;
+import mvm.rya.api.instance.RyaDetails.PCJIndexDetails.PCJDetails.PCJUpdateStrategy;
+import mvm.rya.api.instance.RyaDetails.ProspectorDetails;
+import mvm.rya.api.instance.RyaDetails.TemporalIndexDetails;
+
+/**
+ * Tests the methods of {@link RyaDetailsFormatter}.
+ */
+public class RyaDetailsFormatterTest {
+
+ @Test
+ public void format() {
+ // Create the object that will be formatted.
+ final RyaDetails details = RyaDetails.builder().setRyaInstanceName("test_instance")
+ .setRyaVersion("1.2.3.4")
+ .setEntityCentricIndexDetails( new EntityCentricIndexDetails(true) )
+ .setGeoIndexDetails( new GeoIndexDetails(true) )
+ .setTemporalIndexDetails( new TemporalIndexDetails(true) )
+ .setFreeTextDetails( new FreeTextIndexDetails(true) )
+ .setPCJIndexDetails(
+ PCJIndexDetails.builder()
+ .setEnabled(true)
+ .setFluoDetails( new FluoDetails("test_instance_rya_pcj_updater") )
+ .addPCJDetails(
+ PCJDetails.builder()
+ .setId("pcj 1")
+ .setUpdateStrategy(PCJUpdateStrategy.BATCH)
+ .setLastUpdateTime( new Date(1252521351L) ))
+ .addPCJDetails(
+ PCJDetails.builder()
+ .setId("pcj 2")
+ .setUpdateStrategy(PCJUpdateStrategy.INCREMENTAL)))
+ .setProspectorDetails( new ProspectorDetails(Optional.of(new Date(12525211L))) )
+ .setJoinSelectivityDetails( new JoinSelectivityDetails(Optional.of(new Date(125221351L))) )
+ .build();
+
+ final String formatted = new RyaDetailsFormatter().format(details);
+
+ // Verify the created object matches the expected result.
+ final String expected =
+ "General Metadata:\n" +
+ " Instance Name: test_instance\n" +
+ " RYA Version: 1.2.3.4\n" +
+ "Secondary Indicies:\n" +
+ " Entity Centric Index:\n" +
+ " Enabled: true\n" +
+ " Geospatial Index:\n" +
+ " Enabled: true\n" +
+ " Free Text Index:\n" +
+ " Enabled: true\n" +
+ " Temporal Index:\n" +
+ " Enabled: true\n" +
+ " PCJ Index:\n" +
+ " Enabled: true\n" +
+ " Fluo App Name: test_instance_rya_pcj_updater\n" +
+ " PCJs:\n" +
+ " ID: pcj 1\n" +
+ " Update Strategy: BATCH\n" +
+ " Last Update Time: Thu Jan 15 06:55:21 EST 1970\n" +
+ " ID: pcj 2\n" +
+ " Update Strategy: INCREMENTAL\n" +
+ " Last Update Time: unavailable\n" +
+ "Statistics:\n" +
+ " Prospector:\n" +
+ " Last Update Time: Wed Dec 31 22:28:45 EST 1969\n" +
+ " Join Selectivity:\n" +
+ " Last Updated Time: Fri Jan 02 05:47:01 EST 1970\n";
+
+ assertEquals(expected, formatted);
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.console/src/test/resources/RyaShellTest-context.xml
----------------------------------------------------------------------
diff --git a/extras/rya.console/src/test/resources/RyaShellTest-context.xml b/extras/rya.console/src/test/resources/RyaShellTest-context.xml
new file mode 100644
index 0000000..dfd075a
--- /dev/null
+++ b/extras/rya.console/src/test/resources/RyaShellTest-context.xml
@@ -0,0 +1,52 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements. See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership. The ASF licenses this file
+ to you under the Apache License, Version 2.0 (the
+ "License"); you may not use this file except in compliance
+ with the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing,
+ software distributed under the License is distributed on an
+ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ KIND, either express or implied. See the License for the
+ specific language governing permissions and limitations
+ under the License.
+
+-->
+<beans xmlns="http://www.springframework.org/schema/beans"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns:context="http://www.springframework.org/schema/context"
+ xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
+ http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.1.xsd">
+
+ <!-- Tell Spring where it can find all of the Command components. -->
+ <context:component-scan base-package="mvm.rya.shell"/>
+
+ <!-- Define the shell state bean that will be shared across all of the commands. -->
+ <bean id="sharedShellState" class="mvm.rya.shell.SharedShellState" />
+
+ <!-- We use a mock Password Prompt here to simulate a user entering a password. -->
+ <bean id="passwordPrompt" class="org.mockito.Mockito" factory-method="mock">
+ <constructor-arg value="mvm.rya.shell.util.PasswordPrompt" />
+ </bean>
+
+ <!-- We use a mock Install Prompt here to simulate a user entering the installation configuration. -->
+ <bean id="installPrompt" class="org.mockito.Mockito" factory-method="mock">
+ <constructor-arg value="mvm.rya.shell.util.InstallPrompt"/>
+ </bean>
+
+ <!-- We use a mock SPARQL Prompt here to simulate a user entering the installation configuration. -->
+ <bean id="sparqlPrompt" class="org.mockito.Mockito" factory-method="mock">
+ <constructor-arg value="mvm.rya.shell.util.SparqlPrompt"/>
+ </bean>
+
+ <!-- Define each of the beans that hold onto commands used by the shell. -->
+ <bean id="ryaConnectionCommands" class="mvm.rya.shell.RyaConnectionCommands" />
+ <bean id="ryaAdminCommands" class="mvm.rya.shell.RyaAdminCommands" />
+</beans>
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.indexing.pcj/pom.xml
----------------------------------------------------------------------
diff --git a/extras/rya.indexing.pcj/pom.xml b/extras/rya.indexing.pcj/pom.xml
index ee5ae07..c90ded3 100644
--- a/extras/rya.indexing.pcj/pom.xml
+++ b/extras/rya.indexing.pcj/pom.xml
@@ -43,6 +43,10 @@ under the License.
<groupId>org.apache.rya</groupId>
<artifactId>rya.api</artifactId>
</dependency>
+ <dependency>
+ <groupId>org.apache.rya</groupId>
+ <artifactId>accumulo.rya</artifactId>
+ </dependency>
<!-- Accumulo support dependencies. -->
<dependency>
@@ -80,5 +84,11 @@ under the License.
<artifactId>rya.sail</artifactId>
<scope>test</scope>
</dependency>
+ <dependency>
+ <groupId>org.apache.rya</groupId>
+ <artifactId>accumulo.rya</artifactId>
+ <version>${project.version}</version>
+ <type>test-jar</type>
+ </dependency>
</dependencies>
</project>
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PCJIdFactory.java
----------------------------------------------------------------------
diff --git a/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PCJIdFactory.java b/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PCJIdFactory.java
new file mode 100644
index 0000000..0bba346
--- /dev/null
+++ b/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PCJIdFactory.java
@@ -0,0 +1,34 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.rya.indexing.pcj.storage;
+
+import java.util.UUID;
+
+/**
+ * Creates IDs for new Precomputed Joins.
+ */
+public class PCJIdFactory {
+
+ /**
+ * @return The next ID to use for a PCJ.
+ */
+ public String nextId() {
+ return UUID.randomUUID().toString().replaceAll("-", "");
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-rya/blob/fcc98bd9/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PrecomputedJoinStorage.java
----------------------------------------------------------------------
diff --git a/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PrecomputedJoinStorage.java b/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PrecomputedJoinStorage.java
index fb49b30..caaa8b6 100644
--- a/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PrecomputedJoinStorage.java
+++ b/extras/rya.indexing.pcj/src/main/java/org/apache/rya/indexing/pcj/storage/PrecomputedJoinStorage.java
@@ -19,13 +19,13 @@
package org.apache.rya.indexing.pcj.storage;
import java.util.Collection;
+import java.util.Iterator;
import java.util.List;
-import java.util.Set;
import javax.annotation.ParametersAreNonnullByDefault;
-import org.apache.rya.indexing.pcj.storage.accumulo.VariableOrder;
import org.apache.rya.indexing.pcj.storage.accumulo.VisibilityBindingSet;
+import org.openrdf.query.BindingSet;
/**
* Functions that create and maintain the PCJ tables that are used by Rya.
@@ -36,7 +36,7 @@ public interface PrecomputedJoinStorage {
/**
* Get a list of all Precomputed Join indices that are being maintained.
*
- * @return The lkist of managed Precomputed Join indices.
+ * @return The list of managed Precomputed Join IDs.
*/
public List<String> listPcjs() throws PCJStorageException;
@@ -47,7 +47,7 @@ public interface PrecomputedJoinStorage {
* @param varOrders - The variable orders the results within the table will be written to. (not null)
* @return A unique identifier for the index.
*/
- public String createPcj(final String sparql, final Set<VariableOrder> varOrders) throws PCJStorageException;
+ public String createPcj(final String sparql) throws PCJStorageException;
/**
* Get metadata about the Precomputed Join index.
@@ -67,6 +67,16 @@ public interface PrecomputedJoinStorage {
public void addResults(final String pcjId, final Collection<VisibilityBindingSet> results) throws PCJStorageException;
/**
+ * Get an {@link Iterator} over the {@link BindingSet}s that are stored in the PCJ table.
+ *
+ * @param pcjId - Identifies the index the results will be read from. (not null)
+ * @return An iterator over all of the {@link BindingSet}s that are stored as
+ * results for the PCJ.
+ * @throws PCJStorageException The scan couldn't be performed.
+ */
+ public Iterable<BindingSet> listResults(String pcjId) throws PCJStorageException;
+
+ /**
* Clears all values from a Precomputed Join index. The index will remain,
* but all of its values will be removed.
*