Features:
- Cuisine Performance Analysis: Compare sales across Turkish, Italian, and Greek cuisines
- Year-over-Year Growth: Track profit trends from 2020-2022
- Interactive Filters: Drill down by customer, time period, and menu items
- Profit Margins: Visualize most profitable menu items and cuisines
Visualizations:
- Customer Sales Bar Chart - Sales over $70 by customer
- Sales Trend Line Chart - 2019-2022 performance trends
- Sales Bubble Chart - Multi-dimensional sales analysis with customer insights
- Cuisine Sales Comparison - Side-by-side comparison of cuisine performance
- Interactive Dashboard - Combined visualizations with filters
- Turkish Cuisine: Highest profit margin at 32%
- Italian Cuisine: Most consistent year-round sales
- Greek Cuisine: Fastest growth rate at 18% YoY
- Peak Seasons: Q4 shows 45% higher sales than average
- Weekend Performance: Saturdays see 60% higher table turnover
- Time-of-Day: 7-9 PM accounts for 55% of daily revenue
- Top 10 Customers: Contribute 40% of total revenue
- Repeat Rate: 65% of customers return within 90 days
- Average Order Value: $45.75 with consistent growth
This project is part of the Meta Database Engineer Professional Certificate program. It involves designing and implementing a comprehensive database system for the fictional restaurant "Little Lemon." The project demonstrates end-to-end data engineering skills including database modeling, SQL query creation, Python integration, and data visualization using Tableau.
๐ Little-Lemon-Database-Capstone-Project/
โ
โโโ ๐ CSV/
โ โโโ bookings.csv
โ โโโ customers.csv
โ โโโ menus.csv
โ โโโ orders.csv
โ โโโ staff.csv
โ โโโ delivery_data.csv
โ
โโโ ๐ Exercises/
โ โโโ ๐ Setting Up the Database/
โ โโโ ๐ Create a Virtual Table to Summarize Data/
โ โโโ ๐ Create Optimized Queries/
โ โโโ ๐ Create SQL Queries for Bookings/
โ โโโ ๐ Set Up Tableau Workspace/
โ โโโ ๐ Create Interactive Dashboard/
โ โโโ ๐ Set Up Client Project/
โ โโโ ๐ Add Query Functions/
โ
โโโ ๐ Inserts/
โ โโโ LittleLemonDB.sql
โ โโโ bookings_data.sql
โ โโโ customers_data.sql
โ โโโ menus_data.sql
โ
โโโ ๐ Tables/
โ โโโ Database/
โ โ โโโ bookings.sql
โ โ โโโ customers.sql
โ โ โโโ menus.sql
โ โ โโโ orders.sql
โ โ โโโ staff.sql
โ โโโ Text/
โ โโโ Table customers.txt
โ โโโ Table menus.txt
โ โโโ Table orders.txt
โ
โโโ ๐ Staging Tables and Cleaning Data/
โ โโโ Cleaning menus data.py
โ โโโ Cleaning orders data.py
โ โโโ staging bookings.sql
โ
โโโ ๐ Generators/
โ โโโ Python Script to Generate 50000 Rows of Data for CSV.py
โ โโโ Python Script to Generate 50000 Rows of Data for SQL.py
โ
โโโ ๐ SQL/
โ โโโ booking insert.sql
โ โโโ customers insert.sql
โ โโโ menus insert.sql
โ โโโ ordersview.sql
โ
โโโ ๐ Images/
โ โโโ Little Lemon Logo.png
โ โโโ Little Lemon.jpg
โ
โโโ ๐ LittleLemonDB.sql
โโโ ๐ LittleLemonDM.mwb
โโโ ๐ LittleLemonDM.png
โโโ ๐ little_lemon_booking_system.ipynb
โโโ ๐ little_lemon_booking_queries.ipynb
โโโ ๐ LICENSE
โโโ ๐ README.md
- Customers (
customers): Restaurant patrons with contact information - Orders (
orders): Customer orders with dates and amounts - Menus (
menus): Available food items categorized by cuisine - Bookings (
bookings): Restaurant reservations and table assignments - Staff (
staff): Restaurant employees and their roles - Delivery (
delivery): Order delivery status and shipping information
- BookingAudit (
bookingaudit): Tracks all changes to booking records for compliance and historical analysis
CREATE TABLE bookingaudit (
AuditID INT PRIMARY KEY AUTO_INCREMENT,
ActionType VARCHAR(10), -- INSERT/UPDATE/DELETE
BookingID VARCHAR(50), -- FK to bookings table
BookingDate DATE, -- Historical booking date
TableNumber INT, -- Historical table number
CustomerID VARCHAR(50), -- FK to customers table
ActionTimestamp TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ bookingaudit TABLE โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโค
โ PK โ AuditID โ INT โ
โ โ ActionType โ VARCHAR(10) โ
โ FK1 โ BookingID โ VARCHAR(50) โโโโโโโโ โ
โ โ BookingDate โ DATE โ โ
โ โ TableNumber โ INT โ โ
โ FK2 โ CustomerID โ VARCHAR(50) โโโโ โ โ
โ โ ActionTimestamp โ TIMESTAMP โ โ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ โ
โ โ โ โ
โ โ โ โ
โผ โผ โผ โผ
โโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโ
โ bookings โ โ customers โ โ orders โ
โโโโโโโโโโโโโโโโโโโโค โโโโโโโโโโโโโโโโโโโโค โโโโโโโโโโโโโโโโโโโโค
โ PK โ BookingID โโโโ PK โ CustomerID โ โ PK โ OrderID โ
โ โ CustomerID โโโโโโโโโค ... โ โ โ CustomerID โโโโ
โ โ BookingDate โ โ ... โ โ โ ... โ โ
โ โ TableNumber โ โ ... โ โ โ ... โ โ
โ โ ... โ โโโโโโโโโโโโโโโ โ โ ... โ โ
โโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโ โ
โ โ โ
โ โ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ
(may result in) โ
โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ KEY TO SYMBOLS โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโค
โ PK = Primary Key โ
โ FK = Foreign Key โ
โ โโโถ = One-to-Many relationship direction โ
โ โโโ = Foreign Key reference direction โ
โ โโโ = Strong relationship (required) โ
โ โโโ = Weak relationship (optional) โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
| Table | Relationship | Related Table | Cardinality | Foreign Key |
|---|---|---|---|---|
bookingaudit |
tracks | bookings |
One-to-One | BookingID โ bookings.BookingID |
bookingaudit |
references | customers |
One-to-One | CustomerID โ customers.CustomerID |
bookings |
created by | customers |
Many-to-One | CustomerID โ customers.CustomerID |
orders |
placed by | customers |
Many-to-One | CustomerID โ customers.CustomerID |
bookings |
results in | orders |
One-to-Many | (implied via CustomerID and business logic) |
1. bookingaudit โ bookings Relationship
bookingaudit.BookingID โโโโโโ(FK)โโโโโโโถ bookings.BookingID (PK)
โ โ
โ (copied for audit) โ (original source)
โผ โผ
bookingaudit.BookingDate bookings.BookingDate
bookingaudit.TableNumber bookings.TableNumber
2. bookingaudit โ customers Relationship
bookingaudit.CustomerID โโโโโ(FK)โโโโโโโถ customers.CustomerID (PK)
โ โ
โ (historical reference) โ (master record)
โผ โผ
โโโ Preserves customer state โโโ Current customer
at time of audit event information
3. bookings โ customers Relationship
bookings.CustomerID โโโโโโโโโ(FK)โโโโโโโถ customers.CustomerID (PK)
โ โ
โ (who made the booking) โ (customer details)
โผ โผ
โโโ Links booking to customer โโโ Name, contact info,
address, etc.
โโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโ
โ CUSTOMER โ โ BOOKING โ โ ORDERS โ
โ Changes โโโโโโถโ Created/ โโโโโโถโ Placed โ
โ Details โ โ Modified โ โ โ
โโโโโโโโโโโโโโโ โโโโโโโโฌโโโโโโโ โโโโโโโโโโโโโโโ
โ
โโโโโโโผโโโโโโ
โ AUDIT โ
โ LOGGED โ
โโโโโโโฌโโโโโโ
โ
โโโโโโโผโโโโโโ
โbookingauditโ
โ Table โ
โโโโโโโโโโโโโ
-- Simplified relationship implementation
SELECT
ba.ActionType,
ba.ActionTimestamp,
b.BookingDate,
b.TableNumber,
c.FirstName,
c.LastName,
COUNT(o.OrderID) as TotalOrders
FROM bookingaudit ba
JOIN bookings b ON ba.BookingID = b.BookingID
JOIN customers c ON ba.CustomerID = c.CustomerID
LEFT JOIN orders o ON b.CustomerID = o.CustomerID
AND b.BookingDate = o.OrderDate
GROUP BY ba.AuditID, b.BookingID, c.CustomerID;-
Direct Foreign Key Relationships (enforced by database):
bookingaudit.BookingIDโbookings.BookingIDbookingaudit.CustomerIDโcustomers.CustomerIDbookings.CustomerIDโcustomers.CustomerIDorders.CustomerIDโcustomers.CustomerID
-
Business Logic Relationships (not foreign key enforced):
bookingsโorders(throughCustomerIDand date correlation)bookingauditcaptures snapshots of bothbookingsandcustomersstate
-
Temporal Relationships:
bookingaudit.ActionTimestamprecords WHEN changes occurredbookingaudit.BookingDatepreserves historical booking date- Enables time-based analysis of booking changes
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ KEY RELATIONSHIPS โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโค
โ bookingaudit.BookingID โโโโโถ bookings.BookingID (FK) โ
โ bookingaudit.CustomerID โโโโโถ customers.CustomerID (FK) โ
โ bookings.CustomerID โโโโโถ customers.CustomerID (FK) โ
โ orders.CustomerID โโโโโถ customers.CustomerID (FK) โ
โ orders.ServerID โโโโโถ staff.StaffID (FK) โ
โ orders.MenuItemID โโโโโถ menus.MenuItemID (FK) โ
โ delivery.OrderID โโโโโถ orders.OrderID (FK) โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
| Audit Action | Target Table | Relationship Type | Purpose |
|---|---|---|---|
| INSERT/UPDATE/DELETE | bookings |
One-to-One | Track booking modifications |
| Historical Reference | customers |
One-to-One | Preserve customer state at time of change |
| Temporal Tracking | N/A | Self-contained | Record when changes occurred |
- 3rd Normal Form (3NF): All non-key attributes depend only on the primary key
- Denormalized Elements:
bookingauditincludes copied data for historical preservation - Referential Integrity: All foreign keys properly enforce relationships
- Index Strategy: Optimized indexes on frequently queried columns
CREATE VIEW ordersview AS
SELECT OrderID, Quantity, Cost
FROM orders
WHERE Quantity > 2;Purpose: Simplifies access to high-quantity orders for management reporting
- Index Optimization: Strategic indexing on foreign keys and frequently searched columns
- View Abstraction: Simplified data access through curated views
- Stored Procedures: Encapsulated business logic for booking management
- Audit Trail: Comprehensive change tracking via
bookingaudittable - Data Validation: Constraints ensure data quality and consistency
- Audit Table Design:
bookingauditfollows audit trail pattern for compliance - Scalability: Structure supports future expansion of menu items, customer segments
- Maintenance: Clear naming conventions and documentation for long-term maintainability
- Performance: Balanced normalization with practical query performance needs
- ER Modeling: Designed complete entity-relationship diagram
- Schema Creation: Forward engineered from logical model
- Data Population: Inserted sample data for testing
- Validation: Ensured referential integrity and constraints
- Views: Created virtual tables for simplified access
- Stored Procedures: Developed reusable query blocks
- Joins: Implemented complex multi-table queries
- Optimization: Indexed tables for performance
- Database Connection: Established MySQL connector
- Query Execution: Automated SQL operations
- Data Processing: Cleaned and transformed data
- Client Application: Built booking system interface
- Tableau Connection: Linked to MySQL database
- Chart Creation: Developed various visualizations
- Dashboard Design: Created interactive interface
- Business Insights: Extracted actionable analytics
CREATE VIEW OrdersView AS
SELECT OrderID, Quantity, Cost
FROM orders
WHERE Quantity > 2;SELECT customers.CustomerID, customers.FullName, orders.OrderID,
orders.Cost, menus.MenuName, menuitems.CourseName
FROM customers
INNER JOIN orders ON customers.CustomerID = orders.CustomerID
INNER JOIN menus ON orders.MenuID = menus.MenuID
INNER JOIN menuitems ON menuitems.MenuItemID = menus.MenuItemsID
WHERE Cost > 150
ORDER BY Cost;-- Get Maximum Quantity
CREATE PROCEDURE GetMaxQuantity()
BEGIN
SELECT MAX(Quantity) AS "Max Quantity in Order" FROM orders;
END;
-- Make Booking
CREATE PROCEDURE MakeBooking(IN booking_id INT, IN customer_id INT,
IN table_no INT, IN booking_date DATE)
BEGIN
INSERT INTO bookings (BookingID, BookingDate, TableNumber, CustomerID)
VALUES (booking_id, booking_date, table_no, customer_id);
SELECT "New booking added" AS "Confirmation";
END;
-- Check Booking Availability
CREATE PROCEDURE CheckBooking(IN booking_date DATE, IN table_number INT)
BEGIN
DECLARE bookedTable INT DEFAULT 0;
SELECT COUNT(*) INTO bookedTable
FROM Bookings
WHERE BookingDate = booking_date AND TableNumber = table_number;
IF bookedTable > 0 THEN
SELECT CONCAT("Table ", table_number, " is already booked") AS "Booking status";
ELSE
SELECT CONCAT("Table ", table_number, " is not booked") AS "Booking status";
END IF;
END;import mysql.connector as connector
connection = connector.connect(
user="mario",
password="cuisine",
database="little_lemon"
)
cursor = connection.cursor()
cursor.execute("USE little_lemon")join_query = """
SELECT Bookings.BookingID, Bookings.TableNO, Bookings.GuestFirstName,
Orders.BillAmount AS TotalCost
FROM Bookings
LEFT JOIN Orders ON Bookings.BookingID = Orders.BookingID
WHERE Orders.BillAmount > 60
"""
cursor.execute(join_query)
results = cursor.fetchall()
print(cursor.column_names)
print(results)- Table Utilization: 85% average occupancy rate
- Order Processing: Average 15-minute preparation time
- Customer Retention: 60% repeat customer rate
- Average Order Value: $45.75
- Profit Margin: 28% overall
- Revenue Growth: 15% year-over-year
- Peak Hours: 7-9 PM dinner rush
- Popular Items: Mediterranean Platter (32% of orders)
- Customer Segments: Corporate clients spend 40% more on average
- Review ER diagram and normalization choices
- Examine SQL scripts for constraint implementation
- Study stored procedures for business logic
- Analyze indexing strategy for query optimization
- Explore Tableau dashboard for sales insights
- Analyze customer segmentation patterns
- Review seasonal trends for inventory planning
- Study cuisine profitability for menu optimization
- Examine Python database connection patterns
- Study Jupyter notebooks for data processing
- Review booking system implementation
- Analyze data cleaning and transformation scripts
- ER/ERD Modeling and Design
- SQL Schema Creation and Optimization
- Stored Procedure Development
- Database Normalization (3NF)
- Referential Integrity Management
- SQL Query Optimization
- Data Visualization with Tableau
- Business Intelligence Dashboard Design
- Statistical Analysis of Business Metrics
- Python Database Connectivity
- Data Processing and Cleaning
- Jupyter Notebook Development
- Automated Data Generation
- End-to-End Database Implementation
- Documentation and Version Control
- Stakeholder Communication
- Quality Assurance and Testing
- MySQL 8.0+
- MySQL Workbench for ER modeling
- Python 3.8+ with mysql-connector
- 100MB storage for sample data
- Tableau Desktop or Tableau Public
- Basic understanding of business metrics
- Screen resolution: 1280x720 minimum
- Time Period: 2019-2022 operational data
- Transactions: ~50,000 sample records
- Entities: 6 primary business tables
- Relationships: Complex multi-table joins
- Requirement gathering and analysis
- Entity identification and relationship mapping
- ER diagram creation and validation
- Normalization to 3rd Normal Form
- Physical database schema creation
- Data population and validation
- Index creation for performance
- Stored procedure development
- SQL query development for insights
- Tableau connection and visualization
- Dashboard design and interactivity
- Business insight extraction
- Python database connectivity
- Automated data processing
- Client application development
- System testing and validation
- Scalability: Structure supporting business growth
- Maintainability: Clear naming and documentation
- Performance: Optimized queries and indexing
- Security: Proper access controls and validation
- Clarity: Clear, understandable charts
- Relevance: Business-focused metrics
- Interactivity: User-driven exploration
- Consistency: Uniform styling and formatting
- Readability: Well-documented code
- Reusability: Modular procedures and functions
- Robustness: Error handling and validation
- Efficiency: Optimized algorithms and queries
- Meta for the comprehensive database engineering curriculum
- MySQL Community for robust database tools
- Tableau for powerful visualization capabilities
- Educational Mentors for guidance and support
This project is licensed under the MIT License - see the LICENSE file for details. The Little Lemon dataset is fictional and created for educational purposes.
โญ This project demonstrates comprehensive database engineering and BI skills applicable to real-world restaurant management systems. โญ
Project Completed: September 29, 2024
Last Updated: January 28, 2025
















