Developer: Chahinez Boutemine (Scaphix)
The Inventory Management Tool is a simple, Python-based command-line application designed to help small businesses keep track of their stock efficiently. It allows users to add, update, delete, and display items with clear, color-coded feedback in the terminal. The idea for this project came from my own experience working in my family’s business, where I realized we lacked an organized way to manage inventory. I always wanted to create a tool that could make this process easier, and learning Python gave me the opportunity to finally build it myself.
Purpose
- Provide users with a simple and effective way to track inventory levels and manage products directly from the terminal.
- Help small business owners maintain accurate records of their stock, reduce manual errors, and make informed decisions about restocking or pricing.
Primary User Needs
- Easily add, update, delete, and view items in the inventory.
- Keep track of product quantities and prices with minimal technical knowledge.
- Store data safely in Google Sheets for persistent storage and easy access across sessions.
- Receive clear and user-friendly feedback through color-coded messages in the terminal.
Business Goals
- Offer a lightweight, reliable, and cost-free tool to manage inventory without requiring advanced software.
- Help businesses save time, avoid stock shortages or overstocking, and maintain up-to-date records.
- Support better organization and customer satisfaction by ensuring that stock information is always accurate and easy to access.
| Target | Expectation | Outcome |
|---|---|---|
| As a user | I would like to add new items to my inventory with unique IDs and names | so that I can track each product individually without confusion. |
| As a user | I would like to update existing items (name, quantity, price) | so that I can keep my inventory information current as stock levels and prices change. |
| As a user | I would like to delete items from my inventory with a confirmation prompt | so that I can remove discontinued products while avoiding accidental deletions. |
| As a user | I would like to view all items in a sorted, formatted table | so that I can easily see my complete inventory at a glance. |
| As a user | I would like the application to validate my input (IDs, quantities, prices) | so that I don't accidentally enter invalid data that could corrupt my records. |
| As a user | I would like to see color-coded feedback for success, errors, and warnings | so that I can quickly understand the results of my actions. |
| As a user | I would like the app to prevent duplicate IDs and names | so that each item in my inventory is unique and identifiable. |
| As a user | I would like the app to be intuitive with a clear menu system | so that I can manage my inventory without needing extensive training. |
- User Authentication and Role Management: Implement a login system with roles (e.g., admin, employee) to restrict data access based on user roles.
- Data Visualization: Add charts and graphs to visually represent stock levels, value trends, and inventory metrics over time.
- Search and Filter: Implement search functionality to find items by name, ID range, or price range, with filtering options.
- Low Stock Alerts: Notify users when stock levels fall below a defined threshold, prompting restock orders.
- Bulk Operations: Add ability to import/export multiple items at once via CSV files.
- Transaction History: Track all add/update/delete operations with timestamps for audit trails.
- Reporting and Exporting: Generate and export detailed inventory reports in PDF or CSV format.
- Category Management: Organize items into categories (e.g., electronics, food, clothing) for better organization.
- Mobile App Integration: Develop a mobile version of the app for easier inventory management on the go.
- Multi-location Support: Extend the system to track inventory across multiple warehouse or store locations.
- Price History: Track price changes over time to analyze pricing trends and profitability.
To make the Inventory Management Tool more organised and scalable, I chose to implement an object-oriented structure using two main classes: Item and Inventory. The Item class represents individual products, each with its own attributes such as ID, name, quantity, and price. The Inventory class, on the other hand, manages a collection of these items and provides the functionality to add, display, update, or delete products.
By separating responsibilities, the Item class handles individual product data, while the Inventory class manages the overall collection and business logic. This object-oriented approach allows me to extend the project later (e.g., connecting to a Google Sheet, adding invoices, or tracking quantities automatically) without rewriting the core functions
class Item:
"""
Represents a single product or entry in the inventory.
The Item class is responsible for storing all the details about
an individual product such as its ID, name, quantity, and price.
It ensures that each item can be easily managed, updated, and displayed
as part of the overall inventory.
Attributes:
id (str): A unique identifier for the item.
name (str): The name of the product.
quantity (int): The available stock quantity.
price (float): The price per unit of the product.
"""
def __init__(self, id, name, quantity, price):
self.id = id
self.name = name
self.quantity = quantity
self.price = priceclass Inventory:
"""
Manages a collection of items in the inventory.
The Inventory class acts as a container and controller for all items.
It allows adding, displaying, updating, and deleting products,
as well as saving and loading them from Google Sheets.
This separation of logic (Inventory vs. Item) makes the program
easier to maintain and scale.
Attributes:
items (list): A list that stores all Item objects in the inventory.
worksheet: The Google Sheets worksheet object for data persistence.
"""
def __init__(self, worksheet):
self.worksheet = worksheet
self.items = []The primary functions used on this application are:
add_item()- Prompts user for item details (ID, name, quantity, price), adds a new Item object to the inventory list, and saves it to Google Sheets.
update_item()- Allows user to modify an existing item's name, quantity, and price by searching for it by ID, then syncs changes to Google Sheets.
delete_item(id)- Removes an item from the inventory by ID after user confirmation (y/n prompt) and deletes it from Google Sheets.
display_item()- Displays all items in a formatted table sorted by ID, showing ID, name, quantity, and price.
get_valid_int(prompt)- Static method that validates and returns integer input, re-prompting on invalid entries.
get_valid_float(prompt)- Static method that validates and returns float input for price values.
get_id()- Gets a unique item ID from the user, checking for duplicates in the existing inventory.
get_name()- Gets a unique item name from the user with comprehensive validation: checks for empty input, ensures 3-15 characters with at least 3 letters using regex, and prevents duplicates (case-insensitive).
check_inventory_not_empty()- Decorator function that prevents operations on empty inventory and displays a warning.
get_items()- Loads existing inventory data from Google Sheets into the local inventory on program startup.
save_to_sheet(item)- Saves a new item to the Google Sheets worksheet.
update_item_in_sheet(item_id, item)- Updates an existing item in the Google Sheets worksheet by ID.
main()- Displays the welcome message and program instructions when the application starts.
tasks_list()- Displays the main menu and handles user task selection in a loop until exit.
my_task(selected_task)- Executes the selected task (1-5) by calling the appropriate inventory method.
I've used the following Python packages and external imports.
gspread: used for connecting to and interacting with Google Sheets APIgoogle.oauth2.service_account: used for authenticating with Google Sheets using service account credentialscolorama: used for including color in the terminal (Fore, Back, Style)re: used for regex pattern matching in name validationitem: local module containing the Item class definitioninventory: local module containing the Inventory class and inventory management logic
I have used the recommended PEP8 CI Python Linter to validate all of my Python files.
The final results are as follows:
| File | Screenshot | Notes |
|---|---|---|
| run.py | ![]() |
No errors found |
| inventory.py | ![]() |
No errors found |
| item.py | ![]() |
No errors found |
Description: I deployed the project to Heroku without including all required dependencies in the requirements.txt file. This caused an error where Heroku could not recognize the module.
Correction: I added the missing dependencies to fix the deployment issue.
Bug 2:
Description: I called a method without passing any argument.
elif selected_task == "4":
inventory.delete_item()Correction:
elif selected_task == "4":
name_to_delete = input(" Enter Name: ").strip()
inventory.delete_item(name_to_delete)Bug 3:
Description: The delete function was comparing string input with integer IDs, causing items to not be found. When adding items, IDs were stored as integers via get_valid_int(), but the delete function accepted input as a string without conversion.
Correction: Added type conversion in the delete task handler:
elif selected_task == "4":
print("Please enter the id of the item to delete ")
try:
id_to_delete = int(input("Enter Id: ").strip())
inventory.delete_item(id_to_delete)
except ValueError:
print(Fore.RED + "Invalid ID! Please enter a number.")
print(Style.RESET_ALL)Bug 4:
Description: When a user entered an invalid response (anything other than 'y' or 'n') at the delete confirmation prompt, the code did not return from the function. It would fall through the conditional and print "not found" even though the item was found.
Correction: Added an else clause to handle invalid confirmation input:
if delete == "y":
self.items.remove(item)
print(Fore.GREEN + f" item {id} deleted successfully.")
print(Style.RESET_ALL)
return
elif delete == "n":
print(Fore.YELLOW + " Deletion cancelled.")
print(Style.RESET_ALL)
return
else:
print(Fore.RED + " Invalid input. Deletion cancelled.")
print(Style.RESET_ALL)
returnCode Institute has provided a template to display the terminal view of this backend application in a modern web browser. This is to improve the accessibility of the project to others.
The live deployed application can be found deployed on Heroku.
This project uses Heroku, a platform as a service (PaaS) that enables developers to build, run, and operate applications entirely in the cloud.
Deployment steps are as follows, after account setup:
- Select New in the top-right corner of your Heroku Dashboard, and select Create new app from the dropdown menu.
- Your app name must be unique, and then choose a region closest to you (EU or USA), then finally, click Create App.
- From the new app Settings, click Reveal Config Vars, and set the value of KEY to
PORT, and the VALUE to8000then select ADD. - If using any confidential credentials, such as CREDS.JSON, then these should be pasted in the Config Variables as well.
- Further down, to support dependencies, select Add Buildpack.
- The order of the buildpacks is important; select
Pythonfirst, thenNode.jssecond. (if they are not in this order, you can drag them to rearrange them)
Heroku needs some additional files in order to deploy properly.
You can install this project's requirements.txt (where applicable) using:
pip3 install -r requirements.txt
If you have your own packages that have been installed, then the requirements file needs updated using:
pip3 freeze --local > requirements.txt
The Procfile can be created with the following command:
echo web: node index.js > Procfile
The runtime.txt file tells Heroku the specific version of Python to use when running your application.
python-3.12.2(or similar)
For Heroku deployment, follow these steps to connect your own GitHub repository to the newly created app:
Either (recommended):
- Select Automatic Deployment from the Heroku app.
Or:
- In the Terminal/CLI, connect to Heroku using this command:
heroku login -i - Set the remote for Heroku:
heroku git:remote -a app_name(replaceapp_namewith your app name) - After performing the standard Git
add,commit, andpushto GitHub, you can now type:git push heroku main
The Python terminal window should now be connected and deployed to Heroku!
This application uses Google Sheets to handle a "makeshift" database on the live site.
To run your own version of this application, you will need to create your own Google Sheet with one sheet named stock in the following format:
| ID | Name | Quantity | Price |
|---|---|---|---|
| sample data | sample data | sample data | sample data |
| sample data | sample data | sample data | sample data |
| sample data | sample data | sample data | sample data |
A credentials file in .JSON format from the Google Cloud Platform is also mandatory:
- From the dashboard click on "Select a project", and then the NEW PROJECT button.
- Give the project a name, and then click CREATE.
- Click SELECT PROJECT to get to the project page.
- From the side-menu, select "APIs & Services", then select "Library".
- Search for the "Google Drive API", select it, and then click on ENABLE.
- Click on the CREATE CREDENTIALS button.
- From the "Which API are you using?" dropdown menu, choose Google Drive API.
- For the "What data will you be accessing?" question, select Application Data.
- Click Next.
- Enter a "Service Account" name, then click Create.
- In the "Role" dropdown box, choose "Basic" > "Editor", then press Continue.
- "Grant users access to this service account" can be left blank. Click DONE.
- On the next page, click on the "Service Account" that has been created.
- On the next page, click on the "Keys" tab.
- Click on the "Add Key" dropdown, and select "Create New Key".
- Select
JSON, and then click Create. This will trigger the.jsonfile with your API credentials in it to download to your machine locally. - For local deployment, this needs to be renamed to
creds.json. - Repeat steps 4 & 5 above to add the "Google Sheets API".
- Copy the
client_emailthat is in thecreds.jsonfile. - Share your Google Sheet to the
client_email, ensuring "Editing" is enabled. - Add the
creds.jsonfile to your.gitignorefile, so as not to push your credentials to GitHub publicly.
This project can be cloned or forked in order to make a local copy on your own system.
For either method, you will need to install any applicable packages found within the requirements.txt file.
pip3 install -r requirements.txt.
If using any confidential credentials, such as CREDS.json or env.py data, these will need to be manually added to your own newly created project as well.
-
On GitHub, go to the repository for this project, GitHub repository.
-
Locate and click on the green "Code" button at the very top, above the commits and files.
-
Copy the URL for the repository.
- To clone the repository using HTTPS, under "HTTPS", click the copy button.
- To clone the repository using an SSH key, including a certificate issued by your organization's SSH certificate authority, click SSH, then click the copy button.
- To clone a repository using GitHub CLI, click GitHub CLI, then click the copy button.
-
Open Terminal.
-
Change the current working directory to the location where you want the cloned directory.
-
In your IDE Terminal, type the following command to clone the repository:
git clone https://www.github.com/Scaphix/my_inventory_manager.git
-
Press Enter. Your local clone will be created.
By forking the GitHub Repository, you make a copy of the original repository on our GitHub account to view and/or make changes without affecting the original owner's repository. You can fork this repository by using the following steps:
- Log in to GitHub and locate the GitHub Repository.
- At the top of the Repository, just below the "Settings" button on the menu, locate and click the "Fork" Button.
- Select the dropdown menu and click on owner for the forked repository.
- Click Create fork.
| Source | Notes |
|---|---|
| Markdown Builder | Help generating Markdown files |
| Love Sandwiches | Code Institute walkthrough project inspiration |
| Python Tutor | Additional Python help |
| Colorama | Adding color in Python |
| StackOverflow | Clear screen in Python |
| ChatGPT | Help with code logic and explanations |
I used the background image from the website below:
-
I would like to thank my Code Institute mentors, Tim Nelson and Iuliia Konovalova for their valuable guidance and constructive feedback for this project.
-
I would like to thank the CI community, and especially Kathrinmzl, for taking the time to review my project and offer thoughtful, detailed feedback.
-
I would like to thank my husband for his kindness, help and unwavering support throughout the development of this project.
















