Skip to content

Stop Guessing, Start Visualizing: Turn Retail Data into Decision-Making Tools with Interactive Python Dashboards (Tutorial + Code)

You won’t get noticed unless you are solving real-world business problems.

  • find a problem
  • create a solution
  • share your work
  • land your dream job

Pretty simple.

The hard part is knowing where to start.

It can be super easy though.

Right now, millions of businesses are getting flooded with retail transaction data. Why? Because it’s “Black Friday” and “Cyber Monday” — the busiest shopping period of the entire year. And this can be your golden opportunity.

If you have the expertise.

Follow these exact steps to get noticed

This tutorial walks you through creating an interactive dashboard with Python and Dash.

It’s the perfect solution to the problem that so many business owners are facing today. And you can be the person that solves that painful problem for them. Which all but guarantees your promotion.

Here’s what we’re building today (click here if you can’t see the gif below)

Alright, let’s create this thing.

Step 1: Set Up Your Environment and Load Your Data

First, set up your environment, load your data, and take a peek at what’s inside. This step is crucial to understand the structure of your dataset.

Paste this code into a new Google Collab notebook cell and run it.

You can use my notebook to help you get started.

!pip install dash
!pip install dash-bootstrap-components

from dash import Dash, html, dcc, Input, Output
import dash_bootstrap_components as dbc
import pandas as pd
import plotly.express as px

# Better image quality
%config InlineBackend.figure_formats = 'retina'

# Load the CSV file
data = pd.read_csv('https://query.data.world/s/iulzaqbyt4hklmha6clwp4yl3fhczl?dws=00000')

# Display the first few rows of the dataframe
print(data.head())

Step 2: Clean and Prepare Your Data

Data cleaning is vital. Next, ensure your data is in the right format, handling any missing or incorrect values.

  • Update the ‘order_amt’ column to remove the $ symbol and set it to numeric so that we can sum the values later on in the analysis
  • Fill any empty records with data instead of just blank values
  • Convert the ‘transaction_date’ column to a datetime so we can process it and sort
# Convert 'order_amt' to numerical values and handle missing values
data['order_amt'] = data['order_amt'].replace('[\$,]', '', regex=True).astype(float)
data.fillna({'rewards_member': False, 'coupon_flag': 'No', 'discount_amt': 0}, inplace=True)

# Convert 'transaction_date' to datetime and sort
data['transaction_date'] = pd.to_datetime(data['transaction_date'])
data.sort_values(by='transaction_date', inplace=True)

Step 3: Quickly Visualize Your Data

Next, let’s take a look at the data we have visually. This helps to see what might be interesting or if there are any problems with the data set before moving on to build the dashboard.

Here are some ideas:

  1. Sales over time
  2. Sales by location
  3. Customer demographics
  4. Discounts over time

And here’s the code:

# Summarize data by month
data['month'] = data['transaction_date'].dt.to_period('M').dt.to_timestamp()
monthly_data = data.groupby('month').sum().reset_index()

# Sales Over Time Line Chart (Monthly Summary)
fig1 = px.line(monthly_data, x='month', y='order_amt', title='Monthly Sales Over Time')

# Sales by Location Bar Chart
fig2 = px.bar(data, x='location_city', y='order_amt', title='Sales by Location')

# Customer Demographics Pie Chart
fig3 = px.pie(data, names='rewards_member', title='Customer Demographics')

# Average Discount Amount Over Time (Monthly Summary)
fig4 = px.line(monthly_data, x='month', y='discount_amt', title='Average Discount Amount Over Time')

# Display the figures
fig1.show()
fig2.show()
fig3.show()
fig4.show()

Step 4: Build the Interactive Dashboard with Dash

Now that we’re comfortable with the data, let’s combine the visualizations into a comprehensive and interactive dashboard using Dash.

There’s a lot of code here, but let’s break it down.

  1. Set up the Dash ‘app’ (this is the actual dashboard)
  2. Set up the structure of the dashboard
  3. Create some ‘callbacks’ to add the interactivity
  4. Fill in the dashboard with the charts

I’ve added comments to make it easier to follow.

# Initialize the Dash app
app = Dash(__name__)

