Welcome to the Udatracker Codelab! This guide will walk you through implementing the backend logic and API for your project using a strict Test-Driven Development (TDD) workflow.
Your goal is to use the provided test suites to drive your implementation. You'll follow the classic Red → Green → Refactor cycle: run a test to see it fail, write the code to make it pass, and then move on to the next feature.
First, ensure your environment is ready.
-
Navigate to the Backend: Open your terminal and
cd
into thebackend
directory.cd backend
-
Activate Your Virtual Environment: If you haven't already, activate the virtual environment.
# For macOS/Linux source venv/bin/activate # For Windows (PowerShell) # .\venv\Scripts\Activate.ps1
-
Ensure Dependencies are Installed: Make sure you have
Flask
andpytest
installed from yourrequirements.txt
file.pip install -r requirements.txt
We will build the OrderTracker
class one test at a time. Open both backend/order_tracker.py
and the empty backend/tests/test_order_tracker.py
files in your editor.
-
Write the First Test: Add the following code to
tests/test_order_tracker.py
. This test checks if we can add a simple order.# in backend/tests/test_order_tracker.py import pytest from unittest.mock import Mock from ..order_tracker import OrderTracker @pytest.fixture def mock_storage(): """Provides a mock storage object for tests.""" mock = Mock() mock.get_order.return_value = None return mock @pytest.fixture def order_tracker(mock_storage): """Provides an OrderTracker instance initialized with the mock storage.""" return OrderTracker(mock_storage) def test_add_order_successfully(order_tracker, mock_storage): """Tests adding a new order with default 'pending' status.""" order_tracker.add_order("ORD001", "Laptop", 1, "CUST001") # We expect save_order to be called once mock_storage.save_order.assert_called_once()
-
See it Fail (RED): Run the test. It will fail because the
add_order
method is empty.pytest tests/test_order_tracker.py
-
Write the Code (GREEN): In
order_tracker.py
, write the minimum code in theadd_order
method to make the test pass.# in backend/order_tracker.py def add_order(self, order_id: str, item_name: str, quantity: int, customer_id: str, status: str = "pending"): order = { "order_id": order_id, "item_name": item_name, "quantity": quantity, "customer_id": customer_id, "status": status } self.storage.save_order(order_id, order)
-
See it Pass: Run the test again. It should now pass.
-
Write the Test: Add a new test to
test_order_tracker.py
to check for duplicate IDs.# Add to tests/test_order_tracker.py def test_add_order_raises_error_if_exists(order_tracker, mock_storage): """Tests that adding an order with a duplicate ID raises a ValueError.""" # Simulate that the storage finds an existing order mock_storage.get_order.return_value = {"order_id": "ORD_EXISTING"} with pytest.raises(ValueError, match="Order with ID 'ORD_EXISTING' already exists."): order_tracker.add_order("ORD_EXISTING", "New Item", 1, "CUST001")
-
See it Fail (RED): Run
pytest
. The new test will fail. -
Update the Code (GREEN): Add the validation logic to the
add_order
method inorder_tracker.py
.# Update the add_order method in backend/order_tracker.py def add_order(self, order_id: str, item_name: str, quantity: int, customer_id: str, status: str = "pending"): # This is the new logic if self.storage.get_order(order_id): raise ValueError(f"Order with ID '{order_id}' already exists.") order = { "order_id": order_id, "item_name": item_name, "quantity": quantity, "customer_id": customer_id, "status": status } self.storage.save_order(order_id, order)
-
See it Pass: Run the tests again. Both tests should now pass.
(This TDD cycle of "Write Test -> See Fail -> Write Code -> See Pass" should be continued for all validation logic and all other methods like get_order_by_id
, update_order_status
, etc.)
Once all the unit tests for OrderTracker
are written and passing, you can build the API layer. For this part, you are provided with the complete API test suite (tests/test_api.py
).
-
See the API Tests Fail (RED): Run the integration tests. They will fail because the API endpoints in
app.py
are empty.pytest tests/test_api.py
-
Implement the API Endpoints (GREEN): Open
backend/app.py
. Fill in the logic for each route function to make the tests pass. -
Final Test Run: After implementing all endpoints, run the entire test suite.
pytest tests/
All tests should now pass.
Now for the final reward. Let's see your application in action!
-
Run the Flask Server:
python app.py
-
Open in Browser: Open your web browser and go to
http://127.0.0.1:5000/
.
🎉 Congratulations! You have completed the project with a true test-first approach.