Adding Price Functionality to the Cart
Build Dynamic Shopping Cart with Ruby on Rails
Core Concepts Covered
Subtotal Calculations
Learn to implement accurate product pricing with quantity-based subtotals for cart items.
Rails Delegates
Master delegation patterns to write cleaner, more maintainable code by sharing methods between models.
Order Summary Logic
Build functional order summaries with proper total calculations and extensible architecture.
Git Repository Setup Process
Navigate to Project Directory
Open Terminal and use cd command with drag-and-drop to navigate to your Rails class folder
Clone Repository
Run git clone command to copy the Nutty Guy repository from Bitbucket
Checkout Specific Version
Use git checkout 9C to bring the site up to the end of the previous exercise
Install Dependencies
Run bundle and yarn install commands to set up all necessary gems and JavaScript dependencies
In your code editor, open nutty > app > views > cart > index.html.erb
Look around line 41. This is the code that sets the Total Price column:
<td class="total-price"><%= number_to_currency line_item.product.price %></td>
Notice how this currently shows just the individual product price, not accounting for quantity. This is exactly the kind of bug that would frustrate customers and undermine trust in your application.
Edit that line as shown in bold:
<td class="total-price"><%= number_to_currency line_item.subtotal %></td>Save the file.
In your code editor, open nutty > app > models > line_item.rb
Add the following code shown in bold:
class LineItem < ApplicationRecord
belongs_to :cart
belongs_to :product
def subtotal
product.price * quantity
end
end
This method encapsulates the business logic for calculating subtotals, keeping our view clean and our calculations centralized. This approach follows the principle of putting business logic in models, not views.
Save the file.
Go to the browser where localhost:3000/cart should be open and reload the page. If you closed the browser or didn't do the last exercise:
- Go to localhost:3000 and click on any product.
- Set the Quantity to 9 and click Add to Cart.
The Total Price of the products in the cart now accurately reflects their quantities. This is the foundation of reliable e-commerce functionality.
To delegate is a way of having related models pass their methods down to each other
Benefits and Considerations of Rails Delegates
Setting up separate subtotal and total methods now creates a foundation for future enhancements. When you add shipping and taxes later, you'll only need to modify the total method without changing the entire codebase.
Cart Model Methods
Subtotal Method
Uses line_items.sum(&:subtotal) to calculate the sum of all line item subtotals in the cart.
Total Method
Currently returns subtotal but provides extensibility for adding shipping, taxes, and discounts later.
This implementation demonstrates traversing four models with a single line of code. The has_many through relationship allows direct access from products to carts without explicitly invoking line_items.
Controller Refactoring Process
Separate Concerns
Split load_cart_or_redirect_customer into two distinct methods for better code organization
Create Load Cart Method
Implement load_cart method that returns false if customer not signed in, true otherwise
Update Controllers
Add before_action :load_cart to products_controller for cart access across all product pages
Update View Logic
Modify application layout to display dynamic cart count using @cart.line_items.count
The current implementation counts line items. For displaying total quantity (e.g., 11 toothbrushes + 4 tentacles = 15), you would need to sum the quantity field across all line items instead of just counting them.
Key Takeaways
