File size: 9,084 Bytes
1f21904
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
e2925c0
 
 
 
 
 
 
 
1f21904
 
 
e2925c0
 
 
 
 
 
 
1f21904
 
e2925c0
 
1f21904
 
 
 
 
 
e2925c0
 
 
 
 
 
1f21904
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
8149027
 
 
 
 
 
 
1f21904
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
847009d
1f21904
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
import os
import uuid
import streamlit as st
import matplotlib.pyplot as plt
import pandas as pd
import requests

st.set_page_config(page_title="Miragic Sales Pilot", page_icon="πŸ“Š")

sales_file = None
# st.write("Enter comma-separated numbers (e.g. `10, 20, 30`) to generate a bar chart.")

def upload_sales_data(data: pd.DataFrame):
    upload_url = os.environ['upload_url']
    file_name = 'sample.csv'
    files = {'file': (file_name, data.to_csv(index=False))}
    response = requests.post(upload_url, files=files)
    return response.json()

def analyze_sales_data(sales_file: str, prompt: str):
    analyze_url = os.environ['analyze_url']
    
    data = {'filename': sales_file, 'question': prompt}
    response = requests.post(analyze_url, json=data)
    return response.json()

# Sidebar Menu
with st.sidebar:
    st.markdown("""

        <style>

        [data-testid="stSidebar"][aria-expanded="true"]{

            min-width: 450px;

            max-width: 450px;

        }

        </style>

        """, unsafe_allow_html=True)
    # TODO Name for product
    # st.title("πŸ“Š Miragic Sales Pilot")
    # st.subheader("Intelligent sales assistant")
    # Display logo and title in a horizontal layout
    col1, col2 = st.columns([1, 4])
    with col1:
        st.image("logo.png", width=100)  # Adjust width as needed
    with col2:
        st.title("Miragic Sales Pilot")

    st.markdown("""

    ### πŸ“ Instructions

    1. **Upload your data**: Use the file uploader below to upload your sales excel or csv data

    2. **Chat with your data**: Ask me anything about your sales data

    

    ### πŸ” What this app does

    - Analyzes your sales data

    - Generates visualizations

    - Provides intelligent insights

    

    ### 🀝 Join our Community

    - Discord: [Join our Discord server](https://discord.com/invite/7wmy5H2dwh)

    - YouTube: [Subscribe to our channel](https://www.youtube.com/channel/UCltuweJjWc3A25ub8X6q5oA)

    

    ### 🏒 Company

    Sales Pilot is developed by [Miragic AI](https://miragic.ai), a company focused on bringing Generative AI Solutions.

    """)
    uploaded_file = st.file_uploader("", type=["csv", "excel"])
    if uploaded_file is not None:
      date_found = False
      sales_found = False
      df = pd.read_csv(uploaded_file, parse_dates=True)
      for column in df.columns:
        if 'Date' in column:  
          date_found = True
        if 'Sales' in column:
          sales_found = True
      if(date_found == False or sales_found == False):
        st.error('Please upload a csv containing both Date and Sales...')
        st.stop()

      response = upload_sales_data(df)
      sales_file = response['csv_file']

      st.success("File uploaded successfully!")
      st.write("Your uploaded data:")
      st.write(df)

    #   df = drop(df)
    #   df = date_format(df)
    #   merge_sort(df)
    #   series = group_to_three(df)

      st.session_state.uploaded = True

    with open(os.path.join(os.path.dirname(__file__), 'sample.csv'), 'rb') as f:
       st.download_button("Download our sample CSV", f, file_name='sample.csv')

    st.markdown("""![Visitors](https://api.visitorbadge.io/api/combined?path=https%3A%2F%2Fhuggingface.co%2Fspaces%2FMiragic-AI%2FMiragic-Sales-Pilot&labelColor=%2337d67a&countColor=%23ff8a65&style=plastic&labelStyle=upper)""")

with st.expander("About the Sales Pilot"):
    st.markdown("""

    The Sales Pilot is a sales assistant that can analyze and forecast sales using your historical excel or csv data.

    It can help you understand your sales data and make predictions about future sales.

    """)
    

col1, col2, col3 = st.columns([0.01, 0.98, 0.01])

col2.video("intro.mp4")

# Initialize chat history in session state
if "messages" not in st.session_state:
    st.session_state.messages = []
if "greetings" not in st.session_state:
    st.session_state.greetings = False