# Unique list of states for the dropdown
states = data['location_state'].unique()

# Define the layout
app.layout = html.Div([
    # Dropdown for selecting a state
    html.H1("Retail Analytics Dashboard", 
            style={'text-align': 'center', 'margin-top': '20px', 'font-family': 'Arial'}),
    html.Div([
        dcc.Dropdown(
            id='state-dropdown',
            options=[{'label': state, 'value': state} for state in states],
            value=states[0]  # Default value
        )
    ], style={'padding': '20px', 'font-family': 'Arial'}),

    # Row for the first two graphs
    html.Div([
        html.Div([dcc.Graph(id='sales-over-time')], 
                 style={'width': '50%', 'display': 'inline-block'}),
        html.Div([dcc.Graph(id='sales-by-location')], 
                 style={'width': '50%', 'display': 'inline-block'}),
    ], style={'width': '100%', 'display': 'flex'}),

    # Row for the next two graphs
    html.Div([
        html.Div([dcc.Graph(id='customer-demographics')], 
                 style={'width': '50%', 'display': 'inline-block'}),
        html.Div([dcc.Graph(id='average-discount-over-time')], 
                 style={'width': '50%', 'display': 'inline-block'}),
    ], style={'width': '100%', 'display': 'flex'})
])

# Callbacks for updating the graphs based on selected state
@app.callback(
    Output('sales-over-time', 'figure'),
    Input('state-dropdown', 'value')
)
def update_sales_over_time(selected_state):
    filtered_data = data[data['location_state'] == selected_state]
    filtered_data['month'] = filtered_data['transaction_date'].dt.to_period('M').dt.to_timestamp()
    monthly_filtered_data = filtered_data.groupby('month').sum().reset_index()
    fig = px.line(monthly_filtered_data, x='month', y='order_amt', 
                  title=f'Monthly Sales Over Time in {selected_state}',
                  labels={'month': 'Month', 'order_amt': 'Total Sales ($)'})
    return fig

@app.callback(
    Output('sales-by-location', 'figure'),
    Input('state-dropdown', 'value')
)
def update_sales_by_location(selected_state):
    filtered_data = data[data['location_state'] == selected_state]
    filtered_data.sort_values(by='order_amt', inplace=True)
    fig = px.bar(filtered_data, x='location_city', y='order_amt', 
                 title=f'Total Sales by Location in {selected_state}',
                 labels={'location_city': 'City', 'order_amt': 'Total Sales ($)'})
    return fig

@app.callback(
    Output('customer-demographics', 'figure'),
    Input('state-dropdown', 'value')
)
def update_customer_demographics(selected_state):
    filtered_data = data[data['location_state'] == selected_state]
    fig = px.pie(filtered_data, names='rewards_member', 
                 title=f'Customer Demographics in {selected_state}',
                 labels={'rewards_member': 'Rewards Member'})
    return fig

@app.callback(
    Output('average-discount-over-time', 'figure'),
    Input('state-dropdown', 'value')
)
def update_average_discount_over_time(selected_state):
    filtered_data = data[data['location_state'] == selected_state]
    filtered_data['month'] = filtered_data['transaction_date'].dt.to_period('M').dt.to_timestamp()
    monthly_filtered_data = filtered_data.groupby('month').mean().reset_index()
    fig = px.line(monthly_filtered_data, x='month', y='discount_amt', 
                  title=f'Average Discount Amount Over Time in {selected_state}',
                  labels={'month': 'Month', 'discount_amt': 'Average Discount Amount ($)'})
    return fig

Step 5: Start up the Dashboard

Finally, let’s run the Dash app to see our interactive dashboard and share it with the world!

# Run the app
if __name__ == '__main__':
    app.run_server(debug=True)

Here’s what you’ll see in Google Colab: (click here if you can’t see the gif below)

Looks great!

Try it on your own:

If you made it this far, congratulations! Share a copy with me via email or on x/Twitter.

  • Try different chart types
  • Use the same chart types but use different columns
  • Try it with a data set from your work or another project

Did this tutorial help? Hit reply and let me know or fill out this quick survey.

Leave a Reply

Your email address will not be published. Required fields are marked *