request_Gemini / src /streamlit_app.py
123Sabrina's picture
Update src/streamlit_app.py
2d16509 verified
import pandas as pd
import requests
import os
import csv
from datetime import datetime
import streamlit as st
import threading
# 設定頁面配置
st.set_page_config(
page_title="資料分析與翻譯工具",
page_icon="📊",
layout="wide"
)
# 使用環境變數或直接設定 API 金鑰
# 在生產環境中,應該使用更安全的方法來存儲 API 金鑰
GOOGLE_API_KEY = os.environ.get("GOOGLE_API_KEY", "AIzaSyBxrwdxgs6JemK25piF_RFnxJ9SqKuqhEE")
# 設定 Gemini API 金鑰
@st.cache_resource
def setup_genai():
try:
import google.generativeai as genai
genai.configure(api_key=GOOGLE_API_KEY)
return genai.GenerativeModel("gemini-1.5-flash")
except ImportError:
st.error("無法載入 google.generativeai 模組。請確保您已安裝此套件: pip install google-generativeai")
return None
except Exception as e:
st.error(f"設定 Gemini API 時發生錯誤: {str(e)}")
return None
model = setup_genai()
# 下載並讀取 CSV 資料
@st.cache_data
def fetch_and_analyze_data(url=None):
# 顯示加載狀態
with st.spinner('正在下載與分析資料...'):
# 如果沒有提供 URL,使用預設台南市資料網址
if url is None or url == "":
url = "https://data.tainan.gov.tw/dataset/c4e00530-6367-4b7d-a4ac-085965915c78/resource/fc1990ec-f94f-4845-9cfd-214072d4fbf8/download/eeb5b8ad-a10a-4f6e-a064-f4d6ead73d9d.csv"
try:
# 下載 CSV 檔案
response = requests.get(url)
# 儲存原始 CSV 檔案
with open("original_data.csv", "wb") as file:
file.write(response.content)
# 讀取 CSV 檔案
df = pd.read_csv("original_data.csv", encoding="utf-8-sig")
# 將 DataFrame 轉換為字串
df_str = df.to_string()
# 使用 Gemini 分析資料
if model:
prompt = f"Please analyze the following dataset and provide main insights in both English and Chinese. Provide a comprehensive overview, key observations, and potential implications:\n{df_str}"
gemini_response = model.generate_content(prompt)
analysis_result = gemini_response.text.strip()
# 將分析結果寫入 CSV
with open("gemini_analysis_results.csv", "w", newline="", encoding="utf-8") as f:
writer = csv.writer(f)
writer.writerow(["原始資料摘要", "Gemini 分析"])
writer.writerow([df_str[:1000], analysis_result]) # 限制原始資料長度
else:
analysis_result = "無法使用 Gemini API,請檢查 API 金鑰設定"
return df, analysis_result
except Exception as e:
st.error(f"發生錯誤:{str(e)}")
return None, f"分析時發生錯誤:{str(e)}"
# 翻譯功能
def translate_text(text, source_lang='auto', target_lang='zh-TW'):
with st.spinner('正在翻譯...'):
try:
if not model:
return "無法使用翻譯功能:Gemini API 未正確設定"
prompt = f"Please translate the following text from {source_lang} to {target_lang}. Preserve the original meaning and tone:\n{text}"
translation_response = model.generate_content(prompt)
return translation_response.text.strip()
except Exception as e:
st.error(f"翻譯錯誤:{str(e)}")
return f"翻譯發生錯誤:{str(e)}"
# 應用程式主要功能
def main():
# 標題
st.title("資料分析與翻譯工具")
st.markdown("使用 Gemini AI 進行資料分析與翻譯")
# 側邊欄控制
with st.sidebar:
st.header("設定")
default_url = "https://data.tainan.gov.tw/dataset/c4e00530-6367-4b7d-a4ac-085965915c78/resource/fc1990ec-f94f-4845-9cfd-214072d4fbf8/download/eeb5b8ad-a10a-4f6e-a064-f4d6ead73d9d.csv"
url = st.text_input("資料來源 URL", value=default_url)
analyze_button = st.button("開始分析資料", use_container_width=True)
st.markdown("---")
st.markdown("#### 翻譯設定")
source_lang = st.selectbox("來源語言", ["auto", "en", "zh-TW", "ja", "ko", "fr", "de", "es"])
target_lang = st.selectbox("目標語言", ["zh-TW", "en", "ja", "ko", "fr", "de", "es"])
translate_button = st.button("翻譯分析結果", use_container_width=True)
# 創建標籤頁
tab1, tab2, tab3 = st.tabs(["資料預覽", "分析結果", "翻譯結果"])
# 存儲分析結果的 session state
if 'df' not in st.session_state:
st.session_state.df = None
if 'analysis_result' not in st.session_state:
st.session_state.analysis_result = ""
if 'translated_result' not in st.session_state:
st.session_state.translated_result = ""
# 處理分析按鈕
if analyze_button:
st.session_state.df, st.session_state.analysis_result = fetch_and_analyze_data(url)
if st.session_state.df is not None:
st.success("資料分析已完成,結果已儲存至 gemini_analysis_results.csv")
# 處理翻譯按鈕
if translate_button and st.session_state.analysis_result:
st.session_state.translated_result = translate_text(
st.session_state.analysis_result,
source_lang,
target_lang
)
st.success("翻譯已完成")
# 資料預覽標籤頁
with tab1:
if st.session_state.df is not None:
st.header("資料集預覽")
st.dataframe(st.session_state.df)
st.header("資料集資訊")
buffer = st.expander("查看詳細資訊")
with buffer:
df_info = st.session_state.df.describe().T
st.dataframe(df_info)
st.write("### 資料欄位")
for col in st.session_state.df.columns:
st.write(f"- {col}: {st.session_state.df[col].dtype}")
st.write(f"資料列數: {len(st.session_state.df)}")
# 分析結果標籤頁
with tab2:
if st.session_state.analysis_result:
st.header("Gemini 分析結果")
st.markdown(st.session_state.analysis_result)
# 下載按鈕
st.download_button(
label="下載分析結果",
data=st.session_state.analysis_result,
file_name="gemini_analysis_result.txt",
mime="text/plain"
)
# 翻譯結果標籤頁
with tab3:
if st.session_state.translated_result:
st.header("翻譯結果")
st.markdown(st.session_state.translated_result)
# 下載按鈕
st.download_button(
label="下載翻譯結果",
data=st.session_state.translated_result,
file_name="translated_result.txt",
mime="text/plain"
)
else:
st.info("請先執行分析,然後點擊翻譯按鈕")
if __name__ == "__main__":
main()