Spaces:
Sleeping
Sleeping
| import streamlit as st | |
| import requests | |
| # ------------------------------- | |
| # 1. λ¬Έμ νμ± ν¨μ (HTML μΆμΆ) | |
| # ------------------------------- | |
| def parse_document_to_html(file, api_key): | |
| url = "https://api.upstage.ai/v1/document-ai/document-parse" | |
| headers = {'Authorization': f'Bearer {api_key}'} | |
| files = {"document": file} | |
| data = { | |
| "base64_encoding": "['table']", | |
| "model": "document-parse" | |
| } | |
| response = requests.post(url, headers=headers, files=files, data=data) | |
| if response.status_code != 200: | |
| return None, f"λ¬Έμ νμ± μ€ν¨ (status code: {response.status_code})" | |
| html_text = response.json().get("content", {}).get("html", "") | |
| return html_text, None | |
| # ------------------------------- | |
| # 2. Solar-Pro: μ§λ¬Έ μλ΅ | |
| # ------------------------------- | |
| def chat_with_solar_document(html_text, user_question, history, api_key): | |
| url = "https://api.upstage.ai/v1/chat/completions" | |
| headers = { | |
| "Authorization": f"Bearer {api_key}", | |
| "Content-Type": "application/json" | |
| } | |
| system_prompt = f""" | |
| λ€μμ HTML νμμΌλ‘ μΆμΆλ λ¬Έμμ λλ€. | |
| HTML μμ λ΄μ©λ§ κ·Όκ±°λ‘ μΌμ νμμ μ§λ¬Έμ μ ννκ³ μ½κ² λ΅ν΄μ£ΌμΈμ. | |
| λ¬Έμ: | |
| {html_text} | |
| """ | |
| messages = [{"role": "system", "content": system_prompt}] | |
| for user, bot in history: | |
| messages.append({"role": "user", "content": user}) | |
| messages.append({"role": "assistant", "content": bot}) | |
| messages.append({"role": "user", "content": user_question}) | |
| payload = { | |
| "model": "solar-pro", | |
| "messages": messages, | |
| "temperature": 0, | |
| "max_tokens": 2048 | |
| } | |
| try: | |
| response = requests.post(url, headers=headers, json=payload) | |
| if response.status_code != 200: | |
| return None, history, f"μν μ½λ: {response.status_code}" | |
| bot_reply = response.json()["choices"][0]["message"]["content"] | |
| history.append((user_question, bot_reply)) | |
| return bot_reply, history, None | |
| except Exception as e: | |
| return None, history, f"μμΈ λ°μ: {str(e)}" | |
| # ------------------------------- | |
| # 3. μΆμ² ν€μλ μμ± | |
| # ------------------------------- | |
| def get_recommended_keywords(html_text, user_question, api_key): | |
| url = "https://api.upstage.ai/v1/chat/completions" | |
| headers = { | |
| "Authorization": f"Bearer {api_key}", | |
| "Content-Type": "application/json" | |
| } | |
| prompt = f""" | |
| λ€μμ HTMLλ‘ μΆμΆλ λ¬Έμ λ΄μ©μ λλ€. | |
| λ¬Έμ μ μ§λ¬Έμ λ°νμΌλ‘ νμμκ² λμμ΄ λ λ§ν κ³΅λΆ ν€μλ 3κ°μ§λ₯Ό μ μν΄μ£ΌμΈμ. ν€μλλ§ μ½€λ§λ‘ ꡬλΆν΄μ μΆλ ₯ν΄μ£ΌμΈμ. | |
| λ¬Έμ: {html_text} | |
| νμ μ§λ¬Έ: {user_question} | |
| """ | |
| payload = { | |
| "model": "solar-pro", | |
| "messages": [{"role": "user", "content": prompt}], | |
| "temperature": 0.5, | |
| "max_tokens": 100 | |
| } | |
| try: | |
| res = requests.post(url, headers=headers, json=payload) | |
| if res.status_code != 200: | |
| return [] | |
| raw_text = res.json()["choices"][0]["message"]["content"] | |
| keywords = [kw.strip() for kw in raw_text.split(",") if kw.strip()] | |
| return keywords[:3] | |
| except: | |
| return [] | |
| # ------------------------------- | |
| # 4. ν€μλλ³ κ³΅λΆ ν μμ± | |
| # ------------------------------- | |
| def get_study_tip_for_keyword(keyword, api_key): | |
| url = "https://api.upstage.ai/v1/chat/completions" | |
| headers = { | |
| "Authorization": f"Bearer {api_key}", | |
| "Content-Type": "application/json" | |
| } | |
| prompt = f""" | |
| νμμ΄ '{keyword}'μ(λ₯Ό) 곡λΆνκ³ μΆμ΄ν©λλ€. | |
| κ°λ μ΄ν΄, κ³΅λΆ λ°©λ², μΆμ² μμ λ±μ ν¬ν¨ν΄ μΉμ νκ² νμ΅ νμ μ 곡ν΄μ£ΌμΈμ. | |
| """ | |
| payload = { | |
| "model": "solar-pro", | |
| "messages": [{"role": "user", "content": prompt}], | |
| "temperature": 0.7, | |
| "max_tokens": 300 | |
| } | |
| try: | |
| res = requests.post(url, headers=headers, json=payload) | |
| return res.json()["choices"][0]["message"]["content"] | |
| except: | |
| return "β οΈ νμ΅ μΆμ² μμ±μ μ€ν¨νμ΄μ." | |
| # ------------------------------- | |
| # 5. Streamlit UI | |
| # ------------------------------- | |
| def main(): | |
| st.set_page_config(page_title="Solar κ³΅λΆ λ©ν ", layout="wide") | |
| st.title("π©βπ« Solar κ³΅λΆ λ©ν ") | |
| api_key = st.text_input("π Upstage API Key", type="password") | |
| uploaded_file = st.file_uploader("π λ¬Έμ μ΄λ―Έμ§ μ λ‘λ", type=["pdf", "png", "jpg", "jpeg"]) | |
| if "html_text" not in st.session_state: | |
| st.session_state.html_text = "" | |
| if "chat_history" not in st.session_state: | |
| st.session_state.chat_history = [] | |
| if "keywords" not in st.session_state: | |
| st.session_state.keywords = [] | |
| if "study_tips" not in st.session_state: | |
| st.session_state.study_tips = {} | |
| if uploaded_file and api_key and st.button("π λ¬Έμ λΆμ μμ"): | |
| with st.spinner("λ¬Έμλ₯Ό νμ±νκ³ μμ΄μ..."): | |
| html_text, err = parse_document_to_html(uploaded_file, api_key) | |
| if err: | |
| st.error(err) | |
| return | |
| st.session_state.html_text = html_text | |
| st.success("λ¬Έμ νμ± μ±κ³΅ β ") | |
| # β¨ μ§μμλ΅: μ΄λ―Έμ§μ λΆλ¦¬ν΄μ λ³λ μμμ μμΉ | |
| if st.session_state.html_text: | |
| left_col, right_col = st.columns([1, 2]) | |
| with left_col: | |
| st.image(uploaded_file, caption="πΌοΈ μ λ‘λν λ¬Έμ μ΄λ―Έμ§", use_container_width=True) | |
| with right_col: | |
| st.subheader("β κΆκΈν λ΄μ©μ μ§λ¬Έν΄λ³΄μΈμ") | |
| user_question = st.text_input("μ§λ¬Έμ μ λ ₯νκ³ μλ λ²νΌμ λλ¬λ³΄μΈμ", key="question_input") | |
| if st.button("π¬ Solarμκ² λ¬Όμ΄λ³΄κΈ°") and user_question: | |
| with st.spinner("Solar μ μλμ΄ λ΅λ³ μ€μ λλ€..."): | |
| answer, history, err = chat_with_solar_document( | |
| st.session_state.html_text, | |
| user_question, | |
| st.session_state.chat_history, | |
| api_key | |
| ) | |
| if err: | |
| st.error(f"β Solar μλ΅ μ€λ₯: {err}") | |
| else: | |
| st.session_state.chat_history = history | |
| st.chat_message("user").write(user_question) | |
| st.chat_message("assistant").write(answer) | |
| # ν€μλ μΆμ² μμ± | |
| st.session_state.keywords = get_recommended_keywords( | |
| st.session_state.html_text, | |
| user_question, | |
| api_key | |
| ) | |
| # β¨ μ΄λ―Έμ§ μλμ μΆμ² ν€μλ νμ | |
| if st.session_state.keywords: | |
| st.markdown("### π μΆμ² κ³΅λΆ ν€μλ") | |
| for keyword in st.session_state.keywords: | |
| if st.button(f"π {keyword} κ³΅λΆ μΆμ²λ°κΈ°", key=f"btn_{keyword}"): | |
| tip = get_study_tip_for_keyword(keyword, api_key) | |
| st.session_state.study_tips[keyword] = tip | |
| for keyword, tip in st.session_state.study_tips.items(): | |
| with st.expander(f"π {keyword} 곡λΆλ² 보기"): | |
| st.write(tip) | |
| if __name__ == "__main__": | |
| main() | |