demandregression / src /streamlit_app.py
nab3588's picture
Update src/streamlit_app.py
2886a27 verified
Raw History Blame Contribute Delete
7.36 kB
import streamlit as st
import pandas as pd
import numpy as np
from sklearn.linear_model import LinearRegression
from sklearn.preprocessing import PolynomialFeatures
import plotly.graph_objects as go
import math
import os
os.environ["HF_HOME"] = "./hf_home" # optional, for other HF cache
st.set_page_config(page_title="Prediksi Penjualan Warung", page_icon="πŸ›", layout="centered")
st.markdown(
"""
<style>
iframe[src*="fileUpload"] {
pointer-events: auto !important;
}
</style>
""",
unsafe_allow_html=True
)
st.title("Prediksi & Rekomendasi Penjualan - Profitly")
st.markdown("""
Unggah file **CSV** dengan format dari unduhan Dashboard
""")
# FILE UPLOAD
uploaded_file = st.file_uploader("πŸ“‚ Unggah File CSV Penjualan", type=None)
if uploaded_file is not None:
try:
df = pd.read_csv(uploaded_file)
if "Hari" not in df.columns or "Jumlah Terjual" not in df.columns:
st.error("❌ Format CSV tidak sesuai. Pastikan kolom 'Hari' dan 'Jumlah Terjual' ada.")
else:
# Convert "Day X" to number
df["Hari_Num"] = df["Hari"].str.extract(r"(\d+)").astype(int)
unique_days = df["Hari_Num"].nunique()
if unique_days <= 2:
st.warning("⚠️ Data harus memiliki lebih dari 2 hari agar prediksi bisa dilakukan.")
else:
# Regression type selection
regression_type = "Linear" if unique_days <= 4 else "Polynomial"
st.success(f"βœ… Data berhasil dimuat! Menggunakan **{regression_type} Regression**.")
st.subheader("πŸ“‹ Data Penjualan")
st.dataframe(df, use_container_width=True)
st.markdown("---")
st.header("πŸ“ˆ Prediksi Penjualan per Barang (2 Hari ke Depan)")
predictions = []
fig = go.Figure()
# Loop per item
for item in df["Barang"].unique():
item_df = df[df["Barang"] == item]
X = item_df[["Hari_Num"]]
y = item_df["Jumlah Terjual"]
# Choose regression model
if regression_type == "Linear":
# Linear
model = LinearRegression()
model.fit(X, y)
predict_func = lambda x: model.predict(x)
else:
# Polynomial regression
poly = PolynomialFeatures(degree=2)
X_poly = poly.fit_transform(X)
model = LinearRegression()
model.fit(X_poly, y)
predict_func = lambda x: model.predict(poly.transform(x))
# Generate predictions 2 days
future_days = np.array([max(df["Hari_Num"]) + 1, max(df["Hari_Num"]) + 2]).reshape(-1, 1)
predicted_sales = [max(0, math.floor(p)) for p in predict_func(future_days)]
# Assign consistent color
color = f"hsl({hash(item) % 360}, 70%, 50%)"
# Save for summary
for day, pred in zip(future_days.flatten(), predicted_sales):
predictions.append({
"Barang": item,
"Hari": f"Day {int(day)}",
"Prediksi Terjual": round(pred, 2)
})
# Plot actual line
fig.add_trace(go.Scatter(
x=item_df["Hari_Num"],
y=item_df["Jumlah Terjual"],
mode='lines+markers',
name=f"{item} (Aktual)",
line=dict(color=color, width=3)
))
# Plot predicted line
fig.add_trace(go.Scatter(
x=future_days.flatten(),
y=predicted_sales,
mode='lines+markers',
name=f"{item} (Prediksi)",
line=dict(color=color, dash='dot', width=2)
))
# Plot settings
fig.update_layout(
title=f"Prediksi Penjualan per Barang ({regression_type} Regression)",
xaxis_title="Hari",
yaxis_title="Jumlah Terjual",
template="plotly_white",
height=500
)
st.plotly_chart(fig, use_container_width=True)
# TABEL PREDIKSI CUI
pred_df = pd.DataFrame(predictions)[["Hari", "Barang", "Prediksi Terjual"]]
day_plus1 = pred_df[pred_df["Hari"].str.contains(f"Day {max(df['Hari_Num']) + 1}")]
day_plus2 = pred_df[pred_df["Hari"].str.contains(f"Day {max(df['Hari_Num']) + 2}")]
st.subheader(f"πŸ“… Prediksi Penjualan Hari Berikutnya (Day {max(df['Hari_Num']) + 1})")
st.dataframe(day_plus1, use_container_width=True)
st.subheader(f"πŸ“… Prediksi Penjualan 2 Hari Lagi (Day {max(df['Hari_Num']) + 2})")
st.dataframe(day_plus2, use_container_width=True)
st.markdown("---")
st.header("Analisis & Rekomendasi")
# Find top and bottom performers
avg_sales = df.groupby("Barang")["Jumlah Terjual"].mean().sort_values(ascending=False)
top_items = avg_sales.head(2).index.tolist()
low_items = avg_sales.tail(2).index.tolist()
st.write("**2 Barang dengan Penjualan Tertinggi:**")
st.success(", ".join(top_items))
st.write("**2 Barang dengan Penjualan Terendah:**")
st.warning(", ".join(low_items))
# Smart discount recommendations
st.subheader("Rekomendasi Diskon")
st.markdown("""
Rekomendasi dibuat berdasarkan tren penjualan:
- Barang dengan **penjualan tinggi** bisa diberi diskon kecil untuk menarik lebih banyak pelanggan.
- Barang dengan **penjualan rendah** bisa diberi diskon lebih besar agar stok cepat berputar.
""")
discount_suggestions = []
for item in top_items:
discount_suggestions.append({
"Barang": item,
"Tipe Rekomendasi": "Penjualan Tinggi",
"Saran Diskon": "Diskon ringan (5-10%) untuk menarik loyalitas pelanggan."
})
for item in low_items:
discount_suggestions.append({
"Barang": item,
"Tipe Rekomendasi": "Penjualan Rendah",
"Saran Diskon": "Diskon besar (15-25%) agar penjualan meningkat."
})
st.dataframe(pd.DataFrame(discount_suggestions), use_container_width=True)
st.markdown("✨ _Gunakan prediksi dan rekomendasi ini untuk menyesuaikan strategi penjualan Anda agar semakin menguntungkan!_")
except Exception as e:
st.error(f"Terjadi kesalahan saat memproses file: {e}")
else:
st.info("Silakan unggah file CSV untuk memulai analisis.")