M17idd commited on
Commit
b2c45d8
·
verified ·
1 Parent(s): 8f34ab2

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +47 -87
app.py CHANGED
@@ -1,145 +1,107 @@
1
  import streamlit as st
2
- import time
3
- import os
4
- import pickle
5
- import numpy as np
6
  from langchain.document_loaders import PyPDFLoader
7
  from langchain.text_splitter import RecursiveCharacterTextSplitter
8
- from langchain_together import TogetherEmbeddings
 
9
  from langchain.chat_models import ChatOpenAI
10
- from sklearn.metrics.pairwise import cosine_similarity
11
-
12
- # ------------------ بارگذاری چانک‌ها و امبدینگ‌ها ------------------
13
 
14
- # --- کش کردن امبدینگ‌ها فقط بار اول ---
 
 
15
  @st.cache_resource
16
- def get_embeddings_and_chunks():
17
- # بارگذاری پی دی اف و اسپلیت چانک
18
  pdf_loader = PyPDFLoader('test1.pdf')
19
  pages = pdf_loader.load_and_split(RecursiveCharacterTextSplitter(chunk_size=300, chunk_overlap=0))
20
  chunk_texts = [page.page_content for page in pages]
21
 
22
- # ساخت امبدینگ برای کل چانک‌ها
23
- embeddings = TogetherEmbeddings(
24
  api_key="0291f33aee03412a47fa5d8e562e515182dcc5d9aac5a7fb5eefdd1759005979"
25
  )
 
26
 
27
- return chunk_texts, embeddings
 
28
 
29
- # --- نمایش progress بیرون از کش ---
30
- chunk_texts, embeddings = get_embeddings_and_chunks()
 
 
 
31
 
32
  progress_bar = st.progress(0)
33
-
34
- # حالا شروع به پردازش با آپدیت پروگرس بار
35
  all_embeddings = []
36
- batch_size = 5
37
 
38
  for i in range(0, len(chunk_texts), batch_size):
39
  batch = chunk_texts[i:i+batch_size]
40
- embedded_batch = embeddings.embed_documents(batch)
41
- all_embeddings.extend(embedded_batch)
42
 
43
- # آپدیت پروگرس بار
44
  progress_bar.progress(min((i + batch_size) / len(chunk_texts), 1.0))
45
 
46
- st.success("✅ امبدینگ چانک‌ها با موفقیت ساخته شد!")
47
-
48
- # حالا این all_embeddings رو داری، میتونی بندازی تو index
49
-
50
 
51
- # ذخیره در فایل کش
52
- with open(embeddings_file, 'wb') as f:
53
- pickle.dump({
54
- 'chunk_texts': chunk_texts,
55
- 'chunk_embeddings': chunk_embeddings,
56
- 'embeddings_model': embeddings_model,
57
- }, f)
58
-
59
- st.success(f"✅ {len(chunk_texts)} چانک پردازش و ذخیره شد.")
60
- return chunk_texts, chunk_embeddings, embeddings_model
61
-
62
- chunk_texts, chunk_embeddings, embeddings_model = load_chunks_and_embeddings()
63
-
64
- # ------------------ ساخت مدل LLM ------------------
65
 
 
 
 
66
  llm = ChatOpenAI(
67
  base_url="https://api.together.xyz/v1",
68
  api_key='0291f33aee03412a47fa5d8e562e515182dcc5d9aac5a7fb5eefdd1759005979',
69
- model="meta-llama/Llama-3.3-70B-Instruct-Turbo-Free"
70
  )
71
 
