Currently my app has UI elements in the following order:
- Query
- Agent’s thoughts
- Chat history
- Current dataframe
The problem with such a structure is that if a user asks a lot of questions, the chat history becomes too long, and to see each new answer, the user needs to scroll down and then go back to query. Is there a way to reorder it as:
- Chat history
- Query
- Agent’s thoughts
- Current dataframe
I tried to do it on my own, but I am having a bug. When I provide my first query, no chat is shown. When I provide a second query, chat appears with the first query. If I provide a third chat, it appears with the first and second queries, and so on. I’m not sure how to fix it. My code:
if not user_api_key:
layout.show_api_key_missing()
else:
st.session_state.setdefault("reset_chat", False)
uploaded_file = utils.handle_upload(["csv", "xlsx"])
if uploaded_file:
sidebar.about_()
uploaded_file_content = BytesIO(uploaded_file.getvalue())
if uploaded_file.type == "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet" or uploaded_file.type == "application/vnd.ms-excel":
df = pd.read_excel(uploaded_file_content)
else:
df = pd.read_csv(uploaded_file_content)
st.session_state.df = df
if "chat_history" not in st.session_state:
st.session_state["chat_history"] = []
csv_agent = PandasAgent()
form_submitted = False
if st.session_state.df is not None:
if form_submitted:
result, captured_output = csv_agent.get_agent_response(df, query)
cleaned_thoughts = csv_agent.process_agent_thoughts(captured_output)
csv_agent.display_agent_thoughts(cleaned_thoughts)
csv_agent.update_chat_history(query, result)
csv_agent.display_chat_history()
csv_agent.display_chat_history()
with st.form(key="query"):
query = st.text_input("", value="", type="default",
placeholder="e-g : How many rows ? "
)
submitted_query = st.form_submit_button("Submit")
reset_chat_button = st.form_submit_button("Reset Chat")
if reset_chat_button:
st.session_state["chat_history"] = []
if submitted_query:
form_submitted = True
if form_submitted:
result, captured_output = csv_agent.get_agent_response(df, query)
cleaned_thoughts = csv_agent.process_agent_thoughts(captured_output)
csv_agent.display_agent_thoughts(cleaned_thoughts)
csv_agent.update_chat_history(query, result)
# csv_agent.display_chat_history()
if st.session_state.df is not None:
st.subheader("Current dataframe:")
st.write(st.session_state.df)
where PandasAgent
is:
class PandasAgent :
@staticmethod
def count_tokens_agent(agent, query):
"""
Count the tokens used by the CSV Agent
"""
from langchain.callbacks import get_openai_callback
with get_openai_callback() as cb:
result = agent(query)
st.write(f'Spent a total of {cb.total_tokens} tokens')
return result
def __init__(self):
pass
def get_agent_response(self, uploaded_file_content, query):
from pandasai import PandasAI
# from pandasai.llm.openai import OpenAI
from pandasai.llm.azure_openai import AzureOpenAI
llm = AzureOpenAI(
api_token = os.environ["OPENAI_API_KEY"],
api_base = os.environ["OPENAI_API_BASE"],
deployment_name = os.environ["OPENAI_API_MODEL_NAME"], # os.environ["OPENAI_API_DEPLOYMENT_NAME"],
model_name = os.environ["OPENAI_API_MODEL_NAME"]
)
pandas_ai = PandasAI(llm, verbose=True)
old_stdout = sys.stdout
sys.stdout = captured_output = StringIO()
response = pandas_ai.run(data_frame = uploaded_file_content, prompt=query)
fig = plt.gcf()
if fig.get_axes():
# Adjust the figure size
fig.set_size_inches(12, 6)
# Adjust the layout tightness
plt.tight_layout()
buf = BytesIO()
fig.savefig(buf, format="png")
buf.seek(0)
st.image(buf, caption="Generated Plot")
sys.stdout = old_stdout
return response, captured_output
def process_agent_thoughts(self,captured_output):
thoughts = captured_output.getvalue()
cleaned_thoughts = re.sub(r'\x1b\[[0-9;]*[a-zA-Z]', '', thoughts)
cleaned_thoughts = re.sub(r'\[1m>', '', cleaned_thoughts)
return cleaned_thoughts
def display_agent_thoughts(self,cleaned_thoughts):
with st.expander("Display the agent's thoughts"):
st.write(cleaned_thoughts)
def update_chat_history(self,query, result):
st.session_state.chat_history.append(("user", query))
st.session_state.chat_history.append(("agent", result))
def display_chat_history(self, ):
for i, (sender, message_text) in enumerate(st.session_state.chat_history):
if sender == "user":
message(message_text, is_user=True, key=f"{i}_user", avatar_style="thumbs")
else:
message(message_text, key=f"{i}")