Separate interactive and non-interactive commands
- Add new ShellContext concept which now is just a way to stash info about interaction mode where ShellRunner can update supported mode. - ShellMethod has a new field interactionMode which user can use to define commands between interactive/non-interactive modes which then prevents CommandRegistry to show commands at runtime. - Fixes #345
This commit is contained in:
@@ -21,14 +21,16 @@ import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.shell.CommandRegistry;
|
||||
import org.springframework.shell.ConfigurableCommandRegistry;
|
||||
import org.springframework.shell.MethodTargetRegistrar;
|
||||
import org.springframework.shell.context.ShellContext;
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
public class CommandRegistryAutoConfiguration {
|
||||
|
||||
@Bean
|
||||
public CommandRegistry commandRegistry(
|
||||
ObjectProvider<MethodTargetRegistrar> methodTargetRegistrars) {
|
||||
ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry();
|
||||
ObjectProvider<MethodTargetRegistrar> methodTargetRegistrars,
|
||||
ShellContext shellContext) {
|
||||
ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry(shellContext);
|
||||
methodTargetRegistrars.orderedStream().forEach(resolver -> {
|
||||
resolver.register(registry);
|
||||
});
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
package org.springframework.shell.boot;
|
||||
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.shell.context.DefaultShellContext;
|
||||
import org.springframework.shell.context.ShellContext;
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
public class ShellContextAutoConfiguration {
|
||||
|
||||
@Bean
|
||||
public ShellContext shellContext() {
|
||||
return new DefaultShellContext();
|
||||
}
|
||||
}
|
||||
@@ -22,6 +22,7 @@ import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.shell.Shell;
|
||||
import org.springframework.shell.context.ShellContext;
|
||||
import org.springframework.shell.jline.InteractiveShellRunner;
|
||||
import org.springframework.shell.jline.NonInteractiveShellRunner;
|
||||
import org.springframework.shell.jline.PromptProvider;
|
||||
@@ -34,24 +35,27 @@ public class ShellRunnerAutoConfiguration {
|
||||
private PromptProvider promptProvider;
|
||||
private LineReader lineReader;
|
||||
private Parser parser;
|
||||
private ShellContext shellContext;
|
||||
|
||||
public ShellRunnerAutoConfiguration(Shell shell, PromptProvider promptProvider, LineReader lineReader, Parser parser) {
|
||||
public ShellRunnerAutoConfiguration(Shell shell, PromptProvider promptProvider, LineReader lineReader,
|
||||
Parser parser, ShellContext shellContext) {
|
||||
this.shell = shell;
|
||||
this.promptProvider = promptProvider;
|
||||
this.lineReader = lineReader;
|
||||
this.parser = parser;
|
||||
this.shellContext = shellContext;
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnProperty(prefix = "spring.shell.interactive", value = "enabled", havingValue = "true", matchIfMissing = true)
|
||||
public InteractiveShellRunner interactiveApplicationRunner() {
|
||||
return new InteractiveShellRunner(lineReader, promptProvider, shell);
|
||||
return new InteractiveShellRunner(lineReader, promptProvider, shell, shellContext);
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnProperty(prefix = "spring.shell.noninteractive", value = "enabled", havingValue = "true", matchIfMissing = true)
|
||||
public NonInteractiveShellRunner nonInteractiveApplicationRunner() {
|
||||
return new NonInteractiveShellRunner(shell);
|
||||
return new NonInteractiveShellRunner(shell, shellContext);
|
||||
}
|
||||
|
||||
@Bean
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
|
||||
org.springframework.shell.boot.ShellContextAutoConfiguration,\
|
||||
org.springframework.shell.boot.SpringShellAutoConfiguration,\
|
||||
org.springframework.shell.boot.ShellRunnerAutoConfiguration,\
|
||||
org.springframework.shell.boot.ApplicationRunnerAutoConfiguration,\
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017 the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,12 +13,14 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.shell;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.TreeMap;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
import org.springframework.shell.context.ShellContext;
|
||||
|
||||
/**
|
||||
* A {@link CommandRegistry} that supports registration of new commands.
|
||||
@@ -29,11 +31,31 @@ import java.util.TreeMap;
|
||||
*/
|
||||
public class ConfigurableCommandRegistry implements CommandRegistry {
|
||||
|
||||
private final ShellContext shellContext;
|
||||
private Map<String, MethodTarget> commands = new HashMap<>();
|
||||
|
||||
public ConfigurableCommandRegistry(ShellContext shellContext) {
|
||||
this.shellContext = shellContext;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, MethodTarget> listCommands() {
|
||||
return new TreeMap<>(commands);
|
||||
return commands.entrySet().stream()
|
||||
.filter(e -> {
|
||||
InteractionMode mim = e.getValue().getInteractionMode();
|
||||
InteractionMode cim = shellContext.getInteractionMode();
|
||||
if (mim == null || cim == null || mim == InteractionMode.ALL) {
|
||||
return true;
|
||||
}
|
||||
else if (mim == InteractionMode.INTERACTIVE) {
|
||||
return cim == InteractionMode.INTERACTIVE || cim == InteractionMode.ALL;
|
||||
}
|
||||
else if (mim == InteractionMode.NONINTERACTIVE) {
|
||||
return cim == InteractionMode.NONINTERACTIVE || cim == InteractionMode.ALL;
|
||||
}
|
||||
return true;
|
||||
})
|
||||
.collect(Collectors.toMap(e -> e.getKey(), e -> e.getValue()));
|
||||
}
|
||||
|
||||
public void register(String name, MethodTarget target) {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2015 the original author or authors.
|
||||
* Copyright 2015-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,7 +13,6 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.shell;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
@@ -21,6 +20,7 @@ import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
import org.springframework.util.Assert;
|
||||
import org.springframework.util.ReflectionUtils;
|
||||
|
||||
@@ -37,6 +37,8 @@ public class MethodTarget implements Command {
|
||||
|
||||
private final Help help;
|
||||
|
||||
private final InteractionMode interactionMode;
|
||||
|
||||
/**
|
||||
* If not null, returns whether or not the command is currently available. Implementations must be idempotent.
|
||||
*/
|
||||
@@ -51,6 +53,10 @@ public class MethodTarget implements Command {
|
||||
}
|
||||
|
||||
public MethodTarget(Method method, Object bean, Help help, Supplier<Availability> availabilityIndicator) {
|
||||
this(method, bean, help, availabilityIndicator, null);
|
||||
}
|
||||
|
||||
public MethodTarget(Method method, Object bean, Help help, Supplier<Availability> availabilityIndicator, InteractionMode interactionMode) {
|
||||
Assert.notNull(method, "Method cannot be null");
|
||||
Assert.notNull(bean, "Bean cannot be null");
|
||||
Assert.hasText(help.getDescription(), String.format("Help cannot be blank when trying to define command based on '%s'", method));
|
||||
@@ -59,6 +65,7 @@ public class MethodTarget implements Command {
|
||||
this.bean = bean;
|
||||
this.help = help;
|
||||
this.availabilityIndicator = availabilityIndicator != null ? availabilityIndicator : () -> Availability.available();
|
||||
this.interactionMode = interactionMode;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -103,6 +110,10 @@ public class MethodTarget implements Command {
|
||||
return availabilityIndicator.get();
|
||||
}
|
||||
|
||||
public InteractionMode getInteractionMode() {
|
||||
return interactionMode;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
* Copyright 2022 the original author or authors.
|
||||
*
|
||||
* Licensed 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
|
||||
*
|
||||
* https://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.springframework.shell.context;
|
||||
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* Default implementation of a {@link ShellContext}.
|
||||
*
|
||||
* @author Janne Valkealahti
|
||||
*/
|
||||
public class DefaultShellContext implements ShellContext {
|
||||
|
||||
private InteractionMode interactionMode = InteractionMode.ALL;
|
||||
|
||||
@Override
|
||||
public InteractionMode getInteractionMode() {
|
||||
return interactionMode;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setInteractionMode(InteractionMode interactionMode) {
|
||||
Assert.notNull(interactionMode, "mode cannot be null");
|
||||
this.interactionMode = interactionMode;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
* Copyright 2022 the original author or authors.
|
||||
*
|
||||
* Licensed 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
|
||||
*
|
||||
* https://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.springframework.shell.context;
|
||||
|
||||
/**
|
||||
* Enumeration for modes shell is operating.
|
||||
*
|
||||
* @author Janne Valkealahti
|
||||
*/
|
||||
public enum InteractionMode {
|
||||
|
||||
/**
|
||||
* All possible modes.
|
||||
*/
|
||||
ALL,
|
||||
|
||||
/**
|
||||
* Non-interactive mode which is expected to exit and doesn't have any kind of
|
||||
* running mode to keep shell alive.
|
||||
*/
|
||||
NONINTERACTIVE,
|
||||
|
||||
/**
|
||||
* Interactive mode which is expected to not exit and do have a running mode to
|
||||
* keep shell alive.
|
||||
*/
|
||||
INTERACTIVE
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
* Copyright 2022 the original author or authors.
|
||||
*
|
||||
* Licensed 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
|
||||
*
|
||||
* https://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.springframework.shell.context;
|
||||
|
||||
/**
|
||||
* Interface defining a contract for a context which allows to loosely connect
|
||||
* different components together and keep things alive between commands.
|
||||
*
|
||||
* @author Janne Valkealahti
|
||||
*/
|
||||
public interface ShellContext {
|
||||
|
||||
/**
|
||||
* Gets an interaction mode.
|
||||
*
|
||||
* @return a current interaction mode
|
||||
*/
|
||||
InteractionMode getInteractionMode();
|
||||
|
||||
/**
|
||||
* Sets an interaction mode.
|
||||
*
|
||||
* @param interactionMode the interaction mode
|
||||
*/
|
||||
void setInteractionMode(InteractionMode interactionMode);
|
||||
}
|
||||
@@ -27,6 +27,8 @@ import org.springframework.shell.Input;
|
||||
import org.springframework.shell.InputProvider;
|
||||
import org.springframework.shell.Shell;
|
||||
import org.springframework.shell.ShellRunner;
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
import org.springframework.shell.context.ShellContext;
|
||||
|
||||
/**
|
||||
* Default Boot runner that bootstraps the shell application in interactive
|
||||
@@ -52,14 +54,19 @@ public class InteractiveShellRunner implements ShellRunner {
|
||||
|
||||
private final Shell shell;
|
||||
|
||||
public InteractiveShellRunner(LineReader lineReader, PromptProvider promptProvider, Shell shell) {
|
||||
private final ShellContext shellContext;
|
||||
|
||||
public InteractiveShellRunner(LineReader lineReader, PromptProvider promptProvider, Shell shell,
|
||||
ShellContext shellContext) {
|
||||
this.lineReader = lineReader;
|
||||
this.promptProvider = promptProvider;
|
||||
this.shell = shell;
|
||||
this.shellContext = shellContext;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run(ApplicationArguments args) throws Exception {
|
||||
shellContext.setInteractionMode(InteractionMode.INTERACTIVE);
|
||||
InputProvider inputProvider = new JLineInputProvider(lineReader, promptProvider);
|
||||
shell.run(inputProvider);
|
||||
}
|
||||
|
||||
@@ -24,6 +24,8 @@ import org.springframework.shell.Input;
|
||||
import org.springframework.shell.InputProvider;
|
||||
import org.springframework.shell.Shell;
|
||||
import org.springframework.shell.ShellRunner;
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
import org.springframework.shell.context.ShellContext;
|
||||
import org.springframework.util.ObjectUtils;
|
||||
import org.springframework.util.StringUtils;
|
||||
|
||||
@@ -37,9 +39,11 @@ import org.springframework.util.StringUtils;
|
||||
public class NonInteractiveShellRunner implements ShellRunner {
|
||||
|
||||
private final Shell shell;
|
||||
private final ShellContext shellContext;
|
||||
|
||||
public NonInteractiveShellRunner(Shell shell) {
|
||||
public NonInteractiveShellRunner(Shell shell, ShellContext shellContext) {
|
||||
this.shell = shell;
|
||||
this.shellContext = shellContext;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -50,6 +54,7 @@ public class NonInteractiveShellRunner implements ShellRunner {
|
||||
|
||||
@Override
|
||||
public void run(ApplicationArguments args) throws Exception {
|
||||
shellContext.setInteractionMode(InteractionMode.NONINTERACTIVE);
|
||||
List<String> argsToShellCommand = Arrays.asList(args.getSourceArgs());
|
||||
InputProvider inputProvider = new StringInputProvider(argsToShellCommand);
|
||||
shell.run(inputProvider);
|
||||
|
||||
@@ -18,6 +18,8 @@ package org.springframework.shell;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.shell.context.DefaultShellContext;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.assertj.core.api.Assertions.assertThatThrownBy;
|
||||
|
||||
@@ -30,14 +32,14 @@ public class ConfigurableCommandRegistryTest {
|
||||
|
||||
@Test
|
||||
public void testRegistration() {
|
||||
ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry();
|
||||
ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry(new DefaultShellContext());
|
||||
registry.register("foo", MethodTarget.of("toString", this, new Command.Help("some command")));
|
||||
assertThat(registry.listCommands()).containsKeys("foo");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testDoubleRegistration() {
|
||||
ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry();
|
||||
ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry(new DefaultShellContext());
|
||||
registry.register("foo", MethodTarget.of("toString", this, new Command.Help("some command")));
|
||||
|
||||
assertThatThrownBy(() -> {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-2021 the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -18,6 +18,7 @@ package org.springframework.shell.standard.commands;
|
||||
|
||||
import org.jline.utils.InfoCmp;
|
||||
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
import org.springframework.shell.standard.AbstractShellComponent;
|
||||
import org.springframework.shell.standard.ShellComponent;
|
||||
import org.springframework.shell.standard.ShellMethod;
|
||||
@@ -47,7 +48,7 @@ public class Clear extends AbstractShellComponent {
|
||||
public Clear() {
|
||||
}
|
||||
|
||||
@ShellMethod("Clear the shell screen.")
|
||||
@ShellMethod(value = "Clear the shell screen.", interactionMode = InteractionMode.INTERACTIVE)
|
||||
public void clear() {
|
||||
getTerminal().puts(InfoCmp.Capability.clear_screen);
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017 the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -17,6 +17,7 @@
|
||||
package org.springframework.shell.standard.commands;
|
||||
|
||||
import org.springframework.shell.ExitRequest;
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
import org.springframework.shell.standard.ShellComponent;
|
||||
import org.springframework.shell.standard.ShellMethod;
|
||||
|
||||
@@ -41,7 +42,7 @@ public class Quit {
|
||||
*/
|
||||
public interface Command {}
|
||||
|
||||
@ShellMethod(value = "Exit the shell.", key = {"quit", "exit"})
|
||||
@ShellMethod(value = "Exit the shell.", key = {"quit", "exit"}, interactionMode = InteractionMode.INTERACTIVE)
|
||||
public void quit() {
|
||||
throw new ExitRequest();
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-2021 the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,6 +16,7 @@
|
||||
package org.springframework.shell.standard.commands;
|
||||
|
||||
import org.springframework.beans.factory.ObjectProvider;
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
import org.springframework.shell.result.ThrowableResultHandler;
|
||||
import org.springframework.shell.standard.AbstractShellComponent;
|
||||
import org.springframework.shell.standard.ShellComponent;
|
||||
@@ -49,7 +50,9 @@ public class Stacktrace extends AbstractShellComponent {
|
||||
this.throwableResultHandler = throwableResultHandler;
|
||||
}
|
||||
|
||||
@ShellMethod(key = ThrowableResultHandler.DETAILS_COMMAND_NAME, value = "Display the full stacktrace of the last error.")
|
||||
@ShellMethod(key = ThrowableResultHandler.DETAILS_COMMAND_NAME,
|
||||
value = "Display the full stacktrace of the last error.",
|
||||
interactionMode = InteractionMode.INTERACTIVE)
|
||||
public void stacktrace() {
|
||||
if (throwableResultHandler.getIfAvailable().getLastError() != null) {
|
||||
throwableResultHandler.getIfAvailable().getLastError().printStackTrace(getTerminal().writer());
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2015 the original author or authors.
|
||||
* Copyright 2015-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,7 +13,6 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.shell.standard;
|
||||
|
||||
import java.lang.annotation.Documented;
|
||||
@@ -22,6 +21,8 @@ import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
|
||||
/**
|
||||
* Used to mark a method as invokable via Spring Shell.
|
||||
*
|
||||
@@ -68,4 +69,14 @@ public @interface ShellMethod {
|
||||
*/
|
||||
String group() default INHERITED;
|
||||
|
||||
/**
|
||||
* Defines interaction mode for a command as a hint when command should be
|
||||
* available. For example presense of some commands doesn't make sense if shell
|
||||
* is running as non-interactive mode and vice versa.
|
||||
*
|
||||
* Defaults to {@link InteractionMode#ALL}
|
||||
*
|
||||
* @return interaction mode
|
||||
*/
|
||||
InteractionMode interactionMode() default InteractionMode.ALL;
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2015-2017 the original author or authors.
|
||||
* Copyright 2015-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -13,7 +13,6 @@
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.shell.standard;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
@@ -76,7 +75,8 @@ public class StandardMethodTargetRegistrar implements MethodTargetRegistrar, App
|
||||
String group = getOrInferGroup(method);
|
||||
for (String key : keys) {
|
||||
Supplier<Availability> availabilityIndicator = findAvailabilityIndicator(keys, bean, method);
|
||||
MethodTarget target = new MethodTarget(method, bean, new Command.Help(shellMapping.value(), group), availabilityIndicator);
|
||||
MethodTarget target = new MethodTarget(method, bean, new Command.Help(shellMapping.value(), group),
|
||||
availabilityIndicator, shellMapping.interactionMode());
|
||||
registry.register(key, target);
|
||||
commands.put(key, target);
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017 the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -26,6 +26,8 @@ import org.springframework.context.annotation.AnnotationConfigApplicationContext
|
||||
import org.springframework.shell.Availability;
|
||||
import org.springframework.shell.ConfigurableCommandRegistry;
|
||||
import org.springframework.shell.MethodTarget;
|
||||
import org.springframework.shell.context.DefaultShellContext;
|
||||
import org.springframework.shell.context.InteractionMode;
|
||||
import org.springframework.shell.standard.test1.GroupOneCommands;
|
||||
import org.springframework.shell.standard.test2.GroupThreeCommands;
|
||||
import org.springframework.shell.standard.test2.GroupTwoCommands;
|
||||
@@ -42,7 +44,7 @@ import static org.assertj.core.api.Assertions.assertThatThrownBy;
|
||||
public class StandardMethodTargetRegistrarTest {
|
||||
|
||||
private StandardMethodTargetRegistrar registrar = new StandardMethodTargetRegistrar();
|
||||
private ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry();
|
||||
private ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry(new DefaultShellContext());
|
||||
|
||||
@Test
|
||||
public void testRegistrations() {
|
||||
@@ -256,4 +258,47 @@ public class StandardMethodTargetRegistrarTest {
|
||||
Assertions.assertThat(commands.get("implicit3").getGroup()).isEqualTo("Explicit Group 3 Class Level");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInteractionModeInteractive() {
|
||||
DefaultShellContext shellContext = new DefaultShellContext();
|
||||
shellContext.setInteractionMode(InteractionMode.INTERACTIVE);
|
||||
registry = new ConfigurableCommandRegistry(shellContext);
|
||||
ApplicationContext applicationContext = new AnnotationConfigApplicationContext(InteractionModeCommands.class);
|
||||
registrar.setApplicationContext(applicationContext);
|
||||
registrar.register(registry);
|
||||
|
||||
assertThat(registry.listCommands().get("foo1")).isNotNull();
|
||||
assertThat(registry.listCommands().get("foo2")).isNull();
|
||||
assertThat(registry.listCommands().get("foo3")).isNotNull();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInteractionModeNonInteractive() {
|
||||
DefaultShellContext shellContext = new DefaultShellContext();
|
||||
shellContext.setInteractionMode(InteractionMode.NONINTERACTIVE);
|
||||
registry = new ConfigurableCommandRegistry(shellContext);
|
||||
ApplicationContext applicationContext = new AnnotationConfigApplicationContext(InteractionModeCommands.class);
|
||||
registrar.setApplicationContext(applicationContext);
|
||||
registrar.register(registry);
|
||||
|
||||
assertThat(registry.listCommands().get("foo1")).isNull();
|
||||
assertThat(registry.listCommands().get("foo2")).isNotNull();
|
||||
assertThat(registry.listCommands().get("foo3")).isNotNull();
|
||||
}
|
||||
|
||||
@ShellComponent
|
||||
public static class InteractionModeCommands {
|
||||
|
||||
@ShellMethod(value = "foo1", interactionMode = InteractionMode.INTERACTIVE)
|
||||
public void foo1() {
|
||||
}
|
||||
|
||||
@ShellMethod(value = "foo2", interactionMode = InteractionMode.NONINTERACTIVE)
|
||||
public void foo2() {
|
||||
}
|
||||
|
||||
@ShellMethod(value = "foo3")
|
||||
public void foo3() {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,6 +29,7 @@ import org.springframework.shell.CommandRegistry;
|
||||
import org.springframework.shell.ConfigurableCommandRegistry;
|
||||
import org.springframework.shell.MethodTarget;
|
||||
import org.springframework.shell.ParameterResolver;
|
||||
import org.springframework.shell.context.DefaultShellContext;
|
||||
import org.springframework.shell.standard.ShellMethod;
|
||||
import org.springframework.shell.standard.ShellOption;
|
||||
import org.springframework.shell.standard.StandardParameterResolver;
|
||||
@@ -42,7 +43,7 @@ public class AbstractCompletionsTests {
|
||||
@Test
|
||||
public void testBasicModelGeneration() {
|
||||
DefaultResourceLoader resourceLoader = new DefaultResourceLoader();
|
||||
ConfigurableCommandRegistry commandRegistry = new ConfigurableCommandRegistry();
|
||||
ConfigurableCommandRegistry commandRegistry = new ConfigurableCommandRegistry(new DefaultShellContext());
|
||||
List<ParameterResolver> parameterResolvers = new ArrayList<>();
|
||||
StandardParameterResolver resolver = new StandardParameterResolver(new DefaultConversionService(),
|
||||
Collections.emptySet());
|
||||
@@ -91,7 +92,7 @@ public class AbstractCompletionsTests {
|
||||
@Test
|
||||
public void testBuilder() {
|
||||
DefaultResourceLoader resourceLoader = new DefaultResourceLoader();
|
||||
ConfigurableCommandRegistry commandRegistry = new ConfigurableCommandRegistry();
|
||||
ConfigurableCommandRegistry commandRegistry = new ConfigurableCommandRegistry(new DefaultShellContext());
|
||||
List<ParameterResolver> parameterResolvers = new ArrayList<>();
|
||||
TestCompletions completions = new TestCompletions(resourceLoader, commandRegistry, parameterResolvers);
|
||||
|
||||
|
||||
@@ -25,6 +25,7 @@ import org.junit.jupiter.api.Test;
|
||||
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
|
||||
import org.springframework.shell.ConfigurableCommandRegistry;
|
||||
import org.springframework.shell.ParameterResolver;
|
||||
import org.springframework.shell.context.DefaultShellContext;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
@@ -48,7 +49,7 @@ public class BashCompletionsTests {
|
||||
|
||||
@Test
|
||||
public void testDoesNotError() {
|
||||
ConfigurableCommandRegistry commandRegistry = new ConfigurableCommandRegistry();
|
||||
ConfigurableCommandRegistry commandRegistry = new ConfigurableCommandRegistry(new DefaultShellContext());
|
||||
List<ParameterResolver> parameterResolvers = new ArrayList<>();
|
||||
BashCompletions completions = new BashCompletions(context, commandRegistry, parameterResolvers);
|
||||
String bash = completions.generate("root-command");
|
||||
|
||||
@@ -12,6 +12,7 @@ import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.shell.ConfigurableCommandRegistry;
|
||||
import org.springframework.shell.MethodTarget;
|
||||
import org.springframework.shell.context.DefaultShellContext;
|
||||
import org.springframework.shell.standard.StandardMethodTargetRegistrar;
|
||||
import org.springframework.test.context.ContextConfiguration;
|
||||
import org.springframework.test.context.junit.jupiter.SpringExtension;
|
||||
@@ -32,7 +33,7 @@ public class CalculatorCommandsTest extends BaseCalculatorTest {
|
||||
|
||||
private static final Class<CalculatorCommands> COMMAND_CLASS_UNDER_TEST = CalculatorCommands.class;
|
||||
|
||||
private final ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry();
|
||||
private final ConfigurableCommandRegistry registry = new ConfigurableCommandRegistry(new DefaultShellContext());
|
||||
|
||||
@Autowired
|
||||
private CalculatorState state;
|
||||
|
||||
Reference in New Issue
Block a user