sagar007 commited on
Commit
cf40b67
·
verified ·
1 Parent(s): d6b416e

Create app.py

Browse files
Files changed (1) hide show
  1. app.py +368 -0
app.py ADDED
@@ -0,0 +1,368 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import gradio as gr
2
+ from transformers import AutoModelForCausalLM, AutoTokenizer
3
+ import spaces
4
+ from duckduckgo_search import DDGS
5
+ import time
6
+ import torch
7
+ from datetime import datetime
8
+
9
+ # Initialize model and tokenizer
10
+ model_name = "deepseek-ai/DeepSeek-R1-Distill-Qwen-1.5B"
11
+ tokenizer = AutoTokenizer.from_pretrained(model_name)
12
+ tokenizer.pad_token = tokenizer.eos_token
13
+
14
+ # Modified model loading for CPU
15
+ model = AutoModelForCausalLM.from_pretrained(
16
+ model_name,
17
+ device_map="cpu", # Changed to CPU
18
+ low_cpu_mem_usage=True,
19
+ torch_dtype=torch.float32 # Changed to float32 for CPU
20
+ )
21
+
22
+ def get_web_results(query, max_results=5): # Increased to 5 for better context
23
+ """Get web search results using DuckDuckGo"""
24
+ try:
25
+ with DDGS() as ddgs:
26
+ results = list(ddgs.text(query, max_results=max_results))
27
+ return [{
28
+ "title": result.get("title", ""),
29
+ "snippet": result["body"],
30
+ "url": result["href"],
31
+ "date": result.get("published", "")
32
+ } for result in results]
33
+ except Exception as e:
34
+ return []
35
+
36
+ def format_prompt(query, context):
37
+ """Format the prompt with web context"""
38
+ current_time = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
39
+ context_lines = '\n'.join([f'- [{res["title"]}]: {res["snippet"]}' for res in context])
40
+ return f"""You are an intelligent search assistant. Answer the user's query using the provided web context.
41
+ Current Time: {current_time}
42
+
43
+ Query: {query}
44
+
45
+ Web Context:
46
+ {context_lines}
47
+
48
+ Provide a detailed answer in markdown format. Include relevant information from sources and cite them using [1], [2], etc.
49
+ Answer:"""
50
+
51
+ def format_sources(web_results):
52
+ """Format sources with more details"""
53
+ if not web_results:
54
+ return "<div class='no-sources'>No sources available</div>"
55
+
56
+ sources_html = "<div class='sources-container'>"
57
+ for i, res in enumerate(web_results, 1):
58
+ title = res["title"] or "Source"
59
+ date = f"<span class='source-date'>{res['date']}</span>" if res['date'] else ""
60
+ sources_html += f"""
61
+ <div class='source-item'>
62
+ <div class='source-number'>[{i}]</div>
63
+ <div class='source-content'>
64
+ <a href="{res['url']}" target="_blank" class='source-title'>{title}</a>
65
+ {date}
66
+ <div class='source-snippet'>{res['snippet'][:150]}...</div>
67
+ </div>
68
+ </div>
69
+ """
70
+ sources_html += "</div>"
71
+ return sources_html
72
+
73
+ def generate_answer(prompt):
74
+ """Generate answer using the DeepSeek model"""
75
+ inputs = tokenizer(
76
+ prompt,
77
+ return_tensors="pt",
78
+ padding=True,
79
+ truncation=True,
80
+ max_length=256, # Reduced max length for CPU
81
+ return_attention_mask=True
82
+ ) # Removed .to(model.device) since we're using CPU
83
+
84
+ outputs = model.generate(
85
+ inputs.input_ids,
86
+ attention_mask=inputs.attention_mask,
87
+ max_new_tokens=128, # Reduced for faster generation on CPU
88
+ temperature=0.7,
89
+ top_p=0.95,
90
+ pad_token_id=tokenizer.eos_token_id,
91
+ do_sample=True,
92
+ early_stopping=True,
93
+ num_beams=1 # Reduced beam search for faster generation
94
+ )
95
+ return tokenizer.decode(outputs[0], skip_special_tokens=True)
96
+
97
+ def process_query(query, history):
98
+ """Process user query with streaming effect"""
99
+ try:
100
+ if history is None:
101
+ history = []
102
+
103
+ # Get web results first
104
+ web_results = get_web_results(query)
105
+ sources_html = format_sources(web_results)
106
+
107
+ current_history = history + [[query, "*Searching...*"]]
108
+ yield {
109
+ answer_output: gr.Markdown("*Searching the web...*"),
110
+ sources_output: gr.HTML(sources_html),
111
+ search_btn: gr.Button("Searching...", interactive=False),
112
+ chat_history_display: current_history
113
+ }
114
+
115
+ # Generate answer
116
+ prompt = format_prompt(query, web_results)
117
+ answer = generate_answer(prompt)
118
+ final_answer = answer.split("Answer:")[-1].strip()
119
+
120
+ updated_history = history + [[query, final_answer]]
121
+ yield {
122
+ answer_output: gr.Markdown(final_answer),
123
+ sources_output: gr.HTML(sources_html),
124
+ search_btn: gr.Button("Search", interactive=True),
125
+ chat_history_display: updated_history
126
+ }
127
+ except Exception as e:
128
+ error_message = str(e)
129
+ if "GPU quota" in error_message:
130
+ error_message = "⚠️ GPU quota exceeded. Please try again later when the daily quota resets."
131
+
132
+ yield {
133
+ answer_output: gr.Markdown(f"Error: {error_message}"),
134
+ sources_output: gr.HTML(sources_html),
135
+ search_btn: gr.Button("Search", interactive=True),
136
+ chat_history_display: history + [[query, f"*Error: {error_message}*"]]
137
+ }
138
+
139
+ # Update the CSS for better contrast and readability
140
+ css = """
141
+ .gradio-container {
142
+ max-width: 1200px !important;
143
+ background-color: #f7f7f8 !important;
144
+ }
145
+
146
+ #header {
147
+ text-align: center;
148
+ margin-bottom: 2rem;
149
+ padding: 2rem 0;
150
+ background: #1a1b1e;
151
+ border-radius: 12px;
152
+ color: white;
153
+ }
154
+
155
+ #header h1 {
156
+ color: white;
157
+ font-size: 2.5rem;
158
+ margin-bottom: 0.5rem;
159
+ }
160
+
161
+ #header h3 {
162
+ color: #a8a9ab;
163
+ }
164
+
165
+ .search-container {
166
+ background: #1a1b1e;
167
+ border-radius: 12px;
168
+ box-shadow: 0 4px 12px rgba(0,0,0,0.1);
169
+ padding: 1rem;
170
+ margin-bottom: 1rem;
171
+ }
172
+
173
+ .search-box {
174
+ padding: 1rem;
175
+ background: #2c2d30;
176
+ border-radius: 8px;
177
+ margin-bottom: 1rem;
178
+ }
179
+
180
+ /* Style the input textbox */
181
+ .search-box input[type="text"] {
182
+ background: #3a3b3e !important;
183
+ border: 1px solid #4a4b4e !important;
184
+ color: white !important;
185
+ border-radius: 8px !important;
186
+ }
187
+
188
+ .search-box input[type="text"]::placeholder {
189
+ color: #a8a9ab !important;
190
+ }
191
+
192
+ /* Style the search button */
193
+ .search-box button {
194
+ background: #2563eb !important;
195
+ border: none !important;
196
+ }
197
+
198
+ /* Results area styling */
199
+ .results-container {
200
+ background: #2c2d30;
201
+ border-radius: 8px;
202
+ padding: 1rem;
203
+ margin-top: 1rem;
204
+ }
205
+
206
+ .answer-box {
207
+ background: #3a3b3e;
208
+ border-radius: 8px;
209
+ padding: 1.5rem;
210
+ color: white;
211
+ margin-bottom: 1rem;
212
+ }
213
+
214
+ .answer-box p {
215
+ color: #e5e7eb;
216
+ line-height: 1.6;
217
+ }
218
+
219
+ .sources-container {
220
+ margin-top: 1rem;
221
+ background: #2c2d30;
222
+ border-radius: 8px;
223
+ padding: 1rem;
224
+ }
225
+
226
+ .source-item {
227
+ display: flex;
228
+ padding: 12px;
229
+ margin: 8px 0;
230
+ background: #3a3b3e;
231
+ border-radius: 8px;
232
+ transition: all 0.2s;
233
+ }
234
+
235
+ .source-item:hover {
236
+ background: #4a4b4e;
237
+ }
238
+
239
+ .source-number {
240
+ font-weight: bold;
241
+ margin-right: 12px;
242
+ color: #60a5fa;
243
+ }
244
+
245
+ .source-content {
246
+ flex: 1;
247
+ }
248
+
249
+ .source-title {
250
+ color: #60a5fa;
251
+ font-weight: 500;
252
+ text-decoration: none;
253
+ display: block;
254
+ margin-bottom: 4px;
255
+ }
256
+
257
+ .source-date {
258
+ color: #a8a9ab;
259
+ font-size: 0.9em;
260
+ margin-left: 8px;
261
+ }
262
+
263
+ .source-snippet {
264
+ color: #e5e7eb;
265
+ font-size: 0.9em;
266
+ line-height: 1.4;
267
+ }
268
+
269
+ .chat-history {
270
+ max-height: 400px;
271
+ overflow-y: auto;
272
+ padding: 1rem;
273
+ background: #2c2d30;
274
+ border-radius: 8px;
275
+ margin-top: 1rem;
276
+ }
277
+
278
+ .examples-container {
279
+ background: #2c2d30;
280
+ border-radius: 8px;
281
+ padding: 1rem;
282
+ margin-top: 1rem;
283
+ }
284
+
285
+ .examples-container button {
286
+ background: #3a3b3e !important;
287
+ border: 1px solid #4a4b4e !important;
288
+ color: #e5e7eb !important;
289
+ }
290
+
291
+ /* Markdown content styling */
292
+ .markdown-content {
293
+ color: #e5e7eb !important;
294
+ }
295
+
296
+ .markdown-content h1, .markdown-content h2, .markdown-content h3 {
297
+ color: white !important;
298
+ }
299
+
300
+ .markdown-content a {
301
+ color: #60a5fa !important;
302
+ }
303
+
304
+ /* Accordion styling */
305
+ .accordion {
306
+ background: #2c2d30 !important;
307
+ border-radius: 8px !important;
308
+ margin-top: 1rem !important;
309
+ }
310
+ """
311
+
312
+ # Update the Gradio interface layout
313
+ with gr.Blocks(title="AI Search Assistant", css=css, theme="dark") as demo:
314
+ chat_history = gr.State([])
315
+
316
+ with gr.Column(elem_id="header"):
317
+ gr.Markdown("# 🔍 AI Search Assistant")
318
+ gr.Markdown("### Powered by DeepSeek & Real-time Web Results")
319
+
320
+ with gr.Column(elem_classes="search-container"):
321
+ with gr.Row(elem_classes="search-box"):
322
+ search_input = gr.Textbox(
323
+ label="",
324
+ placeholder="Ask anything...",
325
+ scale=5,
326
+ container=False
327
+ )
328
+ search_btn = gr.Button("Search", variant="primary", scale=1)
329
+
330
+ with gr.Row(elem_classes="results-container"):
331
+ with gr.Column(scale=2):
332
+ with gr.Column(elem_classes="answer-box"):
333
+ answer_output = gr.Markdown(elem_classes="markdown-content")
334
+ with gr.Accordion("Chat History", open=False, elem_classes="accordion"):
335
+ chat_history_display = gr.Chatbot(elem_classes="chat-history")
336
+ with gr.Column(scale=1):
337
+ with gr.Column(elem_classes="sources-box"):
338
+ gr.Markdown("### Sources")
339
+ sources_output = gr.HTML()
340
+
341
+ with gr.Row(elem_classes="examples-container"):
342
+ gr.Examples(
343
+ examples=[
344
+ "What are the latest developments in quantum computing?",
345
+ "Explain the impact of AI on healthcare",
346
+ "What are the best practices for sustainable living?",
347
+ "How is climate change affecting ocean ecosystems?"
348
+ ],
349
+ inputs=search_input,
350
+ label="Try these examples"
351
+ )
352
+
353
+ # Handle interactions
354
+ search_btn.click(
355
+ fn=process_query,
356
+ inputs=[search_input, chat_history],
357
+ outputs=[answer_output, sources_output, search_btn, chat_history_display]
358
+ )
359
+
360
+ # Also trigger search on Enter key
361
+ search_input.submit(
362
+ fn=process_query,
363
+ inputs=[search_input, chat_history],
364
+ outputs=[answer_output, sources_output, search_btn, chat_history_display]
365
+ )
366
+
367
+ if __name__ == "__main__":
368
+ demo.launch(share=True)