72
- # ------------------ پاسخ بر اساس ۱۰ چانک نزدیک ------------------
73
-
74
- def answer_from_pdf(question):
75
- # ۱- ساخت امبدینگ سوال
76
- question_embedding = embeddings_model.embed_query(question)
77
-
78
- # ۲- محاسبه شباهت
79
- similarities = cosine_similarity(
80
- [question_embedding],
81
- chunk_embeddings
82
- )[0]
83
-
84
- # ۳- انتخاب ۱۰ چانک نزدیک
85
- top_indices = np.argsort(similarities)[-10:][::-1]
86
- selected_chunks = [chunk_texts[i] for i in top_indices]
87
-
88
- # ۴- ساخت پرامپت
89
- context = "\n\n".join(selected_chunks)
90
- prompt = f"""با توجه به متن زیر فقط به زبان فارسی پاسخ بده:
91
-
92
- متن:
93
- {context}
94
-
95
- سوال:
96
- {question}
97
-
98
- پاسخ:"""
99
-
100
- response = llm.invoke(prompt)
101
- return response.content
102
-
103
- # ------------------ Chat Streamlit UI ------------------
104
-
105
- st.title('���� چت با PDF (با ۱۰ چانک نزدیک و کش شده)')
106
 
 
 
 
107
  if 'messages' not in st.session_state:
108
  st.session_state.messages = []
109
 
110
  if 'pending_prompt' not in st.session_state:
111
  st.session_state.pending_prompt = None
112
 
113
- # نمایش هیستوری چت
114
  for msg in st.session_state.messages:
115
  with st.chat_message(msg['role']):
116
  st.markdown(f"🗨️ {msg['content']}", unsafe_allow_html=True)
117
 
118
- # گرفتن سوال از کاربر
119
- prompt = st.chat_input("سوال خود را وارد کنید...")
120
 
121
  if prompt:
122
  st.session_state.messages.append({'role': 'user', 'content': prompt})
123
  st.session_state.pending_prompt = prompt
124
  st.rerun()
125
 
126
- # وقتی سوال جدید داری
127
  if st.session_state.pending_prompt:
128
  with st.chat_message('ai'):
129
  thinking = st.empty()
130
- thinking.markdown("🤖 در حال پردازش...")
131
 
132
- # پاسخ بر اساس نزدیک‌ترین چانک‌ها
133
- response = answer_from_pdf(st.session_state.pending_prompt)
134
- answer = response.strip()
135
  if not answer:
136
- answer = "متاسفم، اطلاعات دقیقی در این مورد ندارم."
137
 
138
  thinking.empty()
139
  full_response = ""
140
  placeholder = st.empty()
141
 
142
- # تدریجی نشون دادن پاسخ
143
  for word in answer.split():
144
  full_response += word + " "
145
  placeholder.markdown(full_response + "▌")
@@ -148,5 +110,3 @@ if st.session_state.pending_prompt:
148
  placeholder.markdown(full_response)
149
  st.session_state.messages.append({'role': 'ai', 'content': full_response})
150
  st.session_state.pending_prompt = None
151
-
152
-
 
1
  import streamlit as st
 
 
 
 
2
  from langchain.document_loaders import PyPDFLoader
3
  from langchain.text_splitter import RecursiveCharacterTextSplitter
4
+ from langchain.embeddings import TogetherEmbeddings
5
+ from langchain.vectorstores import FAISS
6
  from langchain.chat_models import ChatOpenAI
7
+ from langchain.chains import RetrievalQA
8
+ import time
 
9
 
10
+ # --------------------------------------------
11
+ # 1. بارگذاری پی دی اف و ساخت امبدینگ چانک‌ها (فقط یکبار و کش شده)
12
+ # --------------------------------------------
13
  @st.cache_resource
14
+ def get_chunks_and_embeddings():
 
15
  pdf_loader = PyPDFLoader('test1.pdf')
16
  pages = pdf_loader.load_and_split(RecursiveCharacterTextSplitter(chunk_size=300, chunk_overlap=0))
17
  chunk_texts = [page.page_content for page in pages]
18
 
19
+ embeddings_model = TogetherEmbeddings(
 
20
  api_key="0291f33aee03412a47fa5d8e562e515182dcc5d9aac5a7fb5eefdd1759005979"
21
  )
22
+ return chunk_texts, embeddings_model
23
 
