From bf0487490bd362d2495d9ecef1b74ccb605c7f50 Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Thu, 21 Mar 2024 10:29:29 +0800 Subject: [PATCH 01/12] Update naming convention for application --- build.gradle | 2 +- .../java/seedu/address/logic/commands/DeleteCommand.java | 2 +- src/main/java/seedu/address/logic/commands/EditCommand.java | 2 +- src/main/java/seedu/address/logic/commands/ExitCommand.java | 2 +- src/main/java/seedu/address/logic/commands/HelpCommand.java | 2 +- .../seedu/address/logic/commands/ListClassesCommand.java | 2 +- src/main/java/seedu/address/logic/commands/ListCommand.java | 4 ++-- .../seedu/address/logic/parser/AddClassCommandParser.java | 6 +++--- .../address/logic/parser/DeleteClassCommandParser.java | 6 +++--- .../address/logic/parser/DeleteStudentCommandParser.java | 6 +++--- src/main/java/seedu/address/logic/parser/Prefix.java | 2 +- src/main/java/seedu/address/model/person/Email.java | 2 +- src/main/java/seedu/address/model/person/Name.java | 4 ++-- src/main/java/seedu/address/model/tag/Tag.java | 2 +- 14 files changed, 22 insertions(+), 22 deletions(-) diff --git a/build.gradle b/build.gradle index 997495b6ade..ce4e7f30fb0 100644 --- a/build.gradle +++ b/build.gradle @@ -71,7 +71,7 @@ dependencies { } shadowJar { - archiveFileName = 'addressbook.jar' + archiveFileName = 'tahelper.jar' } defaultTasks 'clean', 'test' diff --git a/src/main/java/seedu/address/logic/commands/DeleteCommand.java b/src/main/java/seedu/address/logic/commands/DeleteCommand.java index 1135ac19b74..11ae43bd1c9 100644 --- a/src/main/java/seedu/address/logic/commands/DeleteCommand.java +++ b/src/main/java/seedu/address/logic/commands/DeleteCommand.java @@ -12,7 +12,7 @@ import seedu.address.model.person.Person; /** - * Deletes a person identified using it's displayed index from the address book. + * Deletes a person identified using it's displayed index from tahelper system. */ public class DeleteCommand extends Command { diff --git a/src/main/java/seedu/address/logic/commands/EditCommand.java b/src/main/java/seedu/address/logic/commands/EditCommand.java index 73823fc61f6..90f559fb985 100644 --- a/src/main/java/seedu/address/logic/commands/EditCommand.java +++ b/src/main/java/seedu/address/logic/commands/EditCommand.java @@ -27,7 +27,7 @@ import seedu.address.model.tag.Tag; /** - * Edits the details of an existing person in the address book. + * Edits the details of an existing person in tahelper's system */ public class EditCommand extends Command { diff --git a/src/main/java/seedu/address/logic/commands/ExitCommand.java b/src/main/java/seedu/address/logic/commands/ExitCommand.java index 3dd85a8ba90..70703fd7595 100644 --- a/src/main/java/seedu/address/logic/commands/ExitCommand.java +++ b/src/main/java/seedu/address/logic/commands/ExitCommand.java @@ -7,7 +7,7 @@ */ public class ExitCommand extends Command { - public static final String COMMAND_WORD = "exit"; + public static final String COMMAND_WORD = "/exit"; public static final String MESSAGE_EXIT_ACKNOWLEDGEMENT = "Exiting Address Book as requested ..."; diff --git a/src/main/java/seedu/address/logic/commands/HelpCommand.java b/src/main/java/seedu/address/logic/commands/HelpCommand.java index bf824f91bd0..1735597b18f 100644 --- a/src/main/java/seedu/address/logic/commands/HelpCommand.java +++ b/src/main/java/seedu/address/logic/commands/HelpCommand.java @@ -7,7 +7,7 @@ */ public class HelpCommand extends Command { - public static final String COMMAND_WORD = "help"; + public static final String COMMAND_WORD = "/help"; public static final String MESSAGE_USAGE = COMMAND_WORD + ": Shows program usage instructions.\n" + "Example: " + COMMAND_WORD; diff --git a/src/main/java/seedu/address/logic/commands/ListClassesCommand.java b/src/main/java/seedu/address/logic/commands/ListClassesCommand.java index 61b83ef4ce1..dfae02b1de9 100644 --- a/src/main/java/seedu/address/logic/commands/ListClassesCommand.java +++ b/src/main/java/seedu/address/logic/commands/ListClassesCommand.java @@ -5,7 +5,7 @@ import seedu.address.model.Model; /** - * Lists all modules and their associated tutorial classes in the address book to the user. + * Lists all modules and their associated tutorial classes in TAHelper to the user. */ public class ListClassesCommand extends Command { diff --git a/src/main/java/seedu/address/logic/commands/ListCommand.java b/src/main/java/seedu/address/logic/commands/ListCommand.java index 84be6ad2596..84a7a3972b1 100644 --- a/src/main/java/seedu/address/logic/commands/ListCommand.java +++ b/src/main/java/seedu/address/logic/commands/ListCommand.java @@ -6,11 +6,11 @@ import seedu.address.model.Model; /** - * Lists all persons in the address book to the user. + * Lists all persons in TAHelper to the user. */ public class ListCommand extends Command { - public static final String COMMAND_WORD = "list"; + public static final String COMMAND_WORD = "/list"; public static final String MESSAGE_SUCCESS = "Listed all persons"; diff --git a/src/main/java/seedu/address/logic/parser/AddClassCommandParser.java b/src/main/java/seedu/address/logic/parser/AddClassCommandParser.java index 3ff3b8ca12c..d72efc8aa4a 100644 --- a/src/main/java/seedu/address/logic/parser/AddClassCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/AddClassCommandParser.java @@ -15,12 +15,12 @@ /** - * Parses input arguments and creates a new {@code RemarkCommand} object + * Parses input arguments and creates a new {@code AddClassCommandParser} object */ public class AddClassCommandParser implements Parser { /** - * Parses the given {@code String} of arguments in the context of the {@code RemarkCommand} - * and returns a {@code RemarkCommand} object for execution. + * Parses the given {@code String} of arguments in the context of the {@code AddClassCommandParser} + * and returns a {@code AddClassCommandParser} object for execution. * @throws ParseException if the user input does not conform the expected format */ public AddClassCommand parse(String args) throws ParseException { diff --git a/src/main/java/seedu/address/logic/parser/DeleteClassCommandParser.java b/src/main/java/seedu/address/logic/parser/DeleteClassCommandParser.java index fe761612a3f..b50d8e99918 100644 --- a/src/main/java/seedu/address/logic/parser/DeleteClassCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/DeleteClassCommandParser.java @@ -15,12 +15,12 @@ /** - * Parses input arguments and creates a new {@code RemarkCommand} object + * Parses input arguments and creates a new {@code DeleteClassCommandParser} object */ public class DeleteClassCommandParser implements Parser { /** - * Parses the given {@code String} of arguments in the context of the {@code RemarkCommand} - * and returns a {@code RemarkCommand} object for execution. + * Parses the given {@code String} of arguments in the context of the {@code DeleteClassCommandParser} + * and returns a {@code DeleteClassCommandParser} object for execution. * @throws ParseException if the user input does not conform the expected format */ public DeleteClassCommand parse(String args) throws ParseException { diff --git a/src/main/java/seedu/address/logic/parser/DeleteStudentCommandParser.java b/src/main/java/seedu/address/logic/parser/DeleteStudentCommandParser.java index a547a788669..e5e278ef2e1 100644 --- a/src/main/java/seedu/address/logic/parser/DeleteStudentCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/DeleteStudentCommandParser.java @@ -16,14 +16,14 @@ import seedu.address.model.person.StudentId; /** - * Parses input arguments and creates a new DeleteCommand object + * Parses input arguments and creates a new DeleteStudentCommand object */ public class DeleteStudentCommandParser implements Parser { /** * Parses the given {@code String} of arguments in the context of the - * DeleteCommand - * and returns a DeleteCommand object for execution. + * DeleteStudentCommand + * and returns a DeleteStudentCommand object for execution. * * @throws ParseException if the user input does not conform the expected format */ diff --git a/src/main/java/seedu/address/logic/parser/Prefix.java b/src/main/java/seedu/address/logic/parser/Prefix.java index 348b7686c8a..f443e9a28d2 100644 --- a/src/main/java/seedu/address/logic/parser/Prefix.java +++ b/src/main/java/seedu/address/logic/parser/Prefix.java @@ -2,7 +2,7 @@ /** * A prefix that marks the beginning of an argument in an arguments string. - * E.g. 't/' in 'add James t/ friend'. + * E.g. 'tag/' in '/add_students name/john ...... tag/ friend'. */ public class Prefix { private final String prefix; diff --git a/src/main/java/seedu/address/model/person/Email.java b/src/main/java/seedu/address/model/person/Email.java index 24b6faf4001..be632593a54 100644 --- a/src/main/java/seedu/address/model/person/Email.java +++ b/src/main/java/seedu/address/model/person/Email.java @@ -4,7 +4,7 @@ import static seedu.address.commons.util.AppUtil.checkArgument; /** - * Represents a Person's email in the address book. + * Represents a Person's email in TAHelper. * Guarantees: immutable; is valid as declared in {@link #isValidEmail(String)} */ public class Email { diff --git a/src/main/java/seedu/address/model/person/Name.java b/src/main/java/seedu/address/model/person/Name.java index 173f15b9b00..b217db4b5ff 100644 --- a/src/main/java/seedu/address/model/person/Name.java +++ b/src/main/java/seedu/address/model/person/Name.java @@ -4,7 +4,7 @@ import static seedu.address.commons.util.AppUtil.checkArgument; /** - * Represents a Person's name in the address book. + * Represents a Person's name in TAHelper. * Guarantees: immutable; is valid as declared in {@link #isValidName(String)} */ public class Name { @@ -13,7 +13,7 @@ public class Name { "Names should only contain alphanumeric characters and spaces, and it should not be blank"; /* - * The first character of the address must not be a whitespace, + * The first character of the name must not be a whitespace, * otherwise " " (a blank string) becomes a valid input. */ public static final String VALIDATION_REGEX = "[\\p{Alnum}][\\p{Alnum} ]*"; diff --git a/src/main/java/seedu/address/model/tag/Tag.java b/src/main/java/seedu/address/model/tag/Tag.java index f1a0d4e233b..18ecf218856 100644 --- a/src/main/java/seedu/address/model/tag/Tag.java +++ b/src/main/java/seedu/address/model/tag/Tag.java @@ -4,7 +4,7 @@ import static seedu.address.commons.util.AppUtil.checkArgument; /** - * Represents a Tag in the address book. + * Represents a Tag in TAHelper. * Guarantees: immutable; name is valid as declared in {@link #isValidTagName(String)} */ public class Tag { From ffa2916b2a693388b3c7c595f669fd11251f1565 Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Thu, 21 Mar 2024 10:33:33 +0800 Subject: [PATCH 02/12] Update gradle file to support javafx swing library --- build.gradle | 3 +++ 1 file changed, 3 insertions(+) diff --git a/build.gradle b/build.gradle index ce4e7f30fb0..8dba104ccbd 100644 --- a/build.gradle +++ b/build.gradle @@ -57,6 +57,9 @@ dependencies { implementation group: 'org.openjfx', name: 'javafx-graphics', version: javaFxVersion, classifier: 'win' implementation group: 'org.openjfx', name: 'javafx-graphics', version: javaFxVersion, classifier: 'mac' implementation group: 'org.openjfx', name: 'javafx-graphics', version: javaFxVersion, classifier: 'linux' + implementation group: 'org.openjfx', name: 'javafx-swing', version: javaFxVersion, classifier: 'win' + implementation group: 'org.openjfx', name: 'javafx-swing', version: javaFxVersion, classifier: 'mac' + implementation group: 'org.openjfx', name: 'javafx-swing', version: javaFxVersion, classifier: 'linux' implementation group: 'com.fasterxml.jackson.core', name: 'jackson-databind', version: '2.7.0' implementation group: 'com.fasterxml.jackson.datatype', name: 'jackson-datatype-jsr310', version: '2.7.4' From e4f9e34a179cda07223876c229ed932a72ccad12 Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Thu, 21 Mar 2024 10:56:37 +0800 Subject: [PATCH 03/12] Update statusbar for application --- src/main/java/seedu/address/model/UserPrefs.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/seedu/address/model/UserPrefs.java b/src/main/java/seedu/address/model/UserPrefs.java index 6be655fb4c7..6195bf13ca5 100644 --- a/src/main/java/seedu/address/model/UserPrefs.java +++ b/src/main/java/seedu/address/model/UserPrefs.java @@ -14,7 +14,7 @@ public class UserPrefs implements ReadOnlyUserPrefs { private GuiSettings guiSettings = new GuiSettings(); - private Path addressBookFilePath = Paths.get("data" , "addressbook.json"); + private Path addressBookFilePath = Paths.get("data" , "tahelper.json"); /** * Creates a {@code UserPrefs} with default values. From 77d196c35b54592f46008e3322b1ccc99e667581 Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Wed, 27 Mar 2024 14:33:26 +0800 Subject: [PATCH 04/12] Update Allocate Student to Team command --- .../AllocateStudentToTeamCommand.java | 21 +++++++++- .../java/seedu/address/model/AddressBook.java | 42 +++++++++++++++++-- src/main/java/seedu/address/model/Model.java | 26 ++++++++++-- .../seedu/address/model/ModelManager.java | 24 +++++++++-- .../address/model/module/TutorialClass.java | 11 ++++- .../address/model/module/TutorialTeam.java | 16 ++++++- .../seedu/address/model/person/StudentId.java | 10 +++++ .../model/person/UniquePersonList.java | 12 ++++++ 8 files changed, 149 insertions(+), 13 deletions(-) diff --git a/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java b/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java index a7ae38321c3..07504be4c4a 100644 --- a/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java +++ b/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java @@ -2,7 +2,6 @@ import seedu.address.commons.util.ToStringBuilder; import seedu.address.commons.util.CollectionUtil; -import seedu.address.logic.*; import seedu.address.logic.commands.exceptions.*; import seedu.address.model.*; import seedu.address.model.module.*; @@ -34,6 +33,11 @@ public class AllocateStudentToTeamCommand extends Command { + PREFIX_TEAMNAME + "Team 1 "; public static final String MESSAGE_SUCCESS = "Allocate student to team: "; + public static final String MESSAGE_TEAM_DOES_NOT_EXIST = "Team does not exist in tutorial class"; + public static final String MESSAGE_DUPLICATE_PERSON_IN_TEAM = "This person already exists in a team" + + " in the tutorial class!"; + + public static final String MESSAGE_CLASS_DOES_NOT_EXIST = "Tutorial class does not exist in module"; private final StudentId studentId; private final ModuleCode moduleCode; @@ -55,6 +59,21 @@ public AllocateStudentToTeamCommand(StudentId studentId, ModuleCode moduleCode, @Override public CommandResult execute(Model model) throws CommandException { requireNonNull(model); + + if (model.findTutorialClassFromList(tutorialClass, moduleCode) == null) { + throw new CommandException(MESSAGE_CLASS_DOES_NOT_EXIST); + } + + if (!model.hasTeamInTutorial(tutorialClass, tutorialTeam)) { + throw new CommandException(MESSAGE_TEAM_DOES_NOT_EXIST); + } + + if (model.isStudentInAnyTeam(studentId, tutorialClass)) { + throw new CommandException(MESSAGE_DUPLICATE_PERSON_IN_TEAM); + } + + model.allocateStudentToTeam(studentId, tutorialTeam); + return new CommandResult(String.format(MESSAGE_SUCCESS)); } diff --git a/src/main/java/seedu/address/model/AddressBook.java b/src/main/java/seedu/address/model/AddressBook.java index f4cf39d4c5a..80945cc6c9b 100644 --- a/src/main/java/seedu/address/model/AddressBook.java +++ b/src/main/java/seedu/address/model/AddressBook.java @@ -1,6 +1,7 @@ package seedu.address.model; import static java.util.Objects.requireNonNull; +import static seedu.address.commons.util.CollectionUtil.requireAllNonNull; import java.util.ArrayList; import java.util.List; @@ -10,10 +11,8 @@ import seedu.address.commons.util.ToStringBuilder; import seedu.address.logic.commands.exceptions.CommandException; import seedu.address.logic.messages.ModuleMessages; -import seedu.address.model.module.ModuleCode; -import seedu.address.model.module.TutorialClass; -import seedu.address.model.person.Person; -import seedu.address.model.person.UniquePersonList; +import seedu.address.model.module.*; +import seedu.address.model.person.*; /** * Wraps all data at the address-book level @@ -99,6 +98,41 @@ public boolean hasPerson(Person person) { return persons.contains(person); } + /** + * Returns true if a team with the same identity as {@code tutorialTeam} exists in the {@code tutorialClass} + * @param tutorialClass of the tutorialTeam. + * @param tutorialTeam to check if it exist. + */ + public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + requireAllNonNull(tutorialClass, tutorialTeam); + ArrayList listOfTeams = tutorialClass.getTeams(); + ObservableList teams = FXCollections.observableList(listOfTeams); + return teams.stream().anyMatch(tutorialClass::hasTeam); + } + + /** + * Returns true if the {@code studentId} is already in a team of {@code tutorialClass}. + * @param tutorialClass of the teams. + * @param studentId to search for. + */ + public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { + boolean isStudentExist = false; + for (TutorialTeam tutorialTeam : tutorialClass.getTeams()) { + isStudentExist = tutorialTeam.hasStudentVerified(studentId); + } + return isStudentExist; + }; + + /** + * Allocates the {@code studentId} to the {@code tutorialTeam} + * @param tutorialTeam to allocate the student into. + */ + public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { + requireAllNonNull(studentId, tutorialTeam); + Person person = persons.getPerson(studentId); + tutorialTeam.addStudent(person); + } + /** * Adds a person to the address book. * The person must not already exist in the address book. diff --git a/src/main/java/seedu/address/model/Model.java b/src/main/java/seedu/address/model/Model.java index fe7fcdbfbbd..6349f53ea86 100644 --- a/src/main/java/seedu/address/model/Model.java +++ b/src/main/java/seedu/address/model/Model.java @@ -5,9 +5,8 @@ import javafx.collections.ObservableList; import seedu.address.commons.core.GuiSettings; -import seedu.address.model.module.ModuleCode; -import seedu.address.model.module.TutorialClass; -import seedu.address.model.person.Person; +import seedu.address.model.module.*; +import seedu.address.model.person.*; /** * The API of the Model component. @@ -124,9 +123,30 @@ public interface Model { */ void updateFilteredModuleList(Predicate predicate); + /** * Search for person by a given {@code predicate}. */ Person searchPersonByPredicate(Predicate predicate); + /** + * Returns true if a team with the same identity as {@code tutorialTeam} exists in the {@code tutorialClass} + * @param tutorialClass of the tutorialTeam. + * @param tutorialTeam to check if it exist. + */ + boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam); + + /** + * Returns true if the {@code studentId} is already in a team of {@code tutorialClass}. + * @param tutorialClass of the teams. + * @param studentId to search for. + */ + public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass); + + /** + * Allocates the student to the {@code tutorialTeam} under that {@code tutorialClass} of that {@code moduleCode} + * @param studentId to find the Person to add into the team. + * @param tutorialTeam to allocate the student into. + */ + public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam); } diff --git a/src/main/java/seedu/address/model/ModelManager.java b/src/main/java/seedu/address/model/ModelManager.java index 89114f11e07..19388575c36 100644 --- a/src/main/java/seedu/address/model/ModelManager.java +++ b/src/main/java/seedu/address/model/ModelManager.java @@ -11,9 +11,8 @@ import javafx.collections.transformation.FilteredList; import seedu.address.commons.core.GuiSettings; import seedu.address.commons.core.LogsCenter; -import seedu.address.model.module.ModuleCode; -import seedu.address.model.module.TutorialClass; -import seedu.address.model.person.Person; +import seedu.address.model.module.*; +import seedu.address.model.person.*; /** @@ -98,6 +97,25 @@ public boolean hasPerson(Person person) { requireNonNull(person); return addressBook.hasPerson(person); } + + @Override + public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + requireAllNonNull(tutorialClass, tutorialTeam); + return addressBook.hasTeamInTutorial(tutorialClass, tutorialTeam); + } + + @Override + public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { + requireAllNonNull(studentId, tutorialClass); + return addressBook.isStudentInAnyTeam(studentId, tutorialClass); + } + + @Override + public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { + requireAllNonNull(studentId, tutorialTeam); + addressBook.allocateStudentToTeam(studentId, tutorialTeam); + } + @Override public ModuleCode findModuleFromList(ModuleCode module) { requireNonNull(module); diff --git a/src/main/java/seedu/address/model/module/TutorialClass.java b/src/main/java/seedu/address/model/module/TutorialClass.java index ad99f458234..589348ef8ee 100644 --- a/src/main/java/seedu/address/model/module/TutorialClass.java +++ b/src/main/java/seedu/address/model/module/TutorialClass.java @@ -157,7 +157,16 @@ public void addTeam(TutorialTeam team) { * @param team */ public boolean hasTeam(TutorialTeam team) { - return teams.contains(team); + if (teams.contains(team)) { + return true; + } + for (TutorialTeam tutorialTeam : teams) { + if (tutorialTeam.getTeamName().equals(team.getTeamName())) { + return true; + } + }; + + return false; } @Override diff --git a/src/main/java/seedu/address/model/module/TutorialTeam.java b/src/main/java/seedu/address/model/module/TutorialTeam.java index 2410237e59e..677fba8775d 100644 --- a/src/main/java/seedu/address/model/module/TutorialTeam.java +++ b/src/main/java/seedu/address/model/module/TutorialTeam.java @@ -5,7 +5,8 @@ import java.util.ArrayList; -import seedu.address.model.person.Person; +import javafx.collections.*; +import seedu.address.model.person.*; /** * Represents a Module's tutorial team. @@ -176,6 +177,19 @@ public boolean hasStudent(Person student) { return students.contains(student); } + + /** + * Checks if the student is in the tutorial team. + * @param studentId to check with. + * @return true if the student is in the tutorial class + */ + public boolean hasStudentVerified(StudentId studentId) { + ObservableList obList = FXCollections.observableList(students); + return obList.stream().anyMatch(person -> person.getStudentId().isSameStudentId(studentId)); + } + + + @Override public String toString() { return teamName; diff --git a/src/main/java/seedu/address/model/person/StudentId.java b/src/main/java/seedu/address/model/person/StudentId.java index b7a09a46b1b..3dbcb8a4b23 100644 --- a/src/main/java/seedu/address/model/person/StudentId.java +++ b/src/main/java/seedu/address/model/person/StudentId.java @@ -38,6 +38,16 @@ public static boolean isValidStudentId(String test) { return test.matches(VALIDATION_REGEX); } + /** + * Returns true if 2 student ids are identical to {@code studentId} id value. + * @param studentId + * @return boolean if they are identical. + */ + public boolean isSameStudentId(StudentId studentId) { + requireNonNull(studentId); + return this.value.equals(studentId.value); + } + @Override public String toString() { return value; diff --git a/src/main/java/seedu/address/model/person/UniquePersonList.java b/src/main/java/seedu/address/model/person/UniquePersonList.java index 1287447aeff..7cd4693d39e 100644 --- a/src/main/java/seedu/address/model/person/UniquePersonList.java +++ b/src/main/java/seedu/address/model/person/UniquePersonList.java @@ -36,6 +36,18 @@ public boolean contains(Person toCheck) { return internalList.stream().anyMatch(toCheck::isSamePerson); } + /** + * Return the Person object if the list contains the person with {@code studentId} + */ + public Person getPerson(StudentId studentId) { + requireNonNull(studentId); + Person personMatch = internalList.stream() + .filter(person -> person.getStudentId().isSameStudentId(studentId)) + .findFirst() + .orElse(null); + return personMatch; + } + /** * Adds a person to the list. * The person must not already exist in the list. From 9d3dfaa9b378612917ff675fa05ab8e5ecda6aeb Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Wed, 27 Mar 2024 16:13:00 +0800 Subject: [PATCH 05/12] Update Allocate Student Command --- docs/diagrams/ModelClassDiagram.puml | 42 +++-- .../logic/commands/DeleteClassCommand.java | 13 +- .../logic/commands/DeleteModuleCommand.java | 74 ++++++++ .../logic/commands/DeleteTeamCommand.java | 116 ++++++++++++ .../address/logic/commands/EditCommand.java | 22 ++- .../AddStudentToClassByIndexCommand.java | 2 +- .../DeleteStudentFromClassByEmailCommand.java | 80 +++++++++ .../DeleteStudentFromClassByIdCommand.java | 78 ++++++++ .../DeleteStudentFromClassByIndexCommand.java | 77 ++++++++ .../DeleteStudentFromClassCommand.java | 69 ++++++++ .../logic/messages/ModuleMessages.java | 2 + .../logic/messages/PersonMessages.java | 2 + .../logic/messages/TutorialClassMessages.java | 2 + .../logic/parser/AddTeamCommandParser.java | 22 +-- .../logic/parser/AddressBookParser.java | 12 ++ .../parser/DeleteClassCommandParser.java | 24 ++- .../parser/DeleteModuleCommandParser.java | 46 +++++ .../DeleteStudentFromClassCommandParser.java | 76 ++++++++ .../logic/parser/DeleteTeamCommandParser.java | 49 +++++ .../logic/parser/EditCommandParser.java | 13 +- .../java/seedu/address/model/AddressBook.java | 75 ++++---- src/main/java/seedu/address/model/Model.java | 26 +-- .../seedu/address/model/ModelManager.java | 24 +-- .../address/model/module/TutorialClass.java | 8 + .../address/model/module/TutorialTeam.java | 33 +--- .../logic/commands/AddStudentCommandTest.java | 22 +++ .../AddTeamCommandIntegrationTest.java | 12 +- .../commands/DeleteClassCommandTest.java | 8 +- .../commands/DeleteModuleCommandTest.java | 74 ++++++++ .../commands/DeleteStudentCommandTest.java | 2 +- ...tudentFromClassCommandIntegrationTest.java | 118 +++++++++++++ .../DeleteStudentFromClassCommandTest.java | 167 ++++++++++++++++++ .../DeleteTeamCommandIntegrationTest.java | 76 ++++++++ .../logic/commands/DeleteTeamCommandTest.java | 52 ++++++ .../logic/commands/EditCommandTest.java | 94 ++++++++++ .../logic/parser/AddressBookParserTest.java | 40 ++++- .../parser/DeleteModuleCommandParserTest.java | 46 +++++ ...leteStudentFromClassCommandParserTest.java | 50 ++++++ .../parser/DeleteTeamCommandParserTest.java | 54 ++++++ .../logic/parser/EditCommandParserTest.java | 66 +++---- .../seedu/address/model/AddressBookTest.java | 48 +++++ .../seedu/address/model/ModelManagerTest.java | 16 ++ 42 files changed, 1729 insertions(+), 203 deletions(-) create mode 100644 src/main/java/seedu/address/logic/commands/DeleteModuleCommand.java create mode 100644 src/main/java/seedu/address/logic/commands/DeleteTeamCommand.java create mode 100644 src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByEmailCommand.java create mode 100644 src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByIdCommand.java create mode 100644 src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByIndexCommand.java create mode 100644 src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassCommand.java create mode 100644 src/main/java/seedu/address/logic/parser/DeleteModuleCommandParser.java create mode 100644 src/main/java/seedu/address/logic/parser/DeleteStudentFromClassCommandParser.java create mode 100644 src/main/java/seedu/address/logic/parser/DeleteTeamCommandParser.java create mode 100644 src/test/java/seedu/address/logic/commands/DeleteModuleCommandTest.java create mode 100644 src/test/java/seedu/address/logic/commands/DeleteStudentFromClassCommandIntegrationTest.java create mode 100644 src/test/java/seedu/address/logic/commands/DeleteStudentFromClassCommandTest.java create mode 100644 src/test/java/seedu/address/logic/commands/DeleteTeamCommandIntegrationTest.java create mode 100644 src/test/java/seedu/address/logic/commands/DeleteTeamCommandTest.java create mode 100644 src/test/java/seedu/address/logic/parser/DeleteModuleCommandParserTest.java create mode 100644 src/test/java/seedu/address/logic/parser/DeleteStudentFromClassCommandParserTest.java create mode 100644 src/test/java/seedu/address/logic/parser/DeleteTeamCommandParserTest.java diff --git a/docs/diagrams/ModelClassDiagram.puml b/docs/diagrams/ModelClassDiagram.puml index 0de5673070d..c3fd832fdef 100644 --- a/docs/diagrams/ModelClassDiagram.puml +++ b/docs/diagrams/ModelClassDiagram.puml @@ -12,14 +12,21 @@ Class AddressBook Class ModelManager Class UserPrefs +Class ModuleCode +Class ModuleContainsKeywordPredicate +Class ModuleTutorialPair +Class TutorialClass +Class TutorialContainsKeywordPredicate +Class Tag + Class UniquePersonList Class Person -Class Address -Class Email Class Name -Class Phone -Class Tag - +Class Email +Class StudentId +Class NameContainsKeywordPredicate +Class EmailContainsKeywordPredicate +Class StudentIdContainsKeywordPredicate Class I #FFFFFF } @@ -35,20 +42,27 @@ ModelManager -left-> "1" AddressBook ModelManager -right-> "1" UserPrefs UserPrefs .up.|> ReadOnlyUserPrefs +ModelManager *-left> "~* filtered" ModuleCode +AddressBook -left> "~* all" ModuleCode +ModuleCode -up> TutorialClass +ModuleTutorialPair -> ModuleCode +ModuleTutorialPair -down> TutorialClass +ModuleContainsKeywordPredicate -..down> ModuleCode +TutorialContainsKeywordPredicate -..up> TutorialClass +TutorialClass -> Person + AddressBook *--> "1" UniquePersonList UniquePersonList --> "~* all" Person -Person *--> Name -Person *--> Phone -Person *--> Email -Person *--> Address -Person *--> "*" Tag - +Person *--> "1" Name +Person *--> "1" Email +Person *--> "1" StudentId +Person *--> Tag Person -[hidden]up--> I UniquePersonList -[hidden]right-> I -Name -[hidden]right-> Phone -Phone -[hidden]right-> Address -Address -[hidden]right-> Email +NameContainsKeywordPredicate -..> Name +StudentIdContainsKeywordPredicate -left..> StudentId +EmailContainsKeywordPredicate -right..> Email ModelManager --> "~* filtered" Person @enduml diff --git a/src/main/java/seedu/address/logic/commands/DeleteClassCommand.java b/src/main/java/seedu/address/logic/commands/DeleteClassCommand.java index beeb506a5ae..771a3119b5a 100644 --- a/src/main/java/seedu/address/logic/commands/DeleteClassCommand.java +++ b/src/main/java/seedu/address/logic/commands/DeleteClassCommand.java @@ -6,6 +6,7 @@ import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.logic.messages.ModuleMessages; import seedu.address.model.Model; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; @@ -32,7 +33,7 @@ public class DeleteClassCommand extends Command { /** * Constructs a DeleteClassCommand to delete the specified {@code TutorialClass} * from the specified {@code ModuleCode}. - * @param module The module code of the tutorial class to be deleted. + * @param module The module code of the tutorial class to be deleted. * @param tutorialClass The tutorial class to be deleted. */ public DeleteClassCommand(ModuleCode module, TutorialClass tutorialClass) { @@ -47,12 +48,13 @@ public CommandResult execute(Model model) throws CommandException { ModuleCode existingModule = model.findModuleFromList(module); if (existingModule == null) { - String moduleNotFoundMessage = String.format(MESSAGE_MODULE_NOT_FOUND, module); + String moduleNotFoundMessage = String.format(ModuleMessages.MESSAGE_MODULE_NOT_FOUND, module); throw new CommandException(moduleNotFoundMessage); } if (!(existingModule.hasTutorialClass(tutorialString))) { - String classNotFoundMessage = String.format(MESSAGE_CLASS_NOT_FOUND, module, tutorialString); + String classNotFoundMessage = String.format(ModuleMessages.MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE, + tutorialString, module); String tutorialList = existingModule.listTutorialClasses(); throw new CommandException(classNotFoundMessage + "\n" + tutorialList); } else { @@ -63,8 +65,9 @@ public CommandResult execute(Model model) throws CommandException { } /** - * Generates a command execution success message based on whether the tutorial class is successfully deleted. - * @param module The module code of the tutorial class. + * Generates a command execution success message based on whether the tutorial + * class is successfully deleted. + * @param module The module code of the tutorial class. * @param tutorialString The tutorial class. * @return The success message. */ diff --git a/src/main/java/seedu/address/logic/commands/DeleteModuleCommand.java b/src/main/java/seedu/address/logic/commands/DeleteModuleCommand.java new file mode 100644 index 00000000000..ba4725fa9a4 --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/DeleteModuleCommand.java @@ -0,0 +1,74 @@ +package seedu.address.logic.commands; + +import static java.util.Objects.requireNonNull; +import static seedu.address.commons.util.CollectionUtil.requireAllNonNull; +import static seedu.address.logic.messages.ModuleMessages.MESSAGE_DELETE_MODULE_SUCCESS; +import static seedu.address.logic.messages.ModuleMessages.MESSAGE_MODULE_NOT_FOUND; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; + +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; + +/** + * A class used to handle the deletion of tutorial classes. + */ +public class DeleteModuleCommand extends Command { + + public static final String COMMAND_WORD = "/delete_module"; + + public static final String MESSAGE_USAGE = COMMAND_WORD + + ": Deletes a module with the module code specified\n" + + "Parameters:" + PREFIX_MODULECODE + "MODULE_CODE\n" + + "Example: " + COMMAND_WORD + " " + PREFIX_MODULECODE + " CS2103T"; + + private final ModuleCode module; + + /** + * Constructs a DeleteClassCommand to delete the specified {@code TutorialClass} + * from the specified {@code ModuleCode}. + * @param module The module code of the tutorial class to be deleted. + */ + public DeleteModuleCommand(ModuleCode module) { + requireAllNonNull(module); + this.module = module; + } + + @Override + public CommandResult execute(Model model) throws CommandException { + requireNonNull(model); + + ModuleCode existingModule = model.findModuleFromList(module); + if (existingModule == null) { + String moduleNotFoundMessage = String.format(MESSAGE_MODULE_NOT_FOUND, module); + throw new CommandException(moduleNotFoundMessage); + } else { + model.deleteModule(existingModule); + } + return new CommandResult(generateSuccessMessage(module)); + } + + /** + * Generates a command execution success message based on whether the tutorial class is successfully deleted. + * @param module The module code of the tutorial class. + * @return The success message. + */ + private String generateSuccessMessage(ModuleCode module) { + return String.format(MESSAGE_DELETE_MODULE_SUCCESS, module.toString()); + } + + @Override + public boolean equals(Object other) { + if (other == this) { + return true; + } + + // instanceof handles nulls + if (!(other instanceof DeleteModuleCommand)) { + return false; + } + + DeleteModuleCommand e = (DeleteModuleCommand) other; + return module.equals(e.module); + } +} diff --git a/src/main/java/seedu/address/logic/commands/DeleteTeamCommand.java b/src/main/java/seedu/address/logic/commands/DeleteTeamCommand.java new file mode 100644 index 00000000000..763b952bcfb --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/DeleteTeamCommand.java @@ -0,0 +1,116 @@ +package seedu.address.logic.commands; + +import static java.util.Objects.requireNonNull; +import static seedu.address.commons.util.CollectionUtil.requireAllNonNull; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CliSyntax.PREFIX_NAME; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; + +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.logic.messages.ModuleMessages; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.ModuleTutorialPair; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; + +/** + * A class used to handle the deletion of tutorial team. + */ +public class DeleteTeamCommand extends Command { + public static final String MESSAGE_DELETE_TEAM_SUCCESS = "Removed %1$s from %2$s %3$s!"; + public static final String MESSAGE_TEAM_NOT_FOUND = "%1$s not in %2$s %3$s!"; + public static final String COMMAND_WORD = "/delete_team"; + + public static final String MESSAGE_USAGE = COMMAND_WORD + + ": Deletes a team from the tutorial class specified\n" + + "Parameters:" + PREFIX_MODULECODE + "MODULE_CODE " + + PREFIX_TUTORIALCLASS + "TUTORIAL_CLASS " + PREFIX_NAME + "TEAM_NAME\n" + + "Example: " + COMMAND_WORD + " " + PREFIX_MODULECODE + " CS2103T " + + PREFIX_TUTORIALCLASS + "T09 " + PREFIX_NAME + "Team 1"; + + private final ModuleCode module; + private final TutorialClass tutorialClass; + private final TutorialTeam team; + + /** + * Constructs a DeleteTeamCommand to delete the specified {@code TutorialTeam} + * from the specified {@code ModuleCode} and {@code TutorialClass}. + * @param module The module code of the tutorial class to be deleted. + * @param tutorialClass The tutorial class to be deleted. + * @param teamName The name of the team to be deleted. + */ + public DeleteTeamCommand(ModuleCode module, TutorialClass tutorialClass, String teamName) { + requireAllNonNull(module, tutorialClass, teamName); + this.module = module; + this.tutorialClass = tutorialClass; + this.team = new TutorialTeam(teamName); + } + + @Override + public CommandResult execute(Model model) throws CommandException { + requireNonNull(model); + + ModuleTutorialPair moduleAndTutorialClass = getModuleAndTutorialClass(model); + ModuleCode module = moduleAndTutorialClass.getModule(); + TutorialClass tutorialClass = moduleAndTutorialClass.getTutorialClass(); + if (tutorialClass.hasTeam(team)) { + tutorialClass.deleteTeam(team); + } else { + throw new CommandException(String.format(MESSAGE_TEAM_NOT_FOUND, team, module, tutorialClass)); + } + + return new CommandResult(generateSuccessMessage(module, tutorialClass, team)); + } + + protected ModuleTutorialPair getModuleAndTutorialClass(Model model) throws CommandException { + requireNonNull(model); + ModuleCode module = getModule(); + TutorialClass tutorialClass = getTutorialClass(); + ModuleCode existingModule = model.findModuleFromList(module); + TutorialClass existingTutorialClass = model.findTutorialClassFromList(tutorialClass, existingModule); + if (existingModule == null) { + throw new CommandException(String.format(ModuleMessages.MESSAGE_MODULE_NOT_FOUND, module)); + } + if (existingTutorialClass == null) { + throw new CommandException( + String.format(ModuleMessages.MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE, tutorialClass, module)); + } + return new ModuleTutorialPair(existingModule, existingTutorialClass); + } + + protected ModuleCode getModule() { + return module; + } + + protected TutorialClass getTutorialClass() { + return tutorialClass; + } + + /** + * Generates a command execution success message based on whether the tutorial + * team is successfully deleted. + * @param module The module code of the tutorial class. + * @param tutorialString The tutorial class. + * @param team The team to be deleted. + * @return The success message. + */ + private String generateSuccessMessage(ModuleCode module, TutorialClass tutorialString, TutorialTeam team) { + return String.format(MESSAGE_DELETE_TEAM_SUCCESS, team, module, tutorialString); + } + + @Override + public boolean equals(Object other) { + if (other == this) { + return true; + } + + // instanceof handles nulls + if (!(other instanceof DeleteTeamCommand)) { + return false; + } + + DeleteTeamCommand e = (DeleteTeamCommand) other; + return module.equals(e.module) && tutorialClass.equals(e.tutorialClass) && team.equals(e.team); + } +} diff --git a/src/main/java/seedu/address/logic/commands/EditCommand.java b/src/main/java/seedu/address/logic/commands/EditCommand.java index 90f559fb985..e2484c74cf8 100644 --- a/src/main/java/seedu/address/logic/commands/EditCommand.java +++ b/src/main/java/seedu/address/logic/commands/EditCommand.java @@ -2,6 +2,7 @@ import static java.util.Objects.requireNonNull; import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; +import static seedu.address.logic.parser.CliSyntax.PREFIX_INDEX; import static seedu.address.logic.parser.CliSyntax.PREFIX_NAME; import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; import static seedu.address.logic.parser.CliSyntax.PREFIX_TAG; @@ -31,23 +32,26 @@ */ public class EditCommand extends Command { - public static final String COMMAND_WORD = "edit"; + public static final String COMMAND_WORD = "/edit_student"; public static final String MESSAGE_USAGE = COMMAND_WORD + ": Edits the details of the person identified " + "by the index number used in the displayed person list. " + "Existing values will be overwritten by the input values.\n" - + "Parameters: INDEX (must be a positive integer) " + + "Parameters: " + + PREFIX_INDEX + "INDEX (must be a positive integer) " + "[" + PREFIX_NAME + "NAME] " - + "[" + PREFIX_STUDENTID + "PHONE] " + + "[" + PREFIX_STUDENTID + "STUDENT ID] " + "[" + PREFIX_EMAIL + "EMAIL] " + "[" + PREFIX_TAG + "TAG]...\n" + "Example: " + COMMAND_WORD + " 1 " - + PREFIX_STUDENTID + "91234567 " + + PREFIX_STUDENTID + "A1234567Z " + PREFIX_EMAIL + "johndoe@example.com"; public static final String MESSAGE_EDIT_PERSON_SUCCESS = "Edited Person: %1$s"; public static final String MESSAGE_NOT_EDITED = "At least one field to edit must be provided."; public static final String MESSAGE_DUPLICATE_PERSON = "This person already exists in the address book."; + public static final String MESSAGE_DUPLICATE_EMAIL = "This email already exists in the address book."; + public static final String MESSAGE_DUPLICATE_STUDENTID = "This student id already exists in the address book."; private final Index index; private final EditPersonDescriptor editPersonDescriptor; @@ -80,6 +84,16 @@ public CommandResult execute(Model model) throws CommandException { throw new CommandException(MESSAGE_DUPLICATE_PERSON); } + Optional emailToBeEdited = editPersonDescriptor.getEmail(); + if (emailToBeEdited.isPresent() && model.hasPersonWithEmail(emailToBeEdited.get())) { + throw new CommandException(MESSAGE_DUPLICATE_EMAIL); + } + + Optional studentIdToBeEdited = editPersonDescriptor.getStudentId(); + if (studentIdToBeEdited.isPresent() && model.hasPersonWithStudentId(studentIdToBeEdited.get())) { + throw new CommandException(MESSAGE_DUPLICATE_STUDENTID); + } + model.setPerson(personToEdit, editedPerson); model.updateFilteredPersonList(PREDICATE_SHOW_ALL_PERSONS); return new CommandResult(String.format(MESSAGE_EDIT_PERSON_SUCCESS, Messages.format(editedPerson))); diff --git a/src/main/java/seedu/address/logic/commands/addstudenttoclasscommands/AddStudentToClassByIndexCommand.java b/src/main/java/seedu/address/logic/commands/addstudenttoclasscommands/AddStudentToClassByIndexCommand.java index 283be417bdd..3ae352cbfcb 100644 --- a/src/main/java/seedu/address/logic/commands/addstudenttoclasscommands/AddStudentToClassByIndexCommand.java +++ b/src/main/java/seedu/address/logic/commands/addstudenttoclasscommands/AddStudentToClassByIndexCommand.java @@ -65,7 +65,7 @@ public boolean equals(Object other) { return true; } - if (!(other instanceof AddStudentToClassByIdCommand)) { + if (!(other instanceof AddStudentToClassByIndexCommand)) { return false; } diff --git a/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByEmailCommand.java b/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByEmailCommand.java new file mode 100644 index 00000000000..c56a36050b2 --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByEmailCommand.java @@ -0,0 +1,80 @@ +package seedu.address.logic.commands.deletestudentfromclasscommands; + +import static java.util.Objects.requireNonNull; + +import java.util.function.Predicate; + +import seedu.address.logic.Messages; +import seedu.address.logic.commands.CommandResult; +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.logic.messages.PersonMessages; +import seedu.address.logic.messages.TutorialClassMessages; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.ModuleTutorialPair; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Email; +import seedu.address.model.person.Person; + +/** + * Deletes a student from a specified tutorial class, by identifying + * the student via their email. + */ +public class DeleteStudentFromClassByEmailCommand extends DeleteStudentFromClassCommand { + private final Predicate predicate; + + private final Email email; + + /** + * Deletes a student from a class by email. + * @param email + * @param module + * @param tutorialClass + */ + public DeleteStudentFromClassByEmailCommand(Email email, ModuleCode module, TutorialClass tutorialClass) { + super(module, tutorialClass); + this.email = email; + this.predicate = person -> person.getEmail().equals(email); + } + + @Override + public CommandResult execute(Model model) throws CommandException { + requireNonNull(model); + ModuleTutorialPair moduleAndTutorialClass = getModuleAndTutorialClass(model); + TutorialClass tutorialClass = moduleAndTutorialClass.getTutorialClass(); + ModuleCode module = moduleAndTutorialClass.getModule(); + Person personToDelete; + + personToDelete = model.searchPersonByPredicate(predicate); + if (personToDelete == null) { + throw new CommandException(String.format(PersonMessages.MESSAGE_PERSON_EMAIL_NOT_FOUND, email)); + } + if (!(tutorialClass.hasStudent(personToDelete))) { + throw new CommandException( + String.format(TutorialClassMessages.MESSAGE_STUDENT_NOT_FOUND_IN_CLASS, + Messages.format(personToDelete), tutorialClass)); + } else { + model.deletePersonFromTutorialClass(personToDelete, module, tutorialClass); + return new CommandResult( + String.format(TutorialClassMessages.MESSAGE_DELETE_STUDENT_FROM_CLASS_SUCCESS, + Messages.format(personToDelete), module, tutorialClass)); + } + } + + /** + * Returns true if both DeleteStudentFromClassByEmailCommand have the same email. + */ + @Override + public boolean equals(Object other) { + if (other == this) { + return true; + } + + if (!(other instanceof DeleteStudentFromClassByEmailCommand)) { + return false; + } + + DeleteStudentFromClassByEmailCommand otherDeleteCommand = (DeleteStudentFromClassByEmailCommand) other; + return email.equals(otherDeleteCommand.email); + } +} diff --git a/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByIdCommand.java b/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByIdCommand.java new file mode 100644 index 00000000000..cffff4e9438 --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByIdCommand.java @@ -0,0 +1,78 @@ +package seedu.address.logic.commands.deletestudentfromclasscommands; + +import static java.util.Objects.requireNonNull; + +import java.util.function.Predicate; + +import seedu.address.logic.Messages; +import seedu.address.logic.commands.CommandResult; +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.logic.messages.PersonMessages; +import seedu.address.logic.messages.TutorialClassMessages; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.ModuleTutorialPair; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Person; +import seedu.address.model.person.StudentId; + +/** + * Deletes a student from a specified tutorial class, by identifying + * the student via their Student ID. + */ +public class DeleteStudentFromClassByIdCommand extends DeleteStudentFromClassCommand { + + private final Predicate predicate; + + private final StudentId studentId; + + /** + * Deletes a student from a class by student id. + * @param studentId + * @param module + * @param tutorialClass + */ + public DeleteStudentFromClassByIdCommand(StudentId studentId, ModuleCode module, TutorialClass tutorialClass) { + super(module, tutorialClass); + this.studentId = studentId; + this.predicate = person -> person.getStudentId().equals(studentId); + } + + @Override + public CommandResult execute(Model model) throws CommandException { + requireNonNull(model); + ModuleTutorialPair moduleAndTutorialClass = getModuleAndTutorialClass(model); + ModuleCode module = moduleAndTutorialClass.getModule(); + TutorialClass tutorialClass = moduleAndTutorialClass.getTutorialClass(); + Person personToDelete; + personToDelete = model.searchPersonByPredicate(predicate); + if (personToDelete == null) { + throw new CommandException(String.format(PersonMessages.MESSAGE_PERSON_STUDENT_ID_NOT_FOUND, studentId)); + } + if (!(tutorialClass.hasStudent(personToDelete))) { + throw new CommandException(String.format(TutorialClassMessages.MESSAGE_STUDENT_NOT_FOUND_IN_CLASS, + Messages.format(personToDelete), tutorialClass)); + } else { + model.deletePersonFromTutorialClass(personToDelete, module, tutorialClass); + return new CommandResult(String.format(PersonMessages.MESSAGE_DELETE_STUDENT_FROM_CLASS_SUCCESS, + Messages.format(personToDelete), module, tutorialClass)); + } + } + + /** + * Returns true if both DeleteStudentFromClassByIdCommand have the same studentId. + */ + @Override + public boolean equals(Object other) { + if (other == this) { + return true; + } + + if (!(other instanceof DeleteStudentFromClassByIdCommand)) { + return false; + } + + DeleteStudentFromClassByIdCommand otherDeleteCommand = (DeleteStudentFromClassByIdCommand) other; + return studentId.equals(otherDeleteCommand.studentId); + } +} diff --git a/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByIndexCommand.java b/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByIndexCommand.java new file mode 100644 index 00000000000..b9a558b6b0d --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassByIndexCommand.java @@ -0,0 +1,77 @@ +package seedu.address.logic.commands.deletestudentfromclasscommands; + +import static java.util.Objects.requireNonNull; + +import seedu.address.commons.core.index.Index; +import seedu.address.logic.Messages; +import seedu.address.logic.commands.CommandResult; +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.logic.messages.PersonMessages; +import seedu.address.logic.messages.TutorialClassMessages; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.ModuleTutorialPair; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Person; + + +/** + * Deletes a student from a specified tutorial class, by identifying + * the student via their index. + */ +public class DeleteStudentFromClassByIndexCommand extends DeleteStudentFromClassCommand { + private final Index targetIndex; + + /** + * Deletes a student from a class by index. + * @param targetIndex + * @param module + * @param tutorialClass + */ + public DeleteStudentFromClassByIndexCommand(Index targetIndex, ModuleCode module, TutorialClass tutorialClass) { + super(module, tutorialClass); + this.targetIndex = targetIndex; + } + + @Override + public CommandResult execute(Model model) throws CommandException { + requireNonNull(model); + ModuleTutorialPair moduleAndTutorialClass = getModuleAndTutorialClass(model); + TutorialClass tutorialClass = moduleAndTutorialClass.getTutorialClass(); + ModuleCode module = moduleAndTutorialClass.getModule(); + Person personToDelete; + try { + personToDelete = model.getFilteredPersonList().get(targetIndex.getZeroBased()); + } catch (IndexOutOfBoundsException e) { + throw new CommandException( + String.format(PersonMessages.MESSAGE_PERSON_INDEX_NOT_FOUND, targetIndex.getOneBased())); + } + + if (!(tutorialClass.hasStudent(personToDelete))) { + throw new CommandException(String.format(TutorialClassMessages.MESSAGE_STUDENT_NOT_FOUND_IN_CLASS, + Messages.format(personToDelete), tutorialClass)); + } else { + model.deletePersonFromTutorialClass(personToDelete, module, tutorialClass); + return new CommandResult( + String.format(PersonMessages.MESSAGE_DELETE_STUDENT_FROM_CLASS_SUCCESS, + Messages.format(personToDelete), module, tutorialClass)); + } + } + + /** + * Returns true if both DeleteStudentFromClassByIndexCommand have the same index. + */ + @Override + public boolean equals(Object other) { + if (other == this) { + return true; + } + + if (!(other instanceof DeleteStudentFromClassByIndexCommand)) { + return false; + } + + DeleteStudentFromClassByIndexCommand otherDeleteCommand = (DeleteStudentFromClassByIndexCommand) other; + return targetIndex.equals(otherDeleteCommand.targetIndex); + } +} diff --git a/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassCommand.java b/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassCommand.java new file mode 100644 index 00000000000..f8ca13b1a25 --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/deletestudentfromclasscommands/DeleteStudentFromClassCommand.java @@ -0,0 +1,69 @@ +package seedu.address.logic.commands.deletestudentfromclasscommands; + +import static java.util.Objects.requireNonNull; +import static seedu.address.commons.util.CollectionUtil.requireAllNonNull; +import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; + +import seedu.address.logic.commands.Command; +import seedu.address.logic.commands.CommandResult; +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.logic.messages.ModuleMessages; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.ModuleTutorialPair; +import seedu.address.model.module.TutorialClass; + +/** + * The abstract class that handles all delete student from tutorial class commands. + */ +public abstract class DeleteStudentFromClassCommand extends Command { + public static final String COMMAND_WORD = "/delete_student_from_class"; + + public static final String MESSAGE_USAGE = COMMAND_WORD + ": Deletes a student from an existing class\n" + + "Parameters:" + "IDENTIFIER " + PREFIX_MODULECODE + "MODULE_CODE (must be a String) " + + PREFIX_TUTORIALCLASS + "TUTORIAL_CLASS (must be a String)\n" + + "Example: " + COMMAND_WORD + " " + PREFIX_EMAIL + "test@gmail.com " + PREFIX_MODULECODE + " CS2103T " + + PREFIX_TUTORIALCLASS + "T09"; + + private final ModuleCode module; + private final TutorialClass tutorialClass; + + /** + * @param module of the tutorial class to be added + */ + public DeleteStudentFromClassCommand(ModuleCode module, TutorialClass tutorialClass) { + requireAllNonNull(module, tutorialClass); + this.module = module; + this.tutorialClass = tutorialClass; + } + + protected ModuleTutorialPair getModuleAndTutorialClass(Model model) throws CommandException { + requireNonNull(model); + ModuleCode module = getModule(); + TutorialClass tutorialClass = getTutorialClass(); + ModuleCode existingModule = model.findModuleFromList(module); + TutorialClass existingTutorialClass = model.findTutorialClassFromList(tutorialClass, existingModule); + if (existingModule == null) { + throw new CommandException(String.format(ModuleMessages.MESSAGE_MODULE_NOT_FOUND, module)); + } + if (existingTutorialClass == null) { + throw new CommandException( + String.format(ModuleMessages.MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE, tutorialClass, module)); + } + return new ModuleTutorialPair(existingModule, existingTutorialClass); + } + + protected ModuleCode getModule() { + return module; + } + + protected TutorialClass getTutorialClass() { + return tutorialClass; + } + + public abstract CommandResult execute(Model model) throws CommandException; + + public abstract boolean equals(Object other); +} diff --git a/src/main/java/seedu/address/logic/messages/ModuleMessages.java b/src/main/java/seedu/address/logic/messages/ModuleMessages.java index c73bf1ec2f1..e3824abda33 100644 --- a/src/main/java/seedu/address/logic/messages/ModuleMessages.java +++ b/src/main/java/seedu/address/logic/messages/ModuleMessages.java @@ -8,4 +8,6 @@ public class ModuleMessages { + "does not exist in the address book"; public static final String MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE = "The tutorial class with tutorial code %s " + "does not belong to the module with module code %s"; + + public static final String MESSAGE_DELETE_MODULE_SUCCESS = "Removed %1$s!"; } diff --git a/src/main/java/seedu/address/logic/messages/PersonMessages.java b/src/main/java/seedu/address/logic/messages/PersonMessages.java index f3c2061b8ea..3035ca43a05 100644 --- a/src/main/java/seedu/address/logic/messages/PersonMessages.java +++ b/src/main/java/seedu/address/logic/messages/PersonMessages.java @@ -11,5 +11,7 @@ public class PersonMessages { public static final String MESSAGE_PERSON_INDEX_NOT_FOUND = "The student at index %s " + "does not exist in the address book"; public static final String MESSAGE_ADD_STUDENT_TO_CLASS_SUCCESS = "Added student %1$s to %2$s %3$s"; + + public static final String MESSAGE_DELETE_STUDENT_FROM_CLASS_SUCCESS = "Deleted student %1$s from %2$s %3$s"; public static final String MESSAGE_DUPLICATE_STUDENT_IN_CLASS = "%1$s already added to %2$s!"; } diff --git a/src/main/java/seedu/address/logic/messages/TutorialClassMessages.java b/src/main/java/seedu/address/logic/messages/TutorialClassMessages.java index 529b9d0b15a..cfc54fdc2af 100644 --- a/src/main/java/seedu/address/logic/messages/TutorialClassMessages.java +++ b/src/main/java/seedu/address/logic/messages/TutorialClassMessages.java @@ -7,5 +7,7 @@ public class TutorialClassMessages { public static final String MESSAGE_TUTORIAL_CLASS_NOT_FOUND = "The tutorial class with tutorial class code %s " + "does not exist in the address book"; public static final String MESSAGE_DUPLICATE_STUDENT_IN_CLASS = "%1$s already added to %2$s!"; + public static final String MESSAGE_STUDENT_NOT_FOUND_IN_CLASS = "%1$s is not in %2$s!"; public static final String MESSAGE_ADD_STUDENT_TO_CLASS_SUCCESS = "Added student %1$s to %2$s %3$s"; + public static final String MESSAGE_DELETE_STUDENT_FROM_CLASS_SUCCESS = "Deleted student %1$s from %2$s %3$s"; } diff --git a/src/main/java/seedu/address/logic/parser/AddTeamCommandParser.java b/src/main/java/seedu/address/logic/parser/AddTeamCommandParser.java index 5adc660f6d6..c232d177ec0 100644 --- a/src/main/java/seedu/address/logic/parser/AddTeamCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/AddTeamCommandParser.java @@ -36,27 +36,27 @@ public AddTeamCommand parse(String args) throws ParseException { } boolean isTeamSizePresent = argMultimap.getValue(PREFIX_TEAM_SIZE).isPresent(); - String moduleCode = argMultimap.getValue(PREFIX_MODULECODE).orElse(""); - String tutorialClass = argMultimap.getValue(PREFIX_TUTORIALCLASS).orElse(""); + ModuleCode moduleCode = ParserUtil.parseModuleCode(argMultimap.getValue(PREFIX_MODULECODE).get()); + TutorialClass tutorialClass = ParserUtil.parseTutorialClass(argMultimap.getValue(PREFIX_TUTORIALCLASS).get()); String teamName = argMultimap.getValue(PREFIX_NAME).orElse(""); - if (!(ModuleCode.isValidModuleCode(moduleCode))) { - throw new ParseException(ModuleCode.MESSAGE_CONSTRAINTS); - } - if (!(TutorialClass.isValidTutorialClass(tutorialClass))) { - throw new ParseException(TutorialClass.MESSAGE_CONSTRAINTS); - } if (!TutorialTeam.isValidTeamName(teamName)) { throw new ParseException(TutorialTeam.MESSAGE_NAME_CONSTRAINTS); } + if (isTeamSizePresent) { - int teamSize = Integer.parseInt(argMultimap.getValue(PREFIX_TEAM_SIZE).get()); + int teamSize; + try { + teamSize = Integer.parseInt(argMultimap.getValue(PREFIX_TEAM_SIZE).get()); + } catch (NumberFormatException e) { + throw new ParseException(TutorialTeam.MESSAGE_SIZE_CONSTRAINTS); + } if (teamSize <= 0) { throw new ParseException(TutorialTeam.MESSAGE_SIZE_CONSTRAINTS); } - return new AddTeamCommand(new ModuleCode(moduleCode), new TutorialClass(tutorialClass), teamName, teamSize); + return new AddTeamCommand(moduleCode, tutorialClass, teamName, teamSize); } else { - return new AddTeamCommand(new ModuleCode(moduleCode), new TutorialClass(tutorialClass), teamName); + return new AddTeamCommand(moduleCode, tutorialClass, teamName); } } diff --git a/src/main/java/seedu/address/logic/parser/AddressBookParser.java b/src/main/java/seedu/address/logic/parser/AddressBookParser.java index b644f029c2d..c931c111f50 100644 --- a/src/main/java/seedu/address/logic/parser/AddressBookParser.java +++ b/src/main/java/seedu/address/logic/parser/AddressBookParser.java @@ -15,6 +15,8 @@ import seedu.address.logic.commands.Command; import seedu.address.logic.commands.DeleteClassCommand; import seedu.address.logic.commands.DeleteCommand; +import seedu.address.logic.commands.DeleteModuleCommand; +import seedu.address.logic.commands.DeleteTeamCommand; import seedu.address.logic.commands.EditCommand; import seedu.address.logic.commands.ExitCommand; import seedu.address.logic.commands.HelpCommand; @@ -23,6 +25,7 @@ import seedu.address.logic.commands.SearchStudentCommand; import seedu.address.logic.commands.addstudenttoclasscommands.AddStudentToClassCommand; import seedu.address.logic.commands.deletestudentcommands.DeleteStudentCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassCommand; import seedu.address.logic.parser.exceptions.ParseException; /** @@ -75,6 +78,9 @@ public Command parseCommand(String userInput) throws ParseException { case DeleteClassCommand.COMMAND_WORD: return new DeleteClassCommandParser().parse(arguments); + case DeleteModuleCommand.COMMAND_WORD: + return new DeleteModuleCommandParser().parse(arguments); + case DeleteStudentCommand.COMMAND_WORD: return new DeleteStudentCommandParser().parse(arguments); @@ -99,9 +105,15 @@ public Command parseCommand(String userInput) throws ParseException { case AddStudentToClassCommand.COMMAND_WORD: return new AddStudentToClassCommandParser().parse(arguments); + case DeleteStudentFromClassCommand.COMMAND_WORD: + return new DeleteStudentFromClassCommandParser().parse(arguments); + case AddTeamCommand.COMMAND_WORD: return new AddTeamCommandParser().parse(arguments); + case DeleteTeamCommand.COMMAND_WORD: + return new DeleteTeamCommandParser().parse(arguments); + default: logger.finer("This user input caused a ParseException: " + userInput); throw new ParseException(MESSAGE_UNKNOWN_COMMAND); diff --git a/src/main/java/seedu/address/logic/parser/DeleteClassCommandParser.java b/src/main/java/seedu/address/logic/parser/DeleteClassCommandParser.java index b50d8e99918..e52fb517883 100644 --- a/src/main/java/seedu/address/logic/parser/DeleteClassCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/DeleteClassCommandParser.java @@ -12,14 +12,14 @@ import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; - - /** - * Parses input arguments and creates a new {@code DeleteClassCommandParser} object + * Parses input arguments and creates a new {@code DeleteClassCommandParser} + * object */ public class DeleteClassCommandParser implements Parser { /** - * Parses the given {@code String} of arguments in the context of the {@code DeleteClassCommandParser} + * Parses the given {@code String} of arguments in the context of the + * {@code DeleteClassCommandParser} * and returns a {@code DeleteClassCommandParser} object for execution. * @throws ParseException if the user input does not conform the expected format */ @@ -32,18 +32,14 @@ public DeleteClassCommand parse(String args) throws ParseException { throw new ParseException(String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteClassCommand.MESSAGE_USAGE)); } - String moduleCode = argMultimap.getValue(PREFIX_MODULECODE).orElse(""); - String tutorialClass = argMultimap.getValue(PREFIX_TUTORIALCLASS).orElse(""); - if (!(ModuleCode.isValidModuleCode(moduleCode))) { - throw new ParseException(ModuleCode.MESSAGE_CONSTRAINTS); - } - if (!(TutorialClass.isValidTutorialClass(tutorialClass))) { - throw new ParseException(TutorialClass.MESSAGE_CONSTRAINTS); - } - return new DeleteClassCommand(new ModuleCode(moduleCode), new TutorialClass(tutorialClass)); + ModuleCode moduleCode = ParserUtil.parseModuleCode(argMultimap.getValue(PREFIX_MODULECODE).get()); + TutorialClass tutorialClass = ParserUtil.parseTutorialClass(argMultimap.getValue(PREFIX_TUTORIALCLASS).get()); + return new DeleteClassCommand(moduleCode, tutorialClass); } + /** - * Returns true if all the prefixes are present in the given {@code ArgumentMultimap}. + * Returns true if all the prefixes are present in the given + * {@code ArgumentMultimap}. */ private static boolean arePrefixesPresent(ArgumentMultimap argumentMultimap, Prefix... prefixes) { return Stream.of(prefixes).allMatch(prefix -> argumentMultimap.getValue(prefix).isPresent()); diff --git a/src/main/java/seedu/address/logic/parser/DeleteModuleCommandParser.java b/src/main/java/seedu/address/logic/parser/DeleteModuleCommandParser.java new file mode 100644 index 00000000000..67684b5d808 --- /dev/null +++ b/src/main/java/seedu/address/logic/parser/DeleteModuleCommandParser.java @@ -0,0 +1,46 @@ +package seedu.address.logic.parser; + +import static java.util.Objects.requireNonNull; +import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; + +import java.util.stream.Stream; + +import seedu.address.logic.commands.DeleteModuleCommand; +import seedu.address.logic.parser.exceptions.ParseException; +import seedu.address.model.module.ModuleCode; + + + +/** + * Parses input arguments and creates a new {@code DeleteClassCommandParser} object + */ +public class DeleteModuleCommandParser implements Parser { + /** + * Parses the given {@code String} of arguments in the context of the {@code DeleteClassCommandParser} + * and returns a {@code DeleteClassCommandParser} object for execution. + * @throws ParseException if the user input does not conform the expected format + */ + public DeleteModuleCommand parse(String args) throws ParseException { + requireNonNull(args); + ArgumentMultimap argMultimap = ArgumentTokenizer.tokenize(args, PREFIX_MODULECODE); + + if (!arePrefixesPresent(argMultimap, PREFIX_MODULECODE) + || !argMultimap.getPreamble().isEmpty()) { + throw new ParseException(String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteModuleCommand.MESSAGE_USAGE)); + } + + String moduleCode = argMultimap.getValue(PREFIX_MODULECODE).orElse(""); + if (!(ModuleCode.isValidModuleCode(moduleCode))) { + throw new ParseException(ModuleCode.MESSAGE_CONSTRAINTS); + } + return new DeleteModuleCommand(new ModuleCode(moduleCode)); + } + /** + * Returns true if all the prefixes are present in the given {@code ArgumentMultimap}. + */ + private static boolean arePrefixesPresent(ArgumentMultimap argumentMultimap, Prefix... prefixes) { + return Stream.of(prefixes).allMatch(prefix -> argumentMultimap.getValue(prefix).isPresent()); + } +} + diff --git a/src/main/java/seedu/address/logic/parser/DeleteStudentFromClassCommandParser.java b/src/main/java/seedu/address/logic/parser/DeleteStudentFromClassCommandParser.java new file mode 100644 index 00000000000..1a7780dd258 --- /dev/null +++ b/src/main/java/seedu/address/logic/parser/DeleteStudentFromClassCommandParser.java @@ -0,0 +1,76 @@ +package seedu.address.logic.parser; + +import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; +import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; +import static seedu.address.logic.parser.CliSyntax.PREFIX_INDEX; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; + +import java.util.stream.Stream; + +import seedu.address.commons.core.index.Index; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByEmailCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByIdCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByIndexCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassCommand; +import seedu.address.logic.parser.exceptions.ParseException; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Email; +import seedu.address.model.person.StudentId; + +/** + * Parses input arguments and creates a new DeleteStudentFromClassCommand object + */ +public class DeleteStudentFromClassCommandParser implements Parser { + + /** + * Parses the given {@code String} of arguments in the context of the + * DeleteStudentFromClass and returns a DeleteStudentFromClassCommand object for + * execution. + * @throws ParseException if the user input does not conform the expected format + */ + public DeleteStudentFromClassCommand parse(String args) throws ParseException { + ArgumentMultimap argMultimap = ArgumentTokenizer.tokenize(args, PREFIX_INDEX, PREFIX_EMAIL, PREFIX_STUDENTID, + PREFIX_MODULECODE, PREFIX_TUTORIALCLASS); + boolean isIndexPresent = argMultimap.getValue(PREFIX_INDEX).isPresent(); + boolean isEmailPresent = argMultimap.getValue(PREFIX_EMAIL).isPresent(); + boolean isStudentIdPresent = argMultimap.getValue(PREFIX_STUDENTID).isPresent(); + if (!arePrefixesPresent(argMultimap, PREFIX_MODULECODE, PREFIX_TUTORIALCLASS) || (!isIndexPresent + && !isEmailPresent && !isStudentIdPresent) + || !argMultimap.getPreamble().isEmpty()) { + throw new ParseException( + String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteStudentFromClassCommand.MESSAGE_USAGE)); + } + + argMultimap.verifyNoDuplicatePrefixesFor(PREFIX_INDEX, PREFIX_STUDENTID, PREFIX_EMAIL, + PREFIX_MODULECODE, PREFIX_TUTORIALCLASS); + ModuleCode moduleCode = ParserUtil.parseModuleCode(argMultimap.getValue(PREFIX_MODULECODE).get()); + TutorialClass tutorialClass = ParserUtil.parseTutorialClass(argMultimap.getValue(PREFIX_TUTORIALCLASS).get()); + if (isIndexPresent) { + Index index = ParserUtil.parseIndex(argMultimap.getValue(PREFIX_INDEX).get()); + return new DeleteStudentFromClassByIndexCommand(index, moduleCode, tutorialClass); + } else if (isStudentIdPresent) { + StudentId studentId = ParserUtil.parseStudentId(argMultimap.getValue(PREFIX_STUDENTID).get()); + return new DeleteStudentFromClassByIdCommand(studentId, moduleCode, tutorialClass); + } else if (isEmailPresent) { + Email email = ParserUtil.parseEmail(argMultimap.getValue(PREFIX_EMAIL).get()); + return new DeleteStudentFromClassByEmailCommand(email, moduleCode, tutorialClass); + } else { + throw new ParseException( + String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteStudentFromClassCommand.MESSAGE_USAGE)); + } + + } + + /** + * Returns true if none of the prefixes contains empty {@code Optional} values + * in the given + * {@code ArgumentMultimap}. + */ + private static boolean arePrefixesPresent(ArgumentMultimap argumentMultimap, Prefix... prefixes) { + return Stream.of(prefixes).allMatch(prefix -> argumentMultimap.getValue(prefix).isPresent()); + } + +} diff --git a/src/main/java/seedu/address/logic/parser/DeleteTeamCommandParser.java b/src/main/java/seedu/address/logic/parser/DeleteTeamCommandParser.java new file mode 100644 index 00000000000..b29b36a4ba4 --- /dev/null +++ b/src/main/java/seedu/address/logic/parser/DeleteTeamCommandParser.java @@ -0,0 +1,49 @@ +package seedu.address.logic.parser; + +import static java.util.Objects.requireNonNull; +import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CliSyntax.PREFIX_NAME; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; + +import java.util.stream.Stream; + +import seedu.address.logic.commands.DeleteTeamCommand; +import seedu.address.logic.parser.exceptions.ParseException; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; + +/** + * Parses input arguments and creates a new {@code DeleteTeamCommandParser} + * object + */ +public class DeleteTeamCommandParser implements Parser { + /** + * Parses the given {@code String} of arguments in the context of the + * {@code DeleteTeamCommandParser} + * and returns a {@code DeleteTeamCommandParser} object for execution. + * @throws ParseException if the user input does not conform the expected format + */ + public DeleteTeamCommand parse(String args) throws ParseException { + requireNonNull(args); + ArgumentMultimap argMultimap = ArgumentTokenizer.tokenize(args, PREFIX_MODULECODE, PREFIX_TUTORIALCLASS, + PREFIX_NAME); + + if (!arePrefixesPresent(argMultimap, PREFIX_MODULECODE, PREFIX_TUTORIALCLASS, PREFIX_NAME) + || !argMultimap.getPreamble().isEmpty()) { + throw new ParseException(String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteTeamCommand.MESSAGE_USAGE)); + } + ModuleCode moduleCode = ParserUtil.parseModuleCode(argMultimap.getValue(PREFIX_MODULECODE).get()); + TutorialClass tutorialClass = ParserUtil.parseTutorialClass(argMultimap.getValue(PREFIX_TUTORIALCLASS).get()); + String teamName = argMultimap.getValue(PREFIX_NAME).get(); + return new DeleteTeamCommand(moduleCode, tutorialClass, teamName); + } + + /** + * Returns true if all the prefixes are present in the given + * {@code ArgumentMultimap}. + */ + private static boolean arePrefixesPresent(ArgumentMultimap argumentMultimap, Prefix... prefixes) { + return Stream.of(prefixes).allMatch(prefix -> argumentMultimap.getValue(prefix).isPresent()); + } +} diff --git a/src/main/java/seedu/address/logic/parser/EditCommandParser.java b/src/main/java/seedu/address/logic/parser/EditCommandParser.java index f34cce07433..c2213f343eb 100644 --- a/src/main/java/seedu/address/logic/parser/EditCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/EditCommandParser.java @@ -3,6 +3,7 @@ import static java.util.Objects.requireNonNull; import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; +import static seedu.address.logic.parser.CliSyntax.PREFIX_INDEX; import static seedu.address.logic.parser.CliSyntax.PREFIX_NAME; import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; import static seedu.address.logic.parser.CliSyntax.PREFIX_TAG; @@ -31,17 +32,21 @@ public class EditCommandParser implements Parser { public EditCommand parse(String args) throws ParseException { requireNonNull(args); ArgumentMultimap argMultimap = - ArgumentTokenizer.tokenize(args, PREFIX_NAME, PREFIX_EMAIL, PREFIX_STUDENTID, PREFIX_TAG); + ArgumentTokenizer.tokenize(args, PREFIX_INDEX, PREFIX_NAME, PREFIX_EMAIL, PREFIX_STUDENTID, PREFIX_TAG); - Index index; + boolean isIndexPresent = argMultimap.getValue(PREFIX_INDEX).isPresent(); + if (!isIndexPresent) { + throw new ParseException(String.format(MESSAGE_INVALID_COMMAND_FORMAT, EditCommand.MESSAGE_USAGE)); + } + Index index; try { - index = ParserUtil.parseIndex(argMultimap.getPreamble()); + index = ParserUtil.parseIndex(argMultimap.getValue(PREFIX_INDEX).get()); } catch (ParseException pe) { throw new ParseException(String.format(MESSAGE_INVALID_COMMAND_FORMAT, EditCommand.MESSAGE_USAGE), pe); } - argMultimap.verifyNoDuplicatePrefixesFor(PREFIX_NAME, PREFIX_EMAIL, PREFIX_STUDENTID); + argMultimap.verifyNoDuplicatePrefixesFor(PREFIX_INDEX, PREFIX_NAME, PREFIX_EMAIL, PREFIX_STUDENTID); EditPersonDescriptor editPersonDescriptor = new EditPersonDescriptor(); diff --git a/src/main/java/seedu/address/model/AddressBook.java b/src/main/java/seedu/address/model/AddressBook.java index 80945cc6c9b..113ebede187 100644 --- a/src/main/java/seedu/address/model/AddressBook.java +++ b/src/main/java/seedu/address/model/AddressBook.java @@ -1,7 +1,6 @@ package seedu.address.model; import static java.util.Objects.requireNonNull; -import static seedu.address.commons.util.CollectionUtil.requireAllNonNull; import java.util.ArrayList; import java.util.List; @@ -11,8 +10,12 @@ import seedu.address.commons.util.ToStringBuilder; import seedu.address.logic.commands.exceptions.CommandException; import seedu.address.logic.messages.ModuleMessages; -import seedu.address.model.module.*; -import seedu.address.model.person.*; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Email; +import seedu.address.model.person.Person; +import seedu.address.model.person.StudentId; +import seedu.address.model.person.UniquePersonList; /** * Wraps all data at the address-book level @@ -99,38 +102,21 @@ public boolean hasPerson(Person person) { } /** - * Returns true if a team with the same identity as {@code tutorialTeam} exists in the {@code tutorialClass} - * @param tutorialClass of the tutorialTeam. - * @param tutorialTeam to check if it exist. + * Returns true if a person with the same identity as {@code person} exists in + * the address book. */ - public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { - requireAllNonNull(tutorialClass, tutorialTeam); - ArrayList listOfTeams = tutorialClass.getTeams(); - ObservableList teams = FXCollections.observableList(listOfTeams); - return teams.stream().anyMatch(tutorialClass::hasTeam); + public boolean hasPersonWithStudentId(StudentId id) { + requireNonNull(id); + return persons.asUnmodifiableObservableList().stream().anyMatch(s -> s.getStudentId().equals(id)); } /** - * Returns true if the {@code studentId} is already in a team of {@code tutorialClass}. - * @param tutorialClass of the teams. - * @param studentId to search for. - */ - public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { - boolean isStudentExist = false; - for (TutorialTeam tutorialTeam : tutorialClass.getTeams()) { - isStudentExist = tutorialTeam.hasStudentVerified(studentId); - } - return isStudentExist; - }; - - /** - * Allocates the {@code studentId} to the {@code tutorialTeam} - * @param tutorialTeam to allocate the student into. + * Returns true if a person with the same identity as {@code person} exists in + * the address book. */ - public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { - requireAllNonNull(studentId, tutorialTeam); - Person person = persons.getPerson(studentId); - tutorialTeam.addStudent(person); + public boolean hasPersonWithEmail(Email email) { + requireNonNull(email); + return persons.asUnmodifiableObservableList().stream().anyMatch(s -> s.getEmail().equals(email)); } /** @@ -219,6 +205,26 @@ public void addPersonToTutorialClass(Person person, ModuleCode module, TutorialC tutorialClassInList.addStudent(person); } + /** + * Deletes a person from the students list of a specific tutorial class within a + * module. + */ + public void deletePersonFromTutorialClass(Person person, ModuleCode module, TutorialClass tutorialClass) { + requireNonNull(person); + requireNonNull(module); + requireNonNull(tutorialClass); + + ModuleCode moduleInList = findModuleFromList(module); + if (moduleInList == null) { + throw new IllegalArgumentException("Module does not exist in the address book."); + } + TutorialClass tutorialClassInList = moduleInList.getTutorialClasses().stream() + .filter(tutorial -> tutorial.equals(tutorialClass)) + .findFirst() + .orElse(null); + tutorialClassInList.deleteStudent(person); + } + /** * Replaces the given person {@code target} in the list with * {@code editedPerson}. @@ -233,13 +239,20 @@ public void setPerson(Person target, Person editedPerson) { } /** - * Removes {@code key} from this {@code AddressBook}. + * Removes Person {@code key} from this {@code AddressBook}. * {@code key} must exist in the address book. */ public void removePerson(Person key) { persons.remove(key); } + /** + * Removes ModuleCode {@code key} from this {@code AddressBook}. + * {@code key} must exist in the address book. + */ + public void removeModule(ModuleCode key) { + modules.remove(key); + } //// util methods @Override diff --git a/src/main/java/seedu/address/model/Model.java b/src/main/java/seedu/address/model/Model.java index 6349f53ea86..fe7fcdbfbbd 100644 --- a/src/main/java/seedu/address/model/Model.java +++ b/src/main/java/seedu/address/model/Model.java @@ -5,8 +5,9 @@ import javafx.collections.ObservableList; import seedu.address.commons.core.GuiSettings; -import seedu.address.model.module.*; -import seedu.address.model.person.*; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Person; /** * The API of the Model component. @@ -123,30 +124,9 @@ public interface Model { */ void updateFilteredModuleList(Predicate predicate); - /** * Search for person by a given {@code predicate}. */ Person searchPersonByPredicate(Predicate predicate); - /** - * Returns true if a team with the same identity as {@code tutorialTeam} exists in the {@code tutorialClass} - * @param tutorialClass of the tutorialTeam. - * @param tutorialTeam to check if it exist. - */ - boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam); - - /** - * Returns true if the {@code studentId} is already in a team of {@code tutorialClass}. - * @param tutorialClass of the teams. - * @param studentId to search for. - */ - public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass); - - /** - * Allocates the student to the {@code tutorialTeam} under that {@code tutorialClass} of that {@code moduleCode} - * @param studentId to find the Person to add into the team. - * @param tutorialTeam to allocate the student into. - */ - public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam); } diff --git a/src/main/java/seedu/address/model/ModelManager.java b/src/main/java/seedu/address/model/ModelManager.java index 19388575c36..89114f11e07 100644 --- a/src/main/java/seedu/address/model/ModelManager.java +++ b/src/main/java/seedu/address/model/ModelManager.java @@ -11,8 +11,9 @@ import javafx.collections.transformation.FilteredList; import seedu.address.commons.core.GuiSettings; import seedu.address.commons.core.LogsCenter; -import seedu.address.model.module.*; -import seedu.address.model.person.*; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Person; /** @@ -97,25 +98,6 @@ public boolean hasPerson(Person person) { requireNonNull(person); return addressBook.hasPerson(person); } - - @Override - public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { - requireAllNonNull(tutorialClass, tutorialTeam); - return addressBook.hasTeamInTutorial(tutorialClass, tutorialTeam); - } - - @Override - public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { - requireAllNonNull(studentId, tutorialClass); - return addressBook.isStudentInAnyTeam(studentId, tutorialClass); - } - - @Override - public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { - requireAllNonNull(studentId, tutorialTeam); - addressBook.allocateStudentToTeam(studentId, tutorialTeam); - } - @Override public ModuleCode findModuleFromList(ModuleCode module) { requireNonNull(module); diff --git a/src/main/java/seedu/address/model/module/TutorialClass.java b/src/main/java/seedu/address/model/module/TutorialClass.java index 589348ef8ee..4cf554b675d 100644 --- a/src/main/java/seedu/address/model/module/TutorialClass.java +++ b/src/main/java/seedu/address/model/module/TutorialClass.java @@ -169,6 +169,14 @@ public boolean hasTeam(TutorialTeam team) { return false; } + /** + * Deletes a team from the tutorial class. + * @param team + */ + public void deleteTeam(TutorialTeam team) { + teams.remove(team); + } + @Override public String toString() { return tutorialName; diff --git a/src/main/java/seedu/address/model/module/TutorialTeam.java b/src/main/java/seedu/address/model/module/TutorialTeam.java index 677fba8775d..1bee5db01c8 100644 --- a/src/main/java/seedu/address/model/module/TutorialTeam.java +++ b/src/main/java/seedu/address/model/module/TutorialTeam.java @@ -5,8 +5,7 @@ import java.util.ArrayList; -import javafx.collections.*; -import seedu.address.model.person.*; +import seedu.address.model.person.Person; /** * Represents a Module's tutorial team. @@ -38,19 +37,6 @@ public TutorialTeam() { this.teamSize = Integer.MAX_VALUE; } - /** - * Constructs a {@code TutorialTeam} with the specific teamName. - * Initializes the {@code teamName} field to the specified teamName, creates an empty - * list for {@code students} and sets the {@code teamSize} to the maximum. - */ - public TutorialTeam(String teamName) { - this.teamName = teamName; - this.students = new ArrayList<>(); - this.teamSize = Integer.MAX_VALUE; - } - - - /** * A constructor for TutorialTeam. Creates a tutorial team of a certain size * with no students. @@ -68,7 +54,7 @@ public TutorialTeam(String tutorialTeam, int teamSize) { /** * A constructor for TutorialTeam. Creates a tutorial team with students. - * @param tutorialTeam to be added + * @param tutorialClass to be added * @param students in the tutorial class */ public TutorialTeam(String tutorialTeam, ArrayList students) { @@ -82,7 +68,7 @@ public TutorialTeam(String tutorialTeam, ArrayList students) { /** * A constructor for TutorialTeam. Creates a tutorial team with students and * team size. - * @param tutorialTeam to be added + * @param tutorialClass to be added * @param students in the tutorial class * @param teamSize of the tutorial team */ @@ -177,19 +163,6 @@ public boolean hasStudent(Person student) { return students.contains(student); } - - /** - * Checks if the student is in the tutorial team. - * @param studentId to check with. - * @return true if the student is in the tutorial class - */ - public boolean hasStudentVerified(StudentId studentId) { - ObservableList obList = FXCollections.observableList(students); - return obList.stream().anyMatch(person -> person.getStudentId().isSameStudentId(studentId)); - } - - - @Override public String toString() { return teamName; diff --git a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java index 166a3098900..be397526443 100644 --- a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java @@ -24,7 +24,9 @@ import seedu.address.model.ReadOnlyUserPrefs; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Email; import seedu.address.model.person.Person; +import seedu.address.model.person.StudentId; import seedu.address.testutil.PersonBuilder; /** @@ -145,6 +147,16 @@ public boolean hasPerson(Person person) { throw new AssertionError("This method should not be called."); } + @Override + public boolean hasPersonWithEmail(Email email) { + throw new AssertionError("This method should not be called."); + } + + @Override + public boolean hasPersonWithStudentId(StudentId studentId) { + throw new AssertionError("This method should not be called."); + } + @Override public TutorialClass findTutorialClassFromList(TutorialClass tutorialClass, ModuleCode moduleCode) { throw new AssertionError("This method should not be called."); @@ -155,11 +167,21 @@ public void addPersonToTutorialClass(Person person, ModuleCode moduleCode, Tutor throw new AssertionError("This method should not be called."); } + @Override + public void deletePersonFromTutorialClass(Person person, ModuleCode moduleCode, TutorialClass tutorialClass) { + throw new AssertionError("This method should not be called."); + } + @Override public void deletePerson(Person target) { throw new AssertionError("This method should not be called."); } + @Override + public void deleteModule(ModuleCode target) { + throw new AssertionError("This method should not be called."); + } + @Override public void addModule(ModuleCode module) { throw new AssertionError("This method should not be called."); diff --git a/src/test/java/seedu/address/logic/commands/AddTeamCommandIntegrationTest.java b/src/test/java/seedu/address/logic/commands/AddTeamCommandIntegrationTest.java index 8edf10cf5b0..85c67185479 100644 --- a/src/test/java/seedu/address/logic/commands/AddTeamCommandIntegrationTest.java +++ b/src/test/java/seedu/address/logic/commands/AddTeamCommandIntegrationTest.java @@ -67,19 +67,19 @@ public void execute_addTeamWithSize_success() { public void execute_addTeamToInvalidModule_throwsCommandException() { Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); - ModuleCode invalidModule = new ModuleCode(VALID_MODULE_BOB); - assertCommandFailure(new AddTeamCommand(invalidModule, testTutorial, VALID_TEAM_NAME_AMY), + ModuleCode wrongModule = new ModuleCode(VALID_MODULE_BOB); + assertCommandFailure(new AddTeamCommand(wrongModule, testTutorial, VALID_TEAM_NAME_AMY), expectedModel, - String.format(ModuleMessages.MESSAGE_MODULE_NOT_FOUND, invalidModule)); + String.format(ModuleMessages.MESSAGE_MODULE_NOT_FOUND, wrongModule)); } @Test public void execute_addTeamToInvalidTutorial_throwsCommandException() { Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); - TutorialClass invalidTutorial = new TutorialClass(VALID_TUTORIAL_BOB); - assertCommandFailure(new AddTeamCommand(testModule, invalidTutorial, VALID_TEAM_NAME_AMY), + TutorialClass wrongTutorial = new TutorialClass(VALID_TUTORIAL_BOB); + assertCommandFailure(new AddTeamCommand(testModule, wrongTutorial, VALID_TEAM_NAME_AMY), expectedModel, - String.format(ModuleMessages.MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE, invalidTutorial, testModule)); + String.format(ModuleMessages.MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE, wrongTutorial, testModule)); } } diff --git a/src/test/java/seedu/address/logic/commands/DeleteClassCommandTest.java b/src/test/java/seedu/address/logic/commands/DeleteClassCommandTest.java index 3d8140f9a53..f57e1c75048 100644 --- a/src/test/java/seedu/address/logic/commands/DeleteClassCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/DeleteClassCommandTest.java @@ -9,13 +9,12 @@ import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_BOB; import static seedu.address.logic.commands.CommandTestUtil.assertCommandFailure; import static seedu.address.logic.commands.CommandTestUtil.assertCommandSuccess; -import static seedu.address.logic.commands.DeleteClassCommand.MESSAGE_CLASS_NOT_FOUND; import static seedu.address.logic.commands.DeleteClassCommand.MESSAGE_DELETE_CLASS_SUCCESS; -import static seedu.address.logic.commands.DeleteClassCommand.MESSAGE_MODULE_NOT_FOUND; import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; import org.junit.jupiter.api.Test; +import seedu.address.logic.messages.ModuleMessages; import seedu.address.model.Model; import seedu.address.model.ModelManager; import seedu.address.model.UserPrefs; @@ -52,7 +51,7 @@ public void execute_moduleNotFound_fail() { assertCommandFailure(new DeleteClassCommand(new ModuleCode(VALID_MODULE_BOB), new TutorialClass(VALID_TUTORIAL_AMY)), model, - String.format(MESSAGE_MODULE_NOT_FOUND, VALID_MODULE_BOB)); + String.format(ModuleMessages.MESSAGE_MODULE_NOT_FOUND, VALID_MODULE_BOB)); } @Test @@ -60,7 +59,8 @@ public void execute_tutorialNotFound_fail() { ModuleCode module = new ModuleCode(VALID_MODULE_AMY, VALID_TUTORIAL_AMY); model.addModule(module); - String errorMessage = String.format(MESSAGE_CLASS_NOT_FOUND, VALID_MODULE_AMY, VALID_TUTORIAL_BOB); + String errorMessage = String.format(ModuleMessages.MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE, + VALID_TUTORIAL_BOB, VALID_MODULE_AMY); String listOfTutorials = module.listTutorialClasses(); String expectedMessage = errorMessage + "\n" + listOfTutorials; assertCommandFailure(new DeleteClassCommand(new ModuleCode(VALID_MODULE_AMY), diff --git a/src/test/java/seedu/address/logic/commands/DeleteModuleCommandTest.java b/src/test/java/seedu/address/logic/commands/DeleteModuleCommandTest.java new file mode 100644 index 00000000000..afb926634f2 --- /dev/null +++ b/src/test/java/seedu/address/logic/commands/DeleteModuleCommandTest.java @@ -0,0 +1,74 @@ +package seedu.address.logic.commands; + +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertTrue; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_BOB; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandFailure; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandSuccess; +import static seedu.address.logic.messages.ModuleMessages.MESSAGE_DELETE_MODULE_SUCCESS; +import static seedu.address.logic.messages.ModuleMessages.MESSAGE_MODULE_NOT_FOUND; +import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; + +import org.junit.jupiter.api.Test; + +import seedu.address.model.Model; +import seedu.address.model.ModelManager; +import seedu.address.model.UserPrefs; +import seedu.address.model.module.ModuleCode; + +/** + * Contains integration tests (interaction with the Model) for + * {@code DeleteModuleCommand}. + */ +public class DeleteModuleCommandTest { + private final Model model = new ModelManager(getTypicalAddressBook(), new UserPrefs()); + + @Test + public void execute_success() { + Model actualModel = new ModelManager(); + Model expectedModel = new ModelManager(); + ModuleCode module = new ModuleCode(VALID_MODULE_AMY); + actualModel.addModule(module); + + assertCommandSuccess(new DeleteModuleCommand(new ModuleCode(VALID_MODULE_AMY)), actualModel, + String.format(MESSAGE_DELETE_MODULE_SUCCESS, VALID_MODULE_AMY), expectedModel); + + assertEquals(actualModel.getFilteredModuleList().size(), 0); + } + + @Test + public void execute_moduleNotFound_fail() { + ModuleCode module = new ModuleCode(VALID_MODULE_AMY); + model.addModule(module); + + assertCommandFailure(new DeleteModuleCommand(new ModuleCode(VALID_MODULE_BOB)), model, + String.format(MESSAGE_MODULE_NOT_FOUND, VALID_MODULE_BOB)); + } + + @Test + public void equals() { + final DeleteModuleCommand standardCommand = new DeleteModuleCommand(new ModuleCode(VALID_MODULE_AMY)); + + // same values -> returns true + DeleteModuleCommand commandWithSameValues = new DeleteModuleCommand(new ModuleCode(VALID_MODULE_AMY)); + assertTrue(standardCommand.equals(commandWithSameValues)); + + // same object -> returns true + assertTrue(standardCommand.equals(standardCommand)); + + // null -> returns false + assertFalse(standardCommand.equals(null)); + + // different types -> returns false + assertFalse(standardCommand.equals(new ClearCommand())); + + // different module code -> returns false + assertFalse(standardCommand.equals(new DeleteModuleCommand(new ModuleCode(VALID_MODULE_BOB)))); + + // different tutorial class -> returns true + assertTrue(standardCommand.equals(new DeleteModuleCommand(new ModuleCode(VALID_MODULE_AMY)))); + } +} + diff --git a/src/test/java/seedu/address/logic/commands/DeleteStudentCommandTest.java b/src/test/java/seedu/address/logic/commands/DeleteStudentCommandTest.java index 324685e4dc5..c6512c05a93 100644 --- a/src/test/java/seedu/address/logic/commands/DeleteStudentCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/DeleteStudentCommandTest.java @@ -31,7 +31,7 @@ /** * Contains integration tests (interaction with the Model) and unit tests for - * {@code DeleteCommand}. + * {@code DeleteStudentCommand}. */ public class DeleteStudentCommandTest { diff --git a/src/test/java/seedu/address/logic/commands/DeleteStudentFromClassCommandIntegrationTest.java b/src/test/java/seedu/address/logic/commands/DeleteStudentFromClassCommandIntegrationTest.java new file mode 100644 index 00000000000..f7f60ea2caf --- /dev/null +++ b/src/test/java/seedu/address/logic/commands/DeleteStudentFromClassCommandIntegrationTest.java @@ -0,0 +1,118 @@ +package seedu.address.logic.commands; + +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_BOB; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandFailure; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandSuccess; +import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; + +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import seedu.address.logic.Messages; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByEmailCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByIdCommand; +import seedu.address.logic.messages.ModuleMessages; +import seedu.address.logic.messages.PersonMessages; +import seedu.address.model.Model; +import seedu.address.model.ModelManager; +import seedu.address.model.UserPrefs; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Person; +import seedu.address.testutil.PersonBuilder; + +/** + * Contains integration tests (interaction with the Model) for + * {@code DeleteStudentFromClassCommand}. + */ +public class DeleteStudentFromClassCommandIntegrationTest { + + private Model model; + + @BeforeEach + public void setUp() { + model = new ModelManager(getTypicalAddressBook(), new UserPrefs()); + ModuleCode newModule = new ModuleCode(VALID_MODULE_AMY); + model.addModule(newModule); + TutorialClass newTutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + newModule.addTutorialClass(newTutorialClass); + Person validPerson = new PersonBuilder().build(); + Person validPerson2 = new PersonBuilder().withName("otherName").withEmail("other@example.com") + .withStudentId("A0000000A").build(); + model.addPerson(validPerson); + newModule.getTutorialClasses().get(0).addStudent(validPerson); + newModule.getTutorialClasses().get(0).addStudent(validPerson2); + } + + @Test + public void execute_deleteStudentFromClassById_success() { + Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); + + ModuleCode newModule = new ModuleCode(VALID_MODULE_AMY); + expectedModel.addModule(newModule); + Person validPerson2 = new PersonBuilder().withName("otherName").withEmail("other@example.com") + .withStudentId("A0000000A").build(); + TutorialClass newTutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + newModule.addTutorialClass(newTutorialClass); + newModule.getTutorialClasses().get(0).addStudent(validPerson2); + Person validPerson = new PersonBuilder().build(); + + // Attempt to delete the student + assertCommandSuccess(new DeleteStudentFromClassByIdCommand(validPerson.getStudentId(), + newModule, newTutorialClass), + model, + String.format(PersonMessages.MESSAGE_DELETE_STUDENT_FROM_CLASS_SUCCESS, Messages.format(validPerson), + newModule, newTutorialClass), + expectedModel); + } + + @Test + public void execute_deleteStudentFromClassByEmail_success() { + Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); + + ModuleCode newModule = new ModuleCode(VALID_MODULE_AMY); + expectedModel.addModule(newModule); + Person validPerson2 = new PersonBuilder().withName("otherName").withEmail("other@example.com") + .withStudentId("A0000000A").build(); + TutorialClass newTutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + newModule.addTutorialClass(newTutorialClass); + newModule.getTutorialClasses().get(0).addStudent(validPerson2); + Person validPerson = new PersonBuilder().build(); + + // Attempt to delete the student + assertCommandSuccess(new DeleteStudentFromClassByEmailCommand(validPerson.getEmail(), + newModule, newTutorialClass), + model, + String.format(PersonMessages.MESSAGE_DELETE_STUDENT_FROM_CLASS_SUCCESS, Messages.format(validPerson), + newModule, newTutorialClass), expectedModel); + } + + @Test + public void execute_deleteStudentFromInvalidClass_throwsCommandException() { + Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); + + ModuleCode newModule = new ModuleCode(VALID_MODULE_BOB); + TutorialClass newTutorial = new TutorialClass(VALID_TUTORIAL_BOB); + Person validPerson = new PersonBuilder().build(); + + assertCommandFailure(new DeleteStudentFromClassByEmailCommand(validPerson.getEmail(), newModule, newTutorial), + expectedModel, String.format(ModuleMessages.MESSAGE_MODULE_NOT_FOUND, newModule)); + } + + @Test + public void execute_deleteStudentFromValidModuleButInvalidTutorial_throwsCommandException() { + Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); + + ModuleCode newModule = new ModuleCode(VALID_MODULE_AMY); + expectedModel.addModule(newModule); + TutorialClass newTutorial = new TutorialClass(VALID_TUTORIAL_BOB); + Person validPerson = new PersonBuilder().build(); + assertCommandFailure(new DeleteStudentFromClassByEmailCommand(validPerson.getEmail(), newModule, newTutorial), + expectedModel, + String.format(ModuleMessages.MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE, newTutorial, newModule)); + } + +} diff --git a/src/test/java/seedu/address/logic/commands/DeleteStudentFromClassCommandTest.java b/src/test/java/seedu/address/logic/commands/DeleteStudentFromClassCommandTest.java new file mode 100644 index 00000000000..4cc5887dbed --- /dev/null +++ b/src/test/java/seedu/address/logic/commands/DeleteStudentFromClassCommandTest.java @@ -0,0 +1,167 @@ +package seedu.address.logic.commands; + +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertTrue; +import static seedu.address.logic.commands.CommandTestUtil.INVALID_PERSON_EMAIL; +import static seedu.address.logic.commands.CommandTestUtil.INVALID_PERSON_STUDENT_ID; +import static seedu.address.logic.commands.CommandTestUtil.VALID_EMAIL_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_EMAIL_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_BOB; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandFailure; +import static seedu.address.testutil.TypicalIndexes.INDEX_FIRST_PERSON; +import static seedu.address.testutil.TypicalIndexes.INDEX_SECOND_PERSON; +import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; + +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import seedu.address.commons.core.index.Index; +import seedu.address.logic.Messages; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByEmailCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByIdCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByIndexCommand; +import seedu.address.logic.messages.PersonMessages; +import seedu.address.logic.messages.TutorialClassMessages; +import seedu.address.model.Model; +import seedu.address.model.ModelManager; +import seedu.address.model.UserPrefs; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.Email; +import seedu.address.model.person.Person; +import seedu.address.model.person.StudentId; +import seedu.address.testutil.PersonBuilder; + +/** + * Contains integration tests (interaction with the Model) and unit tests for + * {@code DeleteStudentFromClassCommand}. + */ +public class DeleteStudentFromClassCommandTest { + + private Model model = new ModelManager(getTypicalAddressBook(), new UserPrefs()); + private TutorialClass tutorialClass; + + @BeforeEach + public void setUp() { + ModuleCode newModule = new ModuleCode(VALID_MODULE_AMY); + model.addModule(newModule); + TutorialClass newTutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + newModule.addTutorialClass(newTutorialClass); + tutorialClass = newTutorialClass; + } + + @Test + public void execute_invalidStudent_fail() { + DeleteStudentFromClassByEmailCommand deleteStudentFromClassByEmailCommand = + new DeleteStudentFromClassByEmailCommand(new Email(INVALID_PERSON_EMAIL), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + + DeleteStudentFromClassByIdCommand deleteStudentFromClassByIdCommand = + new DeleteStudentFromClassByIdCommand(new StudentId(INVALID_PERSON_STUDENT_ID), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + + DeleteStudentFromClassByIndexCommand deleteStudentFromClassByIndexCommand = + new DeleteStudentFromClassByIndexCommand(Index.fromOneBased(1000), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + + assertCommandFailure(deleteStudentFromClassByEmailCommand, model, + String.format(PersonMessages.MESSAGE_PERSON_EMAIL_NOT_FOUND, INVALID_PERSON_EMAIL)); + + assertCommandFailure(deleteStudentFromClassByIdCommand, model, + String.format(PersonMessages.MESSAGE_PERSON_STUDENT_ID_NOT_FOUND, INVALID_PERSON_STUDENT_ID)); + + assertCommandFailure(deleteStudentFromClassByIndexCommand, model, + String.format(PersonMessages.MESSAGE_PERSON_INDEX_NOT_FOUND, 1000)); + } + + @Test + public void execute_studentDoesNotExist_fail() { + Person person = new PersonBuilder().build(); + Person otherPerson = new PersonBuilder().withName("otherPerson").build(); + model.addPerson(person); + tutorialClass.addStudent(otherPerson); + + DeleteStudentFromClassByEmailCommand addStudentToClassByEmailCommand = + new DeleteStudentFromClassByEmailCommand(person.getEmail(), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + + DeleteStudentFromClassByIdCommand addStudentToClassByIdCommand = + new DeleteStudentFromClassByIdCommand(person.getStudentId(), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + + assertCommandFailure(addStudentToClassByIdCommand, model, + String.format(TutorialClassMessages.MESSAGE_STUDENT_NOT_FOUND_IN_CLASS, Messages.format(person), + tutorialClass)); + + assertCommandFailure(addStudentToClassByEmailCommand, model, + String.format(TutorialClassMessages.MESSAGE_STUDENT_NOT_FOUND_IN_CLASS, Messages.format(person), + tutorialClass)); + } + + @Test + public void equals() { + + // Test index based delete command + DeleteStudentFromClassByIndexCommand deleteStudentFromClassByIndexFirstCommand = + new DeleteStudentFromClassByIndexCommand(INDEX_FIRST_PERSON, + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + + DeleteStudentFromClassByIndexCommand deleteStudentFromClassByIndexSecondCommand = + new DeleteStudentFromClassByIndexCommand(INDEX_SECOND_PERSON, + new ModuleCode(VALID_MODULE_BOB), new TutorialClass(VALID_TUTORIAL_BOB)); + + // same object -> returns true + assertTrue(deleteStudentFromClassByIndexFirstCommand.equals(deleteStudentFromClassByIndexFirstCommand)); + // different types -> returns false + assertFalse(deleteStudentFromClassByIndexFirstCommand.equals(1)); + + // null -> returns false + assertFalse(deleteStudentFromClassByIndexFirstCommand.equals(null)); + + // different person -> returns false + assertFalse(deleteStudentFromClassByIndexFirstCommand.equals(deleteStudentFromClassByIndexSecondCommand)); + + // Test email based delete command + DeleteStudentFromClassByEmailCommand deleteStudentFromClassByEmailFirstCommand = + new DeleteStudentFromClassByEmailCommand(new Email(VALID_EMAIL_AMY), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + + DeleteStudentFromClassByEmailCommand deleteStudentFromClassByEmailSecondCommand = + new DeleteStudentFromClassByEmailCommand(new Email(VALID_EMAIL_BOB), + new ModuleCode(VALID_MODULE_BOB), new TutorialClass(VALID_TUTORIAL_BOB)); + + // same object -> returns true + assertTrue(deleteStudentFromClassByEmailFirstCommand.equals(deleteStudentFromClassByEmailFirstCommand)); + // different types -> returns false + assertFalse(deleteStudentFromClassByEmailFirstCommand.equals(1)); + + // null -> returns false + assertFalse(deleteStudentFromClassByEmailFirstCommand.equals(null)); + + // different person -> returns false + assertFalse(deleteStudentFromClassByEmailFirstCommand.equals(deleteStudentFromClassByEmailSecondCommand)); + + // Test student id based delete command + DeleteStudentFromClassByIdCommand deleteStudentFromClassByIdFirstCommand = + new DeleteStudentFromClassByIdCommand(new StudentId(VALID_STUDENT_ID_AMY), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + + DeleteStudentFromClassByIdCommand deleteStudentFromClassByIdSecondCommand = + new DeleteStudentFromClassByIdCommand(new StudentId(VALID_STUDENT_ID_BOB), + new ModuleCode(VALID_MODULE_BOB), new TutorialClass(VALID_TUTORIAL_BOB)); + + // same object -> returns true + assertTrue(deleteStudentFromClassByIdFirstCommand.equals(deleteStudentFromClassByIdFirstCommand)); + // different types -> returns false + assertFalse(deleteStudentFromClassByIdFirstCommand.equals(1)); + // null -> returns false + assertFalse(deleteStudentFromClassByIdFirstCommand.equals(null)); + // different person -> returns false + assertFalse(deleteStudentFromClassByIdFirstCommand.equals(deleteStudentFromClassByIdSecondCommand)); + } +} diff --git a/src/test/java/seedu/address/logic/commands/DeleteTeamCommandIntegrationTest.java b/src/test/java/seedu/address/logic/commands/DeleteTeamCommandIntegrationTest.java new file mode 100644 index 00000000000..85e6e8f37f0 --- /dev/null +++ b/src/test/java/seedu/address/logic/commands/DeleteTeamCommandIntegrationTest.java @@ -0,0 +1,76 @@ +package seedu.address.logic.commands; + +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_BOB; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandFailure; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandSuccess; +import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; + +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import seedu.address.logic.messages.ModuleMessages; +import seedu.address.model.Model; +import seedu.address.model.ModelManager; +import seedu.address.model.UserPrefs; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; + +/** + * Contains integration tests (interaction with the Model) for + * {@code DeleteTeamCommand}. + */ +public class DeleteTeamCommandIntegrationTest { + + private Model model; + private ModuleCode testModule; + private TutorialClass testTutorial; + + @BeforeEach + public void setUp() { + model = new ModelManager(getTypicalAddressBook(), new UserPrefs()); + ModuleCode newModule = new ModuleCode(VALID_MODULE_AMY); + model.addModule(newModule); + this.testModule = newModule; + TutorialClass newTutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + newModule.addTutorialClass(newTutorialClass); + TutorialTeam newTeam = new TutorialTeam(VALID_TEAM_NAME_AMY); + newTutorialClass.addTeam(newTeam); + this.testTutorial = newTutorialClass; + } + + @Test + public void execute_deleteTeam_success() { + Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); + + assertCommandSuccess(new DeleteTeamCommand(testModule, testTutorial, VALID_TEAM_NAME_AMY), + model, + String.format(DeleteTeamCommand.MESSAGE_DELETE_TEAM_SUCCESS, VALID_TEAM_NAME_AMY, + testModule, testTutorial), + expectedModel); + } + + @Test + public void execute_deleteTeamWithInvalidModule_throwsCommandException() { + Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); + + ModuleCode wrongModule = new ModuleCode(VALID_MODULE_BOB); + assertCommandFailure(new DeleteTeamCommand(wrongModule, testTutorial, VALID_TEAM_NAME_AMY), + expectedModel, + String.format(ModuleMessages.MESSAGE_MODULE_NOT_FOUND, wrongModule)); + } + + @Test + public void execute_deleteTeamWithInvalidTutorial_throwsCommandException() { + Model expectedModel = new ModelManager(model.getAddressBook(), new UserPrefs()); + + TutorialClass wrongTutorial = new TutorialClass(VALID_TUTORIAL_BOB); + assertCommandFailure(new DeleteTeamCommand(testModule, wrongTutorial, VALID_TEAM_NAME_AMY), + expectedModel, + String.format(ModuleMessages.MESSAGE_TUTORIAL_DOES_NOT_BELONG_TO_MODULE, wrongTutorial, testModule)); + } +} diff --git a/src/test/java/seedu/address/logic/commands/DeleteTeamCommandTest.java b/src/test/java/seedu/address/logic/commands/DeleteTeamCommandTest.java new file mode 100644 index 00000000000..9680d4dfff4 --- /dev/null +++ b/src/test/java/seedu/address/logic/commands/DeleteTeamCommandTest.java @@ -0,0 +1,52 @@ +package seedu.address.logic.commands; + +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertTrue; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_BOB; +import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; + +import org.junit.jupiter.api.Test; + +import seedu.address.model.Model; +import seedu.address.model.ModelManager; +import seedu.address.model.UserPrefs; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; + +/** + * Contains integration tests (interaction with the Model) and unit tests for + * {@code DeleteTeamCommand}. + */ +public class DeleteTeamCommandTest { + + private Model model = new ModelManager(getTypicalAddressBook(), new UserPrefs()); + + @Test + public void equals() { + ModuleCode moduleCodeAmy = new ModuleCode(VALID_MODULE_AMY); + TutorialClass tutorialClassAmy = new TutorialClass(VALID_TUTORIAL_AMY); + ModuleCode moduleCodeBob = new ModuleCode(VALID_MODULE_AMY); + TutorialClass tutorialClassBob = new TutorialClass(VALID_TUTORIAL_BOB); + + DeleteTeamCommand deleteTeamFirstCommand = new DeleteTeamCommand(moduleCodeAmy, tutorialClassAmy, + VALID_TEAM_NAME_AMY); + + DeleteTeamCommand deleteTeamSecondCommand = new DeleteTeamCommand(moduleCodeBob, tutorialClassBob, + VALID_TEAM_NAME_BOB); + + // same object -> returns true + assertTrue(deleteTeamFirstCommand.equals(deleteTeamFirstCommand)); + // different types -> returns false + assertFalse(deleteTeamFirstCommand.equals(1)); + + // null -> returns false + assertFalse(deleteTeamFirstCommand.equals(null)); + + // different team -> returns false + assertFalse(deleteTeamFirstCommand.equals(deleteTeamSecondCommand)); + } +} diff --git a/src/test/java/seedu/address/logic/commands/EditCommandTest.java b/src/test/java/seedu/address/logic/commands/EditCommandTest.java index 32d9c395483..1b097e7c692 100644 --- a/src/test/java/seedu/address/logic/commands/EditCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/EditCommandTest.java @@ -23,7 +23,9 @@ import seedu.address.model.Model; import seedu.address.model.ModelManager; import seedu.address.model.UserPrefs; +import seedu.address.model.person.Email; import seedu.address.model.person.Person; +import seedu.address.model.person.StudentId; import seedu.address.testutil.EditPersonDescriptorBuilder; import seedu.address.testutil.PersonBuilder; @@ -104,6 +106,20 @@ public void execute_duplicatePersonUnfilteredList_failure() { EditCommand editCommand = new EditCommand(INDEX_SECOND_PERSON, descriptor); assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_PERSON); + + // duplicate email + descriptor = new EditPersonDescriptorBuilder().withName("Test").withEmail(firstPerson.getEmail().toString()) + .withStudentId("A1111111A").build(); + editCommand = new EditCommand(INDEX_SECOND_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_PERSON); + + // duplicate student id + descriptor = new EditPersonDescriptorBuilder().withName("Test").withEmail("test@example.com") + .withStudentId(firstPerson.getStudentId().toString()).build(); + editCommand = new EditCommand(INDEX_SECOND_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_PERSON); } @Test @@ -116,6 +132,20 @@ public void execute_duplicatePersonFilteredList_failure() { new EditPersonDescriptorBuilder(personInList).build()); assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_PERSON); + + // edit person with only duplicate email + EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder().withName("Test") + .withEmail(personInList.getEmail().toString()).withStudentId("A1111111A").build(); + editCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_PERSON); + + // edit person with only duplicate id + descriptor = new EditPersonDescriptorBuilder().withName("Test").withEmail("test@example.com") + .withStudentId(personInList.getStudentId().toString()).build(); + editCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_PERSON); } @Test @@ -127,6 +157,70 @@ public void execute_invalidPersonIndexUnfilteredList_failure() { assertCommandFailure(editCommand, model, Messages.MESSAGE_INVALID_PERSON_DISPLAYED_INDEX); } + @Test + public void execute_duplicateEmailUnfilteredList_failure() { + // edit with duplicate email + Email secondPersonEmail = model.getFilteredPersonList().get(INDEX_SECOND_PERSON.getZeroBased()).getEmail(); + + EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder() + .withEmail(secondPersonEmail.toString()).build(); + EditCommand editCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_EMAIL); + + // edit with own email + Email firstPersonEmail = model.getFilteredPersonList().get(INDEX_FIRST_PERSON.getZeroBased()).getEmail(); + descriptor = new EditPersonDescriptorBuilder().withEmail(firstPersonEmail.toString()).build(); + editCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_EMAIL); + } + + @Test + public void execute_duplicateEmailFilteredList_failure() { + showPersonAtIndex(model, INDEX_FIRST_PERSON); + + Person personInList = model.getAddressBook().getPersonList().get(INDEX_SECOND_PERSON.getZeroBased()); + EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder() + .withEmail(personInList.getEmail().toString()).build(); + EditCommand editCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_EMAIL); + } + + @Test + public void execute_duplicateStudentIdUnfilteredList_failure() { + // edit with duplicate student id + StudentId secondPersonStudentId = model.getFilteredPersonList() + .get(INDEX_SECOND_PERSON.getZeroBased()).getStudentId(); + + EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder() + .withStudentId(secondPersonStudentId.toString()).build(); + EditCommand editCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_STUDENTID); + + // edit with own student id + StudentId firstPersonStudentId = model.getFilteredPersonList() + .get(INDEX_FIRST_PERSON.getZeroBased()).getStudentId(); + descriptor = new EditPersonDescriptorBuilder().withStudentId(firstPersonStudentId.toString()).build(); + editCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_STUDENTID); + } + + @Test + public void execute_duplicateStudentIdFilteredList_failure() { + showPersonAtIndex(model, INDEX_FIRST_PERSON); + + Person personInList = model.getAddressBook().getPersonList().get(INDEX_SECOND_PERSON.getZeroBased()); + EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder() + .withStudentId(personInList.getStudentId().toString()).build(); + EditCommand editCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); + + assertCommandFailure(editCommand, model, EditCommand.MESSAGE_DUPLICATE_STUDENTID); + } + /** * Edit filtered list where index is larger than size of filtered list, * but smaller than size of address book diff --git a/src/test/java/seedu/address/logic/parser/AddressBookParserTest.java b/src/test/java/seedu/address/logic/parser/AddressBookParserTest.java index 53cea1c0c0b..3bd95ef0342 100644 --- a/src/test/java/seedu/address/logic/parser/AddressBookParserTest.java +++ b/src/test/java/seedu/address/logic/parser/AddressBookParserTest.java @@ -4,6 +4,7 @@ import static org.junit.jupiter.api.Assertions.assertTrue; import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; import static seedu.address.logic.Messages.MESSAGE_UNKNOWN_COMMAND; +import static seedu.address.logic.commands.CommandTestUtil.INDEX_ONE; import static seedu.address.logic.commands.CommandTestUtil.VALID_EMAIL_AMY; import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID_AMY; import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; @@ -24,6 +25,7 @@ import seedu.address.logic.commands.ClearCommand; import seedu.address.logic.commands.DeleteClassCommand; import seedu.address.logic.commands.DeleteCommand; +import seedu.address.logic.commands.DeleteModuleCommand; import seedu.address.logic.commands.EditCommand; import seedu.address.logic.commands.EditCommand.EditPersonDescriptor; import seedu.address.logic.commands.ExitCommand; @@ -34,6 +36,9 @@ import seedu.address.logic.commands.addstudenttoclasscommands.AddStudentToClassByEmailCommand; import seedu.address.logic.commands.addstudenttoclasscommands.AddStudentToClassByIdCommand; import seedu.address.logic.commands.addstudenttoclasscommands.AddStudentToClassCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByEmailCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByIdCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassCommand; import seedu.address.logic.parser.exceptions.ParseException; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; @@ -77,7 +82,7 @@ public void parseCommand_edit() throws Exception { Person person = new PersonBuilder().build(); EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder(person).build(); EditCommand command = (EditCommand) parser.parseCommand(EditCommand.COMMAND_WORD + " " - + INDEX_FIRST_PERSON.getOneBased() + " " + PersonUtil.getEditPersonDescriptorDetails(descriptor)); + + INDEX_ONE + " " + PersonUtil.getEditPersonDescriptorDetails(descriptor)); assertEquals(new EditCommand(INDEX_FIRST_PERSON, descriptor), command); } @@ -128,6 +133,16 @@ public void parseCommand_deleteClass() throws Exception { new TutorialClass(tutorialClass)), command); } + @Test + public void parseCommand_deleteModule() throws Exception { + final String moduleCode = "CS2103T"; + DeleteModuleCommand command = (DeleteModuleCommand) parser.parseCommand(DeleteModuleCommand.COMMAND_WORD + " " + + PREFIX_MODULECODE + moduleCode); + assertEquals(new DeleteModuleCommand(new ModuleCode(moduleCode)), command); + } + + + @Test public void parseCommand_listClasses() throws Exception { assertTrue(parser.parseCommand(ListClassesCommand.COMMAND_WORD) instanceof ListClassesCommand); @@ -156,6 +171,29 @@ public void parseCommand_addStudentToClass() throws Exception { } + @Test + public void parseCommand_deleteStudentFromClass() throws Exception { + final String moduleCode = "CS2103T"; + final String tutorialClass = "T09"; + final String email = VALID_EMAIL_AMY; + final String id = VALID_STUDENT_ID_AMY; + final Index index = INDEX_FIRST_PERSON; + DeleteStudentFromClassCommand deleteByEmailCommand = (DeleteStudentFromClassCommand) parser.parseCommand( + DeleteStudentFromClassCommand.COMMAND_WORD + " " + + PREFIX_EMAIL + email + " " + PREFIX_MODULECODE + + moduleCode + " " + PREFIX_TUTORIALCLASS + tutorialClass); + + DeleteStudentFromClassCommand deleteByIdCommand = (DeleteStudentFromClassCommand) parser.parseCommand( + DeleteStudentFromClassCommand.COMMAND_WORD + " " + + PREFIX_STUDENTID + id + " " + PREFIX_MODULECODE + + moduleCode + " " + PREFIX_TUTORIALCLASS + tutorialClass); + + assertEquals(new DeleteStudentFromClassByEmailCommand(new Email(VALID_EMAIL_AMY), + new ModuleCode(moduleCode), new TutorialClass(tutorialClass)), deleteByEmailCommand); + + assertEquals(new DeleteStudentFromClassByIdCommand(new StudentId(VALID_STUDENT_ID_AMY), + new ModuleCode(moduleCode), new TutorialClass(tutorialClass)), deleteByIdCommand); + } @Test public void parseCommand_unrecognisedInput_throwsParseException() { assertThrows(ParseException.class, diff --git a/src/test/java/seedu/address/logic/parser/DeleteModuleCommandParserTest.java b/src/test/java/seedu/address/logic/parser/DeleteModuleCommandParserTest.java new file mode 100644 index 00000000000..331c5d3ff83 --- /dev/null +++ b/src/test/java/seedu/address/logic/parser/DeleteModuleCommandParserTest.java @@ -0,0 +1,46 @@ +package seedu.address.logic.parser; + +import static seedu.address.logic.commands.CommandTestUtil.MODULE_DESC_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CommandParserTestUtil.assertParseFailure; +import static seedu.address.logic.parser.CommandParserTestUtil.assertParseSuccess; + +import org.junit.jupiter.api.Test; + +import seedu.address.logic.Messages; +import seedu.address.logic.commands.DeleteModuleCommand; +import seedu.address.model.module.ModuleCode; + +/** + * As we are only doing white-box testing, our test cases do not cover path variations + * outside of the DeleteModuleCommand code. For example, inputs "1" and "1 abc" take the + * same path through the DeleteModuleCommand, and therefore we test only one of them. + * The path variation for those two cases occur inside the ParserUtil, and + * therefore should be covered by the ParserUtilTest. + */ +public class DeleteModuleCommandParserTest { + private final DeleteModuleCommandParser parser = new DeleteModuleCommandParser(); + + + @Test + public void parse_validModule_success() { + String userInput = MODULE_DESC_AMY; + DeleteModuleCommand expectedCommand = new DeleteModuleCommand(new ModuleCode(VALID_MODULE_AMY)); + assertParseSuccess(parser, userInput, expectedCommand); + } + + @Test + public void parse_missingCompulsoryField_failure() { + String expectedMessage1 = String.format(Messages.MESSAGE_INVALID_COMMAND_FORMAT, + DeleteModuleCommand.MESSAGE_USAGE); + String expectedMessage2 = ModuleCode.MESSAGE_CONSTRAINTS; + + // no parameters + assertParseFailure(parser, " ", expectedMessage1); + + // invalid module stated + assertParseFailure(parser, " " + PREFIX_MODULECODE + "INVALID", expectedMessage2); + } +} + diff --git a/src/test/java/seedu/address/logic/parser/DeleteStudentFromClassCommandParserTest.java b/src/test/java/seedu/address/logic/parser/DeleteStudentFromClassCommandParserTest.java new file mode 100644 index 00000000000..06258ac9c19 --- /dev/null +++ b/src/test/java/seedu/address/logic/parser/DeleteStudentFromClassCommandParserTest.java @@ -0,0 +1,50 @@ +package seedu.address.logic.parser; + +import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; +import static seedu.address.logic.commands.CommandTestUtil.EMAIL_DESC_BOB; +import static seedu.address.logic.commands.CommandTestUtil.MODULE_DESC_AMY; +import static seedu.address.logic.commands.CommandTestUtil.STUDENT_ID_DESC_BOB; +import static seedu.address.logic.commands.CommandTestUtil.TUTORIAL_DESC_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; +import static seedu.address.logic.parser.CommandParserTestUtil.assertParseFailure; +import static seedu.address.logic.parser.CommandParserTestUtil.assertParseSuccess; +import static seedu.address.testutil.TypicalPersons.BOB; + +import org.junit.jupiter.api.Test; + +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByEmailCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassByIdCommand; +import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassCommand; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; + +public class DeleteStudentFromClassCommandParserTest { + + private DeleteStudentFromClassCommandParser parser = new DeleteStudentFromClassCommandParser(); + @Test + public void parse_validArgs_returnsDeleteStudentFromClassCommand() { + + String commandSuffix = MODULE_DESC_AMY + TUTORIAL_DESC_AMY; + + // Delete by email + DeleteStudentFromClassByEmailCommand expectedDeleteByEmailCommand = + new DeleteStudentFromClassByEmailCommand(BOB.getEmail(), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + assertParseSuccess(parser, EMAIL_DESC_BOB + commandSuffix, expectedDeleteByEmailCommand); + + // Delete by student Id + DeleteStudentFromClassByIdCommand expectedDeleteByIdCommand = + new DeleteStudentFromClassByIdCommand(BOB.getStudentId(), + new ModuleCode(VALID_MODULE_AMY), new TutorialClass(VALID_TUTORIAL_AMY)); + assertParseSuccess(parser, STUDENT_ID_DESC_BOB + commandSuffix, expectedDeleteByIdCommand); + + } + + @Test + public void parse_invalidArgs_throwsParseException() { + String expectedMessage = String.format(MESSAGE_INVALID_COMMAND_FORMAT, + DeleteStudentFromClassCommand.MESSAGE_USAGE); + assertParseFailure(parser, "a", expectedMessage); + } +} diff --git a/src/test/java/seedu/address/logic/parser/DeleteTeamCommandParserTest.java b/src/test/java/seedu/address/logic/parser/DeleteTeamCommandParserTest.java new file mode 100644 index 00000000000..edb3a383487 --- /dev/null +++ b/src/test/java/seedu/address/logic/parser/DeleteTeamCommandParserTest.java @@ -0,0 +1,54 @@ +package seedu.address.logic.parser; + +import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; +import static seedu.address.logic.commands.CommandTestUtil.MODULE_DESC_AMY; +import static seedu.address.logic.commands.CommandTestUtil.TEAM_NAME_DESC_AMY; +import static seedu.address.logic.commands.CommandTestUtil.TUTORIAL_DESC_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; +import static seedu.address.logic.parser.CommandParserTestUtil.assertParseFailure; +import static seedu.address.logic.parser.CommandParserTestUtil.assertParseSuccess; + +import org.junit.jupiter.api.Test; + +import seedu.address.logic.commands.DeleteTeamCommand; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; + +/** + * Contains unit tests for AddTeamCommandParser. + */ +public class DeleteTeamCommandParserTest { + private final DeleteTeamCommandParser parser = new DeleteTeamCommandParser(); + + @Test + public void parse_deleteTeam_success() { + String userInput = MODULE_DESC_AMY + TUTORIAL_DESC_AMY + TEAM_NAME_DESC_AMY; + DeleteTeamCommand expectedCommand = new DeleteTeamCommand(new ModuleCode(VALID_MODULE_AMY), + new TutorialClass(VALID_TUTORIAL_AMY), VALID_TEAM_NAME_AMY); + assertParseSuccess(parser, userInput, expectedCommand); + } + + @Test + public void parse_deleteTeamWithNoName_failure() { + String expectedMessage = String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteTeamCommand.MESSAGE_USAGE); + String userInput = MODULE_DESC_AMY + TUTORIAL_DESC_AMY; + assertParseFailure(parser, userInput, expectedMessage); + } + + @Test + public void parse_deleteTeamWithNoModule_failure() { + String expectedMessage = String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteTeamCommand.MESSAGE_USAGE); + String userInput = TUTORIAL_DESC_AMY + TEAM_NAME_DESC_AMY; + assertParseFailure(parser, userInput, expectedMessage); + } + + @Test + public void parse_deleteTeamWithNoTutorial_failure() { + String expectedMessage = String.format(MESSAGE_INVALID_COMMAND_FORMAT, DeleteTeamCommand.MESSAGE_USAGE); + String userInput = MODULE_DESC_AMY + TEAM_NAME_DESC_AMY; + assertParseFailure(parser, userInput, expectedMessage); + } + +} diff --git a/src/test/java/seedu/address/logic/parser/EditCommandParserTest.java b/src/test/java/seedu/address/logic/parser/EditCommandParserTest.java index b047913bd69..6cc3f60984f 100644 --- a/src/test/java/seedu/address/logic/parser/EditCommandParserTest.java +++ b/src/test/java/seedu/address/logic/parser/EditCommandParserTest.java @@ -3,6 +3,8 @@ import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; import static seedu.address.logic.commands.CommandTestUtil.EMAIL_DESC_AMY; import static seedu.address.logic.commands.CommandTestUtil.EMAIL_DESC_BOB; +import static seedu.address.logic.commands.CommandTestUtil.INDEX_ONE; +import static seedu.address.logic.commands.CommandTestUtil.INDEX_TWO; import static seedu.address.logic.commands.CommandTestUtil.INVALID_EMAIL_DESC; import static seedu.address.logic.commands.CommandTestUtil.INVALID_NAME_DESC; import static seedu.address.logic.commands.CommandTestUtil.INVALID_STUDENT_ID_DESC; @@ -19,13 +21,13 @@ import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID_BOB; import static seedu.address.logic.commands.CommandTestUtil.VALID_TAG_FRIEND; import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; +import static seedu.address.logic.parser.CliSyntax.PREFIX_INDEX; import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; import static seedu.address.logic.parser.CliSyntax.PREFIX_TAG; import static seedu.address.logic.parser.CommandParserTestUtil.assertParseFailure; import static seedu.address.logic.parser.CommandParserTestUtil.assertParseSuccess; import static seedu.address.testutil.TypicalIndexes.INDEX_FIRST_PERSON; import static seedu.address.testutil.TypicalIndexes.INDEX_SECOND_PERSON; -import static seedu.address.testutil.TypicalIndexes.INDEX_THIRD_PERSON; import org.junit.jupiter.api.Test; @@ -54,10 +56,10 @@ public class EditCommandParserTest { @Test public void parse_missingParts_failure() { // no index specified - assertParseFailure(parser, VALID_NAME_AMY, MESSAGE_INVALID_FORMAT); + assertParseFailure(parser, NAME_DESC_AMY, MESSAGE_INVALID_FORMAT); // no field specified - assertParseFailure(parser, "1", EditCommand.MESSAGE_NOT_EDITED); + assertParseFailure(parser, INDEX_TWO, EditCommand.MESSAGE_NOT_EDITED); // no index and no field specified assertParseFailure(parser, "", MESSAGE_INVALID_FORMAT); @@ -66,60 +68,58 @@ public void parse_missingParts_failure() { @Test public void parse_invalidPreamble_failure() { // negative index - assertParseFailure(parser, "-5" + NAME_DESC_AMY, MESSAGE_INVALID_FORMAT); + assertParseFailure(parser, " " + PREFIX_INDEX + "-5" + NAME_DESC_AMY, MESSAGE_INVALID_FORMAT); // zero index - assertParseFailure(parser, "0" + NAME_DESC_AMY, MESSAGE_INVALID_FORMAT); + assertParseFailure(parser, " " + PREFIX_INDEX + "0" + NAME_DESC_AMY, MESSAGE_INVALID_FORMAT); // invalid arguments being parsed as preamble - assertParseFailure(parser, "1 some random string", MESSAGE_INVALID_FORMAT); + assertParseFailure(parser, " " + PREFIX_INDEX + "1 some random string", MESSAGE_INVALID_FORMAT); // invalid prefix being parsed as preamble - assertParseFailure(parser, "1 i/ string", MESSAGE_INVALID_FORMAT); + assertParseFailure(parser, " " + PREFIX_INDEX + "1 i/ string", MESSAGE_INVALID_FORMAT); } @Test public void parse_invalidValue_failure() { - assertParseFailure(parser, "1" + INVALID_NAME_DESC, Name.MESSAGE_CONSTRAINTS); // invalid name - assertParseFailure(parser, "1" + INVALID_STUDENT_ID_DESC, StudentId.MESSAGE_CONSTRAINTS); // invalid studentid - assertParseFailure(parser, "1" + INVALID_EMAIL_DESC, Email.MESSAGE_CONSTRAINTS); // invalid email - assertParseFailure(parser, "1" + INVALID_TAG_DESC, Tag.MESSAGE_CONSTRAINTS); // invalid tag + assertParseFailure(parser, INDEX_ONE + INVALID_NAME_DESC, Name.MESSAGE_CONSTRAINTS); // invalid name + assertParseFailure(parser, INDEX_ONE + INVALID_STUDENT_ID_DESC, StudentId.MESSAGE_CONSTRAINTS); // invalid id + assertParseFailure(parser, INDEX_ONE + INVALID_EMAIL_DESC, Email.MESSAGE_CONSTRAINTS); // invalid email + assertParseFailure(parser, INDEX_ONE + INVALID_TAG_DESC, Tag.MESSAGE_CONSTRAINTS); // invalid tag // invalid student id followed by valid email - assertParseFailure(parser, "1" + INVALID_STUDENT_ID_DESC + EMAIL_DESC_AMY, StudentId.MESSAGE_CONSTRAINTS); + assertParseFailure(parser, INDEX_ONE + INVALID_STUDENT_ID_DESC + EMAIL_DESC_AMY, StudentId.MESSAGE_CONSTRAINTS); // while parsing {@code PREFIX_TAG} alone will reset the tags of the {@code Person} being edited, // parsing it together with a valid tag results in error - assertParseFailure(parser, "1" + TAG_DESC_FRIEND + TAG_DESC_HUSBAND + TAG_EMPTY, Tag.MESSAGE_CONSTRAINTS); - assertParseFailure(parser, "1" + TAG_DESC_FRIEND + TAG_EMPTY + TAG_DESC_HUSBAND, Tag.MESSAGE_CONSTRAINTS); - assertParseFailure(parser, "1" + TAG_EMPTY + TAG_DESC_FRIEND + TAG_DESC_HUSBAND, Tag.MESSAGE_CONSTRAINTS); + assertParseFailure(parser, INDEX_ONE + TAG_DESC_FRIEND + TAG_DESC_HUSBAND + TAG_EMPTY, Tag.MESSAGE_CONSTRAINTS); + assertParseFailure(parser, INDEX_ONE + TAG_DESC_FRIEND + TAG_EMPTY + TAG_DESC_HUSBAND, Tag.MESSAGE_CONSTRAINTS); + assertParseFailure(parser, INDEX_ONE + TAG_EMPTY + TAG_DESC_FRIEND + TAG_DESC_HUSBAND, Tag.MESSAGE_CONSTRAINTS); // multiple invalid values, but only the first invalid value is captured - assertParseFailure(parser, "1" + INVALID_NAME_DESC + INVALID_EMAIL_DESC + assertParseFailure(parser, INDEX_ONE + INVALID_NAME_DESC + INVALID_EMAIL_DESC + VALID_MODULE_AMY + VALID_STUDENT_ID_AMY, Name.MESSAGE_CONSTRAINTS); } @Test public void parse_allFieldsSpecified_success() { - Index targetIndex = INDEX_SECOND_PERSON; - String userInput = targetIndex.getOneBased() + NAME_DESC_AMY + EMAIL_DESC_AMY + String userInput = INDEX_TWO + NAME_DESC_AMY + EMAIL_DESC_AMY + STUDENT_ID_DESC_AMY + TAG_DESC_FRIEND; EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder().withName(VALID_NAME_AMY) .withEmail(VALID_EMAIL_AMY).withStudentId(VALID_STUDENT_ID_AMY).withTags(VALID_TAG_FRIEND).build(); - EditCommand expectedCommand = new EditCommand(targetIndex, descriptor); + EditCommand expectedCommand = new EditCommand(INDEX_SECOND_PERSON, descriptor); assertParseSuccess(parser, userInput, expectedCommand); } @Test public void parse_someFieldsSpecified_success() { - Index targetIndex = INDEX_FIRST_PERSON; - String userInput = targetIndex.getOneBased() + STUDENT_ID_DESC_BOB + EMAIL_DESC_AMY; + String userInput = INDEX_ONE + STUDENT_ID_DESC_BOB + EMAIL_DESC_AMY; EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder().withStudentId(VALID_STUDENT_ID_BOB) .withEmail(VALID_EMAIL_AMY).build(); - EditCommand expectedCommand = new EditCommand(targetIndex, descriptor); + EditCommand expectedCommand = new EditCommand(INDEX_FIRST_PERSON, descriptor); assertParseSuccess(parser, userInput, expectedCommand); } @@ -127,26 +127,26 @@ public void parse_someFieldsSpecified_success() { @Test public void parse_oneFieldSpecified_success() { // name - Index targetIndex = INDEX_THIRD_PERSON; - String userInput = targetIndex.getOneBased() + NAME_DESC_AMY; + Index targetIndex = INDEX_SECOND_PERSON; + String userInput = INDEX_TWO + NAME_DESC_AMY; EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder().withName(VALID_NAME_AMY).build(); EditCommand expectedCommand = new EditCommand(targetIndex, descriptor); assertParseSuccess(parser, userInput, expectedCommand); // student id - userInput = targetIndex.getOneBased() + STUDENT_ID_DESC_AMY; + userInput = INDEX_TWO + STUDENT_ID_DESC_AMY; descriptor = new EditPersonDescriptorBuilder().withStudentId(VALID_STUDENT_ID_AMY).build(); expectedCommand = new EditCommand(targetIndex, descriptor); assertParseSuccess(parser, userInput, expectedCommand); // email - userInput = targetIndex.getOneBased() + EMAIL_DESC_AMY; + userInput = INDEX_TWO + EMAIL_DESC_AMY; descriptor = new EditPersonDescriptorBuilder().withEmail(VALID_EMAIL_AMY).build(); expectedCommand = new EditCommand(targetIndex, descriptor); assertParseSuccess(parser, userInput, expectedCommand); // tags - userInput = targetIndex.getOneBased() + TAG_DESC_FRIEND; + userInput = INDEX_TWO + TAG_DESC_FRIEND; descriptor = new EditPersonDescriptorBuilder().withTags(VALID_TAG_FRIEND).build(); expectedCommand = new EditCommand(targetIndex, descriptor); assertParseSuccess(parser, userInput, expectedCommand); @@ -159,17 +159,17 @@ public void parse_multipleRepeatedFields_failure() { // valid followed by invalid Index targetIndex = INDEX_FIRST_PERSON; - String userInput = targetIndex.getOneBased() + INVALID_STUDENT_ID_DESC + STUDENT_ID_DESC_BOB; + String userInput = INDEX_ONE + INVALID_STUDENT_ID_DESC + STUDENT_ID_DESC_BOB; assertParseFailure(parser, userInput, Messages.getErrorMessageForDuplicatePrefixes(PREFIX_STUDENTID)); // invalid followed by valid - userInput = targetIndex.getOneBased() + STUDENT_ID_DESC_BOB + INVALID_STUDENT_ID_DESC; + userInput = INDEX_ONE + STUDENT_ID_DESC_BOB + INVALID_STUDENT_ID_DESC; assertParseFailure(parser, userInput, Messages.getErrorMessageForDuplicatePrefixes(PREFIX_STUDENTID)); // mulltiple valid fields repeated - userInput = targetIndex.getOneBased() + STUDENT_ID_DESC_AMY + EMAIL_DESC_AMY + userInput = INDEX_ONE + STUDENT_ID_DESC_AMY + EMAIL_DESC_AMY + TAG_DESC_FRIEND + STUDENT_ID_DESC_AMY + EMAIL_DESC_AMY + TAG_DESC_FRIEND + STUDENT_ID_DESC_BOB + EMAIL_DESC_BOB; @@ -177,7 +177,7 @@ public void parse_multipleRepeatedFields_failure() { Messages.getErrorMessageForDuplicatePrefixes(PREFIX_STUDENTID, PREFIX_EMAIL)); // multiple invalid values - userInput = targetIndex.getOneBased() + INVALID_STUDENT_ID_DESC + INVALID_EMAIL_DESC + userInput = INDEX_ONE + INVALID_STUDENT_ID_DESC + INVALID_EMAIL_DESC + INVALID_STUDENT_ID_DESC + INVALID_EMAIL_DESC; assertParseFailure(parser, userInput, @@ -186,8 +186,8 @@ public void parse_multipleRepeatedFields_failure() { @Test public void parse_resetTags_success() { - Index targetIndex = INDEX_THIRD_PERSON; - String userInput = targetIndex.getOneBased() + TAG_EMPTY; + Index targetIndex = INDEX_SECOND_PERSON; + String userInput = INDEX_TWO + TAG_EMPTY; EditPersonDescriptor descriptor = new EditPersonDescriptorBuilder().withTags().build(); EditCommand expectedCommand = new EditCommand(targetIndex, descriptor); diff --git a/src/test/java/seedu/address/model/AddressBookTest.java b/src/test/java/seedu/address/model/AddressBookTest.java index ca7759f40aa..d472a5fe10f 100644 --- a/src/test/java/seedu/address/model/AddressBookTest.java +++ b/src/test/java/seedu/address/model/AddressBookTest.java @@ -4,9 +4,11 @@ import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertTrue; import static seedu.address.logic.commands.CommandTestUtil.VALID_EMAIL_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID_AMY; import static seedu.address.logic.commands.CommandTestUtil.VALID_TAG_HUSBAND; import static seedu.address.testutil.Assert.assertThrows; import static seedu.address.testutil.TypicalPersons.ALICE; +import static seedu.address.testutil.TypicalPersons.AMY; import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; import java.util.Arrays; @@ -83,6 +85,52 @@ public void hasPerson_personWithSameIdentityFieldsInAddressBook_returnsTrue() { assertTrue(addressBook.hasPerson(editedAlice)); } + @Test + public void hasPersonWithEmail_nullEmail_throwsNullPointerException() { + assertThrows(NullPointerException.class, () -> addressBook.hasPersonWithEmail(null)); + } + @Test + public void hasPersonWithEmail_personInAddressBook_returnsTrue() { + addressBook.addPerson(AMY); + assertTrue(addressBook.hasPersonWithEmail(AMY.getEmail())); + } + + @Test + public void hasPersonWithEmail_personNotInAddressBook_returnsFalse() { + assertFalse(addressBook.hasPersonWithEmail(AMY.getEmail())); + } + + @Test + public void hasPersonWithEmail_differentPersonWithSameEmail_returnsTrue() { + addressBook.addPerson(AMY); + Person alice = new PersonBuilder(ALICE).withEmail(VALID_EMAIL_AMY) + .build(); + assertTrue(addressBook.hasPersonWithEmail(alice.getEmail())); + } + + @Test + public void hasPersonWithStudentId_nullStudentId_throwsNullPointerException() { + assertThrows(NullPointerException.class, () -> addressBook.hasPersonWithStudentId(null)); + } + @Test + public void hasPersonWithStudentId_personInAddressBook_returnsTrue() { + addressBook.addPerson(AMY); + assertTrue(addressBook.hasPersonWithStudentId(AMY.getStudentId())); + } + + @Test + public void hasPersonWithStudentId_personNotInAddressBook_returnsFalse() { + assertFalse(addressBook.hasPersonWithStudentId(AMY.getStudentId())); + } + + @Test + public void hasPersonWithStudentId_differentPersonWithSameStudentId_returnsTrue() { + addressBook.addPerson(AMY); + Person alice = new PersonBuilder(ALICE).withStudentId(VALID_STUDENT_ID_AMY) + .build(); + assertTrue(addressBook.hasPersonWithStudentId(alice.getStudentId())); + } + @Test public void getPersonList_modifyList_throwsUnsupportedOperationException() { assertThrows(UnsupportedOperationException.class, () -> addressBook.getPersonList().remove(0)); diff --git a/src/test/java/seedu/address/model/ModelManagerTest.java b/src/test/java/seedu/address/model/ModelManagerTest.java index 7547d3af800..d1cbd6b3886 100644 --- a/src/test/java/seedu/address/model/ModelManagerTest.java +++ b/src/test/java/seedu/address/model/ModelManagerTest.java @@ -7,6 +7,7 @@ import static seedu.address.model.Model.PREDICATE_SHOW_ALL_PERSONS; import static seedu.address.testutil.Assert.assertThrows; import static seedu.address.testutil.TypicalPersons.ALICE; +import static seedu.address.testutil.TypicalPersons.AMY; import static seedu.address.testutil.TypicalPersons.BENSON; import java.nio.file.Path; @@ -91,6 +92,21 @@ public void hasPerson_personInAddressBook_returnsTrue() { assertTrue(modelManager.hasPerson(ALICE)); } + @Test + public void hasPersonWithEmail_nullEmail_throwsNullPointerException() { + assertThrows(NullPointerException.class, () -> modelManager.hasPersonWithEmail(null)); + } + @Test + public void hasPersonWithEmail_personInAddressBook_returnsTrue() { + modelManager.addPerson(AMY); + assertTrue(modelManager.hasPersonWithEmail(AMY.getEmail())); + } + + @Test + public void hasPersonWithEmail_personNotInAddressBook_returnsFalse() { + assertFalse(modelManager.hasPersonWithEmail(AMY.getEmail())); + } + @Test public void getFilteredPersonList_modifyList_throwsUnsupportedOperationException() { assertThrows(UnsupportedOperationException.class, () -> modelManager.getFilteredPersonList().remove(0)); From bc0b0620427b1c612f2537f450a8aa3d46d376b3 Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Wed, 27 Mar 2024 16:13:39 +0800 Subject: [PATCH 06/12] Update UserGuide.md --- docs/UserGuide.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/docs/UserGuide.md b/docs/UserGuide.md index 1cd1b037e6f..afdf7004b9d 100644 --- a/docs/UserGuide.md +++ b/docs/UserGuide.md @@ -13,6 +13,14 @@ TAHelper is a **desktop app for managing contacts, optimized for use via a Line --- +## Target Audience + +TAHelper is specifically designed to assist and help Teaching Assistants (TA) of NUS Computer Science Modules, +which caters to their need to store information in a way that is easy to track and visualise, as well as keep student's +details in a centralised storage. Our target audience is specifically only TAs of NUS Computer Science Modules. + +## Purpose of User Guide + ## Quick start 1. Ensure you have Java `11` or above installed in your Computer. From 83d8320473ffd52d28a5a780bde9e50a7e9b78ea Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Thu, 28 Mar 2024 02:16:55 +0800 Subject: [PATCH 07/12] Add Allocate Student to Team Command and its Parser Add a new command that allows user to add an existing student that is in the tutorial class to an existing team in that tutorial group. Let's * Add a new AllocateStudentToTeamCommand and AllocateStudentToTeamCommandParser class to add the user into an existing team of an existing tutorial group in an existing module. * Add more functions to AddressBook class to support the command and parser above. --- .../logic/commands/AddTeamCommand.java | 2 +- .../AllocateStudentToTeamCommand.java | 35 +++++-- .../logic/parser/AddressBookParser.java | 4 + .../AllocateStudentToTeamCommandParser.java | 24 ++--- .../address/logic/parser/ParserUtil.java | 4 +- .../java/seedu/address/model/AddressBook.java | 99 ++++++++++++++++++- src/main/java/seedu/address/model/Model.java | 37 +++++++ .../seedu/address/model/ModelManager.java | 40 ++++++++ .../address/model/ReadOnlyAddressBook.java | 3 + .../address/model/module/ModuleCode.java | 6 +- .../address/model/module/TutorialClass.java | 14 +-- .../address/model/module/TutorialTeam.java | 26 ++++- .../address/storage/JsonAdaptedModule.java | 29 ++++-- .../address/storage/JsonAdaptedPerson.java | 1 - .../storage/JsonAdaptedTutorialClass.java | 49 +++++---- .../storage/JsonAdaptedTutorialTeam.java | 41 +++++--- .../storage/JsonSerializableAddressBook.java | 5 +- .../logic/commands/AddStudentCommandTest.java | 26 +++++ 18 files changed, 350 insertions(+), 95 deletions(-) diff --git a/src/main/java/seedu/address/logic/commands/AddTeamCommand.java b/src/main/java/seedu/address/logic/commands/AddTeamCommand.java index 173c347f4d4..e06c6bfe565 100644 --- a/src/main/java/seedu/address/logic/commands/AddTeamCommand.java +++ b/src/main/java/seedu/address/logic/commands/AddTeamCommand.java @@ -79,7 +79,7 @@ public CommandResult execute(Model model) throws CommandException { if (tutorialClass.hasTeam(newTeam)) { throw new CommandException(String.format(MESSAGE_DUPLICATE_TEAM, teamName, module, tutorialClass)); } else { - tutorialClass.addTeam(newTeam); + model.addTeam(tutorialClass, newTeam); } if (teamSize != Integer.MAX_VALUE) { diff --git a/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java b/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java index 07504be4c4a..9c5e1377fce 100644 --- a/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java +++ b/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java @@ -1,18 +1,20 @@ package seedu.address.logic.commands; -import seedu.address.commons.util.ToStringBuilder; -import seedu.address.commons.util.CollectionUtil; -import seedu.address.logic.commands.exceptions.*; -import seedu.address.model.*; -import seedu.address.model.module.*; -import seedu.address.model.person.*; - import static java.util.Objects.requireNonNull; import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; import static seedu.address.logic.parser.CliSyntax.PREFIX_TEAMNAME; import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; +import seedu.address.commons.util.CollectionUtil; +import seedu.address.commons.util.ToStringBuilder; +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.StudentId; + /** * Allocates a student to a team in a tutorial Class in TAHelper. */ @@ -38,6 +40,7 @@ public class AllocateStudentToTeamCommand extends Command { + " in the tutorial class!"; public static final String MESSAGE_CLASS_DOES_NOT_EXIST = "Tutorial class does not exist in module"; + public static final String MESSAGE_TEAM_SIZE_EXCEEDED = "Max team size reached"; private final StudentId studentId; private final ModuleCode moduleCode; @@ -64,15 +67,27 @@ public CommandResult execute(Model model) throws CommandException { throw new CommandException(MESSAGE_CLASS_DOES_NOT_EXIST); } - if (!model.hasTeamInTutorial(tutorialClass, tutorialTeam)) { + ModuleCode module = model.findModuleFromList(moduleCode); + TutorialClass tutClass = model.findTutorialClassFromList(tutorialClass, module); + + if (!model.hasTeamInTutorial(tutClass, tutorialTeam)) { + throw new CommandException(MESSAGE_TEAM_DOES_NOT_EXIST); + } + + TutorialTeam tutTeam = model.getTutorialTeam(tutClass, tutorialTeam); + if (tutTeam == null) { throw new CommandException(MESSAGE_TEAM_DOES_NOT_EXIST); } - if (model.isStudentInAnyTeam(studentId, tutorialClass)) { + if (model.isStudentInAnyTeam(studentId, tutClass)) { throw new CommandException(MESSAGE_DUPLICATE_PERSON_IN_TEAM); } - model.allocateStudentToTeam(studentId, tutorialTeam); + if (model.hasTeamSizeExceeded(tutTeam)) { + throw new CommandException(MESSAGE_TEAM_SIZE_EXCEEDED); + } + + model.allocateStudentToTeam(studentId, tutTeam); return new CommandResult(String.format(MESSAGE_SUCCESS)); } diff --git a/src/main/java/seedu/address/logic/parser/AddressBookParser.java b/src/main/java/seedu/address/logic/parser/AddressBookParser.java index ecef39ff8d0..d882a7b627d 100644 --- a/src/main/java/seedu/address/logic/parser/AddressBookParser.java +++ b/src/main/java/seedu/address/logic/parser/AddressBookParser.java @@ -11,6 +11,7 @@ import seedu.address.logic.commands.AddClassCommand; import seedu.address.logic.commands.AddStudentCommand; import seedu.address.logic.commands.AddTeamCommand; +import seedu.address.logic.commands.AllocateStudentToTeamCommand; import seedu.address.logic.commands.ClearCommand; import seedu.address.logic.commands.Command; import seedu.address.logic.commands.DeleteClassCommand; @@ -118,6 +119,9 @@ public Command parseCommand(String userInput) throws ParseException { case DeleteTeamCommand.COMMAND_WORD: return new DeleteTeamCommandParser().parse(arguments); + case AllocateStudentToTeamCommand.COMMAND_WORD: + return new AllocateStudentToTeamCommandParser().parse(arguments); + default: logger.finer("This user input caused a ParseException: " + userInput); throw new ParseException(MESSAGE_UNKNOWN_COMMAND); diff --git a/src/main/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParser.java b/src/main/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParser.java index 1a2618ea9bf..8df61286c54 100644 --- a/src/main/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParser.java @@ -1,26 +1,20 @@ package seedu.address.logic.parser; - -import seedu.address.logic.commands.*; -import seedu.address.logic.commands.addstudenttoclasscommands.*; -import seedu.address.logic.parser.exceptions.*; -import seedu.address.model.module.*; -import seedu.address.model.person.*; -import seedu.address.model.tag.*; - -import java.util.*; -import java.util.stream.*; - import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; -import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; -import static seedu.address.logic.parser.CliSyntax.PREFIX_INDEX; import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; -import static seedu.address.logic.parser.CliSyntax.PREFIX_NAME; import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; -import static seedu.address.logic.parser.CliSyntax.PREFIX_TAG; import static seedu.address.logic.parser.CliSyntax.PREFIX_TEAMNAME; import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; +import java.util.stream.Stream; + +import seedu.address.logic.commands.AllocateStudentToTeamCommand; +import seedu.address.logic.parser.exceptions.ParseException; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.StudentId; + /** * Parses input arguments and creates a new AllocateStudentToTeamCommand object */ diff --git a/src/main/java/seedu/address/logic/parser/ParserUtil.java b/src/main/java/seedu/address/logic/parser/ParserUtil.java index 51a56ee29ba..5962c7c69c8 100644 --- a/src/main/java/seedu/address/logic/parser/ParserUtil.java +++ b/src/main/java/seedu/address/logic/parser/ParserUtil.java @@ -9,7 +9,9 @@ import seedu.address.commons.core.index.Index; import seedu.address.commons.util.StringUtil; import seedu.address.logic.parser.exceptions.ParseException; -import seedu.address.model.module.*; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Email; import seedu.address.model.person.Name; import seedu.address.model.person.StudentId; diff --git a/src/main/java/seedu/address/model/AddressBook.java b/src/main/java/seedu/address/model/AddressBook.java index 738a6aa19f3..2facec0f3a0 100644 --- a/src/main/java/seedu/address/model/AddressBook.java +++ b/src/main/java/seedu/address/model/AddressBook.java @@ -14,6 +14,7 @@ import seedu.address.logic.messages.ModuleMessages; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Email; import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; @@ -29,6 +30,8 @@ public class AddressBook implements ReadOnlyAddressBook { private ObservableList sortedPersons; private final ArrayList modules; private final ArrayList tutorialClasses; + private final ArrayList tutorialTeams; + private final UniquePersonList studentsInTeam; /* * The 'unusual' code block below is a non-static initialization block, @@ -44,6 +47,8 @@ public class AddressBook implements ReadOnlyAddressBook { persons = new UniquePersonList(); modules = new ArrayList<>(); tutorialClasses = new ArrayList<>(); + tutorialTeams = new ArrayList<>(); + studentsInTeam = new UniquePersonList(); } public AddressBook() { @@ -82,6 +87,17 @@ public void setClass(List tutorialClasses) { this.tutorialClasses.addAll(tutorialClasses); } + public void setTutorialTeams(List tutorialTeams) { + requireNonNull(tutorialTeams); + this.tutorialTeams.clear(); + this.tutorialTeams.addAll(tutorialTeams); + } + + public void setStudentsInTeam(List students) { + requireNonNull(students); + this.studentsInTeam.setPersons(students); + } + /** * Resets the existing data of this {@code AddressBook} with {@code newData}. */ @@ -90,7 +106,8 @@ public void resetData(ReadOnlyAddressBook newData) { setPersons(newData.getPersonList()); setModules(newData.getModuleList()); setClass(newData.getTutorialList()); - + setTutorialTeams(newData.getTutorialTeamList()); + setStudentsInTeam(newData.getStudentInTeamList()); } //// person-level operations @@ -228,6 +245,76 @@ public void deletePersonFromTutorialClass(Person person, ModuleCode module, Tuto tutorialClassInList.deleteStudent(person); } + /** + * Allocates the {@code studentId} to the {@code tutorialTeam} + * @param tutorialTeam to allocate the student into. + */ + public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { + requireNonNull(studentId); + requireNonNull(tutorialTeam); + Person student = persons.getPerson(studentId); + tutorialTeam.addStudent(student); + } + + /** + * Returns true if the {@code tutorialTeam} size has exceeded its limit. + * @param tutorialTeam size to check. + * @return a boolean that indicates whether the team size will be exceeded by adding another person. + */ + boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam) { + requireNonNull(tutorialTeam); + int maxTeamSize = tutorialTeam.getTeamSize(); + int currTeamSize = tutorialTeam.getStudents().size(); + return (maxTeamSize >= currTeamSize); + }; + + /** + * Returns true if the {@code studentId} is already in a team of {@code tutorialClass}. + * @param tutorialClass of the teams. + * @param studentId to search for. + */ + public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { + boolean isStudentExist = false; + for (TutorialTeam tutorialTeam : tutorialClass.getTeams()) { + isStudentExist = tutorialTeam.hasStudentVerified(studentId, tutorialTeam); + } + return isStudentExist; + }; + + /** + * Returns true if a team with the same identity as {@code tutorialTeam} exists in the {@code tutorialClass} + * @param tutorialClass of the tutorialTeam. + * @param tutorialTeam to check if it exist. + */ + public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + requireNonNull(tutorialClass); + requireNonNull(tutorialTeam); + ArrayList listOfTeams = tutorialClass.getTeams(); + ObservableList teams = FXCollections.observableList(listOfTeams); + return teams.stream().anyMatch(tutorialClass::hasTeam); + } + + public TutorialTeam getTutorialTeam(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + requireNonNull(tutorialClasses); + requireNonNull(tutorialTeam); + TutorialTeam tutTeam = tutorialClass.getTeams().stream() + .filter(team -> team.getTeamName().equals(tutorialTeam.getTeamName())) + .findFirst() + .orElse(null); + return tutTeam; + } + + /** + * adds a team into the tutorial class + * @param tutorialClass to add the tutorialTeam to. + * @param tutorialTeam to be added into the tutorialClass. + */ + public void addTeam(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + requireNonNull(tutorialClass); + requireNonNull(tutorialTeam); + tutorialClass.addTeam(tutorialTeam); + } + /** * Replaces the given person {@code target} in the list with * {@code editedPerson}. @@ -270,6 +357,16 @@ public ObservableList getPersonList() { return persons.asUnmodifiableObservableList(); } + @Override + public ObservableList getTutorialTeamList() { + return FXCollections.observableList(tutorialTeams); + } + + @Override + public ObservableList getStudentInTeamList() { + return studentsInTeam.asUnmodifiableObservableList(); + } + @Override public ObservableList getModuleList() { return FXCollections.observableList(modules); diff --git a/src/main/java/seedu/address/model/Model.java b/src/main/java/seedu/address/model/Model.java index d35ec2f839b..836fb4ab4c0 100644 --- a/src/main/java/seedu/address/model/Model.java +++ b/src/main/java/seedu/address/model/Model.java @@ -8,6 +8,7 @@ import seedu.address.commons.core.GuiSettings; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Email; import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; @@ -95,12 +96,21 @@ public interface Model { */ void deletePerson(Person target); + /** + * adds a team into the tutorial class + * @param tutorialClass to add the tutorialTeam to. + * @param tutorialTeam to be added into the tutorialClass. + */ + public void addTeam(TutorialClass tutorialClass, TutorialTeam tutorialTeam); + /** * Deletes the given module. * The module must exist in the address book. */ void deleteModule(ModuleCode target); + public TutorialTeam getTutorialTeam(TutorialClass tutorialClass, TutorialTeam tutorialTeam); + /** * Adds the given person. * {@code person} must not already exist in the address book. @@ -113,6 +123,33 @@ public interface Model { */ void addModule(ModuleCode module); + /** + * Allocates the {@code studentId} to the {@code tutorialTeam} + * @param tutorialTeam to allocate the student into. + */ + public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam); + + /** + * Returns true if a team with the same identity as {@code tutorialTeam} exists in the {@code tutorialClass} + * @param tutorialClass of the tutorialTeam. + * @param tutorialTeam to check if it exist. + */ + public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam); + + /** + * Returns true if the {@code studentId} is already in a team of {@code tutorialClass}. + * @param tutorialClass of the teams. + * @param studentId to search for. + */ + public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass); + + /** + * Returns true if the {@code tutorialTeam} size has exceeded its limit. + * @param tutorialTeam size to check. + * @return a boolean that indicates whether the team size will be exceeded by adding another person. + */ + boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam); + /** * Adds the given person to the given tutorial class in the given module. */ diff --git a/src/main/java/seedu/address/model/ModelManager.java b/src/main/java/seedu/address/model/ModelManager.java index 101d78b8d9b..b3c71f10d78 100644 --- a/src/main/java/seedu/address/model/ModelManager.java +++ b/src/main/java/seedu/address/model/ModelManager.java @@ -14,6 +14,7 @@ import seedu.address.commons.core.LogsCenter; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Email; import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; @@ -145,6 +146,45 @@ public void addPerson(Person person) { updateFilteredPersonList(PREDICATE_SHOW_ALL_PERSONS); } + @Override + public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { + addressBook.allocateStudentToTeam(studentId, tutorialTeam); + } + + @Override + public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + requireAllNonNull(tutorialClass, tutorialTeam); + return addressBook.hasTeamInTutorial(tutorialClass, tutorialTeam); + } + + @Override + public TutorialTeam getTutorialTeam(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + requireAllNonNull(tutorialClass, tutorialTeam); + return addressBook.getTutorialTeam(tutorialClass, tutorialTeam); + } + + /** + * Add a team to the tutorial class + * @param tutorialTeam to be added to the tutorial class + */ + @Override + public void addTeam(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + requireNonNull(tutorialTeam); + addressBook.addTeam(tutorialClass, tutorialTeam); + } + + @Override + public boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam) { + requireNonNull(tutorialTeam); + return addressBook.hasTeamSizeExceeded(tutorialTeam); + }; + + @Override + public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { + requireAllNonNull(studentId, tutorialClass); + return addressBook.isStudentInAnyTeam(studentId, tutorialClass); + } + @Override public void addModule(ModuleCode module) { addressBook.addModule(module, diff --git a/src/main/java/seedu/address/model/ReadOnlyAddressBook.java b/src/main/java/seedu/address/model/ReadOnlyAddressBook.java index 840d98b1e28..df019f04605 100644 --- a/src/main/java/seedu/address/model/ReadOnlyAddressBook.java +++ b/src/main/java/seedu/address/model/ReadOnlyAddressBook.java @@ -5,6 +5,7 @@ import javafx.collections.ObservableList; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Person; /** @@ -26,6 +27,8 @@ public interface ReadOnlyAddressBook { void setSortedPersonList(Comparator comparator); ObservableList getSortedPersonList(); + ObservableList getTutorialTeamList(); + ObservableList getStudentInTeamList(); /** * Checks if the address book contains the specified module code. diff --git a/src/main/java/seedu/address/model/module/ModuleCode.java b/src/main/java/seedu/address/model/module/ModuleCode.java index bae5af16c70..b570cf48ce0 100644 --- a/src/main/java/seedu/address/model/module/ModuleCode.java +++ b/src/main/java/seedu/address/model/module/ModuleCode.java @@ -22,7 +22,7 @@ public class ModuleCode { public static final String VALIDATION_REGEX = "^[A-Z]{2,3}\\d{4}[A-Z]?$"; public final String moduleCode; - private final ArrayList tutorialClasses; + private final List tutorialClasses; private String description; /** @@ -75,7 +75,7 @@ public ModuleCode(String moduleCode, List tutorialClass, String d * @param moduleCode of the module to be created * @param tutorialClasses of the module to be created */ - public ModuleCode(String moduleCode, ArrayList tutorialClasses) { + public ModuleCode(String moduleCode, List tutorialClasses) { requireAllNonNull(moduleCode); checkArgument(isValidModuleCode(moduleCode), MESSAGE_CONSTRAINTS); this.moduleCode = moduleCode; @@ -94,7 +94,7 @@ public static boolean isValidModuleCode(String test) { * @return the ArrayList of tutorial classes. */ public ArrayList getTutorialClasses() { - return tutorialClasses; + return (ArrayList) tutorialClasses; } /** diff --git a/src/main/java/seedu/address/model/module/TutorialClass.java b/src/main/java/seedu/address/model/module/TutorialClass.java index facb407dc34..4d696826300 100644 --- a/src/main/java/seedu/address/model/module/TutorialClass.java +++ b/src/main/java/seedu/address/model/module/TutorialClass.java @@ -157,15 +157,11 @@ public void addTeam(TutorialTeam team) { * @param team */ public boolean hasTeam(TutorialTeam team) { - if (teams.contains(team)) { - return true; - } - for (TutorialTeam tutorialTeam : teams) { + for (TutorialTeam tutorialTeam : this.teams) { if (tutorialTeam.getTeamName().equals(team.getTeamName())) { return true; } }; - return false; } @@ -177,14 +173,6 @@ public void deleteTeam(TutorialTeam team) { teams.remove(team); } - /** - * Deletes a team from the tutorial class. - * @param team - */ - public void deleteTeam(TutorialTeam team) { - teams.remove(team); - } - @Override public String toString() { return tutorialName; diff --git a/src/main/java/seedu/address/model/module/TutorialTeam.java b/src/main/java/seedu/address/model/module/TutorialTeam.java index 62ec0857cc2..8be1eb9dcfb 100644 --- a/src/main/java/seedu/address/model/module/TutorialTeam.java +++ b/src/main/java/seedu/address/model/module/TutorialTeam.java @@ -3,9 +3,13 @@ import static seedu.address.commons.util.AppUtil.checkArgument; import static seedu.address.commons.util.CollectionUtil.requireAllNonNull; +import java.lang.reflect.*; import java.util.ArrayList; +import javafx.collections.FXCollections; +import javafx.collections.ObservableList; import seedu.address.model.person.Person; +import seedu.address.model.person.StudentId; /** * Represents a Module's tutorial team. @@ -67,7 +71,7 @@ public TutorialTeam(String tutorialTeam, int teamSize) { /** * A constructor for TutorialTeam. Creates a tutorial team with students. - * @param tutorialClass to be added + * @param tutorialTeam to be added * @param students in the tutorial class */ public TutorialTeam(String tutorialTeam, ArrayList students) { @@ -81,7 +85,7 @@ public TutorialTeam(String tutorialTeam, ArrayList students) { /** * A constructor for TutorialTeam. Creates a tutorial team with students and * team size. - * @param tutorialClass to be added + * @param tutorialTeam to be added * @param students in the tutorial class * @param teamSize of the tutorial team */ @@ -176,6 +180,24 @@ public boolean hasStudent(Person student) { return students.contains(student); } + /** + * Checks if a student exist by their id + * @param studentId + * @return true if a person is in the list of students + */ + public boolean hasStudentVerified(StudentId studentId, TutorialTeam tutorialTeam) { + ArrayList teamList = tutorialTeam.getStudents(); + if (teamList.size() == 0 || teamList == null) { + return false; + } + for (Person student : teamList) { + if (student.getStudentId().value.equals(studentId.value)) { + return true; + }; + } + return false; + } + @Override public String toString() { return teamName; diff --git a/src/main/java/seedu/address/storage/JsonAdaptedModule.java b/src/main/java/seedu/address/storage/JsonAdaptedModule.java index d3206f85089..d882cbaa0e3 100644 --- a/src/main/java/seedu/address/storage/JsonAdaptedModule.java +++ b/src/main/java/seedu/address/storage/JsonAdaptedModule.java @@ -1,6 +1,7 @@ package seedu.address.storage; import java.util.ArrayList; +import java.util.List; import java.util.stream.Collectors; import com.fasterxml.jackson.annotation.JsonCreator; @@ -9,6 +10,7 @@ import seedu.address.commons.exceptions.IllegalValueException; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; +import seedu.address.model.person.StudentId; /** * Jackson-friendly version of {@link ModuleCode}. @@ -18,7 +20,7 @@ class JsonAdaptedModule { public static final String MISSING_FIELD_MESSAGE_FORMAT = "Module name is missing!"; private final String name; - private final ArrayList tutorialClasses; + private final List tutorialClasses = new ArrayList<>(); private final String description; /** @@ -26,11 +28,13 @@ class JsonAdaptedModule { */ @JsonCreator public JsonAdaptedModule(@JsonProperty("name") String name, - @JsonProperty("tutorialClasses") ArrayList tutorialClasses, + @JsonProperty("tutorialClasses") List tutorialClasses, @JsonProperty("description") String description) { this.name = name; - this.tutorialClasses = tutorialClasses; this.description = description; + if (tutorialClasses != null) { + this.tutorialClasses.addAll(tutorialClasses); + } } /** @@ -38,8 +42,8 @@ public JsonAdaptedModule(@JsonProperty("name") String name, */ public JsonAdaptedModule(ModuleCode source) { name = source.toString(); - this.tutorialClasses = source.getTutorialClasses().stream().map(JsonAdaptedTutorialClass::new) - .collect(Collectors.toCollection(ArrayList::new)); + tutorialClasses.addAll(source.getTutorialClasses().stream().map(JsonAdaptedTutorialClass::new) + .collect(Collectors.toCollection(ArrayList::new))); this.description = source.getDescription(); } @@ -53,7 +57,7 @@ public String getModuleName() { /** * Retrieves tutorial classes from the module. */ - public ArrayList getTutorialClasses() { + public List getTutorialClasses() { return tutorialClasses; } @@ -66,16 +70,21 @@ public ModuleCode toModelType() throws IllegalValueException { if (!ModuleCode.isValidModuleCode(name)) { throw new IllegalValueException(String.format(MISSING_FIELD_MESSAGE_FORMAT, name)); } - ArrayList tutorialClasses = new ArrayList<>(); + final List listOfClass = new ArrayList<>(); for (JsonAdaptedTutorialClass tutorialClass : this.tutorialClasses) { - tutorialClasses.add(tutorialClass.toModelType()); + listOfClass.add(tutorialClass.toModelType()); } + ModuleCode moduleCode; + if (!ModuleCode.isValidModuleCode(name)) { + throw new IllegalValueException(StudentId.MESSAGE_CONSTRAINTS); + } + if (description != null && !description.isEmpty()) { - moduleCode = new ModuleCode(name, tutorialClasses, + moduleCode = new ModuleCode(name, listOfClass, description); } else { - moduleCode = new ModuleCode(name, tutorialClasses); + moduleCode = new ModuleCode(name, listOfClass); } return moduleCode; diff --git a/src/main/java/seedu/address/storage/JsonAdaptedPerson.java b/src/main/java/seedu/address/storage/JsonAdaptedPerson.java index 06f62b98cb5..f979448b1c6 100644 --- a/src/main/java/seedu/address/storage/JsonAdaptedPerson.java +++ b/src/main/java/seedu/address/storage/JsonAdaptedPerson.java @@ -95,5 +95,4 @@ public Person toModelType() throws IllegalValueException { final Set modelTags = new HashSet<>(personTags); return new Person(modelName, modelEmail, modelStudentId, modelTags); } - } diff --git a/src/main/java/seedu/address/storage/JsonAdaptedTutorialClass.java b/src/main/java/seedu/address/storage/JsonAdaptedTutorialClass.java index adaf8763c6e..cce9a538175 100644 --- a/src/main/java/seedu/address/storage/JsonAdaptedTutorialClass.java +++ b/src/main/java/seedu/address/storage/JsonAdaptedTutorialClass.java @@ -10,16 +10,19 @@ import seedu.address.commons.exceptions.IllegalValueException; import seedu.address.model.module.TutorialClass; import seedu.address.model.module.TutorialTeam; -import seedu.address.model.person.Person; +import seedu.address.model.person.*; + +import static seedu.address.storage.JsonAdaptedModule.MISSING_FIELD_MESSAGE_FORMAT; /** * Jackson-friendly version of {@link TutorialClass}. */ public class JsonAdaptedTutorialClass { + public static final String MISSING_FIELD_MESSAGE_FORMAT = "tutorial name is missing!"; private final String tutorialName; - private final List students; - private final List teams; + private final List students = new ArrayList<>(); + private final List teams = new ArrayList<>(); /** * Constructs a {@code JsonAdaptedTutorialClass} with the given @@ -30,17 +33,21 @@ public JsonAdaptedTutorialClass(@JsonProperty("tutorialName") String tutorialNam @JsonProperty("teams") List teams, @JsonProperty("students") List students) { this.tutorialName = tutorialName; - this.teams = teams != null ? new ArrayList<>(teams) : new ArrayList<>(); - this.students = students != null ? new ArrayList<>(students) : new ArrayList<>(); + if (teams != null) { + this.teams.addAll(teams); + } + if (students != null) { + this.students.addAll(students); + } } /** * Converts a given {@code TutorialClass} into this class for Jackson use. */ public JsonAdaptedTutorialClass(TutorialClass source) { - this.tutorialName = source.tutorialName; - this.teams = source.getTeams().stream().map(JsonAdaptedTutorialTeam::new).collect(Collectors.toList()); - this.students = source.getStudents().stream().map(JsonAdaptedPerson::new).collect(Collectors.toList()); + this.tutorialName = source.getTutorialClass().tutorialName; + teams.addAll(source.getTeams().stream().map(JsonAdaptedTutorialTeam::new).collect(Collectors.toList())); + students.addAll(source.getStudents().stream().map(JsonAdaptedPerson::new).collect(Collectors.toList())); } public String getTutorialName() { @@ -63,19 +70,23 @@ public List getStudents() { * the adapted tutorial class. */ public TutorialClass toModelType() throws IllegalValueException { - try { - ArrayList students = new ArrayList<>(); - for (JsonAdaptedPerson student : this.students) { - students.add(student.toModelType()); - } - ArrayList teams = new ArrayList<>(); - for (JsonAdaptedTutorialTeam team : this.teams) { - teams.add(team.toModelType()); - } - return new TutorialClass(tutorialName, students, teams); - } catch (IllegalValueException e) { + ArrayList listOfStudents = new ArrayList<>(); + ArrayList listOfTeams = new ArrayList<>(); + + for (JsonAdaptedPerson student : students) { + listOfStudents.add(student.toModelType()); + } + for (JsonAdaptedTutorialTeam team : teams) { + listOfTeams.add(team.toModelType()); + } + + if (tutorialName == null) { + throw new IllegalValueException(String.format(MISSING_FIELD_MESSAGE_FORMAT, tutorialName)); + } + if (!TutorialClass.isValidTutorialClass(tutorialName)) { throw new IllegalValueException(TutorialClass.MESSAGE_CONSTRAINTS); } + return new TutorialClass(tutorialName, listOfStudents, listOfTeams); } @Override diff --git a/src/main/java/seedu/address/storage/JsonAdaptedTutorialTeam.java b/src/main/java/seedu/address/storage/JsonAdaptedTutorialTeam.java index 8e132df59c3..3fe120a0cfd 100644 --- a/src/main/java/seedu/address/storage/JsonAdaptedTutorialTeam.java +++ b/src/main/java/seedu/address/storage/JsonAdaptedTutorialTeam.java @@ -8,17 +8,18 @@ import com.fasterxml.jackson.annotation.JsonProperty; import seedu.address.commons.exceptions.IllegalValueException; -import seedu.address.model.module.TutorialTeam; -import seedu.address.model.person.Person; +import seedu.address.model.module.*; +import seedu.address.model.person.*; /** * Jackson-friendly version of {@link TutorialTeam}. */ public class JsonAdaptedTutorialTeam { + public static final String MISSING_FIELD_MESSAGE_FORMAT = "team name is missing!"; private final String teamName; private final int teamSize; - private final List students; + private final List students = new ArrayList<>(); /** * Constructs a {@code JsonAdaptedTutorialTeam} with the given @@ -29,7 +30,9 @@ public JsonAdaptedTutorialTeam(@JsonProperty("teamName") String teamName, @JsonProperty("teamSize") int teamSize, @JsonProperty("students") List students) { this.teamName = teamName; - this.students = students != null ? new ArrayList<>(students) : new ArrayList<>(); + if (students != null) { + this.students.addAll(students); + } this.teamSize = teamSize; } @@ -37,9 +40,9 @@ public JsonAdaptedTutorialTeam(@JsonProperty("teamName") String teamName, * Converts a given {@code TutorialTeam} into this class for Jackson use. */ public JsonAdaptedTutorialTeam(TutorialTeam source) { - this.teamName = source.teamName; - this.teamSize = source.teamSize; - this.students = source.getStudents().stream().map(JsonAdaptedPerson::new).collect(Collectors.toList()); + this.teamName = source.getTeamName(); + this.teamSize = source.getTeamSize(); + students.addAll(source.getStudents().stream().map(JsonAdaptedPerson::new).collect(Collectors.toList())); } public String getTeamName() { @@ -51,7 +54,7 @@ public int getTeamSize() { } public List getStudents() { - return new ArrayList<>(students); + return this.students; } /** @@ -62,15 +65,21 @@ public List getStudents() { * the adapted tutorial team. */ public TutorialTeam toModelType() throws IllegalValueException { - try { - ArrayList students = new ArrayList<>(); - for (JsonAdaptedPerson student : this.students) { - students.add(student.toModelType()); - } - return new TutorialTeam(teamName, students, teamSize); - } catch (IllegalValueException e) { - throw new IllegalValueException(TutorialTeam.MESSAGE_CONSTRAINTS); + final ArrayList listOfStudents = new ArrayList<>(); + if (teamName == null) { + throw new IllegalValueException(String.format(MISSING_FIELD_MESSAGE_FORMAT, teamName)); + } + if (!TutorialTeam.isValidTeamName(teamName)) { + throw new IllegalValueException(Name.MESSAGE_CONSTRAINTS); + } + + if (!TutorialTeam.isValidSize(teamSize)) { + throw new IllegalValueException(Name.MESSAGE_CONSTRAINTS); + } + for (JsonAdaptedPerson student : students) { + listOfStudents.add(student.toModelType()); } + return new TutorialTeam(teamName, listOfStudents, teamSize); } @Override diff --git a/src/main/java/seedu/address/storage/JsonSerializableAddressBook.java b/src/main/java/seedu/address/storage/JsonSerializableAddressBook.java index e67b72b8113..2f6b729990e 100644 --- a/src/main/java/seedu/address/storage/JsonSerializableAddressBook.java +++ b/src/main/java/seedu/address/storage/JsonSerializableAddressBook.java @@ -33,7 +33,7 @@ class JsonSerializableAddressBook { */ @JsonCreator public JsonSerializableAddressBook(@JsonProperty("persons") List persons, - @JsonProperty("modules") List modules) { + @JsonProperty("modules") List modules) { if (persons != null) { this.persons.addAll(persons); } @@ -72,7 +72,7 @@ public AddressBook toModelType() throws IllegalValueException { throw new IllegalValueException(MESSAGE_DUPLICATE_MODULE); } addressBook.addModule(module, - module.getDescription()); + module.getDescription()); } return addressBook; } @@ -111,5 +111,4 @@ public void addPersonToTutorialClass(String moduleName, String tutorialName, Per throw new IllegalValueException("Module containing tutorial class '" + tutorialName + "' not found."); } } - } diff --git a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java index e448a9e9e1e..3d99f6e794c 100644 --- a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java @@ -25,6 +25,7 @@ import seedu.address.model.ReadOnlyUserPrefs; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Email; import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; @@ -138,6 +139,26 @@ public void setAddressBook(ReadOnlyAddressBook newData) { throw new AssertionError("This method should not be called."); } + @Override + public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { + throw new AssertionError("This method should not be called."); + }; + + @Override + public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + throw new AssertionError("This method should not be called."); + }; + + @Override + public TutorialTeam getTutorialTeam(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + throw new AssertionError("This method should not be called."); + } + + @Override + public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { + throw new AssertionError("This method should not be called."); + }; + @Override public ReadOnlyAddressBook getAddressBook() { throw new AssertionError("This method should not be called."); @@ -168,6 +189,11 @@ public void addPersonToTutorialClass(Person person, ModuleCode moduleCode, Tutor throw new AssertionError("This method should not be called."); } + @Override + public void addTeam(TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + throw new AssertionError("This method should not be called."); + }; + @Override public void deletePersonFromTutorialClass(Person person, ModuleCode moduleCode, TutorialClass tutorialClass) { throw new AssertionError("This method should not be called."); From 8dad9dbe9430aabe3533b324ad6c695d2bb60945 Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Thu, 28 Mar 2024 03:05:16 +0800 Subject: [PATCH 08/12] Update checkstyle and testcases --- .../java/seedu/address/model/AddressBook.java | 2 +- .../address/model/module/TutorialTeam.java | 4 +--- .../storage/JsonAdaptedTutorialClass.java | 18 ++++++++---------- .../storage/JsonAdaptedTutorialTeam.java | 8 ++++---- .../logic/commands/AddStudentCommandTest.java | 5 +++++ .../seedu/address/model/AddressBookTest.java | 11 +++++++++++ .../storage/JsonAdaptedTutorialClassTest.java | 3 ++- .../storage/JsonAdaptedTutorialTeamTest.java | 5 +++-- 8 files changed, 35 insertions(+), 21 deletions(-) diff --git a/src/main/java/seedu/address/model/AddressBook.java b/src/main/java/seedu/address/model/AddressBook.java index 2facec0f3a0..0981dfadd0e 100644 --- a/src/main/java/seedu/address/model/AddressBook.java +++ b/src/main/java/seedu/address/model/AddressBook.java @@ -261,7 +261,7 @@ public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam * @param tutorialTeam size to check. * @return a boolean that indicates whether the team size will be exceeded by adding another person. */ - boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam) { + public boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam) { requireNonNull(tutorialTeam); int maxTeamSize = tutorialTeam.getTeamSize(); int currTeamSize = tutorialTeam.getStudents().size(); diff --git a/src/main/java/seedu/address/model/module/TutorialTeam.java b/src/main/java/seedu/address/model/module/TutorialTeam.java index 8be1eb9dcfb..b10b5ea5a74 100644 --- a/src/main/java/seedu/address/model/module/TutorialTeam.java +++ b/src/main/java/seedu/address/model/module/TutorialTeam.java @@ -3,11 +3,8 @@ import static seedu.address.commons.util.AppUtil.checkArgument; import static seedu.address.commons.util.CollectionUtil.requireAllNonNull; -import java.lang.reflect.*; import java.util.ArrayList; -import javafx.collections.FXCollections; -import javafx.collections.ObservableList; import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; @@ -196,6 +193,7 @@ public boolean hasStudentVerified(StudentId studentId, TutorialTeam tutorialTeam }; } return false; + } @Override diff --git a/src/main/java/seedu/address/storage/JsonAdaptedTutorialClass.java b/src/main/java/seedu/address/storage/JsonAdaptedTutorialClass.java index cce9a538175..8c4f40e0238 100644 --- a/src/main/java/seedu/address/storage/JsonAdaptedTutorialClass.java +++ b/src/main/java/seedu/address/storage/JsonAdaptedTutorialClass.java @@ -10,9 +10,7 @@ import seedu.address.commons.exceptions.IllegalValueException; import seedu.address.model.module.TutorialClass; import seedu.address.model.module.TutorialTeam; -import seedu.address.model.person.*; - -import static seedu.address.storage.JsonAdaptedModule.MISSING_FIELD_MESSAGE_FORMAT; +import seedu.address.model.person.Person; /** * Jackson-friendly version of {@link TutorialClass}. @@ -73,19 +71,19 @@ public TutorialClass toModelType() throws IllegalValueException { ArrayList listOfStudents = new ArrayList<>(); ArrayList listOfTeams = new ArrayList<>(); - for (JsonAdaptedPerson student : students) { - listOfStudents.add(student.toModelType()); - } - for (JsonAdaptedTutorialTeam team : teams) { - listOfTeams.add(team.toModelType()); - } - if (tutorialName == null) { throw new IllegalValueException(String.format(MISSING_FIELD_MESSAGE_FORMAT, tutorialName)); } if (!TutorialClass.isValidTutorialClass(tutorialName)) { throw new IllegalValueException(TutorialClass.MESSAGE_CONSTRAINTS); } + + for (JsonAdaptedPerson student : students) { + listOfStudents.add(student.toModelType()); + } + for (JsonAdaptedTutorialTeam team : teams) { + listOfTeams.add(team.toModelType()); + } return new TutorialClass(tutorialName, listOfStudents, listOfTeams); } diff --git a/src/main/java/seedu/address/storage/JsonAdaptedTutorialTeam.java b/src/main/java/seedu/address/storage/JsonAdaptedTutorialTeam.java index 3fe120a0cfd..30b7460e232 100644 --- a/src/main/java/seedu/address/storage/JsonAdaptedTutorialTeam.java +++ b/src/main/java/seedu/address/storage/JsonAdaptedTutorialTeam.java @@ -8,8 +8,8 @@ import com.fasterxml.jackson.annotation.JsonProperty; import seedu.address.commons.exceptions.IllegalValueException; -import seedu.address.model.module.*; -import seedu.address.model.person.*; +import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Person; /** * Jackson-friendly version of {@link TutorialTeam}. @@ -70,11 +70,11 @@ public TutorialTeam toModelType() throws IllegalValueException { throw new IllegalValueException(String.format(MISSING_FIELD_MESSAGE_FORMAT, teamName)); } if (!TutorialTeam.isValidTeamName(teamName)) { - throw new IllegalValueException(Name.MESSAGE_CONSTRAINTS); + throw new IllegalValueException(TutorialTeam.MESSAGE_NAME_CONSTRAINTS); } if (!TutorialTeam.isValidSize(teamSize)) { - throw new IllegalValueException(Name.MESSAGE_CONSTRAINTS); + throw new IllegalValueException(TutorialTeam.MESSAGE_SIZE_CONSTRAINTS); } for (JsonAdaptedPerson student : students) { listOfStudents.add(student.toModelType()); diff --git a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java index 3d99f6e794c..bb6c921cfcb 100644 --- a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java @@ -159,6 +159,11 @@ public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialCla throw new AssertionError("This method should not be called."); }; + @Override + public boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam) { + throw new AssertionError("This method should not be called."); + } + @Override public ReadOnlyAddressBook getAddressBook() { throw new AssertionError("This method should not be called."); diff --git a/src/test/java/seedu/address/model/AddressBookTest.java b/src/test/java/seedu/address/model/AddressBookTest.java index 119269f2c0a..b09a50d894b 100644 --- a/src/test/java/seedu/address/model/AddressBookTest.java +++ b/src/test/java/seedu/address/model/AddressBookTest.java @@ -23,6 +23,7 @@ import javafx.collections.ObservableList; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Person; import seedu.address.model.person.exceptions.DuplicatePersonException; import seedu.address.testutil.PersonBuilder; @@ -169,6 +170,11 @@ public ObservableList getModuleList() { return null; } + @Override + public ObservableList getStudentInTeamList() { + return null; + } + @Override public void setSortedPersonList(Comparator comparator) { sortedPersons = FXCollections.observableArrayList(); @@ -192,5 +198,10 @@ public void addModule(ModuleCode moduleCode, String description) { public ObservableList getTutorialList() { return null; } + + @Override + public ObservableList getTutorialTeamList() { + return null; + } } } diff --git a/src/test/java/seedu/address/storage/JsonAdaptedTutorialClassTest.java b/src/test/java/seedu/address/storage/JsonAdaptedTutorialClassTest.java index 9f5680e1ad6..0385f2456ab 100644 --- a/src/test/java/seedu/address/storage/JsonAdaptedTutorialClassTest.java +++ b/src/test/java/seedu/address/storage/JsonAdaptedTutorialClassTest.java @@ -10,6 +10,7 @@ import org.junit.jupiter.api.Test; +import seedu.address.commons.exceptions.IllegalValueException; import seedu.address.model.module.TutorialClass; import seedu.address.testutil.PersonBuilder; @@ -36,7 +37,7 @@ void toModelType_invalidTutorialName_throwsIllegalValueException() { JsonAdaptedTutorialClass jsonTutorialClass = new JsonAdaptedTutorialClass(INVALID_TUTORIAL_NAME, VALID_TEAMS_LIST, VALID_STUDENTS_LIST); String expectedMessage = TutorialClass.MESSAGE_CONSTRAINTS; - assertThrows(IllegalArgumentException.class, expectedMessage, jsonTutorialClass::toModelType); + assertThrows(IllegalValueException.class, expectedMessage, jsonTutorialClass::toModelType); } } diff --git a/src/test/java/seedu/address/storage/JsonAdaptedTutorialTeamTest.java b/src/test/java/seedu/address/storage/JsonAdaptedTutorialTeamTest.java index c5a642c91e9..3c0fc3d30d9 100644 --- a/src/test/java/seedu/address/storage/JsonAdaptedTutorialTeamTest.java +++ b/src/test/java/seedu/address/storage/JsonAdaptedTutorialTeamTest.java @@ -10,6 +10,7 @@ import org.junit.jupiter.api.Test; +import seedu.address.commons.exceptions.IllegalValueException; import seedu.address.model.module.TutorialTeam; import seedu.address.testutil.PersonBuilder; @@ -36,7 +37,7 @@ void toModelType_invalidTeamName_throwsIllegalValueException() { JsonAdaptedTutorialTeam jsonTutorialTeam = new JsonAdaptedTutorialTeam(INVALID_TEAM_NAME, VALID_TEAM_SIZE, VALID_STUDENTS_LIST); String expectedMessage = TutorialTeam.MESSAGE_NAME_CONSTRAINTS; - assertThrows(IllegalArgumentException.class, expectedMessage, jsonTutorialTeam::toModelType); + assertThrows(IllegalValueException.class, expectedMessage, jsonTutorialTeam::toModelType); } @Test @@ -44,7 +45,7 @@ void toModelType_invalidTeamSize_throwsIllegalValueException() { JsonAdaptedTutorialTeam jsonTutorialTeam = new JsonAdaptedTutorialTeam(VALID_TEAM_NAME, INVALID_TEAM_SIZE, VALID_STUDENTS_LIST); String expectedMessage = TutorialTeam.MESSAGE_SIZE_CONSTRAINTS; - assertThrows(IllegalArgumentException.class, expectedMessage, jsonTutorialTeam::toModelType); + assertThrows(IllegalValueException.class, expectedMessage, jsonTutorialTeam::toModelType); } } From 29e7690e0c090f2f4aee65f67805154a1a726dd8 Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Thu, 28 Mar 2024 15:58:41 +0800 Subject: [PATCH 09/12] Enhance Allocate command to include add by email or index --- build.gradle | 4 + .../AllocateStudentToTeamByEmailCommand.java | 110 ++++++++++++++++ .../AllocateStudentToTeamByIndexCommand.java | 117 ++++++++++++++++++ .../AllocateStudentToTeamByStuIdCommand.java} | 41 +++--- .../AllocateStudentToTeamCommand.java | 85 +++++++++++++ .../logic/parser/AddressBookParser.java | 2 +- .../AllocateStudentToTeamCommandParser.java | 36 ++++-- .../java/seedu/address/model/AddressBook.java | 40 ++++-- src/main/java/seedu/address/model/Model.java | 23 +++- .../seedu/address/model/ModelManager.java | 34 ++++- .../address/model/ReadOnlyAddressBook.java | 5 +- .../address/model/module/TutorialTeam.java | 12 +- .../seedu/address/model/person/Email.java | 10 ++ .../model/person/UniquePersonList.java | 12 ++ .../logic/commands/AddStudentCommandTest.java | 20 ++- .../seedu/address/model/AddressBookTest.java | 16 ++- 16 files changed, 497 insertions(+), 70 deletions(-) create mode 100644 src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByEmailCommand.java create mode 100644 src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByIndexCommand.java rename src/main/java/seedu/address/logic/commands/{AllocateStudentToTeamCommand.java => allocatestudenttoteamcommands/AllocateStudentToTeamByStuIdCommand.java} (71%) create mode 100644 src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamCommand.java diff --git a/build.gradle b/build.gradle index 8dba104ccbd..05ad2306835 100644 --- a/build.gradle +++ b/build.gradle @@ -20,6 +20,10 @@ checkstyle { toolVersion = '10.2' } +run { + enableAssertions = true +} + test { useJUnitPlatform() finalizedBy jacocoTestReport diff --git a/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByEmailCommand.java b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByEmailCommand.java new file mode 100644 index 00000000000..5a4e998b063 --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByEmailCommand.java @@ -0,0 +1,110 @@ +package seedu.address.logic.commands.allocatestudenttoteamcommands; + +import static java.util.Objects.requireNonNull; +import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TEAMNAME; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; + +import seedu.address.commons.util.ToStringBuilder; +import seedu.address.logic.commands.CommandResult; +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Email; +import seedu.address.model.person.Person; + +/** + * Allocates a student to a team in a tutorial Class in TAHelper. + */ +public class AllocateStudentToTeamByEmailCommand extends AllocateStudentToTeamCommand { + + public static final String COMMAND_WORD = "/allocate_team"; + + public static final String MESSAGE_USAGE = COMMAND_WORD + ": Allocates a student a team in the tutorial class.\n" + + "Parameters: " + + PREFIX_EMAIL + "EMAIL " + + PREFIX_MODULECODE + "MODULE CODE " + + PREFIX_TUTORIALCLASS + "TUTORIAL CLASS " + + PREFIX_TEAMNAME + "TEAM NAME" + + "Example: " + COMMAND_WORD + " " + + PREFIX_EMAIL + "zack@bmail.com " + + PREFIX_MODULECODE + "CS2101 " + + PREFIX_TUTORIALCLASS + "T01 " + + PREFIX_TEAMNAME + "Team 1 "; + + private final Email email; + private final ModuleCode moduleCode; + private final TutorialClass tutorialClass; + private final TutorialTeam tutorialTeam; + + /** + * Creates an AllocateStudentToTeam object. + */ + public AllocateStudentToTeamByEmailCommand(Email email, ModuleCode moduleCode, + TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + this.email = email; + this.moduleCode = moduleCode; + this.tutorialClass = tutorialClass; + this.tutorialTeam = tutorialTeam; + } + + @Override + public CommandResult execute(Model model) throws CommandException { + requireNonNull(model); + + if (model.findTutorialClassFromList(tutorialClass, moduleCode) == null) { + throw new CommandException(String.format(MESSAGE_CLASS_DOES_NOT_EXIST, tutorialClass, moduleCode)); + } + + ModuleCode module = model.findModuleFromList(moduleCode); + TutorialClass tutClass = model.findTutorialClassFromList(tutorialClass, module); + + Person student = model.getUniquePersonList().getPersonByEmail(email); + TutorialTeam tutTeam = model.getTutorialTeam(tutClass, tutorialTeam); + + if (student == null) { + throw new CommandException(MESSAGE_STUDENT_DOES_NOT_EXIST); + } + + if (tutTeam == null) { + throw new CommandException(String.format(MESSAGE_TEAM_DOES_NOT_EXIST, tutorialTeam, tutClass)); + } + + // throws commandException if any condition fails + checkAllocateCondition(model, student, tutClass, tutTeam); + model.allocateStudentToTeam(student, tutTeam); + + return new CommandResult(String.format(MESSAGE_SUCCESS, tutTeam)); + } + + @Override + public boolean equals(Object other) { + if (other == this) { + return true; + } + + // instanceof handles nulls + if (!(other instanceof AllocateStudentToTeamCommand)) { + return false; + } + + AllocateStudentToTeamByEmailCommand otherAllocateCommand = (AllocateStudentToTeamByEmailCommand) other; + return this.email.equals(otherAllocateCommand.email) + && this.moduleCode.equals(otherAllocateCommand.moduleCode) + && this.tutorialClass.equals(otherAllocateCommand.tutorialClass) + && this.tutorialTeam.equals(otherAllocateCommand.tutorialTeam); + } + + @Override + public String toString() { + return new ToStringBuilder(this) + .add("email", email) + .add("moduleCode", moduleCode) + .add("tutorialClass", tutorialClass) + .add("tutorialTeam", tutorialTeam) + .toString(); + } +} diff --git a/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByIndexCommand.java b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByIndexCommand.java new file mode 100644 index 00000000000..a652f7353cf --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByIndexCommand.java @@ -0,0 +1,117 @@ +package seedu.address.logic.commands.allocatestudenttoteamcommands; + +import static java.util.Objects.requireNonNull; +import static seedu.address.logic.parser.CliSyntax.PREFIX_INDEX; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TEAMNAME; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; + +import seedu.address.commons.core.index.Index; +import seedu.address.commons.util.CollectionUtil; +import seedu.address.commons.util.ToStringBuilder; +import seedu.address.logic.commands.CommandResult; +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.model.Model; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Person; + +/** + * Allocates a student to a team in a tutorial Class in TAHelper. + */ +public class AllocateStudentToTeamByIndexCommand extends AllocateStudentToTeamCommand { + + public static final String COMMAND_WORD = "/allocate_team"; + + public static final String MESSAGE_USAGE = COMMAND_WORD + ": Allocates a student a team in the tutorial class.\n" + + "Parameters: " + + PREFIX_INDEX + "INDEX " + + PREFIX_MODULECODE + "MODULE CODE " + + PREFIX_TUTORIALCLASS + "TUTORIAL CLASS " + + PREFIX_TEAMNAME + "TEAM NAME" + + "Example: " + COMMAND_WORD + " " + + PREFIX_INDEX + "1 " + + PREFIX_MODULECODE + "CS2101 " + + PREFIX_TUTORIALCLASS + "T01 " + + PREFIX_TEAMNAME + "Team 1 "; + + public static final String MESSAGE_PERSON_INDEX_NOT_FOUND = + "Student at index %s not found inside tutorial class %s"; + private final Index index; + private final ModuleCode moduleCode; + private final TutorialClass tutorialClass; + private final TutorialTeam tutorialTeam; + + /** + * Creates an AllocateStudentToTeam object. + */ + public AllocateStudentToTeamByIndexCommand(Index index, ModuleCode moduleCode, + TutorialClass tutorialClass, TutorialTeam tutorialTeam) { + CollectionUtil.requireAllNonNull(index, moduleCode, tutorialClass, tutorialTeam); + this.index = index; + this.moduleCode = moduleCode; + this.tutorialClass = tutorialClass; + this.tutorialTeam = tutorialTeam; + } + + @Override + public CommandResult execute(Model model) throws CommandException { + requireNonNull(model); + + if (model.findTutorialClassFromList(tutorialClass, moduleCode) == null) { + throw new CommandException(String.format(MESSAGE_CLASS_DOES_NOT_EXIST, tutorialClass, moduleCode)); + } + + ModuleCode module = model.findModuleFromList(moduleCode); + TutorialClass tutClass = model.findTutorialClassFromList(tutorialClass, module); + + Person studentToAllocate; + try { + studentToAllocate = model.getStudentsInTeamList().get(index.getZeroBased()); + } catch (IndexOutOfBoundsException err) { + throw new CommandException( + String.format(MESSAGE_PERSON_INDEX_NOT_FOUND, index.getOneBased(), tutClass)); + } + + TutorialTeam tutTeam = model.getTutorialTeam(tutClass, tutorialTeam); + + if (tutTeam == null) { + throw new CommandException(MESSAGE_STUDENT_DOES_NOT_EXIST); + } + + // throws commandException if any condition fails + checkAllocateCondition(model, studentToAllocate, tutClass, tutTeam); + model.allocateStudentToTeam(studentToAllocate, tutTeam); + + return new CommandResult(String.format(MESSAGE_SUCCESS, tutTeam)); + } + + @Override + public boolean equals(Object other) { + if (other == this) { + return true; + } + + // instanceof handles nulls + if (!(other instanceof AllocateStudentToTeamCommand)) { + return false; + } + + AllocateStudentToTeamByIndexCommand otherAllocateCommand = (AllocateStudentToTeamByIndexCommand) other; + return this.index.equals(otherAllocateCommand.index) + && this.moduleCode.equals(otherAllocateCommand.moduleCode) + && this.tutorialClass.equals(otherAllocateCommand.tutorialClass) + && this.tutorialTeam.equals(otherAllocateCommand.tutorialTeam); + } + + @Override + public String toString() { + return new ToStringBuilder(this) + .add("index", index) + .add("moduleCode", moduleCode) + .add("tutorialClass", tutorialClass) + .add("tutorialTeam", tutorialTeam) + .toString(); + } +} diff --git a/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByStuIdCommand.java similarity index 71% rename from src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java rename to src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByStuIdCommand.java index 9c5e1377fce..0492ca2bc3b 100644 --- a/src/main/java/seedu/address/logic/commands/AllocateStudentToTeamCommand.java +++ b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByStuIdCommand.java @@ -1,4 +1,4 @@ -package seedu.address.logic.commands; +package seedu.address.logic.commands.allocatestudenttoteamcommands; import static java.util.Objects.requireNonNull; import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; @@ -8,17 +8,19 @@ import seedu.address.commons.util.CollectionUtil; import seedu.address.commons.util.ToStringBuilder; +import seedu.address.logic.commands.CommandResult; import seedu.address.logic.commands.exceptions.CommandException; import seedu.address.model.Model; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; /** * Allocates a student to a team in a tutorial Class in TAHelper. */ -public class AllocateStudentToTeamCommand extends Command { +public class AllocateStudentToTeamByStuIdCommand extends AllocateStudentToTeamCommand { public static final String COMMAND_WORD = "/allocate_team"; @@ -33,14 +35,7 @@ public class AllocateStudentToTeamCommand extends Command { + PREFIX_MODULECODE + "CS2101 " + PREFIX_TUTORIALCLASS + "T01 " + PREFIX_TEAMNAME + "Team 1 "; - - public static final String MESSAGE_SUCCESS = "Allocate student to team: "; - public static final String MESSAGE_TEAM_DOES_NOT_EXIST = "Team does not exist in tutorial class"; - public static final String MESSAGE_DUPLICATE_PERSON_IN_TEAM = "This person already exists in a team" - + " in the tutorial class!"; - - public static final String MESSAGE_CLASS_DOES_NOT_EXIST = "Tutorial class does not exist in module"; - public static final String MESSAGE_TEAM_SIZE_EXCEEDED = "Max team size reached"; + public static final String MESSAGE_STUDENT_DOES_NOT_EXIST = "Student does not exist in tutorial class"; private final StudentId studentId; private final ModuleCode moduleCode; @@ -50,7 +45,7 @@ public class AllocateStudentToTeamCommand extends Command { /** * Creates an AllocateStudentToTeam object. */ - public AllocateStudentToTeamCommand(StudentId studentId, ModuleCode moduleCode, + public AllocateStudentToTeamByStuIdCommand(StudentId studentId, ModuleCode moduleCode, TutorialClass tutorialClass, TutorialTeam tutorialTeam) { CollectionUtil.requireAllNonNull(studentId, moduleCode, tutorialClass, tutorialTeam); this.studentId = studentId; @@ -70,26 +65,22 @@ public CommandResult execute(Model model) throws CommandException { ModuleCode module = model.findModuleFromList(moduleCode); TutorialClass tutClass = model.findTutorialClassFromList(tutorialClass, module); - if (!model.hasTeamInTutorial(tutClass, tutorialTeam)) { - throw new CommandException(MESSAGE_TEAM_DOES_NOT_EXIST); - } - + Person student = model.getUniquePersonList().getPerson(studentId); TutorialTeam tutTeam = model.getTutorialTeam(tutClass, tutorialTeam); - if (tutTeam == null) { - throw new CommandException(MESSAGE_TEAM_DOES_NOT_EXIST); - } - if (model.isStudentInAnyTeam(studentId, tutClass)) { - throw new CommandException(MESSAGE_DUPLICATE_PERSON_IN_TEAM); + if (student == null) { + throw new CommandException(MESSAGE_STUDENT_DOES_NOT_EXIST); } - if (model.hasTeamSizeExceeded(tutTeam)) { - throw new CommandException(MESSAGE_TEAM_SIZE_EXCEEDED); + if (tutTeam == null) { + throw new CommandException(String.format(MESSAGE_TEAM_DOES_NOT_EXIST, tutorialTeam, tutClass)); } - model.allocateStudentToTeam(studentId, tutTeam); + // throws commandException if any condition fails + checkAllocateCondition(model, student, tutClass, tutTeam); + model.allocateStudentToTeam(student, tutTeam); - return new CommandResult(String.format(MESSAGE_SUCCESS)); + return new CommandResult(String.format(MESSAGE_SUCCESS, tutTeam)); } @Override @@ -103,7 +94,7 @@ public boolean equals(Object other) { return false; } - AllocateStudentToTeamCommand otherAllocateCommand = (AllocateStudentToTeamCommand) other; + AllocateStudentToTeamByStuIdCommand otherAllocateCommand = (AllocateStudentToTeamByStuIdCommand) other; return this.studentId.equals(otherAllocateCommand.studentId) && this.moduleCode.equals(otherAllocateCommand.moduleCode) && this.tutorialClass.equals(otherAllocateCommand.tutorialClass) diff --git a/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamCommand.java b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamCommand.java new file mode 100644 index 00000000000..8a92630a68d --- /dev/null +++ b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamCommand.java @@ -0,0 +1,85 @@ +package seedu.address.logic.commands.allocatestudenttoteamcommands; + +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TEAMNAME; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; + +import seedu.address.commons.util.ToStringBuilder; +import seedu.address.logic.commands.Command; +import seedu.address.logic.commands.CommandResult; +import seedu.address.logic.commands.exceptions.CommandException; +import seedu.address.model.Model; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Person; + +/** + * Allocates a student to a team in a tutorial Class in TAHelper. + */ +public abstract class AllocateStudentToTeamCommand extends Command { + + public static final String COMMAND_WORD = "/allocate_team"; + + public static final String MESSAGE_USAGE = COMMAND_WORD + ": Allocates a student a team in the tutorial class.\n" + + "Parameters: " + + PREFIX_STUDENTID + "STUDENT ID " + + PREFIX_MODULECODE + "MODULE CODE " + + PREFIX_TUTORIALCLASS + "TUTORIAL CLASS " + + PREFIX_TEAMNAME + "TEAM NAME" + + "Example: " + COMMAND_WORD + " " + + PREFIX_STUDENTID + "A1234567L " + + PREFIX_MODULECODE + "CS2101 " + + PREFIX_TUTORIALCLASS + "T01 " + + PREFIX_TEAMNAME + "Team 1 "; + + public static final String MESSAGE_SUCCESS = "Allocate student to team: %s"; + public static final String MESSAGE_STUDENT_NOT_IN_TUTORIAL = "Student needs to be in that tutorial group first."; + public static final String MESSAGE_STUDENT_DOES_NOT_EXIST = "Student does not exist in system"; + public static final String MESSAGE_TEAM_DOES_NOT_EXIST = "Team %s does not exist in tutorial class %s"; + public static final String MESSAGE_CLASS_DOES_NOT_EXIST = "Tutorial class %s does not exist in module %s"; + + public static final String MESSAGE_DUPLICATE_PERSON_IN_TEAM = "This person already exists in a team" + + " in the tutorial class %s!"; + public static final String MESSAGE_TEAM_SIZE_EXCEEDED = "Max team size of %d reached"; + + public AllocateStudentToTeamCommand() {} + + @Override + public abstract CommandResult execute(Model model) throws CommandException; + @Override + public abstract boolean equals(Object other); + + /** + * Check the condition needed to allocate the student to a tutorial team. + * @param model + * @param student + * @param tutClass + * @param tutorialTeam + * @throws CommandException + */ + public void checkAllocateCondition(Model model, Person student, TutorialClass tutClass, TutorialTeam tutorialTeam) + throws CommandException { + if (!model.isStudentInTutorialClass(student, tutClass)) { + throw new CommandException(MESSAGE_STUDENT_NOT_IN_TUTORIAL); + } + + if (!model.hasTeamInTutorial(tutClass, tutorialTeam)) { + throw new CommandException(String.format(MESSAGE_TEAM_DOES_NOT_EXIST, tutorialTeam, tutClass)); + } + + if (model.isStudentInAnyTeam(student, tutClass)) { + throw new CommandException(String.format(MESSAGE_DUPLICATE_PERSON_IN_TEAM, tutClass)); + } + + if (model.hasTeamSizeExceeded(tutorialTeam)) { + throw new CommandException(String.format(MESSAGE_TEAM_SIZE_EXCEEDED, tutorialTeam.getTeamSize())); + } + } + + @Override + public String toString() { + return new ToStringBuilder(this) + .toString(); + } +} diff --git a/src/main/java/seedu/address/logic/parser/AddressBookParser.java b/src/main/java/seedu/address/logic/parser/AddressBookParser.java index d882a7b627d..e5ef85920ae 100644 --- a/src/main/java/seedu/address/logic/parser/AddressBookParser.java +++ b/src/main/java/seedu/address/logic/parser/AddressBookParser.java @@ -11,7 +11,6 @@ import seedu.address.logic.commands.AddClassCommand; import seedu.address.logic.commands.AddStudentCommand; import seedu.address.logic.commands.AddTeamCommand; -import seedu.address.logic.commands.AllocateStudentToTeamCommand; import seedu.address.logic.commands.ClearCommand; import seedu.address.logic.commands.Command; import seedu.address.logic.commands.DeleteClassCommand; @@ -26,6 +25,7 @@ import seedu.address.logic.commands.SearchStudentCommand; import seedu.address.logic.commands.SortStudentCommand; import seedu.address.logic.commands.addstudenttoclasscommands.AddStudentToClassCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamCommand; import seedu.address.logic.commands.deletestudentcommands.DeleteStudentCommand; import seedu.address.logic.commands.deletestudentfromclasscommands.DeleteStudentFromClassCommand; import seedu.address.logic.parser.exceptions.ParseException; diff --git a/src/main/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParser.java b/src/main/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParser.java index 8df61286c54..014ad99b96d 100644 --- a/src/main/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParser.java +++ b/src/main/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParser.java @@ -1,6 +1,8 @@ package seedu.address.logic.parser; import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; +import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; +import static seedu.address.logic.parser.CliSyntax.PREFIX_INDEX; import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; import static seedu.address.logic.parser.CliSyntax.PREFIX_TEAMNAME; @@ -8,11 +10,16 @@ import java.util.stream.Stream; -import seedu.address.logic.commands.AllocateStudentToTeamCommand; +import seedu.address.commons.core.index.Index; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamByEmailCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamByIndexCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamByStuIdCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamCommand; import seedu.address.logic.parser.exceptions.ParseException; import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Email; import seedu.address.model.person.StudentId; /** @@ -27,25 +34,38 @@ public class AllocateStudentToTeamCommandParser implements Parser students = tutorialClass.getStudents(); + return students.stream().anyMatch(student::isSamePerson); + } + /** * Allocates the {@code studentId} to the {@code tutorialTeam} * @param tutorialTeam to allocate the student into. */ - public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { - requireNonNull(studentId); + public void allocateStudentToTeam(Person student, TutorialTeam tutorialTeam) { + requireNonNull(student); requireNonNull(tutorialTeam); - Person student = persons.getPerson(studentId); tutorialTeam.addStudent(student); } @@ -265,18 +275,23 @@ public boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam) { requireNonNull(tutorialTeam); int maxTeamSize = tutorialTeam.getTeamSize(); int currTeamSize = tutorialTeam.getStudents().size(); - return (maxTeamSize >= currTeamSize); + System.out.println(currTeamSize); + System.out.println(maxTeamSize); + return (maxTeamSize <= currTeamSize); }; /** - * Returns true if the {@code studentId} is already in a team of {@code tutorialClass}. + * Returns true if the {@code student} is already in a team of {@code tutorialClass}. * @param tutorialClass of the teams. - * @param studentId to search for. + * @param student to search for. */ - public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { + public boolean isStudentInAnyTeam(Person student, TutorialClass tutorialClass) { boolean isStudentExist = false; for (TutorialTeam tutorialTeam : tutorialClass.getTeams()) { - isStudentExist = tutorialTeam.hasStudentVerified(studentId, tutorialTeam); + isStudentExist = tutorialTeam.hasStudentVerified(student, tutorialTeam); + if (isStudentExist) { + break; + } } return isStudentExist; }; @@ -352,6 +367,11 @@ public String toString() { .toString(); } + @Override + public UniquePersonList getUniquePersonList() { + return this.persons; + } + @Override public ObservableList getPersonList() { return persons.asUnmodifiableObservableList(); @@ -363,7 +383,7 @@ public ObservableList getTutorialTeamList() { } @Override - public ObservableList getStudentInTeamList() { + public ObservableList getStudentsInTeamList() { return studentsInTeam.asUnmodifiableObservableList(); } diff --git a/src/main/java/seedu/address/model/Model.java b/src/main/java/seedu/address/model/Model.java index 836fb4ab4c0..c779816a16e 100644 --- a/src/main/java/seedu/address/model/Model.java +++ b/src/main/java/seedu/address/model/Model.java @@ -12,6 +12,7 @@ import seedu.address.model.person.Email; import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; +import seedu.address.model.person.UniquePersonList; /** * The API of the Model component. @@ -124,24 +125,24 @@ public interface Model { void addModule(ModuleCode module); /** - * Allocates the {@code studentId} to the {@code tutorialTeam} + * Allocates the {@code student} to the {@code tutorialTeam} * @param tutorialTeam to allocate the student into. */ - public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam); + void allocateStudentToTeam(Person student, TutorialTeam tutorialTeam); /** * Returns true if a team with the same identity as {@code tutorialTeam} exists in the {@code tutorialClass} * @param tutorialClass of the tutorialTeam. * @param tutorialTeam to check if it exist. */ - public boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam); + boolean hasTeamInTutorial(TutorialClass tutorialClass, TutorialTeam tutorialTeam); /** - * Returns true if the {@code studentId} is already in a team of {@code tutorialClass}. + * Returns true if the {@code student} is already in a team of {@code tutorialClass}. * @param tutorialClass of the teams. - * @param studentId to search for. + * @param student to search for. */ - public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass); + public boolean isStudentInAnyTeam(Person student, TutorialClass tutorialClass); /** * Returns true if the {@code tutorialTeam} size has exceeded its limit. @@ -150,6 +151,14 @@ public interface Model { */ boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam); + /** + * Checks if a student is in the {@code tutorialClass} of that {@code moduleCode} + * @param student to check if student exist in tutorialClass. + * @param tutorialClass to check if the student is in + * @return a boolean indicating if the student is in that {@code tutorialClass} + */ + boolean isStudentInTutorialClass(Person student, TutorialClass tutorialClass); + /** * Adds the given person to the given tutorial class in the given module. */ @@ -164,8 +173,10 @@ public interface Model { /** Returns an unmodifiable view of the filtered person list */ ObservableList getFilteredPersonList(); + UniquePersonList getUniquePersonList(); ObservableList getFilteredModuleList(); ObservableList getSortedPersonList(Comparator comparator); + ObservableList getStudentsInTeamList(); /** * Updates the filter of the filtered person list to filter by the given {@code predicate}. diff --git a/src/main/java/seedu/address/model/ModelManager.java b/src/main/java/seedu/address/model/ModelManager.java index b3c71f10d78..19e0852599b 100644 --- a/src/main/java/seedu/address/model/ModelManager.java +++ b/src/main/java/seedu/address/model/ModelManager.java @@ -18,6 +18,7 @@ import seedu.address.model.person.Email; import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; +import seedu.address.model.person.UniquePersonList; /** @@ -147,8 +148,9 @@ public void addPerson(Person person) { } @Override - public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { - addressBook.allocateStudentToTeam(studentId, tutorialTeam); + public void allocateStudentToTeam(Person student, TutorialTeam tutorialTeam) { + requireAllNonNull(student, tutorialTeam); + addressBook.allocateStudentToTeam(student, tutorialTeam); } @Override @@ -180,9 +182,15 @@ public boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam) { }; @Override - public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { - requireAllNonNull(studentId, tutorialClass); - return addressBook.isStudentInAnyTeam(studentId, tutorialClass); + public boolean isStudentInAnyTeam(Person student, TutorialClass tutorialClass) { + requireAllNonNull(student, tutorialClass); + return addressBook.isStudentInAnyTeam(student, tutorialClass); + } + + @Override + public boolean isStudentInTutorialClass(Person student, TutorialClass tutorialClass) { + requireAllNonNull(student, tutorialClass); + return addressBook.isStudentInTutorialClass(student, tutorialClass); } @Override @@ -218,6 +226,17 @@ public void setPerson(Person target, Person editedPerson) { public ObservableList getFilteredPersonList() { return filteredPersons; } + + /** + * Returns an unmodifiable view of the list of {@code Person} backed by the internal list of + * {@code versionedAddressBook} + * @Return UniquePersonList. + */ + @Override + public UniquePersonList getUniquePersonList() { + return addressBook.getUniquePersonList(); + } + /** * Returns an unmodifiable view of the list of {@code Module} backed by the internal list of * {@code versionedAddressBook} @@ -233,6 +252,11 @@ public ObservableList getSortedPersonList(Comparator comparator) return addressBook.getSortedPersonList(); } + @Override + public ObservableList getStudentsInTeamList() { + return addressBook.getStudentsInTeamList(); + } + @Override public void updateFilteredPersonList(Predicate predicate) { requireNonNull(predicate); diff --git a/src/main/java/seedu/address/model/ReadOnlyAddressBook.java b/src/main/java/seedu/address/model/ReadOnlyAddressBook.java index df019f04605..9af19877712 100644 --- a/src/main/java/seedu/address/model/ReadOnlyAddressBook.java +++ b/src/main/java/seedu/address/model/ReadOnlyAddressBook.java @@ -7,6 +7,7 @@ import seedu.address.model.module.TutorialClass; import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Person; +import seedu.address.model.person.UniquePersonList; /** * Unmodifiable view of an address book @@ -19,6 +20,8 @@ public interface ReadOnlyAddressBook { */ ObservableList getPersonList(); + UniquePersonList getUniquePersonList(); + /** * Returns an unmodifiable view of the modules list. * This list will not contain any duplicate modules. @@ -28,7 +31,7 @@ public interface ReadOnlyAddressBook { void setSortedPersonList(Comparator comparator); ObservableList getSortedPersonList(); ObservableList getTutorialTeamList(); - ObservableList getStudentInTeamList(); + ObservableList getStudentsInTeamList(); /** * Checks if the address book contains the specified module code. diff --git a/src/main/java/seedu/address/model/module/TutorialTeam.java b/src/main/java/seedu/address/model/module/TutorialTeam.java index b10b5ea5a74..ed15bb1dfaa 100644 --- a/src/main/java/seedu/address/model/module/TutorialTeam.java +++ b/src/main/java/seedu/address/model/module/TutorialTeam.java @@ -6,7 +6,6 @@ import java.util.ArrayList; import seedu.address.model.person.Person; -import seedu.address.model.person.StudentId; /** * Represents a Module's tutorial team. @@ -178,19 +177,18 @@ public boolean hasStudent(Person student) { } /** - * Checks if a student exist by their id - * @param studentId + * Checks if a student exist, check by their studentId. * @return true if a person is in the list of students */ - public boolean hasStudentVerified(StudentId studentId, TutorialTeam tutorialTeam) { + public boolean hasStudentVerified(Person student, TutorialTeam tutorialTeam) { ArrayList teamList = tutorialTeam.getStudents(); if (teamList.size() == 0 || teamList == null) { return false; } - for (Person student : teamList) { - if (student.getStudentId().value.equals(studentId.value)) { + for (Person eachStudent : teamList) { + if (eachStudent.getStudentId().value.equals(student.getStudentId().value)) { return true; - }; + } } return false; diff --git a/src/main/java/seedu/address/model/person/Email.java b/src/main/java/seedu/address/model/person/Email.java index be632593a54..8db1c6147c1 100644 --- a/src/main/java/seedu/address/model/person/Email.java +++ b/src/main/java/seedu/address/model/person/Email.java @@ -44,6 +44,16 @@ public Email(String email) { value = email; } + /** + * Returns true if 2 student emails are identical to {@code email} id value. + * @param email + * @return boolean if they are identical. + */ + public boolean isSameEmail(Email email) { + requireNonNull(email); + return this.value.equals(email.value); + } + /** * Returns if a given string is a valid email. */ diff --git a/src/main/java/seedu/address/model/person/UniquePersonList.java b/src/main/java/seedu/address/model/person/UniquePersonList.java index 7cd4693d39e..8c474901587 100644 --- a/src/main/java/seedu/address/model/person/UniquePersonList.java +++ b/src/main/java/seedu/address/model/person/UniquePersonList.java @@ -48,6 +48,18 @@ public Person getPerson(StudentId studentId) { return personMatch; } + /** + * Return the Person object if the list contains the person with {@code email} + */ + public Person getPersonByEmail(Email email) { + requireNonNull(email); + Person personMatch = internalList.stream() + .filter(person -> person.getEmail().isSameEmail(email)) + .findFirst() + .orElse(null); + return personMatch; + } + /** * Adds a person to the list. * The person must not already exist in the list. diff --git a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java index bb6c921cfcb..ddf9ca005f8 100644 --- a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java @@ -29,6 +29,7 @@ import seedu.address.model.person.Email; import seedu.address.model.person.Person; import seedu.address.model.person.StudentId; +import seedu.address.model.person.UniquePersonList; import seedu.address.testutil.PersonBuilder; /** @@ -140,7 +141,7 @@ public void setAddressBook(ReadOnlyAddressBook newData) { } @Override - public void allocateStudentToTeam(StudentId studentId, TutorialTeam tutorialTeam) { + public void allocateStudentToTeam(Person student, TutorialTeam tutorialTeam) { throw new AssertionError("This method should not be called."); }; @@ -155,7 +156,12 @@ public TutorialTeam getTutorialTeam(TutorialClass tutorialClass, TutorialTeam tu } @Override - public boolean isStudentInAnyTeam(StudentId studentId, TutorialClass tutorialClass) { + public boolean isStudentInAnyTeam(Person student, TutorialClass tutorialClass) { + throw new AssertionError("This method should not be called."); + }; + + @Override + public boolean isStudentInTutorialClass(Person student, TutorialClass tutorialClass) { throw new AssertionError("This method should not be called."); }; @@ -243,6 +249,16 @@ public ObservableList getSortedPersonList(Comparator comparator) throw new AssertionError("This method should not be called."); } + @Override + public UniquePersonList getUniquePersonList() { + throw new AssertionError("This method should not be called."); + } + + @Override + public ObservableList getStudentsInTeamList() { + throw new AssertionError("This method should not be called."); + } + @Override public void updateFilteredPersonList(Predicate predicate) { throw new AssertionError("This method should not be called."); diff --git a/src/test/java/seedu/address/model/AddressBookTest.java b/src/test/java/seedu/address/model/AddressBookTest.java index b09a50d894b..9246a24400c 100644 --- a/src/test/java/seedu/address/model/AddressBookTest.java +++ b/src/test/java/seedu/address/model/AddressBookTest.java @@ -25,6 +25,7 @@ import seedu.address.model.module.TutorialClass; import seedu.address.model.module.TutorialTeam; import seedu.address.model.person.Person; +import seedu.address.model.person.UniquePersonList; import seedu.address.model.person.exceptions.DuplicatePersonException; import seedu.address.testutil.PersonBuilder; @@ -170,11 +171,6 @@ public ObservableList getModuleList() { return null; } - @Override - public ObservableList getStudentInTeamList() { - return null; - } - @Override public void setSortedPersonList(Comparator comparator) { sortedPersons = FXCollections.observableArrayList(); @@ -199,6 +195,16 @@ public ObservableList getTutorialList() { return null; } + @Override + public ObservableList getStudentsInTeamList() { + return null; + } + + @Override + public UniquePersonList getUniquePersonList() { + return null; + } + @Override public ObservableList getTutorialTeamList() { return null; From a76ec8f23de2d10bad38f4b2833564004a98210e Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Fri, 29 Mar 2024 00:33:22 +0800 Subject: [PATCH 10/12] Update Testcases to improve codeCoverage * Create Test cases for the Allocate Student to Team command --- .../AllocateStudentToTeamByIndexCommand.java | 4 +- .../AllocateStudentToTeamByStuIdCommand.java | 1 - .../java/seedu/address/model/AddressBook.java | 7 +- src/main/java/seedu/address/model/Model.java | 1 + .../seedu/address/model/ModelManager.java | 5 + .../address/model/ReadOnlyAddressBook.java | 1 + .../logic/commands/AddStudentCommandTest.java | 5 + .../AllocateStudentToTeamCommandTest.java | 152 ++++++++++++++++++ .../logic/commands/CommandTestUtil.java | 3 + .../seedu/address/model/AddressBookTest.java | 111 +++++++++++++ 10 files changed, 285 insertions(+), 5 deletions(-) create mode 100644 src/test/java/seedu/address/logic/commands/AllocateStudentToTeamCommandTest.java diff --git a/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByIndexCommand.java b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByIndexCommand.java index a652f7353cf..e55a0db0aaf 100644 --- a/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByIndexCommand.java +++ b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByIndexCommand.java @@ -37,7 +37,7 @@ public class AllocateStudentToTeamByIndexCommand extends AllocateStudentToTeamCo + PREFIX_TEAMNAME + "Team 1 "; public static final String MESSAGE_PERSON_INDEX_NOT_FOUND = - "Student at index %s not found inside tutorial class %s"; + "Student at index %d not found inside tutorial class %s"; private final Index index; private final ModuleCode moduleCode; private final TutorialClass tutorialClass; @@ -68,7 +68,7 @@ public CommandResult execute(Model model) throws CommandException { Person studentToAllocate; try { - studentToAllocate = model.getStudentsInTeamList().get(index.getZeroBased()); + studentToAllocate = model.getStudentsInTutorialClass(tutClass).get(index.getZeroBased()); } catch (IndexOutOfBoundsException err) { throw new CommandException( String.format(MESSAGE_PERSON_INDEX_NOT_FOUND, index.getOneBased(), tutClass)); diff --git a/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByStuIdCommand.java b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByStuIdCommand.java index 0492ca2bc3b..c7c8feb83d2 100644 --- a/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByStuIdCommand.java +++ b/src/main/java/seedu/address/logic/commands/allocatestudenttoteamcommands/AllocateStudentToTeamByStuIdCommand.java @@ -35,7 +35,6 @@ public class AllocateStudentToTeamByStuIdCommand extends AllocateStudentToTeamCo + PREFIX_MODULECODE + "CS2101 " + PREFIX_TUTORIALCLASS + "T01 " + PREFIX_TEAMNAME + "Team 1 "; - public static final String MESSAGE_STUDENT_DOES_NOT_EXIST = "Student does not exist in tutorial class"; private final StudentId studentId; private final ModuleCode moduleCode; diff --git a/src/main/java/seedu/address/model/AddressBook.java b/src/main/java/seedu/address/model/AddressBook.java index 185df9fe816..dd3e48afbd4 100644 --- a/src/main/java/seedu/address/model/AddressBook.java +++ b/src/main/java/seedu/address/model/AddressBook.java @@ -275,8 +275,6 @@ public boolean hasTeamSizeExceeded(TutorialTeam tutorialTeam) { requireNonNull(tutorialTeam); int maxTeamSize = tutorialTeam.getTeamSize(); int currTeamSize = tutorialTeam.getStudents().size(); - System.out.println(currTeamSize); - System.out.println(maxTeamSize); return (maxTeamSize <= currTeamSize); }; @@ -387,6 +385,11 @@ public ObservableList getStudentsInTeamList() { return studentsInTeam.asUnmodifiableObservableList(); } + @Override + public ObservableList getStudentsInTutorialClass(TutorialClass tutorialClass) { + return FXCollections.observableList(tutorialClass.getStudents()); + } + @Override public ObservableList getModuleList() { return FXCollections.observableList(modules); diff --git a/src/main/java/seedu/address/model/Model.java b/src/main/java/seedu/address/model/Model.java index c779816a16e..8317e8889eb 100644 --- a/src/main/java/seedu/address/model/Model.java +++ b/src/main/java/seedu/address/model/Model.java @@ -177,6 +177,7 @@ public interface Model { ObservableList getFilteredModuleList(); ObservableList getSortedPersonList(Comparator comparator); ObservableList getStudentsInTeamList(); + ObservableList getStudentsInTutorialClass(TutorialClass tutorialClass); /** * Updates the filter of the filtered person list to filter by the given {@code predicate}. diff --git a/src/main/java/seedu/address/model/ModelManager.java b/src/main/java/seedu/address/model/ModelManager.java index 19e0852599b..91a17bb3c1f 100644 --- a/src/main/java/seedu/address/model/ModelManager.java +++ b/src/main/java/seedu/address/model/ModelManager.java @@ -257,6 +257,11 @@ public ObservableList getStudentsInTeamList() { return addressBook.getStudentsInTeamList(); } + @Override + public ObservableList getStudentsInTutorialClass(TutorialClass tutorialClass) { + return addressBook.getStudentsInTutorialClass(tutorialClass); + } + @Override public void updateFilteredPersonList(Predicate predicate) { requireNonNull(predicate); diff --git a/src/main/java/seedu/address/model/ReadOnlyAddressBook.java b/src/main/java/seedu/address/model/ReadOnlyAddressBook.java index 9af19877712..3c20a25b3e0 100644 --- a/src/main/java/seedu/address/model/ReadOnlyAddressBook.java +++ b/src/main/java/seedu/address/model/ReadOnlyAddressBook.java @@ -43,4 +43,5 @@ public interface ReadOnlyAddressBook { void addModule(ModuleCode moduleCode, String description); ObservableList getTutorialList(); + ObservableList getStudentsInTutorialClass(TutorialClass tutorialClass); } diff --git a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java index ddf9ca005f8..4593f89e914 100644 --- a/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/AddStudentCommandTest.java @@ -259,6 +259,11 @@ public ObservableList getStudentsInTeamList() { throw new AssertionError("This method should not be called."); } + @Override + public ObservableList getStudentsInTutorialClass(TutorialClass tutorialClass) { + throw new AssertionError("This method should not be called."); + } + @Override public void updateFilteredPersonList(Predicate predicate) { throw new AssertionError("This method should not be called."); diff --git a/src/test/java/seedu/address/logic/commands/AllocateStudentToTeamCommandTest.java b/src/test/java/seedu/address/logic/commands/AllocateStudentToTeamCommandTest.java new file mode 100644 index 00000000000..8c89a7e6e04 --- /dev/null +++ b/src/test/java/seedu/address/logic/commands/AllocateStudentToTeamCommandTest.java @@ -0,0 +1,152 @@ +package seedu.address.logic.commands; + +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertTrue; +import static seedu.address.logic.commands.CommandTestUtil.VALID_EMAIL_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandFailure; +import static seedu.address.logic.commands.CommandTestUtil.assertCommandSuccess; +import static seedu.address.testutil.TypicalPersons.ALICE; +import static seedu.address.testutil.TypicalPersons.AMY; +import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; + +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import seedu.address.commons.core.index.Index; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamByEmailCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamByIndexCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamByStuIdCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamCommand; +import seedu.address.model.Model; +import seedu.address.model.ModelManager; +import seedu.address.model.UserPrefs; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Person; +import seedu.address.testutil.PersonBuilder; + + +public class AllocateStudentToTeamCommandTest { + private Model model = new ModelManager(getTypicalAddressBook(), new UserPrefs()); + private TutorialClass tutorialClass; + private Person validPerson; + private Person validOtherPerson; + private ModuleCode newModule; + private TutorialTeam newTeam; + + @BeforeEach + public void setUp() { + validPerson = new PersonBuilder(AMY).build(); + validOtherPerson = new PersonBuilder(ALICE) + .withStudentId(VALID_STUDENT_ID_BOB).withEmail(VALID_EMAIL_BOB).build(); + newModule = new ModuleCode(VALID_MODULE_AMY); + model.addModule(newModule); + model.addPerson(validPerson); + model.addPerson(validOtherPerson); + TutorialClass newTutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + newModule.addTutorialClass(newTutorialClass); + tutorialClass = newTutorialClass; + newTeam = new TutorialTeam(VALID_TEAM_NAME, 1); + tutorialClass.addTeam(newTeam); + } + + @Test + public void invalidAllocationToTeam_indexNotInSystem_failure() { + Index index = Index.fromOneBased(1000); + AllocateStudentToTeamByIndexCommand allocateStudentToTeamByIndexCommand = new + AllocateStudentToTeamByIndexCommand(index, + newModule, tutorialClass, newTeam); + assertCommandFailure(allocateStudentToTeamByIndexCommand, model, + String.format(AllocateStudentToTeamByIndexCommand.MESSAGE_PERSON_INDEX_NOT_FOUND, + index.getOneBased(), tutorialClass)); + } + + @Test + public void invalidAllocationToTeam_teamSizeExceeded_failure() { + tutorialClass.addStudent(validPerson); + newTeam.addStudent(validPerson); + tutorialClass.addStudent(validOtherPerson); + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = new + AllocateStudentToTeamByStuIdCommand(validOtherPerson.getStudentId(), newModule, tutorialClass, newTeam); + AllocateStudentToTeamByEmailCommand allocateStudentToTeamByEmailCommand = new + AllocateStudentToTeamByEmailCommand(validOtherPerson.getEmail(), newModule, tutorialClass, newTeam); + assertCommandFailure(allocateStudentToTeamByStuIdCommand, model, + String.format(AllocateStudentToTeamCommand.MESSAGE_TEAM_SIZE_EXCEEDED, newTeam.getTeamSize())); + assertCommandFailure(allocateStudentToTeamByEmailCommand, model, + String.format(AllocateStudentToTeamCommand.MESSAGE_TEAM_SIZE_EXCEEDED, newTeam.getTeamSize())); + } + + @Test + public void validAllocationToTeam_indexInSystem_success() { + tutorialClass.addStudent(validPerson); + tutorialClass.addStudent(validOtherPerson); + Index index = Index.fromZeroBased(1); + AllocateStudentToTeamByIndexCommand allocateStudentToTeamByIndexCommand = new + AllocateStudentToTeamByIndexCommand(index, + newModule, tutorialClass, newTeam); + assertCommandSuccess(allocateStudentToTeamByIndexCommand, model, + String.format(AllocateStudentToTeamByIndexCommand.MESSAGE_SUCCESS, newTeam), model); + } + + + @Test + public void invalidAllocationToTeam_studentNotInTutorialClass_failure() { + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = new + AllocateStudentToTeamByStuIdCommand(validPerson.getStudentId(), newModule, tutorialClass, newTeam); + AllocateStudentToTeamByEmailCommand allocateStudentToTeamByEmailCommand = new + AllocateStudentToTeamByEmailCommand(validPerson.getEmail(), newModule, tutorialClass, newTeam); + assertCommandFailure(allocateStudentToTeamByStuIdCommand, model, + String.format(AllocateStudentToTeamCommand.MESSAGE_STUDENT_NOT_IN_TUTORIAL)); + assertCommandFailure(allocateStudentToTeamByEmailCommand, model, + String.format(AllocateStudentToTeamCommand.MESSAGE_STUDENT_NOT_IN_TUTORIAL)); + } + + @Test + public void equals() { + // creation of 2 allocation command based on 2 different student ID adding to the same team under + // the same module and tutorial class. + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = + new AllocateStudentToTeamByStuIdCommand(validPerson.getStudentId(), newModule, tutorialClass, newTeam); + AllocateStudentToTeamByStuIdCommand allocateOtherStudentToTeamByStuIdCommand = + new AllocateStudentToTeamByStuIdCommand(validOtherPerson.getStudentId(), + newModule, tutorialClass, newTeam); + + // same object --> returns true + assertTrue(allocateStudentToTeamByStuIdCommand.equals(allocateStudentToTeamByStuIdCommand)); + + // different type --> returns false + assertFalse(allocateStudentToTeamByStuIdCommand.equals("hello world")); + + // null --> returns false + assertFalse(allocateStudentToTeamByStuIdCommand.equals(null)); + + // allocation of a different person --> returns false + assertFalse(allocateStudentToTeamByStuIdCommand.equals(allocateOtherStudentToTeamByStuIdCommand)); + + // creation of 2 allocation command based on 2 different student emails adding to the same team under + // the same module and tutorial class. + AllocateStudentToTeamByEmailCommand allocateStudentToTeamByEmailCommand = + new AllocateStudentToTeamByEmailCommand(validPerson.getEmail(), newModule, tutorialClass, newTeam); + AllocateStudentToTeamByEmailCommand allocateOtherStudentToTeamByEmailCommand = + new AllocateStudentToTeamByEmailCommand(validOtherPerson.getEmail(), + newModule, tutorialClass, newTeam); + + // same object --> returns true + assertTrue(allocateStudentToTeamByEmailCommand.equals(allocateStudentToTeamByEmailCommand)); + + // different type --> returns false + assertFalse(allocateStudentToTeamByEmailCommand.equals("hello world")); + + // null --> returns false + assertFalse(allocateStudentToTeamByEmailCommand.equals(null)); + + // allocation of a different person --> returns false + assertFalse(allocateStudentToTeamByEmailCommand.equals(allocateOtherStudentToTeamByEmailCommand)); + } + +} diff --git a/src/test/java/seedu/address/logic/commands/CommandTestUtil.java b/src/test/java/seedu/address/logic/commands/CommandTestUtil.java index 5599bf61c76..3fbb88f8c72 100644 --- a/src/test/java/seedu/address/logic/commands/CommandTestUtil.java +++ b/src/test/java/seedu/address/logic/commands/CommandTestUtil.java @@ -41,6 +41,7 @@ public class CommandTestUtil { public static final String VALID_MODULE_BOB = "CS1231S"; public static final String VALID_TUTORIAL_AMY = "T01"; public static final String VALID_TUTORIAL_BOB = "T02"; + public static final String VALID_TEAM_NAME = "Team 1"; public static final String VALID_TAG_HUSBAND = "husband"; public static final String VALID_TAG_FRIEND = "friend"; @@ -61,6 +62,8 @@ public class CommandTestUtil { public static final String INVALID_PERSON_EMAIL = "test@example.com"; public static final String INVALID_PERSON_STUDENT_ID = "A2222222A"; + public static final String INVALID_MODULECODE = "22JK"; + public static final String INVALID_TUTORIAL = "HHHH@"; // Team related constants public static final String VALID_TEAM_NAME_AMY = "Team 1"; diff --git a/src/test/java/seedu/address/model/AddressBookTest.java b/src/test/java/seedu/address/model/AddressBookTest.java index 9246a24400c..8f0dd24f525 100644 --- a/src/test/java/seedu/address/model/AddressBookTest.java +++ b/src/test/java/seedu/address/model/AddressBookTest.java @@ -6,6 +6,10 @@ import static seedu.address.logic.commands.CommandTestUtil.VALID_EMAIL_AMY; import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID_AMY; import static seedu.address.logic.commands.CommandTestUtil.VALID_TAG_HUSBAND; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; import static seedu.address.testutil.Assert.assertThrows; import static seedu.address.testutil.TypicalPersons.ALICE; import static seedu.address.testutil.TypicalPersons.AMY; @@ -103,6 +107,108 @@ public void hasPersonWithEmail_personNotInAddressBook_returnsFalse() { assertFalse(addressBook.hasPersonWithEmail(AMY.getEmail())); } + @Test + public void isStudentInTutorialClass_personNotInClass_failure() { + Person person = new PersonBuilder(ALICE).build(); + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + assertFalse(addressBook.isStudentInTutorialClass(person, tutorialClass)); + } + + @Test + public void isStudentInTutorialClass_classIsNull_failure() { + Person person = new PersonBuilder(ALICE).build(); + assertThrows(NullPointerException.class, () -> addressBook.isStudentInTutorialClass(person, null)); + } + + @Test + public void isStudentInTutorialClass_personIsNull_failure() { + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + assertThrows(NullPointerException.class, () -> addressBook.isStudentInTutorialClass(null, tutorialClass)); + } + + @Test + public void allocateStudentToTeam_personIsNull_failure() { + TutorialTeam tutorialTeam = new TutorialTeam(VALID_TEAM_NAME); + assertThrows(NullPointerException.class, () -> addressBook.allocateStudentToTeam(null, tutorialTeam)); + } + + @Test + public void allocateStudentToTeam_tutorialTeamIsNull_failure() { + Person person = new PersonBuilder(ALICE).build(); + assertThrows(NullPointerException.class, () -> addressBook.allocateStudentToTeam(person, null)); + } + + @Test + public void hasTeamSizeExceeded_teamSizeNotExceeded_failure() { + TutorialTeam tutorialTeam = new TutorialTeam(VALID_TEAM_NAME, 3); + assertFalse(addressBook.hasTeamSizeExceeded(tutorialTeam)); + } + + @Test + public void hasTeamSizeExceeded_teamSizeExceeded_success() { + TutorialTeam tutorialTeam = new TutorialTeam(VALID_TEAM_NAME, 1); + Person student = new PersonBuilder(ALICE).build(); + tutorialTeam.addStudent(student); + assertTrue(addressBook.hasTeamSizeExceeded(tutorialTeam)); + } + + @Test + public void isStudentInAnyTeam_studentNotInAny_failure() { + TutorialClass tutorialClass = new TutorialClass(); + TutorialTeam firstTutorialTeam = new TutorialTeam(VALID_TEAM_NAME, 1); + TutorialTeam secondtutorialTeam = new TutorialTeam(VALID_TEAM_NAME_BOB, 2); + tutorialClass.addTeam(firstTutorialTeam); + tutorialClass.addTeam(secondtutorialTeam); + Person person = new PersonBuilder(ALICE).build(); + assertFalse(addressBook.isStudentInAnyTeam(person, tutorialClass)); + } + + @Test + public void isStudentInAnyTeam_studentIsNull_failure() { + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + TutorialTeam firstTutorialTeam = new TutorialTeam(VALID_TEAM_NAME_AMY, 1); + TutorialTeam secondtutorialTeam = new TutorialTeam(VALID_TEAM_NAME_BOB, 2); + tutorialClass.addTeam(firstTutorialTeam); + tutorialClass.addTeam(secondtutorialTeam); + assertFalse(addressBook.isStudentInAnyTeam(null, tutorialClass)); + } + + @Test + public void hasTeamInTutorial_success() { + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + TutorialTeam firstTutorialTeam = new TutorialTeam(VALID_TEAM_NAME, 1); + TutorialTeam secondtutorialTeam = new TutorialTeam(VALID_TEAM_NAME_BOB, 2); + tutorialClass.addTeam(firstTutorialTeam); + tutorialClass.addTeam(secondtutorialTeam); + assertTrue(addressBook.hasTeamInTutorial(tutorialClass, firstTutorialTeam)); + } + + @Test + public void hasTeamInTutorial_tutorialTeamIsNull_failure() { + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + TutorialTeam firstTutorialTeam = new TutorialTeam(VALID_TEAM_NAME, 1); + TutorialTeam secondtutorialTeam = new TutorialTeam(VALID_TEAM_NAME_BOB, 2); + tutorialClass.addTeam(firstTutorialTeam); + tutorialClass.addTeam(secondtutorialTeam); + assertThrows(NullPointerException.class, () -> addressBook.hasTeamInTutorial(tutorialClass, null)); + } + + @Test + public void getTutorialTeam_tutorialTeamIsNull_failure() { + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + assertThrows(NullPointerException.class, () -> addressBook.getTutorialTeam(tutorialClass, null)); + } + + @Test + public void getTutorialTeam_tutorialTeamMatch_success() { + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_AMY); + TutorialTeam firstTutorialTeam = new TutorialTeam(VALID_TEAM_NAME, 1); + TutorialTeam secondtutorialTeam = new TutorialTeam(VALID_TEAM_NAME_BOB, 2); + tutorialClass.addTeam(firstTutorialTeam); + tutorialClass.addTeam(secondtutorialTeam); + assertEquals(addressBook.getTutorialTeam(tutorialClass, firstTutorialTeam), firstTutorialTeam); + } + @Test public void hasPersonWithEmail_differentPersonWithSameEmail_returnsTrue() { addressBook.addPerson(AMY); @@ -200,6 +306,11 @@ public ObservableList getStudentsInTeamList() { return null; } + @Override + public ObservableList getStudentsInTutorialClass(TutorialClass tutorialClass) { + return null; + } + @Override public UniquePersonList getUniquePersonList() { return null; From 39cc6ec113899b3b4fab808eb6cf3dbb80811ef9 Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Fri, 29 Mar 2024 02:28:10 +0800 Subject: [PATCH 11/12] Update Testcase for Allocate Student Parser and Json Adapted files * Create new Test Cases for AllocateStudentToTeamCommandParser and add more test cases to JsonAdapted files. --- .../AllocateStudentToTeamCommandTest.java | 112 ++++++++++++++++++ .../logic/commands/CommandTestUtil.java | 3 + ...llocateStudentToTeamCommandParserTest.java | 58 +++++++++ .../storage/JsonAdaptedTutorialClassTest.java | 7 ++ .../storage/JsonAdaptedTutorialTeamTest.java | 7 ++ 5 files changed, 187 insertions(+) create mode 100644 src/test/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParserTest.java diff --git a/src/test/java/seedu/address/logic/commands/AllocateStudentToTeamCommandTest.java b/src/test/java/seedu/address/logic/commands/AllocateStudentToTeamCommandTest.java index 8c89a7e6e04..4cc46ada069 100644 --- a/src/test/java/seedu/address/logic/commands/AllocateStudentToTeamCommandTest.java +++ b/src/test/java/seedu/address/logic/commands/AllocateStudentToTeamCommandTest.java @@ -1,14 +1,22 @@ package seedu.address.logic.commands; +import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertTrue; +import static seedu.address.logic.commands.CommandTestUtil.VALID_EMAIL; import static seedu.address.logic.commands.CommandTestUtil.VALID_EMAIL_BOB; import static seedu.address.logic.commands.CommandTestUtil.VALID_MODULE_AMY; +import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID; import static seedu.address.logic.commands.CommandTestUtil.VALID_STUDENT_ID_BOB; import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME_BOB; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME_NEW; import static seedu.address.logic.commands.CommandTestUtil.VALID_TUTORIAL_AMY; import static seedu.address.logic.commands.CommandTestUtil.assertCommandFailure; import static seedu.address.logic.commands.CommandTestUtil.assertCommandSuccess; +import static seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamCommand.MESSAGE_DUPLICATE_PERSON_IN_TEAM; +import static seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamCommand.MESSAGE_STUDENT_DOES_NOT_EXIST; +import static seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamCommand.MESSAGE_TEAM_DOES_NOT_EXIST; import static seedu.address.testutil.TypicalPersons.ALICE; import static seedu.address.testutil.TypicalPersons.AMY; import static seedu.address.testutil.TypicalPersons.getTypicalAddressBook; @@ -27,7 +35,9 @@ import seedu.address.model.module.ModuleCode; import seedu.address.model.module.TutorialClass; import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Email; import seedu.address.model.person.Person; +import seedu.address.model.person.StudentId; import seedu.address.testutil.PersonBuilder; @@ -38,6 +48,7 @@ public class AllocateStudentToTeamCommandTest { private Person validOtherPerson; private ModuleCode newModule; private TutorialTeam newTeam; + private TutorialTeam tutTeam; @BeforeEach public void setUp() { @@ -52,6 +63,8 @@ public void setUp() { newModule.addTutorialClass(newTutorialClass); tutorialClass = newTutorialClass; newTeam = new TutorialTeam(VALID_TEAM_NAME, 1); + tutTeam = new TutorialTeam(VALID_TEAM_NAME_BOB, 3); + tutorialClass.addTeam(tutTeam); tutorialClass.addTeam(newTeam); } @@ -81,6 +94,69 @@ public void invalidAllocationToTeam_teamSizeExceeded_failure() { String.format(AllocateStudentToTeamCommand.MESSAGE_TEAM_SIZE_EXCEEDED, newTeam.getTeamSize())); } + @Test + public void invalidAllocationToTeam_studentNull_failure() { + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = new + AllocateStudentToTeamByStuIdCommand(new StudentId(VALID_STUDENT_ID), newModule, tutorialClass, newTeam); + AllocateStudentToTeamByEmailCommand allocateStudentToTeamByEmailCommand = new + AllocateStudentToTeamByEmailCommand(new Email(VALID_EMAIL), newModule, tutorialClass, newTeam); + assertCommandFailure(allocateStudentToTeamByStuIdCommand, model, + String.format(MESSAGE_STUDENT_DOES_NOT_EXIST)); + assertCommandFailure(allocateStudentToTeamByEmailCommand, model, + String.format(MESSAGE_STUDENT_DOES_NOT_EXIST)); + } + + @Test + public void invalidAllocationToTeam_tutorialTeamNotExist_failure() { + TutorialTeam team = new TutorialTeam(VALID_TEAM_NAME_NEW); + + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = new + AllocateStudentToTeamByStuIdCommand(validPerson.getStudentId(), newModule, tutorialClass, + team); + AllocateStudentToTeamByEmailCommand allocateStudentToTeamByEmailCommand = new + AllocateStudentToTeamByEmailCommand(validPerson.getEmail(), newModule, tutorialClass, + team); + assertCommandFailure(allocateStudentToTeamByStuIdCommand, model, + String.format(MESSAGE_TEAM_DOES_NOT_EXIST, team, tutorialClass)); + assertCommandFailure(allocateStudentToTeamByEmailCommand, model, + String.format(MESSAGE_TEAM_DOES_NOT_EXIST, team, tutorialClass)); + } + + @Test + public void invalidAllocationToTeam_studentAlreadyInTeam_failure() { + tutorialClass.addStudent(validPerson); + newTeam.addStudent(validPerson); + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = new + AllocateStudentToTeamByStuIdCommand(validPerson.getStudentId(), newModule, tutorialClass, + tutTeam); + AllocateStudentToTeamByEmailCommand allocateStudentToTeamByEmailCommand = new + AllocateStudentToTeamByEmailCommand(validPerson.getEmail(), newModule, tutorialClass, + tutTeam); + assertCommandFailure(allocateStudentToTeamByStuIdCommand, model, + String.format(MESSAGE_DUPLICATE_PERSON_IN_TEAM, tutorialClass)); + assertCommandFailure(allocateStudentToTeamByEmailCommand, model, + String.format(MESSAGE_DUPLICATE_PERSON_IN_TEAM, tutorialClass)); + } + + + + @Test + public void validAllocationToTeam_byEmailOrStudentId_success() { + tutorialClass.addStudent(validPerson); + tutorialClass.addStudent(validOtherPerson); + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = new + AllocateStudentToTeamByStuIdCommand(validPerson.getStudentId(), + newModule, tutorialClass, tutTeam); + AllocateStudentToTeamByEmailCommand allocateStudentToTeamByEmailCommand = new + AllocateStudentToTeamByEmailCommand(validOtherPerson.getEmail(), + newModule, tutorialClass, tutTeam); + assertCommandSuccess(allocateStudentToTeamByStuIdCommand, model, + String.format(AllocateStudentToTeamByIndexCommand.MESSAGE_SUCCESS, tutTeam), model); + assertCommandSuccess(allocateStudentToTeamByEmailCommand, model, + String.format(AllocateStudentToTeamByEmailCommand.MESSAGE_SUCCESS, tutTeam), model); + } + + @Test public void validAllocationToTeam_indexInSystem_success() { tutorialClass.addStudent(validPerson); @@ -106,8 +182,30 @@ public void invalidAllocationToTeam_studentNotInTutorialClass_failure() { String.format(AllocateStudentToTeamCommand.MESSAGE_STUDENT_NOT_IN_TUTORIAL)); } + @Test + public void toString_test() { + tutorialClass.addStudent(validPerson); + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = + new AllocateStudentToTeamByStuIdCommand(validPerson.getStudentId(), newModule, tutorialClass, newTeam); + AllocateStudentToTeamByEmailCommand allocateOtherStudentToTeamByEmailCommand = + new AllocateStudentToTeamByEmailCommand(validOtherPerson.getEmail(), + newModule, tutorialClass, newTeam); + AllocateStudentToTeamByIndexCommand allocateStudentToTeamByIndexCommand = + new AllocateStudentToTeamByIndexCommand(Index.fromZeroBased(0), + newModule, tutorialClass, newTeam); + assertEquals(allocateOtherStudentToTeamByEmailCommand.toString(), + allocateOtherStudentToTeamByEmailCommand.toString()); + assertEquals(allocateStudentToTeamByStuIdCommand.toString(), + allocateStudentToTeamByStuIdCommand.toString()); + assertEquals(allocateStudentToTeamByIndexCommand.toString(), + allocateStudentToTeamByIndexCommand.toString()); + + } + @Test public void equals() { + tutorialClass.addStudent(validPerson); + tutorialClass.addStudent(validOtherPerson); // creation of 2 allocation command based on 2 different student ID adding to the same team under // the same module and tutorial class. AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = @@ -147,6 +245,20 @@ public void equals() { // allocation of a different person --> returns false assertFalse(allocateStudentToTeamByEmailCommand.equals(allocateOtherStudentToTeamByEmailCommand)); + + + AllocateStudentToTeamByIndexCommand allocateOtherStudentToTeamByIndexCommand = + new AllocateStudentToTeamByIndexCommand(Index.fromZeroBased(1), + newModule, tutorialClass, newTeam); + + // same object + assertTrue(allocateOtherStudentToTeamByIndexCommand.equals(allocateOtherStudentToTeamByIndexCommand)); + + // different type --> returns false + assertFalse(allocateOtherStudentToTeamByIndexCommand.equals("hello world")); + + // null --> returns false + assertFalse(allocateOtherStudentToTeamByIndexCommand.equals(null)); } } diff --git a/src/test/java/seedu/address/logic/commands/CommandTestUtil.java b/src/test/java/seedu/address/logic/commands/CommandTestUtil.java index 3fbb88f8c72..d801560be1a 100644 --- a/src/test/java/seedu/address/logic/commands/CommandTestUtil.java +++ b/src/test/java/seedu/address/logic/commands/CommandTestUtil.java @@ -34,9 +34,11 @@ public class CommandTestUtil { public static final String VALID_NAME_BOB = "Bob Choo"; public static final String VALID_EMAIL_AMY = "amy@example.com"; public static final String VALID_EMAIL_BOB = "bob@example.com"; + public static final String VALID_EMAIL = "c@example.com"; public static final String VALID_STUDENT_ID_AMY = "A1111111Z"; public static final String VALID_STUDENT_ID_BOB = "A2222222Z"; + public static final String VALID_STUDENT_ID = "A3333333Z"; public static final String VALID_MODULE_AMY = "CS1101S"; public static final String VALID_MODULE_BOB = "CS1231S"; public static final String VALID_TUTORIAL_AMY = "T01"; @@ -68,6 +70,7 @@ public class CommandTestUtil { // Team related constants public static final String VALID_TEAM_NAME_AMY = "Team 1"; public static final String VALID_TEAM_NAME_BOB = "Team 2"; + public static final String VALID_TEAM_NAME_NEW = "Team 3"; public static final int VALID_TEAM_SIZE = 5; public static final String TEAM_NAME_DESC_AMY = " " + PREFIX_NAME + VALID_TEAM_NAME_AMY; public static final String TEAM_SIZE_DESC = " " + PREFIX_TEAM_SIZE + VALID_TEAM_SIZE; diff --git a/src/test/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParserTest.java b/src/test/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParserTest.java new file mode 100644 index 00000000000..e660d6c6a74 --- /dev/null +++ b/src/test/java/seedu/address/logic/parser/AllocateStudentToTeamCommandParserTest.java @@ -0,0 +1,58 @@ +package seedu.address.logic.parser; + +import static seedu.address.logic.Messages.MESSAGE_INVALID_COMMAND_FORMAT; +import static seedu.address.logic.commands.CommandTestUtil.VALID_TEAM_NAME; +import static seedu.address.logic.parser.CliSyntax.PREFIX_EMAIL; +import static seedu.address.logic.parser.CliSyntax.PREFIX_MODULECODE; +import static seedu.address.logic.parser.CliSyntax.PREFIX_STUDENTID; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TEAMNAME; +import static seedu.address.logic.parser.CliSyntax.PREFIX_TUTORIALCLASS; +import static seedu.address.logic.parser.CommandParserTestUtil.assertParseFailure; +import static seedu.address.logic.parser.CommandParserTestUtil.assertParseSuccess; +import static seedu.address.model.module.ModuleCodeTest.VALID_MODULE_CODE; +import static seedu.address.model.module.ModuleCodeTest.VALID_TUTORIAL_1; +import static seedu.address.testutil.TypicalPersons.AMY; + +import org.junit.jupiter.api.Test; + +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamByEmailCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamByStuIdCommand; +import seedu.address.logic.commands.allocatestudenttoteamcommands.AllocateStudentToTeamCommand; +import seedu.address.model.module.ModuleCode; +import seedu.address.model.module.TutorialClass; +import seedu.address.model.module.TutorialTeam; +import seedu.address.model.person.Person; +import seedu.address.testutil.PersonBuilder; + +public class AllocateStudentToTeamCommandParserTest { + private AllocateStudentToTeamCommandParser parser = new AllocateStudentToTeamCommandParser(); + + @Test + public void parse_validArgs_returnsAllocateStudentToTeamCommand() { + Person person = new PersonBuilder(AMY).build(); + ModuleCode moduleCode = new ModuleCode(VALID_MODULE_CODE); + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_1); + TutorialTeam tutorialTeam = new TutorialTeam(VALID_TEAM_NAME); + moduleCode.addTutorialClass(tutorialClass); + tutorialClass.addTeam(tutorialTeam); + AllocateStudentToTeamByStuIdCommand allocateStudentToTeamByStuIdCommand = + new AllocateStudentToTeamByStuIdCommand(person.getStudentId(), moduleCode, tutorialClass, tutorialTeam); + AllocateStudentToTeamByEmailCommand allocateStudentToTeamByEmailCommand = + new AllocateStudentToTeamByEmailCommand(person.getEmail(), moduleCode, tutorialClass, tutorialTeam); + String userInput = " " + PREFIX_MODULECODE + moduleCode.moduleCode + + " " + PREFIX_TUTORIALCLASS + tutorialClass.tutorialName + + " " + PREFIX_TEAMNAME + tutorialTeam.getTeamName(); + assertParseSuccess(parser, " " + PREFIX_STUDENTID + person.getStudentId().value + userInput, + allocateStudentToTeamByStuIdCommand); + assertParseSuccess(parser, " " + PREFIX_EMAIL + person.getEmail().value + userInput, + allocateStudentToTeamByEmailCommand); + } + + @Test + public void parse_invalidArgs_throwsParseException() { + String expectedMessage = String.format(MESSAGE_INVALID_COMMAND_FORMAT, + AllocateStudentToTeamCommand.MESSAGE_USAGE); + assertParseFailure(parser, "a", expectedMessage); + } + +} diff --git a/src/test/java/seedu/address/storage/JsonAdaptedTutorialClassTest.java b/src/test/java/seedu/address/storage/JsonAdaptedTutorialClassTest.java index 0385f2456ab..80eb9ca88f3 100644 --- a/src/test/java/seedu/address/storage/JsonAdaptedTutorialClassTest.java +++ b/src/test/java/seedu/address/storage/JsonAdaptedTutorialClassTest.java @@ -32,6 +32,13 @@ void toModelType_success() throws Exception { assertEquals(tutorialClass, jsonTutorialClass.toModelType()); } + @Test + void toModelType_test_success() throws Exception { + TutorialClass tutorialClass = new TutorialClass(VALID_TUTORIAL_NAME); + JsonAdaptedTutorialClass jsonTutorialClass = new JsonAdaptedTutorialClass(tutorialClass); + assertEquals(tutorialClass, jsonTutorialClass.toModelType()); + } + @Test void toModelType_invalidTutorialName_throwsIllegalValueException() { JsonAdaptedTutorialClass jsonTutorialClass = new JsonAdaptedTutorialClass(INVALID_TUTORIAL_NAME, diff --git a/src/test/java/seedu/address/storage/JsonAdaptedTutorialTeamTest.java b/src/test/java/seedu/address/storage/JsonAdaptedTutorialTeamTest.java index 3c0fc3d30d9..1fb1ec567f6 100644 --- a/src/test/java/seedu/address/storage/JsonAdaptedTutorialTeamTest.java +++ b/src/test/java/seedu/address/storage/JsonAdaptedTutorialTeamTest.java @@ -32,6 +32,13 @@ void toModelType_success() throws Exception { assertEquals(tutorialTeam, jsonTutorialTeam.toModelType()); } + @Test + void toModelType_test_success() throws Exception { + TutorialTeam tutorialTeam = new TutorialTeam(VALID_TEAM_NAME, VALID_TEAM_SIZE); + JsonAdaptedTutorialTeam jsonTutorialTeam = new JsonAdaptedTutorialTeam(tutorialTeam); + assertEquals(tutorialTeam, jsonTutorialTeam.toModelType()); + } + @Test void toModelType_invalidTeamName_throwsIllegalValueException() { JsonAdaptedTutorialTeam jsonTutorialTeam = new JsonAdaptedTutorialTeam(INVALID_TEAM_NAME, VALID_TEAM_SIZE, From 0f86f96657ba53ad68ca040a04d4192f3dd7bdee Mon Sep 17 00:00:00 2001 From: Zack-Tay Date: Fri, 29 Mar 2024 13:14:49 +0800 Subject: [PATCH 12/12] Update checkstyle --- docs/diagrams/AddStudentSequence.puml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/diagrams/AddStudentSequence.puml b/docs/diagrams/AddStudentSequence.puml index 97a395e5bfc..b687e40ebb2 100644 --- a/docs/diagrams/AddStudentSequence.puml +++ b/docs/diagrams/AddStudentSequence.puml @@ -67,4 +67,4 @@ deactivate AddStudentCommand [<--LogicManager deactivate LogicManager -@enduml \ No newline at end of file +@enduml