Skip to content

Commit

Permalink
Added list command to CLI.
Browse files Browse the repository at this point in the history
  • Loading branch information
hptruong93 committed Jul 7, 2018
1 parent 1c39417 commit e3c0089
Show file tree
Hide file tree
Showing 6 changed files with 146 additions and 13 deletions.
33 changes: 25 additions & 8 deletions src/cli/client/handlers/TaskActionHandler.java
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,14 @@
import cli.messages.TaskExecuteMessage;
import cli.messages.TaskGroupMessage;
import cli.messages.TaskIdentifier;
import cli.messages.TaskListMessage;
import cli.messages.TaskMessage;
import cli.messages.TaskRemoveMessage;
import cli.server.CliRpcCodec;
import net.sourceforge.argparse4j.inf.Namespace;
import net.sourceforge.argparse4j.inf.Subparser;
import net.sourceforge.argparse4j.inf.Subparsers;
import utilities.IJsonable;
import utilities.JSONUtility;
import utilities.NumberUtility;

Expand All @@ -29,9 +31,9 @@ public void addArguments(Subparsers subparsers) {
Subparser parser = subparsers.addParser("task").setDefault("module", "task").help("Task management.");

parser.addArgument("-a", "--action").required(true)
.choices("add", "remove", "execute")
.choices("add", "remove", "execute", "ls", "list")
.help("Specify action on task.");
parser.addArgument("-n", "--name").required(true)
parser.addArgument("-n", "--name").setDefault("")
.help("Name of the task, or its index (zero based) in the group if the task exists. "
+ "This tries to interpret this as an integer index first, then as a task name. "
+ "For remove action, if multiple tasks share the same name, "
Expand All @@ -53,6 +55,8 @@ public void handle(Namespace namespace) {
handleRemove(namespace);
} else if (action.equals("execute")) {
handleExecute(namespace);
} else if (action.equals("ls") || action.equals("list")) {
handleList(namespace);
} else {
LOGGER.log(Level.SEVERE, "Unknown task action " + action);
CliExitCodes.UNKNOWN_ACTION.exit();
Expand All @@ -71,8 +75,7 @@ private void handleAdd(Namespace namespace) {

TaskAddMessage message = TaskAddMessage.of().setFilePath(filePath)
.setTaskIdentifier(TaskIdentifier.of().setGroup(taskGroupMessage).setTask(taskMessage));
byte[] data = CliRpcCodec.encode(JSONUtility.jsonToString(message.jsonize()).getBytes(CliRpcCodec.ENCODING));
sendRequest("/task/add", data);
sendRequest("/task/add", message);
}

private void handleRemove(Namespace namespace) {
Expand All @@ -81,8 +84,7 @@ private void handleRemove(Namespace namespace) {

TaskRemoveMessage message = TaskRemoveMessage.of()
.setTaskIdentifier(TaskIdentifier.of().setGroup(taskGroupMessage).setTask(taskMessage));
byte[] data = CliRpcCodec.encode(JSONUtility.jsonToString(message.jsonize()).getBytes(CliRpcCodec.ENCODING));
sendRequest("/task/remove", data);
sendRequest("/task/remove", message);
}

private void handleExecute(Namespace namespace) {
Expand All @@ -91,8 +93,13 @@ private void handleExecute(Namespace namespace) {

TaskExecuteMessage message = TaskExecuteMessage.of()
.setTaskIdentifier(TaskIdentifier.of().setGroup(taskGroupMessage).setTask(taskMessage));
byte[] data = CliRpcCodec.encode(JSONUtility.jsonToString(message.jsonize()).getBytes(CliRpcCodec.ENCODING));
sendRequest("/task/execute", data);
sendRequest("/task/execute", message);
}

private void handleList(Namespace namespace) {
TaskGroupMessage taskGroupMessage = getGroup(namespace);
TaskListMessage message = TaskListMessage.of().setGroup(taskGroupMessage);
sendRequest("/task/list", message);
}

private TaskGroupMessage getGroup(Namespace namespace) {
Expand All @@ -108,6 +115,11 @@ private TaskGroupMessage getGroup(Namespace namespace) {

private TaskMessage getTask(Namespace namespace) {
String taskName = namespace.getString("name");
if (taskName.isEmpty()) {
LOGGER.warning("Task must be specified.");
CliExitCodes.INVALID_ARGUMENTS.exit();
}

TaskMessage taskMessage = TaskMessage.of();
if (NumberUtility.isNonNegativeInteger(taskName)) {
taskMessage.setIndex(Integer.parseInt(taskName));
Expand All @@ -117,6 +129,11 @@ private TaskMessage getTask(Namespace namespace) {
return taskMessage;
}

private void sendRequest(String path, IJsonable message) {
byte[] data = CliRpcCodec.encode(JSONUtility.jsonToString(message.jsonize()).getBytes(CliRpcCodec.ENCODING));
sendRequest(path, data);
}

private void sendRequest(String path, byte[] data) {
try {
byte[] responseData = httpClient.sendPost(path, data);
Expand Down
49 changes: 49 additions & 0 deletions src/cli/messages/TaskListMessage.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
package cli.messages;

import java.util.HashMap;
import java.util.Map;

import argo.jdom.JsonNode;
import argo.jdom.JsonNodeFactories;
import argo.jdom.JsonRootNode;
import argo.jdom.JsonStringNode;
import utilities.IJsonable;

public class TaskListMessage implements IJsonable {
private TaskGroupMessage group;

private TaskListMessage() {}
public static TaskListMessage of() {
return new TaskListMessage();
}

private TaskListMessage(TaskGroupMessage group) {
this.group = group;
}

public static TaskListMessage parseJSON(JsonNode node) {
TaskGroupMessage group = null;
if (node.isObjectNode("group")) {
group = TaskGroupMessage.parseJSON(node.getNode("group"));
}

return new TaskListMessage(group);
}

@Override
public JsonRootNode jsonize() {
Map<JsonStringNode, JsonNode> data = new HashMap<>();
if (group != null) {
data.put(JsonNodeFactories.string("group"), group.jsonize());
}
return JsonNodeFactories.object(data);
}

public TaskGroupMessage getGroup() {
return group;
}
public TaskListMessage setGroup(TaskGroupMessage group) {
this.group = group;
return this;
}
}
2 changes: 2 additions & 0 deletions src/cli/server/CliServer.java
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
import cli.server.handlers.HttpHandlerWithBackend;
import cli.server.handlers.TaskAddActionHandler;
import cli.server.handlers.TaskExecuteActionHandler;
import cli.server.handlers.TaskListActionHandler;
import cli.server.handlers.TaskRemoveActionHandler;
import cli.server.handlers.UpAndRunningHandler;
import core.config.CliConfig;
Expand Down Expand Up @@ -52,6 +53,7 @@ private Map<String, HttpHandlerWithBackend> createHandlers() {
output.put("/task/add", new TaskAddActionHandler());
output.put("/task/remove", new TaskRemoveActionHandler());
output.put("/task/execute", new TaskExecuteActionHandler());
output.put("/task/list", new TaskListActionHandler());
return output;
}

Expand Down
14 changes: 9 additions & 5 deletions src/cli/server/handlers/TaskActionHandler.java
Original file line number Diff line number Diff line change
Expand Up @@ -57,17 +57,21 @@ protected UserDefinedAction getTask(TaskGroup group, TaskIdentifier taskIdentifi
}

protected TaskGroup getGroup(TaskIdentifier taskIdentifier) {
int index = taskIdentifier.getGroup().getIndex();
String name = taskIdentifier.getGroup().getName();
return getGroup(taskIdentifier.getGroup());
}

protected TaskGroup getGroup(TaskGroupMessage taskGroup) {
int index = taskGroup.getIndex();
String name = taskGroup.getName();
if (index == TaskGroupMessage.UNKNOWN_INDEX && name.isEmpty()) {
index = 0;
}

TaskGroup group = null;
if (taskIdentifier.getGroup() != null) {
group = backEndHolder.getTaskGroup(taskIdentifier.getGroup().getIndex());
if (taskGroup != null) {
group = backEndHolder.getTaskGroup(index);
if (group == null) {
group = backEndHolder.getTaskGroup(taskIdentifier.getGroup().getName());
group = backEndHolder.getTaskGroup(name);
}
}
return group;
Expand Down
37 changes: 37 additions & 0 deletions src/cli/server/handlers/TaskListActionHandler.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
package cli.server.handlers;

import java.io.IOException;
import java.util.List;
import java.util.stream.Collectors;

import org.apache.http.nio.protocol.HttpAsyncExchange;

import argo.jdom.JsonNode;
import cli.messages.TaskGroupMessage;
import cli.messages.TaskListMessage;
import cli.server.CliRpcCodec;
import cli.server.utils.EnumerationUtils;
import core.userDefinedTask.TaskGroup;
import core.userDefinedTask.UserDefinedAction;

public class TaskListActionHandler extends TaskActionHandler {

@Override
protected Void handleTaskActionWithBackend(HttpAsyncExchange exchange, JsonNode request) throws IOException {
TaskListMessage message = TaskListMessage.parseJSON(request);
boolean noGroup = message.getGroup() == null ||
(message.getGroup().getIndex() == TaskGroupMessage.UNKNOWN_INDEX &&
message.getGroup().getName().isEmpty());

if (noGroup) {
List<String> names = backEndHolder.getTaskGroups().stream().map(TaskGroup::getName).collect(Collectors.toList());
return CliRpcCodec.prepareResponse(exchange, 200, EnumerationUtils.enumerate(names));
}
TaskGroup group = getGroup(message.getGroup());
if (group == null) {
return CliRpcCodec.prepareResponse(exchange, 400, "Cannot find group with given arguments.");
}
List<String> taskNames = group.getTasks().stream().map(UserDefinedAction::getName).collect(Collectors.toList());
return CliRpcCodec.prepareResponse(exchange, 200, EnumerationUtils.enumerate(taskNames));
}
}
24 changes: 24 additions & 0 deletions src/cli/server/utils/EnumerationUtils.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package cli.server.utils;

public class EnumerationUtils {
private EnumerationUtils() {}

/**
* Converts an iterable of Strings into a readable list.
* Index starts from 0.
*
* E.g. [aa,bb,cc,dd] will become
* 0) aa
* 1) bb
* 2) cc
* 3) dd
*/
public static String enumerate(Iterable<String> data) {
StringBuilder builder = new StringBuilder();
int i = 0;
for (String s : data) {
builder.append(String.format("%d) %s\n", i++, s));
}
return builder.toString();
}
}

0 comments on commit e3c0089

Please sign in to comment.