Skip to content

Commit 8fdb704

Browse files
committed
Merge remote-tracking branch 'origin' into wangzt-dev
2 parents 875586c + 1eaf648 commit 8fdb704

17 files changed

+209
-40
lines changed

application/Dockerfile

Lines changed: 1 addition & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4,16 +4,10 @@ WORKDIR /app
44

55
RUN adduser --disabled-password --gecos '' appuser
66

7-
RUN apt-get update && apt-get install -y \
8-
build-essential \
9-
curl \
10-
software-properties-common \
11-
&& rm -rf /var/lib/apt/lists/*
12-
137
WORKDIR /app
148

159
COPY requirements.txt /app/
16-
RUN pip3 install -r requirements.txt
10+
RUN pip3 install -r requirements.txt -i https://pypi.tuna.tsinghua.edu.cn/simple
1711

1812
COPY . /app/
1913

application/Dockerfile-api

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ FROM public.ecr.aws/docker/library/python:3.10-slim
33
WORKDIR /app
44

55
COPY . /app/
6-
RUN pip3 install -r requirements-api.txt
6+
RUN pip3 install -r requirements-api.txt -i https://pypi.tuna.tsinghua.edu.cn/simple
77

88
EXPOSE 8000
99

application/api/schemas.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ class Question(BaseModel):
99
visualize_results_flag: bool = True
1010
intent_ner_recognition_flag: bool = True
1111
agent_cot_flag: bool = True
12-
profile_name: str = "shopping-demo"
12+
profile_name: str
1313
explain_gen_process_flag: bool = True
1414
gen_suggested_question_flag: bool = False
1515
answer_with_insights: bool = False

application/config_files/stauth_config.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ credentials:
55
failed_login_attempts: 0 # Will be managed automatically
66
logged_in: False # Will be managed automatically
77
name: AWS
8-
password: # Set the password following instructions in README
8+
password: $2b$12$NDQv5NLaWiVlNuzQYHwAo.tv.f.TuX1nbdoUZi44/Y3xv4I4QAfjy # Set the password following instructions in README
99
cookie:
1010
expiry_days: 30
1111
key: some_signature_key # Must be string

application/docker-compose.yml

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
version: '3'
22
services:
33
opensearch-node1:
4-
image: opensearchproject/opensearch:2.11.1
4+
image: public.ecr.aws/opensearchproject/opensearch:2.11.1
55
container_name: opensearch-node1
66
environment:
77
- cluster.name=opensearch-cluster
@@ -25,7 +25,7 @@ services:
2525
networks:
2626
- opensearch-net
2727
opensearch-node2:
28-
image: opensearchproject/opensearch:2.11.1
28+
image: public.ecr.aws/opensearchproject/opensearch:2.11.1
2929
container_name: opensearch-node2
3030
environment:
3131
- cluster.name=opensearch-cluster
@@ -46,7 +46,7 @@ services:
4646
networks:
4747
- opensearch-net
4848
opensearch-dashboards:
49-
image: opensearchproject/opensearch-dashboards:2.11.1
49+
image: public.ecr.aws/opensearchproject/opensearch-dashboards:2.11.1
5050
read_only: true
5151
container_name: opensearch-dashboards
5252
ports:
@@ -61,7 +61,7 @@ services:
6161
# 指定容器的名称
6262
container_name: nlq-mysql
6363
# 指定镜像和版本
64-
image: mysql:8.0
64+
image: public.ecr.aws/docker/library/mysql:8.0
6565
ports:
6666
- "3306:3306"
6767
restart: always

application/pages/1_🌍_Generative_BI_Playground.py

Lines changed: 28 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -127,7 +127,8 @@ def recurrent_display(messages, i):
127127
return i
128128

129129

130-
def normal_text_search_streamlit(search_box, model_type, database_profile, entity_slot, opensearch_info, selected_profile,
130+
def normal_text_search_streamlit(search_box, model_type, database_profile, entity_slot, opensearch_info,
131+
selected_profile,
131132
use_rag,
132133
model_provider=None):
133134
entity_slot_retrieve = []
@@ -241,6 +242,12 @@ def main():
241242
if 'current_profile' not in st.session_state:
242243
st.session_state['current_profile'] = ''
243244

245+
if 'current_model_id' not in st.session_state:
246+
st.session_state['current_model_id'] = ''
247+
248+
if 'config_data_with_analyse' not in st.session_state:
249+
st.session_state['config_data_with_analyse'] = False
250+
244251
if 'nlq_chain' not in st.session_state:
245252
st.session_state['nlq_chain'] = None
246253

@@ -250,7 +257,8 @@ def main():
250257
if "current_sql_result" not in st.session_state:
251258
st.session_state.current_sql_result = {}
252259

253-
model_ids = ['anthropic.claude-3-sonnet-20240229-v1:0', 'anthropic.claude-3-5-sonnet-20240620-v1:0', 'anthropic.claude-3-opus-20240229-v1:0',
260+
model_ids = ['anthropic.claude-3-sonnet-20240229-v1:0', 'anthropic.claude-3-5-sonnet-20240620-v1:0',
261+
'anthropic.claude-3-opus-20240229-v1:0',
254262
'anthropic.claude-3-haiku-20240307-v1:0', 'mistral.mixtral-8x7b-instruct-v0:1',
255263
'meta.llama3-70b-instruct-v1:0']
256264

@@ -263,8 +271,15 @@ def main():
263271
with st.sidebar:
264272
st.title('Setting')
265273
# The default option can be the first one in the profiles dictionary, if exists
266-
267-
selected_profile = st.selectbox("Data Profile", list(st.session_state.get('profiles', {}).keys()))
274+
session_state_list = list(st.session_state.get('profiles', {}).keys())
275+
if st.session_state.current_profile != "":
276+
if st.session_state.current_profile in session_state_list:
277+
profile_index = session_state_list.index(st.session_state.current_profile)
278+
selected_profile = st.selectbox("Data Profile", session_state_list, index=profile_index)
279+
else:
280+
selected_profile = st.selectbox("Data Profile", session_state_list)
281+
else:
282+
selected_profile = st.selectbox("Data Profile", session_state_list)
268283
if selected_profile != st.session_state.current_profile:
269284
# clear session state
270285
st.session_state.selected_sample = ''
@@ -273,7 +288,11 @@ def main():
273288
st.session_state.messages[selected_profile] = []
274289
st.session_state.nlq_chain = NLQChain(selected_profile)
275290

276-
model_type = st.selectbox("Choose your model", model_ids)
291+
if st.session_state.current_model_id != "" and st.session_state.current_model_id in model_ids:
292+
model_index = model_ids.index(st.session_state.current_model_id)
293+
model_type = st.selectbox("Choose your model", model_ids, index=model_index)
294+
else:
295+
model_type = st.selectbox("Choose your model", model_ids)
277296

278297
use_rag_flag = st.checkbox("Using RAG from Q/A Embedding", True)
279298
visualize_results_flag = st.checkbox("Visualize Results", True)
@@ -363,10 +382,13 @@ def main():
363382
database_profile['db_url'] = db_url
364383
database_profile['db_type'] = ConnectionManagement.get_db_type_by_name(conn_name)
365384
prompt_map = database_profile['prompt_map']
385+
prompt_map_flag = False
366386
for key in prompt_map_dict:
367387
if key not in prompt_map:
368388
prompt_map[key] = prompt_map_dict[key]
369-
ProfileManagement.update_table_prompt_map(selected_profile, prompt_map)
389+
prompt_map_flag = True
390+
if prompt_map_flag:
391+
ProfileManagement.update_table_prompt_map(selected_profile, prompt_map)
370392

371393
# Multiple rounds of dialogue, query rewriting
372394
user_query_history = get_user_history(selected_profile)

application/pages/3_🪙_Data_Profile_Management.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,9 @@ def main():
2222
if 'profile_page_mode' not in st.session_state:
2323
st.session_state['profile_page_mode'] = 'default'
2424

25+
if 'current_profile' not in st.session_state:
26+
st.session_state['current_profile'] = ''
27+
2528
with st.sidebar:
2629
st.title("Data Profile Management")
2730
st.selectbox("My Data Profiles", ProfileManagement.get_all_profiles(),

application/pages/4_🪙_Schema_Description_Management.py

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,17 @@ def main():
1212
st.set_page_config(page_title="Schema Management", )
1313
make_sidebar()
1414

15+
if 'current_profile' not in st.session_state:
16+
st.session_state['current_profile'] = ''
17+
1518
with st.sidebar:
1619
st.title("Schema Management")
17-
current_profile = st.selectbox("My Data Profiles", ProfileManagement.get_all_profiles(),
20+
all_profiles_list = ProfileManagement.get_all_profiles()
21+
if st.session_state.current_profile != "" and st.session_state.current_profile in all_profiles_list:
22+
profile_index = all_profiles_list.index(st.session_state.current_profile)
23+
current_profile = st.selectbox("My Data Profiles", all_profiles_list, index=profile_index)
24+
else:
25+
current_profile = st.selectbox("My Data Profiles", ProfileManagement.get_all_profiles(),
1826
index=None,
1927
placeholder="Please select data profile...", key='current_profile_name')
2028

application/pages/5_🪙_Prompt_Management.py

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,17 @@ def main():
1414
st.set_page_config(page_title="Prompt Management")
1515
make_sidebar()
1616

17+
if 'current_profile' not in st.session_state:
18+
st.session_state['current_profile'] = ''
19+
1720
with st.sidebar:
1821
st.title("Prompt Management")
19-
current_profile = st.selectbox("My Data Profiles", ProfileManagement.get_all_profiles(),
22+
all_profiles_list = ProfileManagement.get_all_profiles()
23+
if st.session_state.current_profile != "" and st.session_state.current_profile in all_profiles_list:
24+
profile_index = all_profiles_list.index(st.session_state.current_profile)
25+
current_profile = st.selectbox("My Data Profiles", all_profiles_list, index=profile_index)
26+
else:
27+
current_profile = st.selectbox("My Data Profiles", ProfileManagement.get_all_profiles(),
2028
index=None,
2129
placeholder="Please select data profile...", key='current_profile_name')
2230

@@ -29,6 +37,9 @@ def main():
2937
format_func=lambda x: prompt_map[x].get('title'),
3038
placeholder="Please select a prompt type")
3139

40+
profile_detail = ProfileManagement.get_profile_by_name(current_profile)
41+
prompt_map = profile_detail.prompt_map
42+
3243
if prompt_type_selected_table is not None:
3344
single_type_prompt_map = prompt_map.get(prompt_type_selected_table)
3445
system_prompt = single_type_prompt_map.get('system_prompt')

application/pages/6_📚_Index_Management.py

Lines changed: 53 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import time
22

3+
import pandas as pd
34
import streamlit as st
45
from dotenv import load_dotenv
56
import logging
@@ -14,6 +15,26 @@ def delete_sample(profile_name, id):
1415
VectorStore.delete_sample(profile_name, id)
1516
st.success(f'Sample {id} deleted.')
1617

18+
def read_file(uploaded_file):
19+
"""
20+
read upload csv file
21+
:param uploaded_file:
22+
:return:
23+
"""
24+
file_type = uploaded_file.name.split('.')[-1].lower()
25+
if file_type == 'csv':
26+
uploaded_data = pd.read_csv(uploaded_file)
27+
elif file_type in ['xls', 'xlsx']:
28+
uploaded_data = pd.read_excel(uploaded_file)
29+
else:
30+
st.error(f"Unsupported file type: {file_type}")
31+
return None
32+
columns = list(uploaded_data.columns)
33+
if "question" in columns and "sql" in columns:
34+
return uploaded_data
35+
else:
36+
st.error(f"The columns need contains question and sql")
37+
return None
1738

1839
def main():
1940
load_dotenv()
@@ -24,13 +45,22 @@ def main():
2445
if 'profile_page_mode' not in st.session_state:
2546
st.session_state['index_mgt_mode'] = 'default'
2647

48+
49+
if 'current_profile' not in st.session_state:
50+
st.session_state['current_profile'] = ''
51+
2752
with st.sidebar:
2853
st.title("Index Management")
29-
current_profile = st.selectbox("My Data Profiles", ProfileManagement.get_all_profiles(),
54+
all_profiles_list = ProfileManagement.get_all_profiles()
55+
if st.session_state.current_profile != "" and st.session_state.current_profile in all_profiles_list:
56+
profile_index = all_profiles_list.index(st.session_state.current_profile)
57+
current_profile = st.selectbox("My Data Profiles", all_profiles_list, index = profile_index)
58+
else:
59+
current_profile = st.selectbox("My Data Profiles", ProfileManagement.get_all_profiles(),
3060
index=None,
3161
placeholder="Please select data profile...", key='current_profile_name')
3262

33-
tab_view, tab_add, tab_search = st.tabs(['View Samples', 'Add New Sample', 'Sample Search'])
63+
tab_view, tab_add, tab_search, batch_insert = st.tabs(['View Samples', 'Add New Sample', 'Sample Search', 'Batch Insert Samples'])
3464

3565
if current_profile is not None:
3666
with tab_view:
@@ -69,6 +99,27 @@ def main():
6999
st.code(sample_res)
70100
st.button('Delete ' + sample['_id'], key=sample['_id'], on_click=delete_sample,
71101
args=[current_profile, sample['_id']])
102+
with batch_insert:
103+
if current_profile is not None:
104+
st.write("This page support CSV or Excel files batch insert sql samples.")
105+
st.write("**The Column Name need contain 'question' and 'sql'**")
106+
uploaded_files = st.file_uploader("Choose CSV or Excel files", accept_multiple_files=True,
107+
type=['csv', 'xls', 'xlsx'])
108+
if uploaded_files:
109+
progress_bar = st.progress(0)
110+
status_text = st.empty()
111+
for i, uploaded_file in enumerate(uploaded_files):
112+
status_text.text(f"Processing file {i + 1} of {len(uploaded_files)}: {uploaded_file.name}")
113+
each_upload_data = read_file(uploaded_file)
114+
if each_upload_data is not None:
115+
for index, item in each_upload_data.iterrows():
116+
question = str(item["question"])
117+
sql = str(item["sql"])
118+
VectorStore.add_sample(current_profile, question, sql)
119+
progress_bar.progress((i + 1) / len(uploaded_files))
120+
121+
st.success("{uploaded_file} uploaded successfully!".format(uploaded_file=uploaded_file.name))
122+
progress_bar.empty()
72123
else:
73124
st.info('Please select data profile in the left sidebar.')
74125

0 commit comments

Comments
 (0)