24
+ # کش شده
25
+ chunk_texts, embeddings_model = get_chunks_and_embeddings()
26
 
27
+ # --------------------------------------------
28
+ # 2. ساختن امبدینگ چانک‌ها با پروگرس بار
29
+ # --------------------------------------------
30
+ st.title("📄 Chat with your PDF (با پی‌دی‌اف خودت حرف بزن!)")
31
+ st.subheader("در حال آماده‌سازی امبدینگ چانک‌ها...")
32
 
33
  progress_bar = st.progress(0)
 
 
34
  all_embeddings = []
35
+ batch_size = 128
36
 
37
  for i in range(0, len(chunk_texts), batch_size):
38
  batch = chunk_texts[i:i+batch_size]
39
+ embedded = embeddings_model.embed_documents(batch)
40
+ all_embeddings.extend(embedded)
41
 
 
42
  progress_bar.progress(min((i + batch_size) / len(chunk_texts), 1.0))
43
 
44
+ st.success("✅ همه چانک‌ها آماده شدند!")
 
 
 
45
 
46
+ # --------------------------------------------
47
+ # 3. ساختن ایندکس FAISS از امبدینگ‌ها
48
+ # --------------------------------------------
49
+ vectorstore = FAISS.from_embeddings(all_embeddings, chunk_texts)
 
 
 
 
 
 
 
 
 
 
50
 
51
+ # --------------------------------------------
52
+ # 4. آماده سازی مدل LLM و چین
53
+ # --------------------------------------------
54
  llm = ChatOpenAI(
55
  base_url="https://api.together.xyz/v1",
56
  api_key='0291f33aee03412a47fa5d8e562e515182dcc5d9aac5a7fb5eefdd1759005979',
57
+ model="meta-llama/Llama-3-70B-Instruct-Turbo-Free"
58
  )
59
 
60
+ chain = RetrievalQA.from_chain_type(
61
+ llm=llm,
62
+ chain_type='stuff',
63
+ retriever=vectorstore.as_retriever(search_kwargs={"k": 10}),
64
+ input_key='question'
65
+ )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
66
 
67
+ # --------------------------------------------
68
+ # 5. چت بات Streamlit
69
+ # --------------------------------------------
70
  if 'messages' not in st.session_state:
71
  st.session_state.messages = []
72
 
73
  if 'pending_prompt' not in st.session_state:
74
  st.session_state.pending_prompt = None
75
 
76
+ # نمایش پیام‌های قبلی
77
  for msg in st.session_state.messages:
78
  with st.chat_message(msg['role']):
79
  st.markdown(f"🗨️ {msg['content']}", unsafe_allow_html=True)
80
 
81
+ # دریافت ورودی از کاربر
82
+ prompt = st.chat_input("چطور میتونم کمکت کنم؟")
83
 
84
  if prompt:
85
  st.session_state.messages.append({'role': 'user', 'content': prompt})
86
  st.session_state.pending_prompt = prompt
87
  st.rerun()
88
 
 
89
  if st.session_state.pending_prompt:
90
  with st.chat_message('ai'):
91
  thinking = st.empty()
92
+ thinking.markdown("🤖 در حال فکر کردن...")
93
 
94
+ # اجرای جستجو در ایندکس برای پاسخ
95
+ response = chain.run(f"فقط به زبان فارسی پاسخ بده. سوال: {st.session_state.pending_prompt}")
96
+ answer = response.split("Helpful Answer:")[-1].strip()
97
  if not answer:
98
+ answer = "متأسفم، اطلاعات دقیقی در این مورد ندارم."
99
 
100
  thinking.empty()
101
  full_response = ""
102
  placeholder = st.empty()
103
 
104
+ # نمایش پاسخ به صورت تایپی
105
  for word in answer.split():
106
  full_response += word + " "
107
  placeholder.markdown(full_response + "▌")
 
110
  placeholder.markdown(full_response)
111
  st.session_state.messages.append({'role': 'ai', 'content': full_response})
112
  st.session_state.pending_prompt = None