# Display chat history
for msg in st.session_state.messages:
    with st.chat_message(msg["role"]):
        if isinstance(msg["content"], str):
            st.markdown(msg["content"])
        else:
            st.pyplot(msg["content"])

# Greet user
if not st.session_state.greetings:
    with st.chat_message("assistant"):
        intro = "Hey! As a sales analyst, I can analyze and forecast sales using your historical excel or csv data. Please ❀️ this space if it's helpful."
        st.markdown(intro)
        # Add assistant response to chat history
        st.session_state.messages.append({"role": "assistant", "content": intro})
        st.session_state.greetings = True

# Example prompts
example_prompts = [
    "Top 10 best selling products",
    "Top 10 worst selling products",
    "Sales forecast for next month",
    "How many items were sold in total each month?",
    "What are the projected sales for next month?",
    "How many unique product categories are there?",
]

example_prompts_help = [
    "Search for the best selling products",
    "Search for the worst selling products",
    "Search for the projected sales for next month",
    "Search for the number of items sold in total each month",
    "Search for the sales forecast for next month",
    "Search for the number of unique product categories",
]

button_cols = st.columns(3)
button_cols_2 = st.columns(3)

button_pressed = ""

if button_cols[0].button(example_prompts[0], help=example_prompts_help[0]):
    button_pressed = example_prompts[0]
elif button_cols[1].button(example_prompts[1], help=example_prompts_help[1]):
    button_pressed = example_prompts[1]
elif button_cols[2].button(example_prompts[2], help=example_prompts_help[2]):
    button_pressed = example_prompts[2]

elif button_cols_2[0].button(example_prompts[3], help=example_prompts_help[3]):
    button_pressed = example_prompts[3]
elif button_cols_2[1].button(example_prompts[4], help=example_prompts_help[4]):
    button_pressed = example_prompts[4]
elif button_cols_2[2].button(example_prompts[5], help=example_prompts_help[5]):
    button_pressed = example_prompts[5]

# Chat input
if prompt := (st.chat_input("Ask me anything about your sales data") or button_pressed):
    # Add user message
    st.session_state.messages.append({"role": "user", "content": prompt})
    with st.chat_message("user"):
        st.markdown(prompt)

    if sales_file is None:
        st.error("Please upload a file first")
        st.stop()

    response = analyze_sales_data(sales_file, prompt)
    print("==========>: ", response)

    if response['status'] == 'success':
        dummy_response = response['result'][0]

        try:
            # Process input
            # values = list(map(int, prompt.strip().split(',')))
            # labels = [f"Item {i+1}" for i in range(len(values))]
            values = [item['y_axis'] for item in dummy_response['visualization']['data']]
            labels = [item['x_axis'] for item in dummy_response['visualization']['data']]

            # Create chart
            fig, ax = plt.subplots()
            if dummy_response['visualization']['type'] == 'line_chart':
                ax.plot(labels, values, marker='o', color="lightcoral")
            else:
                ax.bar(labels, values, color="lightcoral")
            plt.xticks(rotation=45, ha='right')
            ax.set_title(dummy_response['visualization']['config']['title'])
            ax.set_ylabel(dummy_response['visualization']['config']['y_axis'])
            ax.set_xlabel(dummy_response['visualization']['config']['x_axis'])
            
            # Add value labels on top of each bar
            for i, v in enumerate(values):
                ax.text(i, v, f'{v:,.2f}', ha='center', va='bottom')

            # Generate analysis message
            analysis = "πŸ“Š Insights:\n"
            for insight in dummy_response['insights']:
                analysis += f"- {insight}\n"

            # Add bot replies
            st.session_state.messages.append({"role": "assistant", "content": fig})
            st.session_state.messages.append({"role": "assistant", "content": analysis})
            with st.chat_message("assistant"):
                st.pyplot(fig)
                st.markdown(analysis)

        except Exception as e:
            err_msg = f"❌ Error: {str(e)} β€” please enter only comma-separated numbers."
            st.session_state.messages.append({"role": "assistant", "content": err_msg})
            with st.chat_message("assistant"):
                st.markdown(err_msg)
    else:
        err_msg = "❌ Error: Unable to process the request. Here are some example queries you can try:\n\n"
        for candidate in response['candidate_questions']:
            err_msg += f"- {candidate}\n"

        st.session_state.messages.append({"role": "assistant", "content": err_msg})
        with st.chat_message("assistant"):
            st.markdown(err_msg)

    st.rerun()