Skip to content

Commit

Permalink
Added Master CommandRegistry
Browse files Browse the repository at this point in the history
  • Loading branch information
mattirn committed Jan 10, 2020
1 parent 55c1624 commit 57c9a61
Show file tree
Hide file tree
Showing 6 changed files with 197 additions and 98 deletions.
12 changes: 11 additions & 1 deletion builtins/src/main/java/org/jline/builtins/CommandRegistry.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2002-2019, the original author or authors.
* Copyright (c) 2002-2020, the original author or authors.
*
* This software is distributable under the BSD license. See the terms of the
* BSD license in the documentation provided with this software.
Expand All @@ -17,6 +17,8 @@
import java.util.Set;

public interface CommandRegistry {

enum Type {BASE, CONSOLE, SYSTEM}

/**
* Aggregate SystemCompleters of commandRegisteries
Expand Down Expand Up @@ -81,6 +83,14 @@ static Completers.SystemCompleter compileCompleters(CommandRegistry ... commandR
*/
Widgets.CmdDesc commandDescription(String command);

default Type getType() {
return Type.BASE;
}

default void setMasterRegistry(CommandRegistry masterRegistry) {
throw new IllegalAccessError("Not implemented!");
}

default Object execute(String command, String[] args) throws Exception {
throw new IllegalAccessError("Not implemented!");
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,11 @@
/*
* Copyright (c) 2002-2020, the original author or authors.
*
* This software is distributable under the BSD license. See the terms of the
* BSD license in the documentation provided with this software.
*
* https://opensource.org/licenses/BSD-3-Clause
*/
package org.jline.builtins;

import java.io.File;
Expand All @@ -23,7 +31,12 @@
import org.jline.utils.AttributedStringBuilder;
import org.jline.utils.AttributedStyle;

public class ConsoleCommands implements CommandRegistry {
/**
* Console commands and script execution.
*
* @author <a href="mailto:matti.rintanikkola@gmail.com">Matti Rinta-Nikkola</a>
*/
public class ConsoleEngine implements CommandRegistry {
public enum Command {SHOW
, DEL
, ENGINES};
Expand All @@ -38,7 +51,7 @@ public enum Command {SHOW
private String scriptExtension = "jline";
private Parser parser;

public ConsoleCommands(ScriptEngine engine, Parser parser) {
public ConsoleEngine(ScriptEngine engine, Parser parser) {
this.engine = engine;
this.parser = parser;
Set<Command> cmds = new HashSet<>(EnumSet.allOf(Command.class));
Expand All @@ -51,11 +64,19 @@ public ConsoleCommands(ScriptEngine engine, Parser parser) {
commandExecute.put(Command.SHOW, new CommandMethods(this::show, this::defaultCompleter));
}

@Override
public CommandRegistry.Type getType() {
return CommandRegistry.Type.CONSOLE;
}

public void setMasterRegistry(CommandRegistry masterRegistry) {
if (masterRegistry.getType() != CommandRegistry.Type.SYSTEM) {
throw new IllegalArgumentException();
}
this.masterRegistry = masterRegistry;
}

public ConsoleCommands scriptExtension(String extension) {
public ConsoleEngine scriptExtension(String extension) {
this.scriptExtension = extension;
return this;
}
Expand Down Expand Up @@ -115,7 +136,7 @@ public void alias(String alias, String command) {
}

public List<String> commandInfo(String command) {
return null;
return new ArrayList<>();
}

public Completers.SystemCompleter compileCompleters() {
Expand Down
134 changes: 134 additions & 0 deletions builtins/src/main/java/org/jline/builtins/Master.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
/*
* Copyright (c) 2002-2020, the original author or authors.
*
* This software is distributable under the BSD license. See the terms of the
* BSD license in the documentation provided with this software.
*
* https://opensource.org/licenses/BSD-3-Clause
*/
package org.jline.builtins;

import java.util.*;

import org.jline.builtins.CommandRegistry;
import org.jline.builtins.Widgets;
import org.jline.reader.ParsedLine;
import org.jline.reader.Parser;
import org.jline.utils.AttributedStringBuilder;

/**
* Aggregate command registeries.
*
* @author <a href="mailto:matti.rintanikkola@gmail.com">Matti Rinta-Nikkola</a>
*/
public class Master {
public static class Registry implements CommandRegistry {
private final CommandRegistry[] commandRegistries;
private Integer consoleId = null;

public Registry(CommandRegistry... commandRegistries) {
this.commandRegistries = commandRegistries;
for (int i = 0; i < commandRegistries.length; i++) {
if (commandRegistries[i].getType() == CommandRegistry.Type.CONSOLE) {
if (consoleId != null) {
throw new IllegalArgumentException();
} else {
this.consoleId = i;
commandRegistries[i].setMasterRegistry(this);
}
} else if (commandRegistries[i].getType() == CommandRegistry.Type.SYSTEM) {
throw new IllegalArgumentException();
}
}
}

public CommandRegistry.Type getType() {
return CommandRegistry.Type.SYSTEM;
}

public Set<String> commandNames() {
Set<String> out = new HashSet<>();
for (CommandRegistry r : commandRegistries) {
out.addAll(r.commandNames());
}
return out;
}

public Map<String, String> commandAliases() {
Map<String, String> out = new HashMap<>();
for (CommandRegistry r : commandRegistries) {
out.putAll(r.commandAliases());
}
return out;
}

public List<String> commandInfo(String command) {
int id = registryId(command);
return id > -1 ? commandRegistries[id].commandInfo(command) : new ArrayList<>();
}

public boolean hasCommand(String command) {
return registryId(command) > -1;
}

public Completers.SystemCompleter compileCompleters() {
return CommandRegistry.compileCompleters(commandRegistries);
}

public Widgets.CmdDesc commandDescription(String command) {
int id = registryId(command);
return id > -1 ? commandRegistries[id].commandDescription(command) : new Widgets.CmdDesc(false);
}

public Object execute(ParsedLine pl) throws Exception {
String[] argv = pl.words().subList(1, pl.words().size()).toArray(new String[0]);
String cmd = Parser.getCommand(pl.word());
Object out = null;
boolean done = false;
if ("help".equals(cmd) || "?".equals(cmd)) {
help();
done = true;
}
else {
int id = registryId(cmd);
if (id > -1) {
out = commandRegistries[id].execute(cmd, argv);
} else if (consoleId != null) {
out = commandRegistries[0].execute(pl);
}
}
return out;
}

private void help() {
System.out.println("List of available commands:");
for (CommandRegistry r : commandRegistries) {
TreeSet<String> commands = new TreeSet<>(r.commandNames());
AttributedStringBuilder asb = new AttributedStringBuilder().tabs(2);
asb.append("\t");
asb.append(r.getClass().getSimpleName());
asb.append(":");
System.out.println(asb.toString());
for (String c: commands) {
asb = new AttributedStringBuilder().tabs(Arrays.asList(4,20));
asb.append("\t");
asb.append(c);
asb.append("\t");
asb.append(r.commandInfo(c).size() > 0 ? r.commandInfo(c).get(0) : " ");
System.out.println(asb.toString());
}
}
System.out.println(" Additional help:");
System.out.println(" <command> --help");
}

private int registryId(String command) {
for (int i = 0; i < commandRegistries.length; i++) {
if (commandRegistries[i].hasCommand(command)) {
return i;
}
}
return -1;
}
}
}
105 changes: 13 additions & 92 deletions builtins/src/test/java/org/jline/example/Example.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2002-2019, the original author or authors.
* Copyright (c) 2002-2020, the original author or authors.
*
* This software is distributable under the BSD license. See the terms of the
* BSD license in the documentation provided with this software.
Expand Down Expand Up @@ -30,8 +30,9 @@
import org.jline.builtins.Completers;
import org.jline.builtins.Completers.SystemCompleter;
import org.jline.builtins.Completers.TreeCompleter;
import org.jline.builtins.ConsoleEngine;
import org.jline.builtins.Options;
import org.jline.builtins.ConsoleCommands;
import org.jline.builtins.Master;
import org.jline.builtins.Widgets.ArgDesc;
import org.jline.builtins.Widgets.AutopairWidgets;
import org.jline.builtins.Widgets.AutosuggestionWidgets;
Expand Down Expand Up @@ -136,98 +137,19 @@ private static Map<String,CmdDesc> compileTailTips() {
return tailTips;
}

public static class MasterRegistry implements CommandRegistry {
private final CommandRegistry[] commandRegistries;
private Parser parser;
private static class DescriptionGenerator {
CommandRegistry masterRegistry;

public MasterRegistry(CommandRegistry... commandRegistries) {
this.commandRegistries = commandRegistries;
}

public void setParser(Parser parser) {
this.parser = parser;
}

public Object execute(ParsedLine pl) throws Exception {
String[] argv = pl.words().subList(1, pl.words().size()).toArray(new String[0]);
String cmd = Parser.getCommand(pl.word());
Object out = null;
boolean done = false;
if ("help".equals(cmd) || "?".equals(cmd)) {
help();
done = true;
}
else {
for (CommandRegistry r : commandRegistries) {
if (r.hasCommand(cmd)) {
out = r.execute(cmd, argv);
done = true;
break;
}
}
}
if (!done) {
out = commandRegistries[0].execute(pl);
}
return out;
}

public void help() {
System.out.println("List of available commands:");
for (CommandRegistry r : commandRegistries) {
TreeSet<String> commands = new TreeSet<>(r.commandNames());
AttributedStringBuilder asb = new AttributedStringBuilder().tabs(2);
asb.append("\t");
asb.append(r.getClass().getSimpleName());
asb.append(":");
System.out.println(asb.toString());
for (String c: commands) {
asb = new AttributedStringBuilder().tabs(Arrays.asList(4,20));
asb.append("\t");
asb.append(c);
asb.append("\t");
asb.append(r.commandInfo(c).get(0));
System.out.println(asb.toString());
}
}
System.out.println(" Additional help:");
System.out.println(" <command> --help");
}
public Set<String> commandNames(){
return null;
}

public Map<String, String> commandAliases(){
return null;
}

public List<String> commandInfo(String command) {
return null;
}

public boolean hasCommand(String command) {
return true;
}

public Completers.SystemCompleter compileCompleters() {
return null;
}

public CmdDesc commandDescription(String command) {
return null;
public DescriptionGenerator(CommandRegistry masterRegistry) {
this.masterRegistry = masterRegistry;
}

public CmdDesc commandDescription(CmdLine line) {
CmdDesc out = null;
switch (line.getDescriptionType()) {
case COMMAND:
String cmd = Parser.getCommand(line.getArgs().get(0));
for (CommandRegistry r : commandRegistries) {
if (r.hasCommand(cmd)) {
out = r.commandDescription(cmd);
break;
}
}
out = masterRegistry.commandDescription(cmd);
break;
case METHOD:
out = methodDescription(line);
Expand Down Expand Up @@ -697,14 +619,12 @@ public void complete(LineReader reader, ParsedLine line, List<Candidate> candida
builtins.alias("zle", "widget");
builtins.alias("bindkey", "keymap");
ExampleCommands exampleCommands = new ExampleCommands();
ConsoleCommands consoleCommands = new ConsoleCommands(new Engine(), parser);
MasterRegistry masterRegistry = new MasterRegistry(consoleCommands, builtins, exampleCommands);
masterRegistry.setParser(parser);
consoleCommands.setMasterRegistry(masterRegistry);
ConsoleEngine consoleEngine = new ConsoleEngine(new Engine(), parser);
Master.Registry masterRegistry = new Master.Registry(consoleEngine, builtins, exampleCommands);
//
// Command completers
//
AggregateCompleter finalCompleter = new AggregateCompleter(CommandRegistry.compileCompleters(builtins, consoleCommands, exampleCommands)
AggregateCompleter finalCompleter = new AggregateCompleter(masterRegistry.compileCompleters()
, completer != null ? completer : NullCompleter.INSTANCE);
//
// Terminal & LineReader
Expand All @@ -730,7 +650,8 @@ public void complete(LineReader reader, ParsedLine line, List<Candidate> candida
if (argument) {
tailtipWidgets = new TailTipWidgets(reader, compileTailTips(), 5, TipType.COMPLETER);
} else {
tailtipWidgets = new TailTipWidgets(reader, masterRegistry::commandDescription, 5, TipType.COMPLETER);
DescriptionGenerator descriptionGenerator = new DescriptionGenerator(masterRegistry);
tailtipWidgets = new TailTipWidgets(reader, descriptionGenerator::commandDescription, 5, TipType.COMPLETER);
}
//
// complete command registeries
Expand Down
Loading

0 comments on commit 57c9a61

Please sign in to comment.