Spaces:
Sleeping
Sleeping
import pickle | |
import streamlit as st | |
from html_information2 import html2 | |
st.set_page_config(page_title="My App", page_icon=":money_with_wings:", layout="wide", initial_sidebar_state="auto") | |
st.header("Frequently Bought Together Recommendations") | |
def read_pickle_files(pickle_file): | |
with open(pickle_file, 'rb') as f: | |
return pickle.load(f) | |
# Load sephora pickle files | |
corrected_fp_growth_results_sephora = read_pickle_files("sephora_corrected_fp_growth_results_cleaned.pkl") | |
all_products_with_names_sephora = read_pickle_files ("item_catalog.pkl") | |
dictionary_of_transactions_sephora = read_pickle_files("transaction_metadata.pkl") | |
images_sephora = read_pickle_files("uid_url_map.pkl") | |
item_costs_sephora_data = read_pickle_files("wavg_item_costs_sephora.pkl") | |
# Load digital pickle files | |
corrected_fp_growth_results = read_pickle_files("corrected_fp_growth_results.pkl") | |
all_products_with_names = read_pickle_files ("all_products_with_names.pkl") | |
dictionary_of_transactions = read_pickle_files("reliance_digital_transactions.pkl") | |
item_costs_digital_data = read_pickle_files("avg_item_costs_reliance_digital_wa.pkl") | |
# Dropdown for selecting the dataset | |
dataset_choice = st.selectbox( | |
"Select A Dataset", | |
["Sephora Order Complete Dataset", "Reliance Digital Order Complete Dataset"] | |
) | |
if dataset_choice == "Sephora Order Complete Dataset": | |
list_of_products_to_display = {} | |
for itemid in (list(all_products_with_names_sephora.keys())): #for items in the total list of items in all transactions | |
if itemid in (list(corrected_fp_growth_results_sephora.keys())): #if the item has a result from fp-growth | |
list_of_products_to_display[itemid]= all_products_with_names_sephora[itemid] #show it in the drop down menu | |
name_to_id = {name: product_id for product_id, name in list_of_products_to_display.items()} # Reverse the dictionary to map product names to IDs | |
selected_product_name = st.selectbox('Select A Product:', list(name_to_id.keys())) # Create a dropdown menu with the product names | |
# Get the corresponding product_id | |
query_id = name_to_id[selected_product_name] | |
url = "https://www.sephora.com/" | |
st.write("Created using the clickstream order-completed and catalog data from [Sephora.com](%s)" % url) | |
st.write("Cost of chosen item:", str(round(item_costs_sephora_data[query_id], 2))) | |
query_url = images_sephora[int(query_id)] | |
st.image(query_url, width=500) | |
if dataset_choice == "Reliance Digital Order Complete Dataset": | |
list_of_products_to_display = {} | |
for itemid in (list(all_products_with_names.keys())): #for items in the total list of items in all transactions | |
if itemid[0:3]!="600": | |
if itemid in (list(corrected_fp_growth_results.keys())): #if the item has a result from fp-growth | |
list_of_products_to_display[itemid]= all_products_with_names[itemid] #show it in the drop down menu | |
name_to_id = {name: product_id for product_id, name in list_of_products_to_display.items()} # Reverse the dictionary to map product names to IDs | |
selected_product_name = st.selectbox('Select A Product:', list(name_to_id.keys())) # Create a dropdown menu with the product names | |
# Get the corresponding product_id | |
query_id = name_to_id[selected_product_name] | |
url = "https://www.reliancedigital.in/" | |
st.write("Created using the clickstream order-completed data from [reliancedigital.com](%s)" % url) | |
st.write("An item is only recommended if it costs less than the chosen item.") | |
st.write("Cost of chosen item:", str(round(item_costs_digital_data[query_id], 2))) | |
# Inject custom CSS for the tab headings | |
st.markdown( | |
""" | |
<style> | |
/* Style the tab container */ | |
div[data-testid="stTabs"] button { | |
background-color: #e0e0e0; /* Light grey background */ | |
color: #333333; /* Dark grey text color */ | |
font-size: 18px; /* Increase font size */ | |
font-weight: bold; /* Make text bold */ | |
padding: 10px 20px; /* Add some padding to the tabs */ | |
border-radius: 10px; /* Rounded corners */ | |
border: none; /* Remove default border */ | |
margin: 5px; /* Add margin between tabs */ | |
transition: background-color 0.3s ease; /* Add hover effect */ | |
} | |
/* Hover effect for tabs */ | |
div[data-testid="stTabs"] button:hover { | |
background-color: #b0b0b0; /* Darker grey on hover */ | |
color: #333333; /* Keep text color the same */ | |
} | |
/* Active tab styling */ | |
div[data-testid="stTabs"] button[aria-selected="true"] { | |
background-color: #808080; /* Dark grey for active tab */ | |
color: white; /* White text for active tab */ | |
font-size: 20px; /* Larger font size for active tab */ | |
} | |
</style> | |
""", | |
unsafe_allow_html=True | |
) | |
tab2, tab3 = st.tabs(["Frequently Bought Together Demo", "Historical Order Data"]) | |
with tab2: | |
if dataset_choice == "Sephora Order Complete Dataset": | |
if query_id in corrected_fp_growth_results_sephora: | |
# Separate the sorted items into IDs and counts | |
item_ids = [item for item in corrected_fp_growth_results_sephora[query_id]] | |
item_counts = [corrected_fp_growth_results_sephora[query_id][item] for item in corrected_fp_growth_results_sephora[query_id]] | |
item_costs_sephora = [item_costs_sephora_data.get(item, "cost missing") for item in corrected_fp_growth_results_sephora[query_id]] | |
item_image = [] | |
for item in corrected_fp_growth_results_sephora[query_id]: | |
try: | |
# Attempt to retrieve the image URL | |
image_url = images_sephora[int(item)] | |
if not image_url: # If the URL is empty or None, skip it | |
raise ValueError("Empty image URL") | |
item_image.append(image_url) | |
except (KeyError, ValueError, TypeError): | |
# Handle missing or invalid image URLs by appending a default image URL | |
item_image.append("default_image_url") | |
confidence_list = [] | |
transactions_list_sephora = [] | |
for i in dictionary_of_transactions_sephora: | |
transactions_list_sephora.append(i["transaction"]) | |
transactions_with_query_item = len([transaction for transaction in transactions_list_sephora if int(query_id) in transaction]) | |
copurchase_count = [] | |
# Generate a list of product names to display | |
product_names = [] | |
for each_item in corrected_fp_growth_results_sephora[query_id]: | |
product_names.append(all_products_with_names_sephora.get(each_item, "Unknown Product")) | |
for recommended_item in item_ids: | |
transactions_with_item_and_query_item = [] | |
transactions_with_item_and_query_item.extend([transaction for transaction in transactions_list_sephora if (int(recommended_item) in transaction) and (int(query_id) in transaction)]) | |
number_of_transactions_with_recommended_item_and_query_item = len(transactions_with_item_and_query_item) | |
copurchase_count.append(number_of_transactions_with_recommended_item_and_query_item) | |
confidence_list.append(number_of_transactions_with_recommended_item_and_query_item / transactions_with_query_item) | |
mid_section = "" | |
for index, value in enumerate(product_names): | |
count_info = f"Co-purchased {copurchase_count[index]}/{transactions_with_query_item} times" | |
item_counts_info = f"item-count {item_counts[index]} " | |
confidence_info = f"Confidence: {round(confidence_list[index], 3)}" | |
item_cost_info_sephora = f"Cost: {round(item_costs_sephora[index],2)}" | |
# Use <br> to display each line separately | |
mid_section += f"""<div class="item"> | |
<div id="image-container"><img src='{item_image[index]}' /></div> | |
<p style="font-size: 16px; font-weight: bold; white-space: normal; word-wrap: break-word;">{str(product_names[index])}</p> | |
<p>{count_info}<br>{confidence_info}<br>{item_cost_info_sephora}</p> | |
</div>""" | |
mid_html = html2 + mid_section + """</div></div></body>""" | |
st.markdown(mid_html, unsafe_allow_html=True) | |
else: | |
st.write("No frequent purchases found for this item.") | |
if dataset_choice == "Reliance Digital Order Complete Dataset": | |
if query_id in corrected_fp_growth_results: | |
# Separate the sorted items into IDs and counts | |
item_ids = [item for item in corrected_fp_growth_results[query_id]] | |
item_counts = [corrected_fp_growth_results[query_id][item] for item in corrected_fp_growth_results[query_id]] | |
item_costs = [item_costs_digital_data.get(item, "cost missing") for item in corrected_fp_growth_results[query_id]] | |
no_image = "https://upload.wikimedia.org/wikipedia/commons/6/65/No-Image-Placeholder.svg" | |
confidence_list = [] | |
transactions_list_digital = [] | |
for i in dictionary_of_transactions: | |
transactions_list_digital.append(i["transaction"]) | |
transactions_with_querry_item = len([transaction for transaction in transactions_list_digital if query_id in transaction]) | |
copurchase_count = [] | |
# Generate a list of product names to display | |
product_names = [] | |
for each_item in corrected_fp_growth_results[query_id]: | |
product_names.append(all_products_with_names[each_item]) | |
for reccomended_item in item_ids: | |
transactions_with_item_and_query_item = [] | |
transactions_with_item_and_query_item.extend([transaction for transaction in transactions_list_digital if (reccomended_item in transaction) and (query_id in transaction)]) | |
number_of_transactions_with_reccomended_item_and_query_item = len(transactions_with_item_and_query_item) | |
copurchase_count.append(number_of_transactions_with_reccomended_item_and_query_item) | |
confidence_list.append(number_of_transactions_with_reccomended_item_and_query_item/transactions_with_querry_item) | |
mid_section = "" | |
for index, value in enumerate(product_names): | |
count_info = f"Co-purchased {copurchase_count[index]}/{transactions_with_querry_item} times" | |
item_counts_info = f"item-count {item_counts[index]} " | |
confidence_info = f"Confidence: {round(confidence_list[index], 3)}" | |
item_cost_info = f"Cost: {round(item_costs[index],3)}" | |
# Use <br> to display each line separately | |
mid_section += f"""<div class="item"> | |
<div id="image-container"><img src='{no_image}' /></div> | |
<p style="font-size: 16px; font-weight: bold; white-space: normal; word-wrap: break-word;">{str(product_names[index])}</p> | |
<p>{count_info}<br>{confidence_info}<br>{item_cost_info}</p> | |
</div>""" | |
mid_html = html2 + mid_section + """</div></div></body>""" | |
st.markdown(mid_html, unsafe_allow_html=True) | |
else: | |
st.write("No frequent purchases found for this item.") | |
with tab3: # historical transactions tab | |
if dataset_choice == "Sephora Order Complete Dataset": | |
st.subheader("Historical Transactions With Chosen Product (shows maximum 20)") | |
example_transactions = [] | |
for transaction_dict in dictionary_of_transactions_sephora: | |
if int(query_id) in transaction_dict["transaction"]: | |
example_transactions.append(transaction_dict) | |
if example_transactions: | |
# Begin constructing the carousel for transactions | |
for i, transaction in enumerate(example_transactions): | |
st.markdown(f"**Transaction {i+1}:** Placed on {transaction['event_timestamp']} by {transaction['user_id']}", unsafe_allow_html=True) | |
transaction_names = [all_products_with_names_sephora.get(str(item), "Unknown Product") for item in transaction["transaction"]] | |
no_image = "https://upload.wikimedia.org/wikipedia/commons/6/65/No-Image-Placeholder.svg" | |
item_images = [] | |
for item in corrected_fp_growth_results_sephora.get(query_id, []): | |
try: | |
# Attempt to retrieve the image URL | |
image_url = images_sephora[int(item)] | |
if not image_url: # If the URL is empty or None, skip it | |
raise ValueError("Empty image URL") | |
item_images.append(image_url) | |
except (KeyError, ValueError, TypeError): | |
# Handle missing or invalid image URLs by appending a default image URL | |
item_images.append("default_image_url") | |
# Ensure item_images and transaction_names are of the same length | |
if len(item_images) > len(transaction_names): | |
item_images = item_images[:len(transaction_names)] | |
elif len(item_images) < len(transaction_names): | |
item_images.extend(["default_image_url"] * (len(transaction_names) - len(item_images))) | |
# Build the HTML for displaying the transaction in a carousel format | |
transaction_section = "" | |
for index, image_url in enumerate(item_images): | |
transaction_section += f"""<div class="item"> | |
<div id="image-container"><img src='{image_url}' /></div> | |
<p style="font-size: 16px; font-weight: bold; white-space: normal; word-wrap: break-word;">{transaction_names[index]}</p> | |
</div>""" | |
# Complete the carousel HTML structure | |
transaction_html = html2 + transaction_section + """</div></div></body>""" | |
# Render the carousel for each transaction | |
st.markdown(transaction_html, unsafe_allow_html=True) | |
else: | |
st.write("No transactions found for this item.") | |
if dataset_choice == "Reliance Digital Order Complete Dataset": | |
st.subheader("Historical Transactions With Chosen Product (shows maximum 20)") | |
example_transactions = [] | |
for transaction_dict in dictionary_of_transactions: | |
if query_id in transaction_dict["transaction"]: | |
example_transactions.append(transaction_dict) | |
if example_transactions: | |
# Begin constructing the carousel for transactions | |
for i, transaction in enumerate(example_transactions): | |
st.markdown(f"**Transaction {i+1}:** Placed on {transaction['order_date']} by {transaction['customer_id']} from {transaction['delivery_city']}", unsafe_allow_html=True) | |
transaction_names = [] | |
for i in transaction["transaction"]: | |
transaction_names = [all_products_with_names.get(str(item), "Unknown Product") for item in transaction["transaction"]] | |
# Build the HTML for displaying the transaction in a carousel format | |
transaction_section = "" | |
for index, image_url in enumerate(transaction_names): | |
transaction_section += f"""<div class="item"> | |
<div id="image-container"><img src='{no_image}' /></div> | |
<p style="font-size: 16px; font-weight: bold; white-space: normal; word-wrap: break-word;">{str(transaction_names[index])}</p> | |
</div>""" | |
# Complete the carousel HTML structure | |
transaction_html = html2 + transaction_section + """</div></div></body>""" | |
# Render the carousel for each transaction | |
st.markdown(transaction_html, unsafe_allow_html=True) | |
else: | |
st.write("No transactions found for this item.") | |
# Inject custom CSS for the 'Know More' button | |
st.markdown( | |
""" | |
<style> | |
.know-more-button { | |
background-color: #808080; /* Dark grey background */ | |
color: white !important; /* Force white text color */ | |
font-size: 18px; /* Font size */ | |
font-weight: bold; /* Bold text */ | |
padding: 10px 20px; /* Padding */ | |
border-radius: 10px; /* Rounded corners */ | |
border: none; /* Remove default border */ | |
cursor: pointer; /* Mouse pointer */ | |
text-align: center; | |
text-decoration: none; /* Remove underline */ | |
display: inline-block; /* Make it inline */ | |
transition: background-color 0.3s ease; | |
} | |
.know-more-button:hover { | |
background-color: #b0b0b0; /* Lighter grey background on hover */ | |
color: #333333 !important; /* Dark grey text on hover */ | |
text-decoration: none; /* Keep underline removed on hover */ | |
} | |
</style> | |
""", | |
unsafe_allow_html=True | |
) | |
# Add the 'Know More' button with the link and no underline | |
st.markdown( | |
'<a href="https://gofynd.quip.com/fOONA5yDkSr2/Frequently-Bought-Together-Recommendations" class="know-more-button">Know More</a>', | |
unsafe_allow_html=True | |
) | |