diff --git a/src/planmysem/commands/FindCommand.java b/src/planmysem/commands/FindCommand.java index e0df29207..027f718fb 100644 --- a/src/planmysem/commands/FindCommand.java +++ b/src/planmysem/commands/FindCommand.java @@ -4,12 +4,14 @@ import java.util.ArrayList; import java.util.List; import java.util.Map; +import java.util.Set; import java.util.regex.Pattern; import javafx.util.Pair; import planmysem.data.semester.Day; import planmysem.data.slot.ReadOnlySlot; import planmysem.data.slot.Slot; +import planmysem.data.tag.Tag; /** @@ -23,15 +25,16 @@ public class FindCommand extends Command { private static final String MESSAGE_SUCCESS = "%1$s Slots listed.\n%2$s"; private static final String MESSAGE_SUCCESS_NONE = "0 Slots listed.\n"; public static final String MESSAGE_USAGE = COMMAND_WORD + ":\n" + "Finds all slots whose name " - - + "contains the specified keywords (not case-sensitive).\n\t" + + "contains the specified keywords (case-sensitive).\n\t" + "Parameters: KEYWORD [MORE_KEYWORDS]...\n\t" + "Example: " + COMMAND_WORD + "n/CS"; private final String keyword; + private final boolean isFindByName; - public FindCommand(String keyword) { - this.keyword = keyword; + public FindCommand(String name, String tag ) { + this.keyword = (name == null) ? tag.trim() : name.trim(); + this.isFindByName = (name != null); } @Override @@ -42,10 +45,21 @@ public CommandResult execute() { for (Map.Entry entry : planner.getSemester().getDays().entrySet()) { for (Slot slots : entry.getValue().getSlots()) { - if (Pattern.matches(".*" + keyword + ".*", slots.getName().value)) { - matchedSlots.add(slots); - date = entry.getKey(); - relevantSlots.add(new Pair<>(date, slots)); + if (isFindByName) { + if (Pattern.matches(".*" + keyword + ".*", slots.getName().value)) { + matchedSlots.add(slots); + date = entry.getKey(); + relevantSlots.add(new Pair<>(date, slots)); + } + } else { + Set tagSet = slots.getTags(); + for (Tag tag : tagSet) { + if (Pattern.matches(".*" + keyword + ".*", tag.value)) { + matchedSlots.add(slots); + date = entry.getKey(); + relevantSlots.add(new Pair<>(date, slots)); + } + } } } } @@ -57,6 +71,27 @@ public CommandResult execute() { return new CommandResult(String.format(MESSAGE_SUCCESS, matchedSlots.size(), craftSuccessMessage(relevantSlots))); +// final List> relevantSlots = new ArrayList<>(); +// List matchedSlots = new ArrayList<>(); +// LocalDate date; +// +// for (Map.Entry entry : planner.getSemester().getDays().entrySet()) { +// for (Slot slots : entry.getValue().getSlots()) { +// if (Pattern.matches(".*" + keyword + ".*", slots.getName().value)) { +// matchedSlots.add(slots); +// date = entry.getKey(); +// relevantSlots.add(new Pair<>(date, slots)); +// } +// } +// } +// +// if (matchedSlots.isEmpty()) { +// return new CommandResult(MESSAGE_SUCCESS_NONE); +// } +// setData(this.planner, relevantSlots); +// +// return new CommandResult(String.format(MESSAGE_SiUCCESS, matchedSlots.size(), +// craftSuccessMessage(rele } /** @@ -77,6 +112,9 @@ private String craftSuccessMessage(List> sb.append(",\n\t"); sb.append("Start Time: "); sb.append(pair.getValue().getStartTime()); + sb.append("\n\t"); + sb.append("Tags: "); + sb.append(pair.getValue().getTags()); sb.append("\n"); count++; } diff --git a/src/planmysem/commands/ListCommand.java b/src/planmysem/commands/ListCommand.java index 6df29b376..3f898693d 100644 --- a/src/planmysem/commands/ListCommand.java +++ b/src/planmysem/commands/ListCommand.java @@ -4,11 +4,13 @@ import java.util.ArrayList; import java.util.List; import java.util.Map; +import java.util.Set; import javafx.util.Pair; import planmysem.data.semester.Day; import planmysem.data.slot.ReadOnlySlot; import planmysem.data.slot.Slot; +import planmysem.data.tag.Tag; /** * Displays a list of all slots in the planner whose name matches the argument keyword. @@ -22,15 +24,17 @@ public class ListCommand extends Command { public static final String MESSAGE_SUCCESS_NONE = "0 Slots listed.\n"; public static final String MESSAGE_USAGE = COMMAND_WORD + ": Lists all slots whose name " - + "directly matches the specified keyword (not case-sensitive)." + + "directly matches the specified keyword (case-sensitive)." //+ "\n\tOptional Parameters: [past] [next] [all]" //+ "\n\tDefault: list all" + "\n\tExample: " + COMMAND_WORD + " n/CS1010"; - private final String name; + private final String keyword; + private final boolean isListByName; - public ListCommand(String name) { - this.name = name; + public ListCommand(String name, String tag) { + this.keyword = (name == null) ? tag.trim() : name.trim(); + this.isListByName = (name != null); } @Override public CommandResult execute() { @@ -40,10 +44,21 @@ public CommandResult execute() { for (Map.Entry entry : planner.getSemester().getDays().entrySet()) { for (Slot slots : entry.getValue().getSlots()) { - if (slots.getName().value.equalsIgnoreCase(name)) { - matchedSlots.add(slots); - date = entry.getKey(); - relevantSlots.add(new Pair<>(date, slots)); + if (isListByName) { + if (slots.getName().value.equalsIgnoreCase(keyword)) { + matchedSlots.add(slots); + date = entry.getKey(); + relevantSlots.add(new Pair<>(date, slots)); + } + } else { + Set tagSet = slots.getTags(); + for (Tag tag : tagSet) { + if (tag.value.equalsIgnoreCase(keyword)) { + matchedSlots.add(slots); + date = entry.getKey(); + relevantSlots.add(new Pair<>(date, slots)); + } + } } } } @@ -57,6 +72,7 @@ public CommandResult execute() { craftSuccessMessage(relevantSlots))); } + /** * Craft success message. */ @@ -75,6 +91,9 @@ private String craftSuccessMessage(List> sb.append(",\n\t"); sb.append("Start Time: "); sb.append(pair.getValue().getStartTime()); + sb.append("\n\t"); + sb.append("Tags: "); + sb.append(pair.getValue().getTags()); sb.append("\n"); count++; } diff --git a/src/planmysem/common/Messages.java b/src/planmysem/common/Messages.java index cd9046f37..e338992e5 100644 --- a/src/planmysem/common/Messages.java +++ b/src/planmysem/common/Messages.java @@ -12,6 +12,7 @@ public class Messages { public static final String MESSAGE_INVALID_COMMAND_FORMAT = "Invalid command format! \n%1$s"; public static final String MESSAGE_INVALID_COMMAND_FORMAT_ADDITIONAL = "Invalid command format! \n%1$s\n\n%2$s"; public static final String MESSAGE_INVALID_PERSON_DISPLAYED_INDEX = "The person index provided is invalid"; + public static final String MESSAGE_INVALID_MULTIPLE_PARAMS = "Either search by NAME or by TAG only, not both."; public static final String MESSAGE_INVALID_SLOT_DISPLAYED_INDEX = "The slot index provided is invalid"; public static final String MESSAGE_PERSON_NOT_IN_ADDRESSBOOK = "Person could not be found in address book"; public static final String MESSAGE_SLOT_NOT_IN_PLANNER = "Slot could not be found in Planner"; diff --git a/src/planmysem/parser/Parser.java b/src/planmysem/parser/Parser.java index 7e451b6a6..408c2c9ee 100644 --- a/src/planmysem/parser/Parser.java +++ b/src/planmysem/parser/Parser.java @@ -3,6 +3,7 @@ import static planmysem.common.Messages.MESSAGE_INVALID_COMMAND_FORMAT; import static planmysem.common.Messages.MESSAGE_INVALID_COMMAND_FORMAT_ADDITIONAL; import static planmysem.common.Messages.MESSAGE_INVALID_DATE; +import static planmysem.common.Messages.MESSAGE_INVALID_MULTIPLE_PARAMS; import static planmysem.common.Messages.MESSAGE_INVALID_TIME; import java.time.LocalDate; @@ -322,10 +323,14 @@ private Command prepareDelete(String args) { private Command prepareFind(String args) { HashMap> arguments = getParametersWithArguments(args); String name = getFirstInSet(arguments.get(PARAMETER_NAME)); - if (name == null || name.trim().isEmpty()) { + String tag = getFirstInSet(arguments.get(PARAMETER_TAG)); + if (name == null && tag == null) { return new IncorrectCommand(String.format(MESSAGE_INVALID_COMMAND_FORMAT, FindCommand.MESSAGE_USAGE)); + } else if (name != null && tag != null) { + return new IncorrectCommand(String.format(MESSAGE_INVALID_MULTIPLE_PARAMS, FindCommand.MESSAGE_USAGE)); + } - return new FindCommand(name); + return new FindCommand(name, tag); } /** @@ -337,10 +342,13 @@ private Command prepareFind(String args) { private Command prepareList(String args) { HashMap> arguments = getParametersWithArguments(args); String name = getFirstInSet(arguments.get(PARAMETER_NAME)); - if (name == null || name.trim().isEmpty()) { + String tag = getFirstInSet(arguments.get(PARAMETER_TAG)); + if (name == null && tag == null) { return new IncorrectCommand(String.format(MESSAGE_INVALID_COMMAND_FORMAT, ListCommand.MESSAGE_USAGE)); + } else if (name != null && tag != null) { + return new IncorrectCommand(String.format(MESSAGE_INVALID_MULTIPLE_PARAMS, ListCommand.MESSAGE_USAGE)); } - return new ListCommand(name); + return new ListCommand(name, tag); } /** diff --git a/test/java/planmysem/logic/LogicTest.java b/test/java/planmysem/logic/LogicTest.java index d1c19631e..d72c5fdfd 100644 --- a/test/java/planmysem/logic/LogicTest.java +++ b/test/java/planmysem/logic/LogicTest.java @@ -2,10 +2,7 @@ import static junit.framework.TestCase.assertEquals; -import static planmysem.common.Messages.MESSAGE_INVALID_DATE; -import static planmysem.common.Messages.MESSAGE_INVALID_COMMAND_FORMAT; -import static planmysem.common.Messages.MESSAGE_INVALID_COMMAND_FORMAT_ADDITIONAL; -import static planmysem.common.Messages.MESSAGE_INVALID_TIME; +import static planmysem.common.Messages.*; import java.time.LocalDate; import java.time.LocalTime; @@ -27,6 +24,8 @@ import planmysem.commands.ClearCommand; import planmysem.commands.CommandResult; import planmysem.commands.DeleteCommand; +import planmysem.commands.FindCommand; +import planmysem.commands.ListCommand; import planmysem.commands.EditCommand; import planmysem.commands.ExitCommand; import planmysem.commands.HelpCommand; @@ -206,6 +205,26 @@ public void execute_delete_invalidArgsFormat() throws Exception { "d wrong", expectedMessage); } + @Test + public void execute_find_invalidArgsFormat() throws Exception { + String expectedMessageSingle = String.format(MESSAGE_INVALID_COMMAND_FORMAT, FindCommand.MESSAGE_USAGE); + String expectedMessageMultipleParams = String.format(MESSAGE_INVALID_MULTIPLE_PARAMS, FindCommand.MESSAGE_USAGE); + assertCommandBehavior( + "find wrong args wrong args", expectedMessageSingle); + assertCommandBehavior( + "find n/CS2113T t/Tutorial", expectedMessageMultipleParams); + } + + @Test + public void execute_list_invalidArgsFormat() throws Exception { + String expectedMessageSingle = String.format(MESSAGE_INVALID_COMMAND_FORMAT, ListCommand.MESSAGE_USAGE); + String expectedMessageMultipleParams = String.format(MESSAGE_INVALID_MULTIPLE_PARAMS, ListCommand.MESSAGE_USAGE); + assertCommandBehavior( + "list wrong args wrong args", expectedMessageSingle); + assertCommandBehavior( + "list n/CS2113T t/Tutorial", expectedMessageMultipleParams); + } + /** * Executes the command and confirms that the result message is correct. * Both the 'planner' and the 'last shown list' are expected to be empty.