Overview
Pet Store Helper is a desktop application designed for owners of pet stores to help them manage their store and operations. The user interacts with it using a CLI, and it has a GUI created with JavaFX. It is written in Java, and has about 15 kLoC.
Summary of contributions
-
Major enhancement: added the ability to schedule when to bathe my own (in-store) pets
-
What it does: allows the user to add/delete/edit/find slots with a specified timing and duration for their (in-store) pets
-
Justification: This feature allows the user to manage the slots for their pets to avoid clashes.
-
Highlights: This enhancement is the foundation to other systems such as calendar view and slot list view. Integration between Pets and slots need to be carefully handled in order to achieve both immutability of the two systems and synchronization between the two systems. It required an in-depth analysis of structural design to avoid promoting high coupling.
-
Credits: The use of a listener on the internal UniquePetList to update Slots automatically was inspired by my teammates' efforts to synchronize the inventory system with the pet system.
-
-
Minor enhancement: Changed the color scheme and modified the window properties of the UI to give the application a cute look to fit its function
-
Credits: Window resizing and dragging function implementation referenced from Alexander.Berg, Evgenii Kanivets, Zachary Perales from stackoverflow.com, retrieved: https://stackoverflow.com/questions/19455059/allow-user-to-resize-an-undecorated-stage
-
-
Code contributed: [Functional code] [Test code]
-
Other contributions:
-
Project management:
-
Managed releases
v1.2
&v1.3.2
(2 releases) on GitHub
-
-
Enhancements to existing features:
-
Documentation:
-
Did cosmetic tweaks to existing contents of the User Guide: #75
-
-
Community:
-
Tools:
-
Integrated a new Github plugin (TravisCI) to the team repo
-
-
Contributions to the Developer Guide
Given below are sections I contributed to the Developer Guide. They showcase my ability to write a technical documentation and the technical depth of my contributions to the project. |
Schedule feature
Written by Zhao Mingjian
Implementation
The schedule feature uses instances of class Slot
to organise bathing schedule for the pets. Each Slot
contains a
starting time of the bath, stored internally as a LocalDateTime
, and the duration of the bath stored internally as a
Duration
. It stores a reference to the Pet
in the ModelManager
as specified by the user.
Given below is an example usage scenario and how the Schedule
mechanism behaves at each step.
Step 1. The user launches the application with some pets stored (Garfield
, for instance). ObservableList<Slot>
in Schedule
is currently empty.
Step 2. The user executes addslot n/Garfield t/1/4/2020 1200 d/120
command to create a Slot
for Garfield
.
The AddSlotCommandParser
calls parsePet()
in SlotParserUtil
, which then takes in the Model
passed in to find a
reference for the specific Pet
with Model.getPet()
. Prior to this stage, if the name string is invalid, a
ParseException(MESSAGE_INVALID_PETNAME)
will be thrown. Or the program cannot find the Pet
in the model, a
ParseException(MESSAGE_PET_DOES_NOT_EXIST)
will be thrown. This ensures that every slot created actually points to an
existing Pet
found in PetTracker
.
If parsePet() fails its execution, no new Slot is created.
|
Step 3. New Slot
is created.
Step 4. The user now decides that this exact slot should be occupied by another pet, and decides to edit it, executing
the editslot
command.
Step 5. SlotParserUtil
is used again to create a reference to a pet in the ModelManager
.
Step 6. The user now decides that they need to see slots occupied by a particular pet on a particular date, executing
the findslots n/Garfield t/1/4/2020
command.
Step 7. The FindSlotCommand
reduces the two predicates* and pass it to ModelManager
to create a filtered list of
slots.
*The FindSlotCommand
uses the following classes which both inherit Predicate<Slot>
to search for the user specified
slots:
-
SlotPetNamePredicate()
— Internally stores theName
to search for, and compares it withgetPet().getName().fullName
. -
SlotDateTimePredicate()
— Internally stores theLocalDateTime
to search for (Timing will be ignored), and compares it withgetDate()
.
The activity diagram below is an illustration of the flow of events that happen in the model component when the steps above occurs.
Given below is an example usage scenario that demonstrates how the Schedule
system integrates with the Pet
system.
Step 1. The user launches the application with a pet stored: Garfield
. A single instance of Slot
occupies
ObservableList<Slot>
in Schedule
, whose parameters are: petName: Garfield
,
dateTime: 11/4/2020 1200
, duration: 40
. Upon launch, a PetListChangeListener
will be attached to internalList
of
UniquePetList
.
Step 2. The user executes deletepet 1
command to delete Garfield
from the UniquePetList
. When user deletes the pet,
function onChanged
in PetListChangeListener
is called. This function calls removeExcessSlot
within the
PetListChangeListener
for each pet removed.
Step 3. removeExcessSlot
calls remove
in Schedule
to remove slots based on the name of the removed pet.
Step 4. The user now have successfully removed Garfield
and all the slots the pet used to occupy.
The sequence diagram below is an illustration of the flow of events that happen in the model component when the steps above occurs.
Design Considerations
Aspect: How schedule stores the pets internally
-
Alternative 1 (current choice): Makes a reference to the the memory address in
ModelManager
.-
Pros: When the pet is edited, it is easier to update the corresponding slot. Also reduces save file size and conserve system memory as there will be no duplicate information.
-
Cons: Harder to implement and test. Testing requires a sample list of pets to be instantiated first.
-
-
Alternative 2: Simply create a new Pet.
-
Pros: Easy to implement and test (A refactor of
Pet
), low coupling withModel
. -
Cons: Harder to synchronize with any changes in
UniquePetList
-
Appendix A: Product Scope
Written collaboratively, collated by Zhao Mingjian
Target user profile:
-
has a need to manage their pet store with a variety of animals and features
-
has a need to make schedules for pet grooming and ensure no-conflict in the scheduling
-
prefer desktop apps over other types
-
can type fast
-
prefers typing over mouse input
-
is reasonably comfortable using CLI apps
Value proposition: manage pets, pet consumables and schedule faster than a typical mouse/GUI driven app
Appendix B: User Stories
Written collaboratively, collated by Zhao Mingjian
Priorities: High (must have) - * * *
, Low (nice to have) - * *
Priority | As a … | I want to … | So that I can… |
---|---|---|---|
|
user |
key in a new pet, enter its breed, age, size and food consumption. |
keep track of the pets I have in my store and their details |
|
user |
delete a pet |
remove pets that I have sold or no longer taking care of |
|
user |
find a pet by name, species or tags |
locate details of the pets without having to go through the entire list |
|
user |
keep track of pet food, cleaning products and other consumables |
not run low on items needed to keep the pets healthy |
|
user |
schedule when to bathe my own (in-store) pets |
avoid clashes in bathing schedule |
|
user |
view the schedule and see which slots are available to bathe the customers' pets |
avoid clashes in bathing schedule |
|
user |
see which free slots are available for grooming |
avoid clashes in grooming |
|
user |
view a statistical summary of the pets, stocks and schedule |
handle logistics of the store more efficiently |
|
user |
add photos for the pets in store to illustrate |
easier to make a mental link between the actual pets in the store and the names |
|
user |
keep track of the cost and revenue generated by each pet |
so to buy the more popular ones in next restock |
Appendix C: Use Cases
Written by Zhao Mingjian
(For all use cases below, the System is the PSH
and the Actor is the user
, unless specified otherwise)
Use case: Delete pet
MSS
-
User requests to list pets
-
PSH shows a list of pets
-
User requests to delete a specific pet in the list
-
PetTracker deletes the pet
Use case ends.
Extensions
-
2a. The list is empty.
Use case ends.
-
3a. The given index is invalid.
-
3a1. PSH shows an error message.
Use case resumes at step 2.
-
Use case: Removing a bathing slot
MSS
-
User requests to show schedule
-
PSH shows schedule of that day
-
User requests of delete a slot at a specified timing
-
PSH deletes the slot
Use case ends.
Extensions
-
2a. There is currently conflict in the scheduling (i.e. One slot begins before the previous one ends), the latter slot is shown in red.
Use case resumes at step 2
-
3a. The given timing does not exist.
-
3a1. PSH shows an error message.
Use case resumes at step 2.
-
Appendix D: Non Functional Requirements
-
Should work on any mainstream OS as long as it has Java
11
or above installed. -
Should be able to hold up to 500 pets + items in total without a noticeable sluggishness in performance for typical usage.
-
A user with above average typing speed for regular English text (i.e. not code, not system admin commands) should be able to accomplish most of the tasks faster using commands than using the mouse.
Appendix F: Instructions for Manual Testing
Applied from AB3 by Zhao Mingjian
Given below are instructions to test the app manually.
These instructions only provide a starting point for testers to work on; testers are expected to do more exploratory testing. |
Launch and Shutdown
-
Initial launch
-
Download the jar file and copy into an empty folder
-
Double-click the jar file
Expected: Shows the GUI with a set of sample pets and slots. The window size may not be optimum.
-
-
Saving window preferences
-
Resize the window to an optimum size. Move the window to a different location. Close the window.
-
Re-launch the app by double-clicking the jar file.
Expected: The most recent window size and location is retained.
-
Switching display
-
Change display of the program
-
Prerequisites: Program is pre-populated with the sample data of pets and slots.
-
Test case:
display s
Expected: Program display is changed to show list of slots. -
Test case:
display c
Expected: Program display is changed to show slots in calendar view. -
Test case:
display i
Expected: Program display is changed to show inventory. -
Test case:
display p
Expected: Program display is changed to back show list of pets. -
Test case:
display x
Expected: Program display does not change. Error message shown. -
Other incorrect display commands to try:
display
,display I
,Display i
Expected: Similar to previous.
-
-
Adding a pet
-
Adding a pet while all pets are displayed
-
Prerequisites: Program is showing list of pets to (run
display p
)-
Test case:
addpet n/Alice g/female b/13/11/2015 s/dog f/Dog Food: 10 t/cute
Expected: A new pet "Alice" is added to the end of the pet list. Details of the newly added pet shown above the list of pets. -
Test case:
addpet n/Alice g/female b/24/12/2015 s/rabbit f/Rabbit Food: 15 t/fluffy
Expected: No pet is added. Error details shown above the list of pets. -
Other incorrect addpet commands to try:
addpet n/Bubbles g/helicopter b/8/10/2015 s/cat f/Cat Food: 15 t/white
,addpet n/Bubbles g/female b/78/10/2015 s/cat f/Cat Food: 15 t/white
Expected: No pet is added, with the relevant and appropriate error details shown above the list of pets.
-
-
Deleting a pet
-
Deleting a pet while all pets are displayed
-
Prerequisites: Display all pets using the
display p
command. Multiple pets in the display. -
Test case:
deletepet 1
Expected: First pet is deleted from the list. Details of the deleted pet shown above the list of pets. Slots that the pet used to occupy is also deleted. -
Test case:
deletepet 0
Expected: No pet is deleted. Error details shown above the list of pets. Slots remain the same. -
Other incorrect delete commands to try:
deletepet
,deletepet x
(where x is larger than the list size)
Expected: Similar to previous.
-
Adding a slot
-
Adding a slot while all slots are displayed
-
Prerequisites: Program is showing list of slots to (run
display s
). Program is pre-populated with the sample data of pets and slots.-
Test case:
addslot n/Bob t/6/4/2020 1000 d/60
Expected: A new slot is added to slot list. Details of the newly added slot shown above the list of slots. Because it is the earliest of all slots, it appears at the 1st slot in the list. -
Test case:
addslot n/Cindy t/67/4/2020 1000 d/60
Expected: No slot is added. Error details shown above the list of slots. -
Other incorrect addslot commands to try:
addslot
,addslot n/Duke t/6/4/2020 1130 d/60
,addslot n/Cindy t/6/4/2020 2300 d/120
Expected: No slot is added, with the relevant and appropriate error details shown above the list of slots.
-
-
Deleting a slot
-
Deleting a slot while all slots are displayed
-
Prerequisites: Program is showing list of slots to (run
display s
). Program is pre-populated with the sample data of pets and slots.-
Test case:
deleteslot 1
Expected: First slot is deleted from the list. Details of the deleted slot shown above the list of slots. -
Test case:
deleteslot 0
Expected: No slot is deleted. Error details shown above the list of slots. -
Other incorrect deleteslot commands to try:
deleteslot
,deleteslot x
(where x is larger than the list size)
Expected: Similar to previous.
-
-
View conflicted slots
-
Viewing slots with conflicts
-
Prerequisites: Program is pre-populated with the sample data of pets and slots.
Initial view: On Mon 6/4/2020, there is a single slot occupied by "Gru" from 13:00 - 14:40 (as per the sample data). It is not in conflict.-
Test case:
conflicts
Expected: Program successfully shows no slots with message "0 slots listed!", as the sample data has no slots in conflict. -
Test case:
addslot n/Bob t/6/4/2020 1400 d/60
Expected: A new slot is added to slot list. Details of the newly added slot shown above the list of slots. This newly added slot and the slot occupied by Gru are now marked as "[CONFLICT]" -
Test case:
conflicts
Expected: Program successfully shows only the two slots on 6/4/2020 with message "2 slots listed!"
-
-
Saving data
-
Dealing with missing/corrupted data files
-
Prerequisites: List of pets is well populated.
-
Test case: changing pet name manually to an invalid name in pettracker.json
Expected: Data is not loaded. Start with an empty Pet Tracker. -
Test case: changing pet name of a slot manually to pet that does not exist in pettracker.json
Expected: Data is not loaded. Start with an empty Pet Tracker.
-