Skip to content

Commit

Permalink
Merge pull request #22387 from stuartwdouglas/22345
Browse files Browse the repository at this point in the history
Add ability to change included tags
  • Loading branch information
famod authored Jan 10, 2022
2 parents 6071b57 + ce63afb commit 7eae75b
Show file tree
Hide file tree
Showing 8 changed files with 271 additions and 10 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -225,10 +225,12 @@ public void run() {
if (delegateConnection != null) {
//console mode
//just sent the input to the delegate
for (var k : keys) {
if (k == 27) { // escape key
exitCliMode();
return;
if (keys.length == 1) {
for (var k : keys) {
if (k == 27) { // escape key
exitCliMode();
return;
}
}
}
if (delegateConnection.getStdinHandler() != null) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,10 @@ ConsoleInstalledBuildItem setupConsole(TestConfig config,
@Consume(ConsoleInstalledBuildItem.class)
@BuildStep
void setupExceptionHandler(BuildProducer<ExceptionNotificationBuildItem> exceptionNotificationBuildItem,
EffectiveIdeBuildItem ideSupport) {
EffectiveIdeBuildItem ideSupport, LaunchModeBuildItem launchModeBuildItem) {
if (launchModeBuildItem.isAuxiliaryApplication()) {
return;
}
final AtomicReference<StackTraceElement> lastUserCode = new AtomicReference<>();
exceptionNotificationBuildItem
.produce(new ExceptionNotificationBuildItem(new BiConsumer<Throwable, StackTraceElement>() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -244,6 +244,7 @@ void redraw() {
.collect(Collectors.toList());
if (sorted.isEmpty()) {
QuarkusConsole.INSTANCE.setPromptMessage(null);
oldPrompt = null;
} else {
StringBuilder sb = new StringBuilder("Press");
boolean first = true;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package io.quarkus.deployment.console;

import org.aesh.command.Command;
import org.aesh.command.CommandException;
import org.aesh.command.CommandResult;
import org.aesh.command.invocation.CommandInvocation;
import org.aesh.command.option.Option;

import io.quarkus.dev.console.QuarkusConsole;

public abstract class QuarkusCommand implements Command {

@Option(shortName = 'd', hasValue = false)
public boolean done;

@Override
public CommandResult execute(CommandInvocation commandInvocation) throws CommandException, InterruptedException {
var result = doExecute(commandInvocation);
if (done) {
QuarkusConsole.INSTANCE.exitCliMode();
}
return result;
}

public abstract CommandResult doExecute(CommandInvocation commandInvocation) throws CommandException, InterruptedException;
}
Original file line number Diff line number Diff line change
@@ -1,10 +1,26 @@
package io.quarkus.deployment.dev.testing;

import java.util.Collections;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.function.BiFunction;

import org.aesh.command.Command;
import org.aesh.command.CommandDefinition;
import org.aesh.command.CommandException;
import org.aesh.command.CommandResult;
import org.aesh.command.GroupCommandDefinition;
import org.aesh.command.invocation.CommandInvocation;
import org.aesh.command.option.Argument;
import org.aesh.command.option.Arguments;
import org.aesh.command.option.Option;
import org.jboss.jandex.AnnotationInstance;
import org.jboss.jandex.ClassInfo;
import org.jboss.jandex.DotName;
import org.junit.jupiter.api.Tag;
import org.objectweb.asm.ClassVisitor;
import org.objectweb.asm.MethodVisitor;
import org.objectweb.asm.Opcodes;
Expand All @@ -19,13 +35,18 @@
import io.quarkus.deployment.annotations.Produce;
import io.quarkus.deployment.builditem.BytecodeTransformerBuildItem;
import io.quarkus.deployment.builditem.CombinedIndexBuildItem;
import io.quarkus.deployment.builditem.ConsoleCommandBuildItem;
import io.quarkus.deployment.builditem.LaunchModeBuildItem;
import io.quarkus.deployment.builditem.LiveReloadBuildItem;
import io.quarkus.deployment.builditem.LogHandlerBuildItem;
import io.quarkus.deployment.builditem.ServiceStartBuildItem;
import io.quarkus.deployment.console.QuarkusCommand;
import io.quarkus.deployment.console.SetCompleter;
import io.quarkus.deployment.logging.LogCleanupFilterBuildItem;
import io.quarkus.dev.config.CurrentConfig;
import io.quarkus.dev.spi.DevModeType;
import io.quarkus.dev.testing.ContinuousTestingSharedStateManager;
import io.quarkus.dev.testing.KnownTags;
import io.quarkus.dev.testing.TracingHandler;
import io.quarkus.gizmo.Gizmo;

Expand Down Expand Up @@ -95,6 +116,7 @@ public void instrumentTestClasses(CombinedIndexBuildItem combinedIndexBuildItem,
if (!launchModeBuildItem.isAuxiliaryApplication()) {
return;
}

for (ClassInfo clazz : combinedIndexBuildItem.getIndex().getKnownClasses()) {
String theClassName = clazz.name().toString();
if (isAppClass(theClassName)) {
Expand All @@ -110,6 +132,22 @@ public ClassVisitor apply(String s, ClassVisitor classVisitor) {

}

@BuildStep(onlyIf = IsTest.class)
public ServiceStartBuildItem searchForTags(CombinedIndexBuildItem combinedIndexBuildItem,
LaunchModeBuildItem launchModeBuildItem) {
if (!launchModeBuildItem.isAuxiliaryApplication()) {
return null;
}

Set<String> ret = new HashSet<>();
for (AnnotationInstance clazz : combinedIndexBuildItem.getIndex()
.getAnnotations(DotName.createSimple(Tag.class.getName()))) {
ret.add(clazz.value().asString());
}
KnownTags.setKnownTags(ret);
return null;
}

public boolean isAppClass(String theClassName) {
QuarkusClassLoader cl = (QuarkusClassLoader) Thread.currentThread()
.getContextClassLoader();
Expand Down Expand Up @@ -146,4 +184,177 @@ public void visitCode() {
};
}
}

@BuildStep
ConsoleCommandBuildItem testConsoleCommand(CombinedIndexBuildItem indexBuildItem) {
return new ConsoleCommandBuildItem(new TestCommand());
}

@GroupCommandDefinition(name = "test", description = "Test Commands", groupCommands = { TagsCommand.class,
PatternCommand.class })
public static class TestCommand implements Command {

@Override
public CommandResult execute(CommandInvocation commandInvocation) throws CommandException, InterruptedException {
return CommandResult.SUCCESS;
}
}

@GroupCommandDefinition(name = "tags", description = "Tag Commands", groupCommands = { IncludeTagsCommand.class,
ExcludeTagsCommand.class })
public static class TagsCommand implements Command {

@Override
public CommandResult execute(CommandInvocation commandInvocation) throws CommandException, InterruptedException {
return CommandResult.SUCCESS;
}
}

@CommandDefinition(name = "include", description = "Sets the current included tags")
public static class IncludeTagsCommand extends TestSelectionCommand {

@Arguments(completer = TagCompleter.class)
private List<String> tags;

@Override
protected String configValue() {
if (tags == null) {
return "";
} else {
return String.join(",", tags);
}
}

@Override
protected String configKey() {
return "quarkus.test.include-tags";
}

@Override
protected void configure(TestSupport testSupport) {
testSupport.setTags(tags == null ? List.of() : tags, testSupport.excludeTags);
}
}

@CommandDefinition(name = "exclude", description = "Sets the current excluded tags")
public static class ExcludeTagsCommand extends TestSelectionCommand {

@Arguments(completer = TagCompleter.class)
private List<String> tags;

@Override
protected String configValue() {
if (tags == null) {
return "";
} else {
return String.join(",", tags);
}
}

@Override
protected String configKey() {
return "quarkus.test.exclude-tags";
}

@Override
protected void configure(TestSupport testSupport) {
testSupport.setTags(testSupport.includeTags, tags == null ? List.of() : tags);
}
}

@GroupCommandDefinition(name = "pattern", description = "Include/Exclude pattern Commands", groupCommands = {
IncludePatternCommand.class,
ExcludePatternCommand.class })
public static class PatternCommand implements Command {

@Override
public CommandResult execute(CommandInvocation commandInvocation) throws CommandException, InterruptedException {
return CommandResult.SUCCESS;
}
}

@CommandDefinition(name = "include", description = "Sets the current include pattern")
public static class IncludePatternCommand extends TestSelectionCommand {

@Argument
private String pattern;

@Override
protected String configValue() {
return Objects.requireNonNullElse(pattern, "");
}

@Override
protected String configKey() {
return "quarkus.test.include-pattern";
}

@Override
protected void configure(TestSupport testSupport) {
testSupport.setPatterns(pattern, testSupport.exclude.pattern());
}
}

@CommandDefinition(name = "exclude", description = "Sets the current excluded tags")
public static class ExcludePatternCommand extends TestSelectionCommand {

@Argument(completer = TagCompleter.class)
private String pattern;

@Override
protected String configValue() {
return Objects.requireNonNullElse(pattern, "");
}

@Override
protected String configKey() {
return "quarkus.test.exclude-pattern";
}

@Override
protected void configure(TestSupport testSupport) {
testSupport.setPatterns(testSupport.include.pattern(), pattern);
}
}

static abstract class TestSelectionCommand extends QuarkusCommand {

@Option(shortName = 'p', hasValue = false)
protected boolean persistent;

@Option(shortName = 'r', hasValue = false)
protected boolean run;

protected abstract String configValue();

protected abstract String configKey();

@Override
public final CommandResult doExecute(CommandInvocation commandInvocation)
throws CommandException, InterruptedException {
TestSupport testSupport = TestSupport.instance().get();
configure(testSupport);
if (persistent) {
CurrentConfig.EDITOR.accept(Map.of(configKey(), configValue()));
}
if (run) {
if (!testSupport.isStarted()) {
testSupport.start();
}
testSupport.runAllTests();
}
return CommandResult.SUCCESS;
}

protected abstract void configure(TestSupport testSupport);
}

public static class TagCompleter extends SetCompleter {

@Override
protected Set<String> allOptions(String soFar) {
return KnownTags.getKnownTags();
}
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@
import io.quarkus.deployment.builditem.nativeimage.RuntimeInitializedClassBuildItem;
import io.quarkus.deployment.builditem.nativeimage.ServiceProviderBuildItem;
import io.quarkus.deployment.console.ConsoleInstalledBuildItem;
import io.quarkus.deployment.console.QuarkusCommand;
import io.quarkus.deployment.console.SetCompleter;
import io.quarkus.deployment.dev.ExceptionNotificationBuildItem;
import io.quarkus.deployment.dev.testing.MessageFormat;
Expand Down Expand Up @@ -536,7 +537,7 @@ public CommandResult execute(CommandInvocation commandInvocation) throws Command
}

@CommandDefinition(name = "set-level", description = "Sets the log level for a logger")
public static class SetLogLevelCommand implements Command {
public static class SetLogLevelCommand extends QuarkusCommand {

@Option(required = true, completer = LoggerCompleter.class)
private String logger;
Expand All @@ -545,7 +546,7 @@ public static class SetLogLevelCommand implements Command {
private String level;

@Override
public CommandResult execute(CommandInvocation commandInvocation) throws CommandException, InterruptedException {
public CommandResult doExecute(CommandInvocation commandInvocation) throws CommandException, InterruptedException {
java.util.logging.Logger logger = LogManager.getLogManager().getLogger(this.logger);
Level level = org.jboss.logmanager.Level.parse(this.level);
logger.setLevel(level);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package io.quarkus.dev.testing;

import java.util.Collections;
import java.util.Set;

public class KnownTags {

private static volatile Set<String> knownTags = Set.of();

public static Set<String> getKnownTags() {
return knownTags;
}

public static void setKnownTags(Set<String> knownTag) {
knownTags = Collections.unmodifiableSet(knownTag);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
import java.util.Set;
import java.util.stream.Collectors;

import org.aesh.command.Command;
import org.aesh.command.CommandDefinition;
import org.aesh.command.CommandException;
import org.aesh.command.CommandResult;
Expand All @@ -29,6 +28,7 @@
import io.quarkus.deployment.annotations.Record;
import io.quarkus.deployment.builditem.ApplicationArchivesBuildItem;
import io.quarkus.deployment.builditem.ConsoleCommandBuildItem;
import io.quarkus.deployment.console.QuarkusCommand;
import io.quarkus.resteasy.reactive.server.runtime.ExceptionMapperRecorder;
import io.quarkus.resteasy.reactive.server.runtime.NotFoundExceptionMapper;
import io.quarkus.resteasy.reactive.spi.CustomExceptionMapperBuildItem;
Expand Down Expand Up @@ -128,7 +128,7 @@ ConsoleCommandBuildItem openCommand(HttpRootPathBuildItem rp, NonApplicationRoot
}

@CommandDefinition(name = "open", description = "Opens a path in a web browser")
public static class OpenCommand implements Command {
public static class OpenCommand extends QuarkusCommand {

@Argument(required = true, completer = PathCompleter.class)
private String url;
Expand All @@ -146,7 +146,7 @@ public OpenCommand(HttpRootPathBuildItem rp, NonApplicationRootPathBuildItem np,
}

@Override
public CommandResult execute(CommandInvocation commandInvocation) throws CommandException, InterruptedException {
public CommandResult doExecute(CommandInvocation commandInvocation) throws CommandException, InterruptedException {
DevConsoleProcessor.openBrowser(rp, np, url.startsWith("/") ? url : "/" + url, host, port);
return CommandResult.SUCCESS;
}
Expand Down

0 comments on commit 7eae75b

Please sign in to comment.